我试图制作一个尽可能快的队列,我打算这样做,以便我从中获取许多功能,从一开始你就知道了。这意味着我永远不会尝试添加更多的元素,而不是我分配的数组。
即使我只实现了我需要的东西,但当我完成(~2000)读写操作时,我会输入内置队列。
我很好奇是什么使得内置队列比我自己构建的裸机更快?
正如您所看到的,队列基于圆形数组,因此我不必移动任何元素。我也只是编写数据而不是创建一个新节点以节省一些时间。 (即使在我的测试中它没有产生任何重大差异。)
class Queue<T> {
private class Node {
public T data;
public Node(T data) {
this.data = data;
}
public Node() {
}
}
Node[] nodes;
int current;
int emptySpot;
public Queue(int size) {
nodes = new Node[size];
for (int i = 0; i < size; i++) {
nodes[i] = new Node();
}
this.current = 0;
this.emptySpot = 0;
}
public void Enqueue(T value){
nodes[emptySpot].data = value;
emptySpot++;
if (emptySpot >= nodes.Length) {
emptySpot = 0;
}
}
public T Dequeue() {
int ret = current;
current++;
if (current >= nodes.Length) {
current = 0;
}
return nodes[ret].data;
}
}
我的测试代码是使用内置秒表完成的,所有内容都以刻度写出。
static void Main(string[] args) {
MinimalCollections.Queue<char> queue = new MinimalCollections.Queue<char>(5500);
Queue<char> CQueue = new Queue<char>(5500);
Stopwatch sw = new Stopwatch();
sw.Start();
for (int y = 0; y < 4; y++) {
for (int i = 0; i < 5500; i++) {
queue.Enqueue('f');
}
for (int i = 0; i < 5500; i++) {
queue.Dequeue();
}
}
sw.Stop();
Console.WriteLine("My queue method ticks is = {0}", sw.ElapsedTicks);
sw.Reset();
sw.Start();
for (int y = 0; y < 4; y++) {
for (int i = 0; i < 5500; i++) {
CQueue.Enqueue('f');
}
for (int i = 0; i < 5500; i++) {
CQueue.Dequeue();
}
}
sw.Stop();
Console.WriteLine("C# queue method ticks is = {0}", sw.ElapsedTicks);
Console.ReadKey();
}
输出结果为:
我的队列方法滴答是= 2416
C#队列方法ticks = 2320
答案 0 :(得分:4)
我可以看到一个明显的开销是引入Node
个对象。当您实际将此值用作Queue
的值char
时,这将特别明显,因为内置实现不会将值包装到引用类型中。
以下是我将如何更改您的实施方式:
class Queue<T>
{
T[] nodes;
int current;
int emptySpot;
public Queue(int size)
{
nodes = new T[size];
this.current = 0;
this.emptySpot = 0;
}
public void Enqueue(T value)
{
nodes[emptySpot] = value;
emptySpot++;
if (emptySpot >= nodes.Length)
{
emptySpot = 0;
}
}
public T Dequeue()
{
int ret = current;
current++;
if (current >= nodes.Length)
{
current = 0;
}
return nodes[ret];
}
}
这似乎好得多(发布版本,任何CPU,赢得8.1):
My queue method ticks is = 582
C# queue method ticks is = 2166