MDStressLab++
Loading...
Searching...
No Matches
Grid.cpp
Go to the documentation of this file.
1/*
2 * Grid.cpp
3 *
4 * Created on: Nov 5, 2019
5 * Author: Nikhil
6 */
7
8#include "Grid.h"
9#include <fstream>
10#include "typedef.h"
11#include "SpatialHash.h"
12#include <iostream>
13
14template<ConfigType T>
15Grid<T>::Grid(int _ngrid) : ngrid(_ngrid)
16{
17 this->setCounter();
19 if (numberOfGrids == 1) MY_HEADING("Creating Grids");
20
21 std::cout << "Grid " << numberOfGrids << ". Initializing a grid of size " << ngrid << " to the origin." << std::endl;
22 this->coordinates.resize(ngrid,Vector3d(0.0,0.0,0.0));
23}
24
25template<ConfigType T>
27 Vector3d upperLimit,
28 int ngridx, int ngridy, int ngridz):ngrid(ngridx*ngridy*ngridz)
29{
30 if ( !(lowerLimit.array() < upperLimit.array()).prod() )
31 MY_ERROR("ERROR: The coordinates of lowerLimit are not less than the upperLimit");
32
33 this->setCounter();
35 if (numberOfGrids == 1) MY_HEADING("Creating Grids");
36
37
38 std::cout << "Grid " << numberOfGrids << ". Creating a uniform grid of " << ngrid << " points between (" << lowerLimit
39 << ") and (" << upperLimit << ")"<< std::endl;
40 std::cout << std::endl;
41 coordinates.resize(ngrid);
42
43 int index= 0;
44 Vector3d coordinate;
45 coordinate= lowerLimit;
46 for (auto i : range<int>(0,ngridx))
47 {
48 coordinate(0) = lowerLimit(0) + i*(upperLimit(0)-lowerLimit(0))/ngridx;
49 for (auto j : range<int>(0,ngridy))
50 {
51 coordinate(1) = lowerLimit(1) + j*(upperLimit(1)-lowerLimit(1))/ngridy;
52 for (auto k : range<int>(0,ngridz))
53 {
54 coordinate(2)= lowerLimit(2) + k*(upperLimit(2)-lowerLimit(2))/ngridz;
55 coordinates[index]= coordinate;
56 index++;
57 }
58 }
59 }
60}
61
62template<ConfigType T>
64 Matrix3d cell,
65 Vector3d lowerLimit,
66 Vector3d upperLimit,
67 int ngridx,
68 int ngridy,
69 int ngridz):ngrid(ngridx*ngridy*ngridz)
70{
71 (void) origin;
72 this->setCounter();
74 if (numberOfGrids == 1) MY_HEADING("Creating Grids");
75
76 std::cout << "Grid " << numberOfGrids << ". Creating a cell-aligned uniform grid of " << ngrid
77 << " points between (" << lowerLimit << ") and (" << upperLimit << ")" << std::endl;
78 std::cout << std::endl;
79 coordinates.resize(ngrid);
80
81 Vector3d cellVectorLengths;
82 for (int i_dim=0; i_dim<DIM; ++i_dim)
83 {
84 cellVectorLengths(i_dim)= cell.col(i_dim).norm();
85 if (cellVectorLengths(i_dim)<epsilon)
86 MY_ERROR("ERROR: Degenerate cell vector in grid construction.");
87 }
88
89 Vector3d cellDisplacement= (cell.inverse()*(upperLimit-lowerLimit).transpose()).transpose();
90 if ((cellDisplacement.array() < -epsilon).any())
91 MY_ERROR("ERROR: upperLimit-lowerLimit has negative components in the cell-vector basis.");
92
93 int index= 0;
94 for (auto i : range<int>(0,ngridx))
95 {
96 double coordinate0= 0.0;
97 if (ngridx>1) coordinate0 += i*cellDisplacement(0)/ngridx;
98 for (auto j : range<int>(0,ngridy))
99 {
100 double coordinate1= 0.0;
101 if (ngridy>1) coordinate1 += j*cellDisplacement(1)/ngridy;
102 for (auto k : range<int>(0,ngridz))
103 {
104 double coordinate2= 0.0;
105 if (ngridz>1) coordinate2 += k*cellDisplacement(2)/ngridz;
106
107 Vector3d fractionalCoordinates(coordinate0,coordinate1,coordinate2);
108 coordinates[index]= lowerLimit + (cell*fractionalCoordinates.transpose()).transpose();
109 index++;
110 }
111 }
112 }
113}
114
115template<ConfigType T>
116Grid<T>::Grid(std::string filename)
117{
118 this->setCounter();
120 if (numberOfGrids == 1) MY_HEADING("Creating Grids");
121 std::cout << "Grid " << numberOfGrids << ". Reading grid from filename: " << filename << std::endl;
122 std::cout << std::endl;
123
124 std::ifstream file(filename);
125
126 file >> ngrid;
127 coordinates.resize(ngrid);
128 for(auto& position : coordinates)
129 for (int i_dim=0; i_dim<DIM; i_dim++)
130 if(!(file >> position(i_dim))) MY_ERROR("ERROR: Reading grid coordinates");
131}
132
133// Function to calculate neighbor lists of grid points consisting of particles in subconfig within a distance of
134// padding from the grid points
135template<ConfigType T>
136std::vector<std::set<int>> Grid<T>::getGridNeighborLists(const SubConfiguration& subconfig, const double& padding) const
137{
138 std::vector<std::set<int>> gridNeighborLists;
139
140 // Hash the coordinates
141 Vector3d origin,step;
142 origin.setConstant(0.0);
143 step.setConstant(padding);
144 ConstSpatialHash hashParticles(origin,step,subconfig.coordinates.at(T));
145 // Hash the grid points
146 ConstSpatialHash hashGrid(origin,step,coordinates);
147
148
149 int i_gridPoint= 0;
150 for(const auto& gridPoint : coordinates)
151 {
152 std::set<int> gridContributingList;
153 Triplet bin= hashGrid.hashFunction(i_gridPoint);
154 Triplet neighborBin;
155 // for each neighboring bin of a grid point's bin
156 for (const auto& neighborBin : bin.neighborList())
157 {
158 std::vector<int>& particleList= hashParticles.hashTable[neighborBin];
159 // for each particle in a neighboring bin
160 for(const auto& particle : particleList)
161 {
162 double distance= (subconfig.coordinates.at(T).row(particle)-gridPoint).squaredNorm();
163 if (distance<=pow(padding,2))
164 gridContributingList.insert(particle);
165 }
166 }
167 gridNeighborLists.push_back(gridContributingList);
168 i_gridPoint++;
169
170 }
171 return gridNeighborLists;
172}
173
174template<ConfigType T>
175void Grid<T>::write(std::string filename) const
176{
177 std::ofstream file(filename+".grid");
178
179 file << ngrid << "\n";
180 file << "\n";
181 for (const auto& coordinate : coordinates)
182 file << coordinate << std::endl;
183}
184
185template<ConfigType T>
186void Grid<T>::read(std::string filename)
187{
188 std::cout << "Reading grid from file " << filename << "\n" << std::endl;
189
190 std::ifstream file(filename);
191
192 int ngridInFile;
193 file >> ngridInFile;
194 if (ngrid!= ngridInFile)
195 MY_ERROR("Error: Number of grid points in file" << " = " << ngridInFile <<
196 ", does not equal to " << ngrid << " in grid.");
197
198 for(auto& position : coordinates)
199 for (int i_dim=0; i_dim<DIM; i_dim++)
200 if(!(file >> position(i_dim))) MY_ERROR("ERROR: Reading grid coordinates");
201}
202
203template<ConfigType T>
205{
207 else if (T == Current) GridBase::numberOfCurrentGrids+=1;
208 else MY_ERROR("Unrecognized grid type");
209}
210
211
212template<ConfigType T>
214 // TODO Auto-generated destructor stub
215}
216
217template<ConfigType T>
218GridSubConfiguration<T>::GridSubConfiguration(const Grid<T>& grid, const SubConfiguration& subconfig, const double& padding) :
219grid(grid),
220subconfig(subconfig),
221padding(padding),
222hashGridSubconfig(std::make_pair(ConstSpatialHash(Vector3d::Zero(),Vector3d::Constant(padding),grid.coordinates),
223 ConstSpatialHash(Vector3d::Zero(),Vector3d::Constant(padding),subconfig.coordinates.at(T))))
224{}
225
226template<ConfigType T>
227std::set<int> GridSubConfiguration<T>::getGridPointNeighbors(const int& i_gridPoint) const
228{
229 const ConstSpatialHash& hashGrid= hashGridSubconfig.first;
230 const ConstSpatialHash& hashParticles= hashGridSubconfig.second;
231
232 std::set<int> gridContributingList;
233 Triplet bin= hashGrid.hashFunction(i_gridPoint);
234 Triplet neighborBin;
235 // for each neighboring bin of a grid point's bin
236 for (const auto& neighborBin : bin.neighborList())
237 {
238 //const std::vector<int>& particleList= hashParticles.hashTable.at(neighborBin);
239 const std::vector<int>& particleList=
240 (hashParticles.hashTable.find(neighborBin)!=hashParticles.hashTable.end()) ?
241 hashParticles.hashTable.at(neighborBin) : std::vector<int>();
242
243 // for each particle in a neighboring bin
244 for(const auto& particle : particleList)
245 {
246 double distance= (subconfig.coordinates.at(T).row(particle)-grid.coordinates[i_gridPoint]).squaredNorm();
247 if (distance<=pow(padding,2))
248 gridContributingList.insert(particle);
249 }
250 }
251 return gridContributingList;
252}
std::map< ConfigType, MatrixXd > coordinates
Map from configuration type (Reference or Current) to coordinate matrices.
static int numberOfReferenceGrids
Definition Grid.h:19
static int numberOfCurrentGrids
Definition Grid.h:20
std::vector< Vector3d > coordinates
Definition Grid.h:18
std::set< int > getGridPointNeighbors(const int &) const
Definition Grid.cpp:227
GridSubConfiguration(const Grid< T > &, const SubConfiguration &, const double &)
Definition Grid.cpp:218
Definition Grid.h:38
void setCounter()
Definition Grid.cpp:204
virtual ~Grid()
Definition Grid.cpp:213
std::vector< std::set< int > > getGridNeighborLists(const SubConfiguration &, const double &) const
Definition Grid.cpp:136
void read(std::string)
Definition Grid.cpp:186
int ngrid
Definition Grid.h:53
Grid(int)
Definition Grid.cpp:15
void write(std::string) const
Definition Grid.cpp:175
Triplet hashFunction(const int &i) const
std::map< Triplet, std::vector< int > > hashTable
std::vector< Triplet > neighborList()
Definition SpatialHash.h:43
Definition range.h:11
void transpose(double const *mat, double *const trans)
Definition helper.hpp:59
#define DIM
#define MY_ERROR(message)
Definition typedef.h:17
Eigen::Matrix< double, DIM, DIM, Eigen::RowMajor > Matrix3d
Definition typedef.h:56
Eigen::Matrix< double, 1, DIM, Eigen::RowMajor > Vector3d
Definition typedef.h:60
@ Current
Definition typedef.h:70
@ Reference
Definition typedef.h:69
const double epsilon
Definition typedef.h:73
#define MY_HEADING(heading)
Definition typedef.h:36