STL 字符串中止的析构函数

Posted

技术标签:

【中文标题】STL 字符串中止的析构函数【英文标题】:Destructor of STL string abort 【发布时间】:2018-11-05 13:04:32 【问题描述】:

我有一个多线程程序,我忘了使用互斥锁。有一次,程序因以下堆栈跟踪而中止:

 T abort
 T __libc_message
 t malloc_printerr
 T free
 T operator delete(void*)
 W std::basic_string<char, std::char_traits<char>, std::allocator<char>>::~basic_string()`

我使用了 gnu c++ 编译器 4.4.3(在 Ubuntu 10.04 上)。是真的吗,这种行为可能是因为使用了如下示例中的字符串。实际上它要复杂得多,但我想知道下面的简单代码是否会导致这样的中止。

    复制字符串的析构函数被调用时中止的线程:

    void f()
    
        std::string s = someglobalstring;
    
    

    修改字符串的线程:

    void g()
    
         someglobalstring = newcontent;
    
    

问题: 对于 std::string 的读取和写入,较新的 C++ 实现是否线程安全? 预计析构函数在这里中止吗?

【问题讨论】:

您的代码不是线程安全的,您需要使用lock_guard 来防止修改字符串时出现任何竞争条件。 @πάνταῥεῖ "...您需要使用lock_guard..." 真的吗?只有lock_guard?没有其他同步机制? @DanielLangr 这是处理同步结构最简单、最安全的方法。 lock_guard 表示您将使用它与 std::mutex 或类似的。 @πάνταῥεῖ 同意。但它不是唯一的。 “您需要使用” 意味着哪个措辞。您也可以使用不带锁保护的互斥锁、唯一锁、原子标志、openmp 锁或临界区等。 我已经在使用 boost::threads 库,因为该项目在 std::mutex 可用之前几年就开始了。我刚刚忘记在这个地方锁定互斥锁。 【参考方案1】:

字符串不是线程安全的。如果您想这样做,请在访问您的字符串时使用std::mutex

void g()

    std::lock_guard<std::mutex> lock(m);
    someglobalstring = newcontent;

f 也一样,用字符串定义m(输入std::mutex)。

【讨论】:

以上是关于STL 字符串中止的析构函数的主要内容,如果未能解决你的问题,请参考以下文章

重读STL源码剖析:析构

可连接 std::thread 的析构函数

在不调用析构函数的情况下结束 STL 容器的生命周期

C++ 堆栈分配对象,显式析构函数调用

mfc 类的析构函数

C++ 设置基类的析构函数为虚函数