|
|
@ -1,11 +1,3 @@ |
|
|
|
/*
|
|
|
|
* @Author: lab pc yjxkwp@foxmail.com |
|
|
|
* @Date: 2023-04-28 22:24:13 |
|
|
|
* @LastEditors: lab pc yjxkwp@foxmail.com |
|
|
|
* @LastEditTime: 2023-04-29 12:17:53 |
|
|
|
* @FilePath: /designauto/da-sha/sha-topology-optimization-3d/Mesh.cpp |
|
|
|
* @Description: 这是默认设置,请设置`customMade`, 打开koroFileHeader查看配置 进行设置: https://github.com/OBKoro1/koro1FileHeader/wiki/%E9%85%8D%E7%BD%AE
|
|
|
|
*/ |
|
|
|
//
|
|
|
|
// Created by cflin on 4/20/23.
|
|
|
|
//
|
|
|
@ -15,11 +7,141 @@ |
|
|
|
|
|
|
|
namespace da::sha { |
|
|
|
namespace top { |
|
|
|
Mesh::Mesh(int len_x, int len_y, int len_z,int dofs_each_node) : DOFS_EACH_NODE(dofs_each_node), lx_(len_x), ly_(len_y), lz_(len_z), |
|
|
|
Mesh::Mesh(int len_x, int len_y, int len_z, const Tensor3d &user_defined_grid, int |
|
|
|
dofs_each_node) : DOFS_EACH_NODE(dofs_each_node), lx_(len_x), ly_(len_y), lz_(len_z), |
|
|
|
num_node_((lx_ + 1) * (ly_ + 1) * (lz_ + 1)), |
|
|
|
num_ele_(lx_ * ly_ * lz_), origin_(0,0,0), len_pixel_(1.0), len_box_(len_x,len_y,len_z){ |
|
|
|
valid_ele_idx_ = Eigen::VectorXi::LinSpaced(num_ele_, 0, num_ele_ - 1); |
|
|
|
init_ele_rho_=Eigen::VectorXd::Ones(num_ele_); |
|
|
|
num_ele_(lx_ * ly_ * lz_), |
|
|
|
origin_(0, 0, 0), |
|
|
|
len_pixel_(1.0), |
|
|
|
len_box_(len_x, len_y, len_z) { |
|
|
|
|
|
|
|
if (!(user_defined_grid.dimension(0) == lx_ && user_defined_grid.dimension(1) == ly_ |
|
|
|
&& user_defined_grid.dimension(2) == lz_)) { |
|
|
|
spdlog::critical("pls check dimension!"); |
|
|
|
exit(-1); |
|
|
|
}; |
|
|
|
// valid_ele_idx_
|
|
|
|
// init_rho_of_ele_in_use_
|
|
|
|
|
|
|
|
ten_ele_coord2ele_id_ = Tensor3i(lx_, ly_, lz_); |
|
|
|
ten_ele_coord2ele_id_.setConstant(-1); |
|
|
|
ten_node_coord2node_id_ = Tensor3i(lx_ + 1, ly_ + 1, lz_ + 1); |
|
|
|
ten_node_coord2node_id_.setConstant(-1); |
|
|
|
|
|
|
|
static const Eigen::MatrixXi delta_coord = (Eigen::MatrixXi(8, 3) << |
|
|
|
0, 0, 0, |
|
|
|
1, 0, 0, |
|
|
|
1, 1, 0, |
|
|
|
0, 1, 0, |
|
|
|
0, 0, 1, |
|
|
|
1, 0, 1, |
|
|
|
1, 1, 1, |
|
|
|
0, 1, 1 |
|
|
|
).finished(); |
|
|
|
|
|
|
|
// count ele really in use && fill ten_ele_coord2ele_id_ && set flg for ten_node_coord2node_id_
|
|
|
|
const int NOT_EMPTY_FLG = 1; |
|
|
|
int cnt_ele_in_use = 0; |
|
|
|
// std::vector<int> v_chosen_ele_id;
|
|
|
|
std::vector<double> v_rho_non_empty; |
|
|
|
for (int k = 0; k < lz_; ++k) { |
|
|
|
for (int j = 0; j < ly_; ++j) { |
|
|
|
for (int i = 0; i < lx_; ++i) { |
|
|
|
if (user_defined_grid(i, j, k) > 0) { |
|
|
|
ten_ele_coord2ele_id_(i, j, k) = cnt_ele_in_use; |
|
|
|
// v_chosen_ele_id.push_back(cnt_ele_in_use);
|
|
|
|
++cnt_ele_in_use; |
|
|
|
v_rho_non_empty.push_back(user_defined_grid(i, j, k)); |
|
|
|
for (int di = 0; di < delta_coord.rows(); ++di) { |
|
|
|
Eigen::Vector3i cur_delta_coord = delta_coord.row(di); |
|
|
|
ten_node_coord2node_id_(i + cur_delta_coord(0), |
|
|
|
j + cur_delta_coord(1), |
|
|
|
k + cur_delta_coord(2)) = NOT_EMPTY_FLG; |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
// chosen_ele_id_=Eigen::VectorXi::LinSpaced(cnt_ele_in_use,0,cnt_ele_in_use);
|
|
|
|
init_rho_of_ele_in_use_ = Eigen::Map<Eigen::VectorXd>(v_rho_non_empty.data(), |
|
|
|
v_rho_non_empty.size()); |
|
|
|
num_ele_in_use_ = cnt_ele_in_use; |
|
|
|
|
|
|
|
// get_num_node_pixel && fill node_id
|
|
|
|
int cnt_node_pixel = 0; |
|
|
|
std::vector<Eigen::Vector3i> v_node_coords; |
|
|
|
for (int k = 0; k < lz_ + 1; ++k) { |
|
|
|
for (int j = 0; j < ly_ + 1; ++j) { |
|
|
|
for (int i = 0; i < lx_ + 1; ++i) { |
|
|
|
if (ten_node_coord2node_id_(i, j, k) == NOT_EMPTY_FLG) { |
|
|
|
ten_node_coord2node_id_(i, j, k) = cnt_node_pixel; |
|
|
|
v_node_coords.push_back({i, j, k}); |
|
|
|
++cnt_node_pixel; |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
num_node_in_use_ = cnt_node_pixel; |
|
|
|
// fill mat_node_id 2 node_coord
|
|
|
|
mat_node_id2node_coord_ = Eigen::MatrixXi(v_node_coords.size(), 3); |
|
|
|
for (int i = 0; i < v_node_coords.size(); ++i) { |
|
|
|
mat_node_id2node_coord_.row(i) = v_node_coords[i]; |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
// fill mat_ele_id2dofs_
|
|
|
|
mat_ele_id2dofs_.resize(num_ele_in_use_, NUM_NODES_EACH_ELE * DOFS_EACH_NODE); |
|
|
|
mat_ele_id2node_id_.resize(num_ele_in_use_, NUM_NODES_EACH_ELE); |
|
|
|
for (int k = 0; k < lz_; ++k) { |
|
|
|
for (int j = 0; j < ly_; ++j) { |
|
|
|
for (int i = 0; i < lx_; ++i) { |
|
|
|
int cur_ele_id = ten_ele_coord2ele_id_(i, j, k); |
|
|
|
if (cur_ele_id == -1) { |
|
|
|
continue; |
|
|
|
} |
|
|
|
Eigen::MatrixXi world_node_coords = |
|
|
|
delta_coord.rowwise() + Eigen::RowVector3i(i, j, k); |
|
|
|
assert(world_node_coords.rows() == 8 && world_node_coords.cols() == 3); |
|
|
|
Eigen::Vector<int, 8> node_ids = ten_node_coord2node_id_(world_node_coords); |
|
|
|
mat_ele_id2node_id_.row(cur_ele_id) = node_ids; |
|
|
|
for (int nodi = 0; nodi < NUM_NODES_EACH_ELE; ++nodi) { |
|
|
|
for (int dofi = 0; dofi < DOFS_EACH_NODE; ++dofi) { |
|
|
|
mat_ele_id2dofs_(cur_ele_id, DOFS_EACH_NODE * nodi + dofi) = |
|
|
|
DOFS_EACH_NODE * node_ids(nodi) + dofi; |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
// fill valid_ele_idx_
|
|
|
|
global_idx_of_ele_in_use.resize(num_ele_in_use_); |
|
|
|
cnt_ele_in_use = 0; |
|
|
|
for (int k = 0; k < lz_; ++k) { |
|
|
|
for (int j = 0; j < ly_; ++j) { |
|
|
|
for (int i = 0; i < lx_; ++i) { |
|
|
|
int idx=k*ly_*lx_+ j *lx_ +i; |
|
|
|
if (ten_ele_coord2ele_id_(i, j, k) != -1) { |
|
|
|
global_idx_of_ele_in_use(cnt_ele_in_use++) =idx; |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
assert(cnt_ele_in_use == num_ele_in_use_); |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
Mesh::Mesh(int len_x, int len_y, int len_z, int dofs_each_node) |
|
|
|
: |
|
|
|
DOFS_EACH_NODE(dofs_each_node), lx_(len_x), ly_(len_y), lz_(len_z), |
|
|
|
num_node_((lx_ + 1) * (ly_ + 1) * (lz_ + 1)), |
|
|
|
num_ele_(lx_ * ly_ * lz_), origin_(0, 0, 0), len_pixel_(1.0), |
|
|
|
len_box_(len_x, len_y, len_z) { |
|
|
|
num_node_in_use_ = num_node_; |
|
|
|
num_ele_in_use_ = num_ele_; |
|
|
|
|
|
|
|
global_idx_of_ele_in_use = Eigen::VectorXi::LinSpaced(num_ele_, 0, num_ele_); |
|
|
|
init_rho_of_ele_in_use_ = Eigen::VectorXd::Ones(num_ele_); |
|
|
|
|
|
|
|
// ten_node_coord2node_id_ = Tensor3i(num_node_, 1, 1);
|
|
|
|
// for (int i = 0; i < num_node_; ++i) {
|
|
|
@ -30,20 +152,20 @@ namespace da::sha { |
|
|
|
// get node_coord <---> node_id
|
|
|
|
int cnt_node_pixel = 0; |
|
|
|
std::vector<Eigen::Vector3i> v_node_coords; |
|
|
|
ten_node_coord2node_id_=Tensor3i(lx_ + 1, ly_ + 1, lz_ + 1); |
|
|
|
ten_node_coord2node_id_ = Tensor3i(lx_ + 1, ly_ + 1, lz_ + 1); |
|
|
|
for (int k = 0; k < lz_ + 1; ++k) { |
|
|
|
for (int j = 0; j < ly_ + 1; ++j) { |
|
|
|
for (int i = 0; i < lx_ + 1; ++i) { |
|
|
|
ten_node_coord2node_id_(i, j, k) = cnt_node_pixel; |
|
|
|
v_node_coords.push_back({i,j,k}); |
|
|
|
v_node_coords.push_back({i, j, k}); |
|
|
|
++cnt_node_pixel; |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
// fill mat_node_id 2 node_coord
|
|
|
|
mat_node_id2node_coord_=Eigen::MatrixXi(v_node_coords.size(),3); |
|
|
|
for(int i=0;i<v_node_coords.size();++i){ |
|
|
|
mat_node_id2node_coord_.row(i)=v_node_coords[i]; |
|
|
|
mat_node_id2node_coord_ = Eigen::MatrixXi(v_node_coords.size(), 3); |
|
|
|
for (int i = 0; i < v_node_coords.size(); ++i) { |
|
|
|
mat_node_id2node_coord_.row(i) = v_node_coords[i]; |
|
|
|
} |
|
|
|
//
|
|
|
|
|
|
|
@ -51,10 +173,11 @@ namespace da::sha { |
|
|
|
for (int i = 0; i < num_ele_; ++i) { |
|
|
|
ten_ele_coord2ele_id_(i, 0, 0) = i; |
|
|
|
} |
|
|
|
ten_ele_coord2ele_id_ = ten_ele_coord2ele_id_.reshape(Eigen::array<Eigen::DenseIndex, 3>{lx_, ly_, lz_}); |
|
|
|
ten_ele_coord2ele_id_ = ten_ele_coord2ele_id_.reshape( |
|
|
|
Eigen::array<Eigen::DenseIndex, 3>{lx_, ly_, lz_}); |
|
|
|
|
|
|
|
mat_ele_id2dofs_.resize(num_ele_, NUM_NODES_EACH_ELE * DOFS_EACH_NODE); |
|
|
|
mat_ele_id2node_id_.resize(num_ele_,NUM_NODES_EACH_ELE); |
|
|
|
mat_ele_id2node_id_.resize(num_ele_, NUM_NODES_EACH_ELE); |
|
|
|
static const Eigen::MatrixXi delta_coord = (Eigen::MatrixXi(8, 3) << |
|
|
|
0, 0, 0, |
|
|
|
1, 0, 0, |
|
|
@ -69,13 +192,15 @@ namespace da::sha { |
|
|
|
for (int j = 0; j < ly_; ++j) { |
|
|
|
for (int i = 0; i < lx_; ++i) { |
|
|
|
int cur_ele_id = ten_ele_coord2ele_id_(i, j, k); |
|
|
|
Eigen::MatrixXi world_node_coords = delta_coord.rowwise() + Eigen::RowVector3i(i, j, k); |
|
|
|
Eigen::MatrixXi world_node_coords = |
|
|
|
delta_coord.rowwise() + Eigen::RowVector3i(i, j, k); |
|
|
|
assert(world_node_coords.rows() == 8 && world_node_coords.cols() == 3); |
|
|
|
Eigen::Vector<int, 8> node_ids = ten_node_coord2node_id_(world_node_coords); |
|
|
|
mat_ele_id2node_id_.row(cur_ele_id)=node_ids; |
|
|
|
mat_ele_id2node_id_.row(cur_ele_id) = node_ids; |
|
|
|
for (int nodi = 0; nodi < NUM_NODES_EACH_ELE; ++nodi) { |
|
|
|
for(int dofi=0; dofi < DOFS_EACH_NODE; ++dofi){ |
|
|
|
mat_ele_id2dofs_(cur_ele_id, DOFS_EACH_NODE * nodi + dofi)= DOFS_EACH_NODE * node_ids(nodi) + dofi; |
|
|
|
for (int dofi = 0; dofi < DOFS_EACH_NODE; ++dofi) { |
|
|
|
mat_ele_id2dofs_(cur_ele_id, DOFS_EACH_NODE * nodi + dofi) = |
|
|
|
DOFS_EACH_NODE * node_ids(nodi) + dofi; |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|