首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >C#的C++代码帮助

C#的C++代码帮助
EN

Stack Overflow用户
提问于 2012-03-20 09:33:43
回答 2查看 218关注 0票数 1

我偶然发现了这段代码,但不确定如何用C#编写它:

代码语言:javascript
复制
bool getBestFitPlane(unsigned int vcount,
                     const float *points,
                     unsigned int vstride,
                     const float *weights,
                     unsigned int wstride,
                     float *plane)
{
  bool ret = false;

  SinglePrecision::Vec3 kOrigin(0,0,0);

  float wtotal = 0;

  if ( 1 )
  {
    const char *source  = (const char *) points;
    const char *wsource = (const char *) weights;

    for (unsigned int i=0; i<vcount; i++)
    {

      const float *p = (const float *) source;

      float w = 1;

      if ( wsource )
      {
        const float *ws = (const float *) wsource;
        w = *ws; //
        wsource+=wstride;
      }

      kOrigin.x+=p[0]*w;
      kOrigin.y+=p[1]*w;
      kOrigin.z+=p[2]*w;

      wtotal+=w;

      source+=vstride;
    }
  }

  float recip = 1.0f / wtotal; // reciprocol of total weighting

  kOrigin.x*=recip;
  kOrigin.y*=recip;
  kOrigin.z*=recip;


  float fSumXX=0;
  float fSumXY=0;
  float fSumXZ=0;

  float fSumYY=0;
  float fSumYZ=0;
  float fSumZZ=0;


  if ( 1 )
  {
    const char *source  = (const char *) points;
    const char *wsource = (const char *) weights;

    for (unsigned int i=0; i<vcount; i++)
    {

      const float *p = (const float *) source;

      float w = 1;

      if ( wsource )
      {
        const float *ws = (const float *) wsource;
        w = *ws; //
        wsource+=wstride;
      }

      SinglePrecision::Vec3 kDiff;

      kDiff.x = w*(p[0] - kOrigin.x); // apply vertex weighting!
      kDiff.y = w*(p[1] - kOrigin.y);
      kDiff.z = w*(p[2] - kOrigin.z);

      fSumXX+= kDiff.x * kDiff.x; // sume of the squares of the differences.
      fSumXY+= kDiff.x * kDiff.y; // sume of the squares of the differences.
      fSumXZ+= kDiff.x * kDiff.z; // sume of the squares of the differences.

      fSumYY+= kDiff.y * kDiff.y;
      fSumYZ+= kDiff.y * kDiff.z;
      fSumZZ+= kDiff.z * kDiff.z;


      source+=vstride;
    }
  }

  fSumXX *= recip;
  fSumXY *= recip;
  fSumXZ *= recip;
  fSumYY *= recip;
  fSumYZ *= recip;
  fSumZZ *= recip;

  // setup the eigensolver
  SinglePrecision::Eigen kES;

  kES.mElement[0][0] = fSumXX;
  kES.mElement[0][1] = fSumXY;
  kES.mElement[0][2] = fSumXZ;

  kES.mElement[1][0] = fSumXY;
  kES.mElement[1][1] = fSumYY;
  kES.mElement[1][2] = fSumYZ;

  kES.mElement[2][0] = fSumXZ;
  kES.mElement[2][1] = fSumYZ;
  kES.mElement[2][2] = fSumZZ;

  // compute eigenstuff, smallest eigenvalue is in last position
  kES.DecrSortEigenStuff();

  SinglePrecision::Vec3 kNormal;

  kNormal.x = kES.mElement[0][2];
  kNormal.y = kES.mElement[1][2];
  kNormal.z = kES.mElement[2][2];

  // the minimum energy
  plane[0] = kNormal.x;
  plane[1] = kNormal.y;
  plane[2] = kNormal.z;

  plane[3] = 0 - kNormal.dot(kOrigin);

  return ret;
}

我主要不理解const char行。它是否正在尝试获取值数组的第一项?

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2012-03-20 10:17:58

,我主要不理解const char行。它是否正在尝试获取值数组的第一项?

points强制转换为source的目的是获得(有效地) float数组的常量字节数组版本,

代码语言:javascript
复制
// use points as a byte array
const char *source  = (const char *) points;

for (unsigned int i=0; i<vcount; i++)
{
  // get a reference to the current position in the source array
  const float *p = (const float *) source;

  ...

  // iterate to the next series of points
  source+=vstride;
}

我假设vstride是一个12或更大的值。vstride用于跳过当前点的任意字节数,以便计算加权值。因为每个位置至少有3个float点,所以我想出了至少12个点(3乘以4)。如果在z坐标和下一个点的起点之间,数组中还有其他数据,那么它可能会更多。

之所以有必要使用source指针,是因为指针算法是基于指针数据的sizeof来工作的。因此,(points + 12)不同于(source + 12),很明显,vstride与要跳过的字节数相关联(这意味着points引用实际上可能是一个为了方便而用作float数组的struct,这在C/C++中并不少见)。

在C#中,您不会编写这样的代码。您将传入一个点数组/集合,它将是一个具有X、Y和Zfloat点坐标的对象。类似地,将有一个可选的权重数组/集合(可以是null,如if (wsource)所示),其中包含表示当前坐标的权重的单个float值。将它们组合在一起可能是有意义的。如果定义了weights,则点和权重具有相同数量的元素。

您不需要在C#中使用vcountvstridewstride变量。您可以遍历Points数组/集合并应用权重(如果提供了任何权重)。

代码语言:javascript
复制
float weight = 1.0f;

for (int i = 0; i < points.Length; ++i)
{
    if (weights != null)
    {
        weight = weights[i].Weight;
    }

    x += points[i].X * weight;
    y += points[i].Y * weight;
    z += points[i].Z * weight;

    wtotal += weight;
}
票数 2
EN

Stack Overflow用户

发布于 2012-03-20 09:53:13

从本质上说,是的--尽管这里进行了一些奇怪的类型转换,这似乎是不必要的,至少给出了您所发布的代码片段。

这一行声明了一个指向名为“source”的字符(有符号字节)的常量(即不可更改的)指针(*),并将“value”的起始地址分配给它。这很奇怪,因为正如您从参数列表中看到的,值是一个常量浮点*类型。

指针类型通常用于在旧的C/C++程序中处理数组,因为它们在某种程度上是可互换的。

对于C#,您将改用内置数组类型。

编辑现在你已经发布了更多的源代码,很明显,这样做是为了让他们可以使用' source‘变量指向一个浮点数块,并在需要移动到要处理的浮点数时将其递增'stride’量的字节(字符)。如果需要,您当然可以设计C#代码来处理这种内存布局(System.IntPtr可能会对您有所帮助)。

票数 3
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/9780302

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档