【发布时间】:2015-05-26 18:41:01
【问题描述】:
我正在与 SWIG 合作,在 Python 中封装一些 C++ 代码。我包装的 C++ 函数定义为:
template <typename T>
void getData(const std::string& fileName, T*& data);
数据作为对指针的引用传递,因为文件中的数据可以与指针具有相同类型或不同类型。在前一种情况下,我们只需将指针替换为指向文件数据的指针,在后一种情况下,我们使用 std::copy 将每个值转换为请求的类型。
现在我们来回答我的问题,SWIG 包装为我提供了以下功能:
void wrap_getData(const std::string& fileName, T* data) {
getData(fileName, data);
}
这被称为使用:
unsigned char* data = new unsigned char[dataSizeInFile]
wrap_getData(fileName, data)
由于文件中的数据类型也是无符号字符,通常它只会更改指针内存地址(如果我使用的是 getData)。但是,现在我希望这不会发生,但确实发生了。
例如,指针的原始内存地址 (&ptr) = 0x000000000c840070,然后在 wrap_getData 函数内部,数据指针内存地址 (&ptr) 为 0x00000000002393e8,正如预期的不同,因为指针被复制。但是现在,当我通过引用实际的 getData 函数来传递这个指针时,内存地址 (&ptr) 再次是 0x000000000c840070,这是我没想到的,我希望它保持 0x00000000002393e8,因为副本是通过引用传递的。为什么会这样?
【问题讨论】:
-
请编辑您的问题,以便在任何特定点更清楚地定义“地址”的含义。使用诸如“指针的地址”之类的术语来表示
&ptr,使用“指针指向的地址”来简单地表示ptr。现在真的不清楚你的意思是什么时候,这两个值中的哪一个不是你所期望的。 -
请到这里编辑您看到的内容以匹配您要解释的内容:coliru.stacked-crooked.com/a/61d21d0af7c9b1e2
-
PaulMcKenzie,我编辑了它,Coliru Viewer 中的行为确实是我所期望的 (coliru.stacked-crooked.com/a/5080224fe682ebe0),但不是我在 Visual Studio 2012 中看到的行为。所以,我不确定为什么它在那里表现得像预期的那样,而不是在我的系统上。
-
@Geert - 好吧,我有 VS 2008 和 VS 2013,行为与 Coliru 示例相同。
-
@PaulMcKenzie,你是对的,我应该看起来更好。我想出了自己的问题,这是因为运气。我在 Coliru 中做了一个最小的例子来展示这一点 (coliru.stacked-crooked.com/a/9f09393b04b51926)。当在 getData 函数中删除数组并立即在使用相同内存位置的数组中创建一个相同大小的新结果时(尝试将 50 更改为 5)。如果我制作一个更大的数组,它不再使用相同的内存位置,事情就会分崩离析。所以正如预期的那样,它不应该工作。感谢您的帮助!
标签: c++ pointers pass-by-reference pass-by-value