添加向量时出现分段错误。 (C++)
Posted
技术标签:
【中文标题】添加向量时出现分段错误。 (C++)【英文标题】:Segmentation fault when adding a vector. (C++) 【发布时间】:2011-10-03 03:49:55 【问题描述】:所以我有一个非常基本的类,它有一些方法和一些类变量。一切都很好,直到我在头文件中的成员变量中添加了一个向量:
std::vector <std::string> vectorofstuff;
如果我所做的只是添加这一行,那么我的程序可以完美运行,但最后,在所有输出都存在之后,我会收到一条关于 seg 错误的消息。
我的第一个猜测是我需要调用向量上的析构函数,但这似乎不起作用。另外,我的理解是我不需要调用析构函数,除非我使用“新”这个词。
朝着正确的方向推进了吗?谢谢大家!
【问题讨论】:
请发布您的实际代码。声明向量不是问题。您也许可以使用 valgrind.org/">valgrind</a> 解决此问题(如果您在支持它的平台上)。 你永远不需要自己调用析构函数,我的意思是从不,除非你做了一个叫做“in-place new”的东西,我可以保证你没有。显然这一行没有任何问题,您需要共享更多代码。发布重现此问题的 非常少 数量的代码。 您真正的问题可能不是向量,因为您没有更改std::string
或 std::vector
类,而是另一个问题在您使包含 sumofurls
的类更大之前被掩盖了。尝试在调试器中运行程序并查看出现段错误的位置,记住该问题实际上可能是由早期的内存损坏引起的。
对不起,我忘了你必须发布这样的链接:valgrind
@InBetween:你的 makefile 可能已经损坏(检查每个编译单元的依赖关系...)
【参考方案1】:
我猜您可能遇到过以下情况,或者是涉及未实现的依赖项/标头的类似情况。无论哪种方式,我希望这个答案可能会出现在 Google 上,并帮助后来一些极度困惑的程序员弄清楚他们为什么突然观察到任意崩溃。
因此,根据经验,如果您编译 SomeObject.o
的新版本,但不小心将另一个目标文件 #include
与旧版本的 SomeObject.hpp
相结合,就会发生这种情况。这会导致损坏,这将由编译器引用过时的成员偏移量等引起。有时这主要有效,并且仅在破坏对象时产生段错误 - 无论是相关的还是看似遥远的对象 - 有时程序会立即或某处出现段错误介于两者之间;我见过几种排列方式(很遗憾!)。
对于任何想知道为什么会发生这种情况的人,也许这只是我在编程时睡眠不足的反映,但我在 Git 子模块的上下文中遇到过这种模式,例如:
MyRepo
/GuiSubmodule
/HelperSubmodule
//GuiSubmodule
如果 (A) 你在 GuiSubmodule
中有一个新的提交,它还没有被拉到 HelperSubmodule
的副本中,(B) 你的 makefile
编译 MyRepo/uiSubmodule/SomeObject.o
,并且 (C) 另一个翻译单元- 通过#include
的危险在子模块或主仓库中 - 链接到具有不同类布局的旧版本SomeObject.hpp
...红鲱鱼,直到你最终意识到这个简单的错误。
由于我从头开始拼凑我的构建过程,我可能只是没有正确使用 Git/make
- 或者说不够严格(忘记推/拉所有子模块)。大概是后者!我现在至少看到更少的奇怪错误:)
【讨论】:
【参考方案2】:您可能在班级某处损坏了vectorofstuff
成员的内存。当类析构函数被调用时,向量的析构函数也会被调用,它会尝试指向和/或删除无效内存。
【讨论】:
我根本没有在vectorofstuff中添加任何东西,也没有触及它,只是将那行添加到我的.h文件中。我将如何破坏vectorofstuff? (我不是想听起来讽刺,我真的想知道,哈哈) @InBetween:例如,通过尝试写入同一类中的静态数组并且未能在其范围内操作。甚至更愚蠢的事情,比如打电话给memset( this, 0, sizeof( *this )
(相信我,我已经看到了)......【参考方案3】:
我在玩弄它并决定,只是为了确定,对所有内容执行 rm 并重新编译。你猜怎么着?那解决了它。我不知道为什么,在makefile中我还是这样做了,但无论如何,我很高兴我可以继续前进并继续工作。非常感谢大家的帮助!
【讨论】:
我认为这支持@Benoit 的早期评论和我的(很晚的)答案,因为它似乎是由一些头文件/对象文件在类布局或类似方面存在分歧引起的。这实际上是 UB,因为代码的某些部分最终可能会以现在不正确的对象偏移量等读/写。很高兴你把它排序了!我也是……最终;-)以上是关于添加向量时出现分段错误。 (C++)的主要内容,如果未能解决你的问题,请参考以下文章