对象按位运算的int转换

时间:2012-08-21 22:55:36

标签: c++ casting bit-manipulation xor

大家好,这是我第二次尝试解释C ++代码(我是一个非常新手),我只是想确定下面C ++代码的含义:

//| Get other endpoint of an edge  |  
//+--------------------------------+    
inline Node *Node::NextNode( Edge *next)  
   {  
   return (Node *) ((!next) ? NULL : ( (int)next->node[0] ^ (int)next->node[1] ^ (int)this ) );  
   }

是将next->node[0]next->node[1]中保存的对象转换/转换为int的代码方法,并将XOR运算符应用于它们的位值?并使用结果作为对Node*的引用作为回报? 感谢您的帮助:)

4 个答案:

答案 0 :(得分:2)

是的。 (虽然你也忽略了三元和其中的演员)

请记住,除非您非常小心,否则此类代码可能具有未定义的行为且不可移植(例如,在x86-64上,指针大于整数。)

答案 1 :(得分:1)

我最好的猜测是Edge表示两个Node之间的边缘,并且定义如下

struct Edge {
    Node *node[2];
    // perhaps other fields
}

必须填写node中的两个元素。它们可能指向不同的节点,或者至关重要的是,可能指向同一节点。

此外,Node::NextNode()只能传递一个Edge对象,该对象包含节点本身作为边缘上两个node元素之一(或者可以传递NULL)。 / p>

鉴于此,此功能基本上等同于

if (next) {
    if (next->node[0] == next->node[1]) return this;
    if (next->node[0] == this) return next->node[1];
    return next->node[0];
}
return NULL;

虽然正如锑已经指出的那样,它实际上是错误的,因为它正在转向int,它会在指针大于整数的任何架构上表现不正确。当然,如果不满足不变量,函数将表现不正确(例如,您传入的Edge不包含该节点作为其两个node中的任何一个。)

答案 2 :(得分:0)

您的解释是正确的。这是非常奇怪的代码。通常不会将某些整数放在一起并将结果视为指针。

查看node声明附近的头文件,看看该字段编码的内容。如果没有这样的评论,请尽快远离此代码!

答案 3 :(得分:0)

(int)next->node[0] ^ (int)next->node[1] ^ (int)this

鉴于next-> node [0]和[1]显然是指针,在isolate中看到它们的XOR提供了无意义的值(除非在它们相等的平凡情况下),但是期望XORing使用this产生一些有意义的东西,我假设其中一个node []值已知为this,这样我们就会留下this中的任何一个。{1}}。换句话说,对于这种情况,代码可能意味着相当于:

next->node[next->node[0] == this]

(或者,如果这有点神秘,您可能更喜欢next->node[next->node[0] == this ? 1 : 0];在C ++ true转换为1时false为0时预期数字

源代码“获取边缘的其他端点”中的注释似乎支持这一点:显然已知this是一个端点,代码找到“其他”端点....

产生有效指针的另一种情况是node[0]node[1]都相同,在这种情况下返回this。如果打算支持这种情况(而不仅仅是实现的巧合),那么上面建议的简化将失败。你可以尝试:

next->node[0] == next->node[1] ? this : next->node[next->node[0] == this]

如果对运行时数据是否包含两个相同的节点值有任何疑问,那么这种替换更安全。

正如其他人所指出的,代码假设指针的大小与int相同,这非常讨厌!我不会在其他地方讨论这个问题,但请记住这一点。