C++ 指针使用 Visual Studio 更改地址,而不是使用 OsX 中的 Xcode 或 Linux 中的 gcc

Posted

技术标签:

【中文标题】C++ 指针使用 Visual Studio 更改地址,而不是使用 OsX 中的 Xcode 或 Linux 中的 gcc【英文标题】:C++ pointer changes address with Visual Studio, not with Xcode in OsX or gcc in Linux 【发布时间】:2014-03-30 22:32:19 【问题描述】:

我有一个 C++ 问题困扰了我好几个小时:我有一个类,其中包含我需要对其进行指针引用的项目映射;在 Osx 和 Linux 下一切正常,但是当在 Windows 下运行我用 MSVC 构建的程序时,地图中项目的地址以及地图的基地址根据使用它的类的功能而变化,所以我的指针指向某物他们不知道;有人知道可以做类似事情的一些晦涩的编译器选项吗?

class Base 
   std::map <uint64_t, long> items ;

   ...

   void functA() 
      std::cout << "FunctA: " << &items ;
   

   void functB() 
      std::cout << "FunctB: " << &items ;
   

...

void main() 
      Base a ;
      ...
      a.functA() ;
      a.functB() ;
   

调用functA和functB的输出可能是例如:

Linux/OSX 功能A:013FF7A0 功能B:013FF7A0

窗户: 功能A:013FF900 功能B:013FF7A0

我也尝试过指向迭代器,但它们的作用与我从 c++ 文档中了解到的相同,即对于具有固定地址的地图元素,它们仅针对已删除的项目进行更改。

【问题讨论】:

这个问题没有意义。 functAfunctBmember 函数,所以你不能只是“调用”它们。您需要一个可以调用它们的对象。 是的,你是对的,我省略了部分代码;我创建一个“基础”对象,然后调用函数 你的问题在于你没有显示的代码。 您发布的代码是虚构的。没有Main(应该是main)。请从您的编辑器中粘贴您用于创建问题的确切代码。 另外,如果您使用的是 unix,请尝试运行 valgrind 以查看是否有任何内存错误。但是,是的,问题在于您没有显示的代码。 【参考方案1】:

问题非常微妙,但我找到了解决方案,事实是显然 GCC 和 XCode 编译器会生成隐式 new 而 MSVC 不会,因此该对象未在免费存储中分配,这将事情搞砸了Windows,通过将源代码更改为以下内容一切正常:

 class Base 
   std::map <uint64_t, long> items ;

   ...

   void functA() 
      std::cout << "FunctA: " << &items ;
   

   void functB() 
      std::cout << "FunctB: " << &items ;
   


...

void main() 
      Base* a ;
      a = new Base() ;
      ...
      a.functA() ;
      a.functB() ;
   

特别是当将指向“Base”对象的指针传递给其他获取所有错误数据的线程时,问题变得很明显。

【讨论】:

以上是关于C++ 指针使用 Visual Studio 更改地址,而不是使用 OsX 中的 Xcode 或 Linux 中的 gcc的主要内容,如果未能解决你的问题,请参考以下文章

C++ Visual Studio 非标准语法使用 '&' 创建指向成员的指针

C++ Visual Studio 2015“非标准语法;使用 '&' 创建指向成员的指针”

C++ 指针 - Visual Studio 抛出异常

字符串长度导致访问冲突值 -Visual Studio C++

如何在 Visual Studio for C++ 中更改工作目录

如何更改静态链接库中 const 字符串数组的 Visual Studio C++ 初始化序列