【问题标题】:How can I show on screen an objetct list?如何在屏幕上显示对象列表?
【发布时间】:2020-02-09 20:54:15
【问题描述】:

正如我在问题中所说,我试图在屏幕上显示已创建对象的值,但输出是下面的循环而不是列表本身。

我已经使用函数list.begin() 来检查列表是否正确并有效地显示1,所以我不明白为什么for 循环中的值不正确。

总之,我没有发现错误,所以我想问你我哪里错了。

提前致谢。

#include <iostream>
#include <list>
using namespace std;

class Algo{

private:
    list <int> l;

public:
    Algo() {l = {1, 2, 3, 4, 5};}
    list <int> getList() {return l;}

};

int main()
{
    Algo a;
    list <int>::iterator it;
    it = (a.getList().begin()); 
    for(it; it != (a.getList().end()); it++)
    {
        cout << *it << "\n";
    }
}

预期输出:1,2,3,4,5

实际输出:1

-1952806520

16122456

-1228957360

1

-1952806520

16122456

-1228957360

1(无限循环)

【问题讨论】:

  • 更重要的是,没有答案中提到的更改it=(a.getList().begin()); 获取一个迭代器到 temporary list&lt;int&gt;。该列表很快就消失了,留下一个 dangling 迭代器,使用它会调用 undefined behavior

标签: c++ list stl


【解决方案1】:

正如其他人指出的那样,您返回列表的副本。

  1. 避免使用l 之类的名称:它们非常令人困惑。使用 _lst 之类的内容。
  2. 根据您的目的,您可能希望返回:
    • 副本——客户端可以修改副本而不更改_lst成员:list &lt;int&gt; getList()
    • 参考——避免复制,客户可以直接修改:list &lt;int&gt;&amp; getList()
    • 或者一个常量引用——没有副本,客户端不能修改它_lst:const list &lt;int&gt;&amp; getList() const
  3. 如果您的唯一目的是显示列表的内容,只需添加一个公共成员函数并删除 getList:void dump() const
  4. 您可以使用copy 算法将列表的内容复制到控制台,而不是直接通过_lst 进行迭代

    void dump()
    {
      copy(_lst.begin(), _lst.end(), std::ostream_iterator<int>(std::cout, "\n"));
    }
    
  5. 你的主要变成:

    int main()
    {
      Algo a;
      a.dump();
    }
    

【讨论】:

    【解决方案2】:

    list &lt;int&gt; getList() 返回封装列表的临时副本。每次在循环中调用 a.getList().end() 时,都会得到另一个列表副本的迭代器,它无法与 getList().begin() 的初始迭代器进行比较。因此循环是无限的(迭代器不可比较)并且输出是垃圾(输出处不存在临时副本)。通过返回对封装列表的引用来修复它:

    list <int>& getList()
    

    【讨论】:

      【解决方案3】:

      在你的 getlist 函数中你应该返回

      list <int>& getList() { return l; }
      

      而不是

      list <int> getList() { return l; }
      

      这是列表的副本。由于您使用该列表的方式

      当你在这里调用它时

      it=(a.getList().begin());   
      

      get list 函数将列表和迭代器的副本返回到其第一个元素

      现在在for循环中

      a.getList().end()
      

      更昂贵的是,这部分您正在创建另一个副本,而不是您在上面的初始化中使用的副本

      现在在

      中使用“&”
      list <int>& getList() 
      

      您返回的是算法类的实际列表,而不是它的副本,因此 getlist 函数每次都会为您返回相同的列表

      【讨论】:

      • const list&lt;int&gt;&amp; 会更好
      猜你喜欢
      • 2018-07-21
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多