C++中##与#define 用法记录
在VTK中有一类vtkPointsProjectedHull,关于该类的说明是这样的:
the convex hull of the orthogonal projection of the vtkPoints in the 3 coordinate directions
意思就是,将一空间点集投影到某一坐标平面并求解2d凸包,投影平面有三种:XY平面,XZ平面,YZ平面。 该类包含成员以下成员函数:
// Description:
// Returns the coordinates (y,z) of the points in the convex hull
// of the projection of the points down the positive x-axis. pts has
// storage for len*2 values.
int GetCCWHullX(float *pts, int len);
int GetCCWHullX(double *pts, int len);
// Description:
// Returns the coordinates (z, x) of the points in the convex hull
// of the projection of the points down the positive y-axis. pts has
// storage for len*2 values.
int GetCCWHullY(float *pts, int len);
int GetCCWHullY(double *pts, int len);
// Description:
// Returns the coordinates (x, y) of the points in the convex hull
// of the projection of the points down the positive z-axis. pts has
// storage for len*2 values.
int GetCCWHullZ(float *pts, int len);
int GetCCWHullZ(double *pts, int len);
为了代码避免重复,成员函数的实现很有技巧性:
#define VTK_GETCCWHULL(which, dim) \
int vtkPointsProjectedHull::GetCCWHull##which(float *pts, int len)\
{ \
int i; \
double *dpts = new double [len*2]; \
int copypts = this->GetCCWHull##which(dpts, len); \
for (i=0; i<copypts*2; i++) \
{ \
pts[i] = static_cast<float>(dpts[i]); \
} \
delete [] dpts; \
return copypts; \
} \
int vtkPointsProjectedHull::GetCCWHull##which(double *pts, int len) \
{ \
if ((this->HullSize[dim] == 0) || (this->GetMTime() > this->HullTime[dim]))\
{ \
GrahamScanAlgorithm(dim); \
} \
int copylen = (this->HullSize[dim] <= len) ? this->HullSize[dim] : len; \
if (copylen <= 0) return 0; \
memcpy(pts, this->CCWHull[dim], sizeof(double) * 2 * copylen); \
return copylen; \
}
VTK_GETCCWHULL(X, 0);
VTK_GETCCWHULL(Y, 1);
VTK_GETCCWHULL(Z, 2);
首先, 根据输入点集的数据类型(double,float),调用了对应类型的方法;其次,利用#define宏定义实现了对应float、double两种类型的函数,注意#define后面的内容每行末尾的“\”,表示同一行;最后,通过##操作符将VTK_GETCCWHULL与which进行连接,分别对应了VTK_GETCCWHULLX, VTK_GETCCWHULLY和VTK_GETCCWHULLZ。