gpt4 book ai didi

c++ - 如何允许单例构造函数在 VS2017 中重新进入/传递?

转载 作者:太空狗 更新时间:2023-10-29 21:34:34 26 4
gpt4 key购买 nike

我一直在将一些 c++ 应用程序从 Visual Studio 2013 移植到 Visual Studio 2017。除了我必须修复的大量新警告之外,编译和链接都没有问题。

但是,当运行 应用程序时,它会在尝试重新进入单例的构造函数时“停止”(当连续的函数调用形成返回构造函数的循环时)。似乎这种行为在 VS2013 中是可以的,但在 VS2017 中不再有效。没有错误信息。

我知道与单例相关的所有坏事,并且至少不应该有循环。问题不在那里。

有没有办法告诉 VS2017 编译器我想搬起石头砸自己的脚,并允许与 VS2013 中相同的行为?

我无权访问导致此行为的代码,因为它来自第三方库,这就是为什么我不能“修复它”,很遗憾。

这是一个在 VS2013 中有效但在 VS2017 中无效的示例:

main.cpp

#include "Singleton.h";

int
main( void )
{

std::cout << "let's do this!" << std::endl;
int two = Singleton::GetReference().getTwo();
std::cout << "ok" << std::endl;
return 0;
}

单例.h

#pragma once

class Stuff;

class Singleton
{
public:
static Singleton& GetReference();

int getTwo() { return 2; }

private:
Singleton();

Stuff* stuff;
};

单例.cpp

#include "Singleton.h"
#include "Stuff.h"

Singleton&
Singleton::GetReference() {
static Singleton theInstance;
return theInstance;
}

Singleton::Singleton()
{
stuff = new Stuff();
}

东西.h

#pragma once

class Stuff
{
public:
Stuff();
private:
int two;
};

东西.cpp

#include "Stuff.h"
#include "Singleton.h"

Stuff::Stuff()
{
two = Singleton::GetReference().getTwo();
}

在上面的代码中,在逐步调试的时候,第一次上线static Singleton theInstance;会按预期工作,但是第二次,一个F11 将转到文件 thread_safe_statics.cpp,进入方法 extern "C"void __cdecl _Init_thread_header(int* const pOnce)Shift+F11 将退出该方法,程序将无限期地等待在指定的行(从调试器暂停程序时观察到)。


附言

这个问题也可能发生在 Visual Studio 2015 中,因为从接受的答案链接的文档提到了 VS2015。

最佳答案

/Zc:threadSafeInit-

一般的“一致性”页面是 MSDN: Conformance ,其中详细说明了您可以禁用哪些新功能。

我需要 sizedDealloc 的代码,我的新编译器正在为一个库创建一个 sized new 运算符,这打破了旧的编译预期。

由于这是一个编译标志,至少部分代码将在您的控制之下,您应该能够解开这头野兽。

构造函数 Stuff::Stuff 正在对未完全构造的对象调用函数。

那会产生“未定义的行为”。如果直到构造函数结束时才设置值“2”(例如)。

可能需要将 Singleton 分成 2 个,其中一个提供早期的静态数据(例如 2)。

第二个传递持有的对象 Stuff。 Stuff 将只依赖第一个,这将打破僵局。

或者,Stuff 的第二个构造函数告诉它要使用哪个对象,并从 Singleton::Singleton

中调用

有关禁用“Magic Statics”的 MSDN 文章 MSDN : disable threadsafe static initialization

关于c++ - 如何允许单例构造函数在 VS2017 中重新进入/传递?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45962859/

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