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。

posted @ 2018-06-11 23:28  Louie-Liu  阅读(134)  评论(0编辑  收藏  举报