清除推送列表时,清除通用列表堆栈

时间:2016-11-19 18:07:41

标签: c# parameter-passing generic-collections

当我想在c#中执行某些操作时,我遇到了一些问题。我会举一个小例子。

Stack<List<HufmannLetter>> steps = new Stack<List<HufmannLetter>>();
List<HufmannLetter> letterList = new List<HufmannLetter>();    

while(true){

    letterList.Add("asd");
    letterList.Add("sad");

    steps.Push(letterList);
    letterlist.Clear();    
}

在此代码中,我想将我的链表推送到堆栈而不是删除列表中的所有项目。当我清除列表时,我的堆栈的第一个索引会消失,因为它通过引用传递。我错了吗?因为我不知道为什么会这样。

所以我使用pass by value方法。

Stack<List<HufmannLetter>> steps = new Stack<List<HufmannLetter>>();
List<HufmannLetter> letterList = new List<HufmannLetter>();

while(true) {

    letterList.Add("asd");
    letterList.Add("sad");

    List<HufmannLetter> tempLetterList = new List<HufmannLetter>(letterList);
    steps.Push(tempLetterList);
    letterlist.Clear();    
}

这是解决问题的好方法吗?这样它工作,但可读性降低。你有什么建议我的?

...谢谢

4 个答案:

答案 0 :(得分:3)

只需在循环中创建一个新的List<HufmannLetter>对象并将其添加到堆栈中。重用相同的列表对象不会有任何性能优势。

Stack<List<HufmannLetter>> steps = new Stack<List<HufmannLetter>>();

while(true)
{
    List<HufmannLetter> letterList = new List<HufmannLetter>();

    letterList.Add("asd");
    letterList.Add("sad");

    steps.push(letterList);
}

答案 1 :(得分:1)

您可以创建new List<HufmannLetter>()并在构造函数中输入上一个列表,这将创建不会被清除的新对象。

while(condition)
{
    letterList.Add("asd");
    letterList.Add("sad");

    steps.push(new List<HufmannLetter>(letterList));
    letterlist.Clear();
}

修改

所以List<T>是引用类型,你将letterList放在堆栈中。这样,您将在堆栈中传输引用List<T>的值。因此,您的letterList变量引用与堆栈中的项相同的对象。清除letterList中的项目时,它们也会在堆栈项目中清除。

检查Reference Types

是什么

答案 2 :(得分:1)

List<>是一种可变的引用类型。

List<>传递给方法时,会传递参考的副本。所以你只知道它是List<>。这不会复制(克隆)List<>的全部内容。

当您在Push上放置{List<>Stack<>时,Stack<>真正保留的是List<>此实例的引用的副本}。如果稍后修改了该实例,例如使用.Add("asd").Clear(),则会看到此“突变”是否遵循Stack<>或您拥有的其他参考所保留的引用,局部变量。 两个引用都指向List<>的同一个实例。

在您的代码中,您说:

letterList.Clear(); // do not change reference, follow reference and mutate the instance it refers to

将修改(mutate)List<>的现有实例,使其变为空。任何持有对List<>的特定实例的引用的人都会看到此更改。

相反,如果你做了:

letterList = new List<string>(); // create new instance, change reference to point there (reference assignment), old instance is unchanged

会将letterList的引用“移动”为指向List<>实例。这不会影响其他人对“旧”实例的引用。

标题传递参考用法具有误导性。它应该是参考类型和传递参考或类似的东西。

答案 3 :(得分:-1)

你也可以这样做

Stack<List<HufmannLetter>> steps = new Stack<List<HufmannLetter>>();

while(true)
{
var tempList = new List<HufmannLetter>;
tempList.add("asd");
steps.push(tempList);
 }

或者你可以试试这个

steps.push(tempList.ToList());
   tempList.Clear();