// As we use integer grid point, integer division is used and some precision may be lost. grid3d findCentroid(grid3d A, grid3d B, grid3d C) { int x, y, z; x = (A.getx() + B.getx() + C.getx()) / 3; y = (A.gety() + B.gety() + C.gety()) / 3; z = (A.getz() + B.getz() + C.getz()) / 3; return grid3d(x, y, z); }
int main(int argc, char *argv[]) { cout << "Point A is created by "; grid3d ptA(3, 4, 5); cout << "Point A is "; ptA.print(); cout << endl << endl; cout << "Point B is created by "; grid3d ptB = 2; cout << "Point B is "; ptB.print(); cout << endl << endl; cout << "Point C is created by "; grid3d ptC; ptC = -6; cout << "Point C is "; ptC.print(); cout << endl << endl; cout << "Point D is created by "; grid3d ptD(ptA); cout << "Point D is "; ptD.print(); cout << endl << endl; cout << "Point E is created by "; grid3d ptE = grid3d(-2,2,7); cout << "Point E is "; ptE.print(); cout << endl << endl; cout << "Creating an array of points... "<<endl; grid3d ptArr[2]; cout << "The points in the array are "; ptArr[0].print(); ptArr[1].print(); cout << endl << endl; cout << "Please enter three integers to set a point in the array "; cin >> ptArr[0]; cout << "The point is set to "; ptArr[0].print(); cout << endl << endl; cout << "Start to compute centroid" << endl; grid3d centroid = findCentroid(ptA, ptB, ptE); cout << "The centroid of triange "; ptA.print(); ptB.print(); ptE.print(); cout << " is "; centroid.print(); cout << endl << endl; cout << "Start to compute area" << endl; double area; area = findArea(ptA, ptB, ptE); cout << "The area of triangle "; ptA.print(); ptB.print(); ptE.print(); cout << " is " << area << endl << endl; return 0; }
//apply_kernel3d() implementation static PyObject *_apply_kernel3d(PyObject *args,double(*kernel)(double,double,double,double)){ PyObject *positions_obj,*bins_obj,*weights_obj,*radius_obj,*concentration_obj; float *weights; double *radius,*concentration; //parse input tuple if(!PyArg_ParseTuple(args,"OOOOO",&positions_obj,&bins_obj,&weights_obj,&radius_obj,&concentration_obj)){ return NULL; } //interpret parsed objects as arrays PyObject *positions_array = PyArray_FROM_OTF(positions_obj,NPY_FLOAT32,NPY_IN_ARRAY); PyObject *binsX_array = PyArray_FROM_OTF(PyTuple_GET_ITEM(bins_obj,0),NPY_DOUBLE,NPY_IN_ARRAY); PyObject *binsY_array = PyArray_FROM_OTF(PyTuple_GET_ITEM(bins_obj,1),NPY_DOUBLE,NPY_IN_ARRAY); PyObject *binsZ_array = PyArray_FROM_OTF(PyTuple_GET_ITEM(bins_obj,2),NPY_DOUBLE,NPY_IN_ARRAY); //check if anything failed if(positions_array==NULL || binsX_array==NULL || binsY_array==NULL || binsZ_array==NULL){ Py_XDECREF(positions_array); Py_XDECREF(binsX_array); Py_XDECREF(binsY_array); Py_XDECREF(binsZ_array); return NULL; } //check if weights,radius,concentration are provided PyObject *weights_array,*radius_array,*concentration_array; if(weights_obj!=Py_None){ weights_array = PyArray_FROM_OTF(weights_obj,NPY_FLOAT32,NPY_IN_ARRAY); if(weights_array==NULL){ Py_DECREF(positions_array); Py_DECREF(binsX_array); Py_DECREF(binsY_array); Py_DECREF(binsZ_array); return NULL; } //Data pointer weights = (float *)PyArray_DATA(weights_array); } else{ weights = NULL; } if(radius_obj!=Py_None){ radius_array = PyArray_FROM_OTF(radius_obj,NPY_DOUBLE,NPY_IN_ARRAY); if(radius_array==NULL){ Py_DECREF(positions_array); Py_DECREF(binsX_array); Py_DECREF(binsY_array); Py_DECREF(binsZ_array); if(weights) Py_DECREF(weights_array); return NULL; } //Data pointer radius = (double *)PyArray_DATA(radius_array); } else{ radius = NULL; } if(concentration_obj!=Py_None){ concentration_array = PyArray_FROM_OTF(concentration_obj,NPY_DOUBLE,NPY_IN_ARRAY); if(concentration_array==NULL){ Py_DECREF(positions_array); Py_DECREF(binsX_array); Py_DECREF(binsY_array); Py_DECREF(binsZ_array); if(weights) Py_DECREF(weights_array); if(radius) Py_DECREF(radius_array); return NULL; } //Data pointer concentration = (double *)PyArray_DATA(concentration_array); } else{ concentration = NULL; } //Get data pointers float *positions_data = (float *)PyArray_DATA(positions_array); double *binsX_data = (double *)PyArray_DATA(binsX_array); double *binsY_data = (double *)PyArray_DATA(binsY_array); double *binsZ_data = (double *)PyArray_DATA(binsZ_array); //Get info about the number of bins int NumPart = (int)PyArray_DIM(positions_array,0); int nx = (int)PyArray_DIM(binsX_array,0) - 1; int ny = (int)PyArray_DIM(binsY_array,0) - 1; int nz = (int)PyArray_DIM(binsZ_array,0) - 1; //Allocate the new array for the grid PyObject *grid_array; npy_intp gridDims[] = {(npy_intp) nx,(npy_intp) ny,(npy_intp) nz}; grid_array = PyArray_ZEROS(3,gridDims,NPY_FLOAT32,0); if(grid_array==NULL){ Py_DECREF(positions_array); Py_DECREF(binsX_array); Py_DECREF(binsY_array); Py_DECREF(binsZ_array); if(weights) Py_DECREF(weights_array); if(radius) Py_DECREF(radius_array); if(concentration) Py_DECREF(concentration_array); return NULL; } //Get a data pointer float *grid_data = (float *)PyArray_DATA(grid_array); //Snap the particles on the grid grid3d(positions_data,weights,radius,concentration,NumPart,binsX_data[0],binsY_data[0],binsZ_data[0],binsX_data[1] - binsX_data[0],binsY_data[1] - binsY_data[0],binsZ_data[1] - binsZ_data[0],nx,ny,nz,grid_data,kernel); //return the grid Py_DECREF(positions_array); Py_DECREF(binsX_array); Py_DECREF(binsY_array); Py_DECREF(binsZ_array); if(weights) Py_DECREF(weights_array); if(radius) Py_DECREF(radius_array); if(concentration) Py_DECREF(concentration_array); return grid_array; }