首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> 關於C語言

C# 泛型 Queue 與 Stack 複製技巧:透過 IEnumerable<T> 建構函數實現淺拷貝

     編輯:關於C語言

前言

泛型版 Queue<T> 與 Stack<T> 不支援非泛型版本擁有的 Clone() 方法(因未實作 ICloneable)。本文介紹利用建構函數接受 IEnumerable<T> 參數的特性,優雅實現佇列與堆疊的淺拷貝。

核心機制:建構函數接受 IEnumerable<T>

Queue<T> 與 Stack<T> 皆提供建構函數:

public Queue(IEnumerable<T> collection)
public Stack(IEnumerable<T> collection)

此建構函數會遍歷來源集合,將元素順序加入新實例。因兩者皆實作 IEnumerable<T>,可直接將現有實例傳入建立副本。

Queue<T> 複製完整範例

public static void CloneQueue()
{
    // 建立原始佇列
    Queue<int> numericQueue = new Queue<int>();
    numericQueue.Enqueue(1);
    numericQueue.Enqueue(2);
    numericQueue.Enqueue(3);

    // 複製:傳入實作 IEnumerable<T> 的原始佇列
    Queue<int> clonedNumericQueue = new Queue<int>(numericQueue);

    // 驗證:foreach 不移除元素,僅檢視
    Console.WriteLine("=== 複製後內容(foreach 檢視)===");
    foreach (int i in clonedNumericQueue)
    {
        Console.WriteLine($"foreach: {i}");
    }

    // 實際 Dequeue 驗證獨立性
    Console.WriteLine("\n=== Dequeue 順序 ===");
    Console.WriteLine(clonedNumericQueue.Dequeue());  // 1
    Console.WriteLine(clonedNumericQueue.Dequeue());  // 2
    Console.WriteLine(clonedNumericQueue.Dequeue());  // 3
}

執行結果

=== 複製後內容(foreach 檢視)===
foreach: 1
foreach: 2
foreach: 3

=== Dequeue 順序 ===
1
2
3

Stack<T> 複製完整範例

public static void CloneStack()
{
    // 建立原始堆疊
    Stack<int> numericStack = new Stack<int>();
    numericStack.Push(1);
    numericStack.Push(2);
    numericStack.Push(3);

    // 複製
    Stack<int> clonedNumericStack = new Stack<int>(numericStack);

    // 驗證
    Console.WriteLine("=== 複製後內容(foreach 檢視)===");
    foreach (int i in clonedNumericStack)
    {
        Console.WriteLine($"foreach: {i}");
    }

    Console.WriteLine("\n=== Pop 順序 ===");
    Console.WriteLine(clonedNumericStack.Pop());  // 3 (LIFO)
    Console.WriteLine(clonedNumericStack.Pop());  // 2
    Console.WriteLine(clonedNumericStack.Pop());  // 1
}

執行結果

=== 複製後內容(foreach 檢視)===
foreach: 1
foreach: 2
foreach: 3

=== Pop 順序 ===
3
2
1

關鍵行為說明

行為Queue<T>Stack<T>
複製順序 保持 FIFO 順序(先進先出) 保持 LIFO 邏輯順序(後進先出)
foreach 迭代順序 1 → 2 → 3(Dequeue 順序) 1 → 2 → 3(Push 順序,非 Pop 順序)
獨立性 副本操作不影響原始實例,反之亦然
拷貝深度 淺拷貝(參考型別元素共享同一物件實例)

為什麼不實作 ICloneable?

.NET 設計團隊決定移除泛型集合的 ICloneable 支援,因為:

  • ICloneable 未定義淺/深拷貝語意,導致使用者誤解
  • 建構函數 + IEnumerable<T> 提供更明確、型別安全的複製方式
  • 統一集合複製模式:new List<T>(source)、new HashSet<T>(source) 等同樣模式

總結

泛型 Queue<T> 與 Stack<T> 雖無 Clone(),但透過接受 IEnumerable<T> 的建構函數,提供更清晰、型別安全的複製機制。此模式適用於所有實作 IEnumerable<T> 的泛型集合,是 .NET 集合框架的標準複製慣用語。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved