异常程序终止时的访问冲突 (C++)

发布于 2024-11-14 23:26:35 字数 969 浏览 6 评论 0原文

以下最少代码示例在正常终止(按 Enter 键)时运行良好:

#include <stdio.h>
#include <iostream>
#include <string>

using namespace std;

class SingletonLogClass
{

private:

    SingletonLogClass() {}

public:

    ~SingletonLogClass()
    {
        LogMessage("~SingletonLogClass()");
    }

    static SingletonLogClass& getInstance(void)
    {
        static SingletonLogClass inst;
        return inst;
    }

    void LogMessage(string msg)
    {
        //printf("%s\n", msg.c_str());
        cout << msg << endl;
    }

};

int main(int argc, char* argv[])
{
    SingletonLogClass::getInstance().LogMessage("This is a message");
    getchar();
    return 0;
}

当我通过关闭控制台窗口终止程序时,它取决于 LogMessage 函数的实现。如果使用 printf 实现,一切都很好。但是当使用 cout 实现它时,我遇到了访问冲突。

有人可以解释一下吗? 通过关闭控制台窗口终止程序时到底会发生什么? 为什么它可以与 printf 一起使用,但不能与 cout 一起使用?

我正在使用 VC++ 2010。

The following minimum code examples runs fine when it is terminated normally (by pressing enter):

#include <stdio.h>
#include <iostream>
#include <string>

using namespace std;

class SingletonLogClass
{

private:

    SingletonLogClass() {}

public:

    ~SingletonLogClass()
    {
        LogMessage("~SingletonLogClass()");
    }

    static SingletonLogClass& getInstance(void)
    {
        static SingletonLogClass inst;
        return inst;
    }

    void LogMessage(string msg)
    {
        //printf("%s\n", msg.c_str());
        cout << msg << endl;
    }

};

int main(int argc, char* argv[])
{
    SingletonLogClass::getInstance().LogMessage("This is a message");
    getchar();
    return 0;
}

When I terminate the program by closing the console window it depends on the implementation of the LogMessage function. If it's implemented using printf everything is fine. But when it's implemented using cout I get an access violation.

Can someone explain this?
What exactly happens when the program is terminated by closing the console window?
Why does it work with printf but not with cout?

I'm working with VC++ 2010.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

心清如水 2024-11-21 23:26:35

cout 是一个全局对象。您的单例实例(在 getInstance 静态成员函数中定义为静态)也是一个全局对象。

在 C++ 中,您无法控制构造顺序,也无法控制全局对象的销毁。因此,cout 对象可能会在 SingletonLogClass 之前被破坏。当您的 SingletonLogClass 的析构函数记录某些内容时,它不能再使用 cout (而 printf 就可以了)。

程序正常终止(按 Enter 键)并退出 main 函数以及程序通过关闭 shell 突然终止时的行为差异来自于全局变量的销毁顺序。 您无法控制全局对象的销毁顺序。

cout is a global object. Your singleton instance (defined as static in the getInstance static member function) is also a global object.

In C++, you cannot have control over the order of construction, neither destruction of global objects. As such, it is possible that the cout object is destructed before your SingletonLogClass is. As the destructor of your SingletonLogClass logs something, it cannot use anymore cout (whereas printf is fine).

The difference in behaviour when the program is terminated normally (pressing enter) and thus exiting the main function, and when the program is terminated abruptly by closing the shell comes from the order of destruction of globals. You cannot have control over the order of destruction of global objects.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文