【问题标题】:using std::string with Qt causes run-time error on destruction将 std::string 与 Qt 一起使用会导致破坏时出现运行时错误
【发布时间】:2010-02-25 10:45:59
【问题描述】:

我有一个 Qt 应用程序,它使用另一个库,其中函数输出是 std::string 而不是 QString。

所以在我的程序中我有一个方法

void doSomething() {
...
std::string std_string = MyExternalLibraryThatReturnsSTLstring.getString();
QString myQString = QString::fromStdString(std_string);
...
process(myQString);
...
}

当我的外部库返回非空 std::string 时,一切正常。 但是当返回一个空的 std::string 时,应用程序会在范围结束时崩溃。我猜这与 std::string 对象(?)的破坏有关。

到 QString 的转换工作正常,即使是空的 std::string。

谁能告诉我为什么会发生这种情况,以及如何避免这个运行时错误?

(在其他线程中,有些人讨论了调试库和发布库的混合,但我认为我没有这样做。顺便说一句,如何找出?)

【问题讨论】:

    标签: destructor runtime-error stdstring qstring


    【解决方案1】:

    解决方案是确保您的 Qt 版本使用与您的应用程序相同的编译器进行编译。

    就我而言,我下载了使用 VS2008 预构建的 Qt 4.7.3。当我迁移到 VS2010 时,toStdString 导致我的应用程序崩溃。 STL 字符串也会出现其他一些奇怪的错误。

    因此,只需配置您的发行版,然后使用 VS2010 编译器重新制作即可。

    【讨论】:

      【解决方案2】:

      使用“dependency walker”查看您的应用程序(以及外部 DLL 和 QT DLL)依赖于哪个 DLL。

      【讨论】:

      • 好的.. 我这样做了,它只使用标准的 Qt 库 + 我的 external.dll 再次使用了很多东西。我真的无法判断这里是否有问题,但看起来不像。
      【解决方案3】:

      您需要使用 Dependency Walker(Patrick 建议)查看不同版本的 msvc 运行时库(msvcrt 和朋友),以及它们是否被碰巧交换 memory 在他们之间。

      这是关键部分,因为堆保存在运行时 dll 中,每个运行时都有自己的堆(即 vs 2008、2010、2005)。

      因此,如果您在一个 dll 中分配内存(例如通过创建一个包含超过 16 个左右字符的 std::string)并将其发送到另一个 dll 中(在作用域结束时),删除调用将转到与新堆不同的堆:ed,然后崩溃。

      因此,为了在 Windows 上跨 DLL 的 STL 兼容性,必须使用相同的编译器。

      如果 DLL 公开了一个 API,它总是可以释放它自己的内存,那么就不存在这样的问题。 (即认为 COM,或类似但不那么可怕的东西)。

      也可能存在 ABI 不兼容问题,但我不太确定。多年来,我大多被内存分配/释放问题所困扰。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2017-10-25
        • 2018-07-19
        • 1970-01-01
        • 2010-09-15
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多