【问题标题】:Object allocated on stack or heap c++在堆栈或堆c ++上分配的对象
【发布时间】:2014-02-10 21:44:53
【问题描述】:
Dictionary::Dictionary() {
    ifstream infile;
    infile.open("words");
    string wread;
    while(getline(infile,wread)){
        wordset.insert(wread);
        vector<string> st =Read::Trigrams(wread);
                //Word w(wread,st) stack försvinner när vi lämnar metoden.
        words[wread.length()].push_back(Word(wread,st)); //stack eller heap
    }
    infile.close();
}

这是一个类 Dictionary 的构造函数。 我想创建一个单词对象并将其添加到向量中。 我应该写吗 words[wread.length()].push_back(Word(wread,st)); 或者 字 w(wread,st); 单词[wread.length()].push_back(w); w 会被分配到栈中,当我们离开构造函数时它会被移除。

【问题讨论】:

  • 没什么区别,都是在栈上分配的。
  • 实际上你应该使用emplace_back 以提高性能和清晰度。
  • @HansPassant 标准实际上并没有具体说明,但实际上你是正确的。具有自动 存储持续时间的对象几乎总是在堆栈上分配。但是,只要生命周期仍然是自动的,实现可能会选择在堆上分配。
  • @Mgetz “具有自动存储持续时间的对象几乎总是在堆栈上分配” - 嗯,没有。那么类中声明的所有值对象呢?

标签: c++


【解决方案1】:

您提到的两种形式都不会在堆上分配。要在堆上分配,一般使用new关键字

new Word()

还有其他在堆上分配的方法,包括std::make_shared。但是您的示例中没有使用任何内容。简单地使用Word() 将在堆栈上分配

【讨论】:

  • 你也可以通过调用std::make_shared而不是new在堆上分配对象。
【解决方案2】:

执行此操作的“正确”方法是使用emplace_back,它将就地构造 Word,甚至删除移动。

请注意,emplace_back 采用与对象的构造函数相同的参数。

【讨论】:

  • 你可能应该提到这是一个 C++11 特性。
【解决方案3】:

在 C++11 中,第一种形式 push_back(Word()); 会更高效,如果 Word 有一个移动构造函数。第二种形式无论如何都会制作副本。

在功能方面,两者是等价的。第二个污染范围,第一个没有。第一个更有可能得到有效优化,第二个则不然。

除非受到向后兼容性的限制,否则您应该使用 vector::emplace_back 并传递 T 的值或其构造函数之一的参数。

【讨论】:

  • 但是如果你推送一个在堆栈上创建的 obj,当构造函数完成时会发生什么?
  • @user2975699:它被复制到容器中。构造函数完成后本地实例将被销毁,但容器中的副本是安全的。
  • @user2975699 当您push_back 一个对象时,会制作一个副本并将其保存在向量中。已复制的值被销毁。
猜你喜欢
  • 2013-01-25
  • 2020-03-30
  • 2017-02-21
  • 1970-01-01
  • 2020-08-24
  • 2018-01-06
  • 2018-09-09
  • 2015-03-13
相关资源
最近更新 更多