假设我有一个整数队列(或任何类T),我可以更改队列中元素的值吗? 更具体地说,如果我将队列定义如下:
Queue<int> q = new Queue<int>();
我们可以更改其元素的值,类似于我们处理数组的方式吗? (如果q是一个数组,我们可以做这样的事情:q[0]=1
来改变它的元素)。我只是想简化场景并使用int作为示例,但我的目的是试图查看队列中T类的第1项,进行一些计算并更新队列以供其他程序处理。我不想将它出列,因为队列中的序列将与原始序列不同。希望我想要做的事情有意义。请指教。
答案 0 :(得分:6)
如果队列中的项目是可变类型,那么您可以更改队列具有的第一个项目的值。在不重新创建队列或执行大量队列/队列的情况下,无法更改队列前面的哪个项目。
作为第一种情况的示例,如果您的Queue<MyClass>
定义为:
class MyClass
{
public string Value { get; set; }
}
Queue<MyClass> queue = new Queue<MyClass>();
queue.Enqueue(new MyClass() { Value = "1" });
queue.Peek().Value = 2;
string value = queue.Peek().Value; // is 2
答案 1 :(得分:4)
您无法直接更改Queue
中的项目(尽管您可以使用解决方法as Tudor suggested)。但是,如果您想拥有一个队列,则不必使用Queue
。 .Net的另一种可能类型是LinkedList
。它允许您添加和删除两端的内容,这些内容可以在您的场景中使用:
LinkedList<int> list = new LinkedList<int>();
// enqueue an item
list.AddLast(1);
// dequeue an item
var item = list.First.Value;
list.RemoveFirst();
// put item back to the front of the queue
list.AddFirst(item);
您似乎想要按顺序处理几个模块中的每个项目。但我不确定这是做这种工作的正确方法。更好的方法可能是在每两个模块之间建立一个队列。模块总是从其输入队列中获取一个项目,对其进行处理,然后将其放入其输出队列中。
这种方法的一个优点是更大的灵活性:模块在输出上可以具有与输入不同的类型,这对于“一个队列”方法是不可能的(除非你求助于{{{ 1}} s,或类似的东西)。
TPL Dataflow(.Net 4.5中的新增功能)使用此方法通过并行化提高性能。它可以做到这一点,因为如果你没有一个中央队列,每个模块可以独立于其他模块处理项目。
答案 2 :(得分:1)
您可以使用简单的包装器:
class Wrapper<T>
{
public T Value { get; set; }
}
static void Main(string[] args)
{
Queue<Wrapper<int>> q = new Queue<Wrapper<int>>();
Wrapper<int> wr = new Wrapper<int> { Value = 1 };
q.Enqueue(wr);
Wrapper<int> wr1 = q.Peek();
wr1.Value = 2;
int value = q.Dequeue().Value;
Console.WriteLine(value);
}
答案 3 :(得分:1)
只要您像类一样存储引用类型,您对其所做的任何更改都将反映在队列中。下面代码的输出将为“2”:
public class MyClass
{
public int Value { get; set; }
}
static void Main(string[] args)
{
Queue<MyClass> q = new Queue<MyClass>();
q.Enqueue(new MyClass { Value = 1 });
var i = q.Peek();
i.Value++;
i = q.Peek();
Console.WriteLine(i.Value);
}
答案 4 :(得分:1)
public static class Extensions
{
public static Queue<T> SetFirstTo<T>(this Queue<T> q, T value)
{
T[] array = q.ToArray();
array[0] = value;
return new Queue<T>(array);
}
}
严格来说,这不会改变队列,因此需要重新分配。
[TestMethod]
public void Queue()
{
var queue = new Queue<int>(new[]{1,2,3,4});
queue = queue.SetFirstTo(9);
Assert.AreEqual(queue.Peek(),9);
}
答案 5 :(得分:-3)
简单的答案是否定的。它不是Queue对象API的一部分
http://msdn.microsoft.com/en-us/library/system.collections.queue.aspx
当然,任何事情都是可能的。您可以编写一个扩展方法来执行此操作,但它必须使用对象的API,因此在保留顺序的同时将所有项目与变更一起出列/排队。
但是如果你想这样做,你将队列视为列表,那么为什么不使用List呢?