gpt4 book ai didi

C++ 在结构中重载 operator()

转载 作者:塔克拉玛干 更新时间:2023-11-03 02:21:23 26 4
gpt4 key购买 nike

这是来自 Box2d 物理引擎的 b2Math.h 的代码。

struct b2Vec2
{ ...
/// Read from and indexed element.
float operator () (int i) const
{
return (&x)[i];
}
/// Write to an indexed element.
float operator () (int i)
{
return (&x)[i];
}
...
float x, y;
}

为什么我们不能只使用 SomeVector.x 和 SomeVector.y 来读/写 vector 坐标? return (&x)[i]; 行实际上是如何工作的?我的意思是,对结构的 x 组件的引用之后的数组括号 [] 对我来说并不清楚。

预先感谢您的回复。

最佳答案

Here is a code from b2Math.h from Box2d physics engine.

您发布的 Box2D 源代码的复制和粘贴似乎有错误。特别是,非常量方法中似乎缺少一个 & 号。

此外,此代码片段似乎来自当前 2.3.2 发布代码以外的代码库。

这是来自 Box2D 2.3.2 sources on GitHub 的部分:

/// Read from and indexed element.
float32 operator () (int32 i) const
{
return (&x)[i];
}

/// Write to an indexed element.
float32& operator () (int32 i)
{
return (&x)[i];
}

Why can't we just use SomeVector.x and SomeVector.y to read/write vector coordinates?

我们可以,而且我们通常会这样做。

但是 Box2D 中有一些代码(特别是 b2AABB::RayCast)似乎是根据算法编写的(b2AABB::RayCast 的注释说“来自 Real-time Collision Detection, p179"),它将 x 和 y 作为数组下标 0 和 1 进行迭代。我猜 Erin Cato(Box2D 的作者)以这种方式实现了这些运算符:(a) 使访问在风格上更符合算法,(b) 使其工作,以及 (c) 使其在看起来有效的方式。我可以确认它至少有效。

我有my own fork of Box2D我在其中重写了这些运算符。我将其接口(interface)更改为使用 [](而不是 ()),并将其实现更改为使用 switch 语句来显式访问任一 xy。我所做的后者对我来说很清楚地避免了潜在的未定义行为 w.r.t. C++ 标准。

这里是我的实现的相关部分的片段(请注意,我并不声称这是完美的或好的,只是它是一个可行的替代实现并且它应该清楚地依赖于定义的行为):

/// Accesses element by index.
/// @param i Index (0 for x, 1 for y).
auto operator[] (size_type i) const
{
assert(i < max_size());
switch (i)
{
case 0: return x;
case 1: return y;
default: break;
}
return x;
}

/// Accesses element by index.
/// @param i Index (0 for x, 1 for y).
auto& operator[] (size_type i)
{
assert(i < max_size());
switch (i)
{
case 0: return x;
case 1: return y;
default: break;
}
return x;
}

And how actually line return (&x)[i]; works?

正如我上面所暗示的,我之前已经研究过这个确切的问题。

当结构的 x 和 y 成员变量的内存布局与具有两个 float 的数组相同时,它起作用;它通常会这样做。因此,& 符号 (&) 获取 x 参数的地址,然后将该地址视为数组开头的地址,然后通过 i 对其进行索引

但就 C++ 标准而言,我不认为这是已定义的行为。然而,它的定义不够明确,不符合我的口味。

希望这能回答您的问题。

关于C++ 在结构中重载 operator(),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/43398287/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com