簡介
在 C#
里,比較兩個 List
是否相等,需要考慮多個方面,例如列表中的元素順序、元素本身是否相等。下面介紹幾種常見的比較方法:
基本類型比較(元素順序必須一致)
var list1 = new List<int> { 1, 2, 3 };
var list2 = new List<int> { 1, 2, 3 };bool areEqual = list1.SequenceEqual(list2); // ? true
忽略順序比較
var list1 = new List<int> { 1, 2, 3 };
var list2 = new List<int> { 3, 2, 1 };bool areEqual = list1.OrderBy(x => x).SequenceEqual(list2.OrderBy(x => x)); // ? true
或先分別排完序,再比較:
list3.Sort();
list4.Sort();
Console.WriteLine(list3.SequenceEqual(list4)); // 輸出: True
復雜類型(自定義對象列表)
- 實現
Equals
和GetHashCode
方法
public class Person
{public string Name { get; set; }public int Age { get; set; }public override bool Equals(object? obj){if (obj is Person person){return Name == person.Name && Age == person.Age;}return false;}public override int GetHashCode(){return HashCode.Combine(Name, Age);}
}
使用:
Console.WriteLine(person1.SequenceEqual(person2)); // 輸出: True
- 自定義比較器:
public class Person
{public string Name { get; set; }public int Age { get; set; }
}
public class PersonComparer : IEqualityComparer<Person>
{public bool Equals(Person? x, Person? y){return x?.Name == y?.Name && x?.Age == y?.Age;}public int GetHashCode(Person obj){return HashCode.Combine(obj.Name, obj.Age);// 還有一種寫法:// return obj.Name.GetHashCode() ^ obj.Age.GetHashCode();}
}
使用方式:
var list1 = new List<Person>
{new Person { Name = "Alice", Age = 25 },new Person { Name = "Bob", Age = 30 }
};var list2 = new List<Person>
{new Person { Name = "Alice", Age = 25 },new Person { Name = "Bob", Age = 30 }
};bool areEqual = list1.SequenceEqual(list2, new PersonComparer()); // ? true
判斷是否完全包含對方(不關心順序)
bool setEqual = list1.Count == list2.Count &&!list1.Except(list2).Any() &&!list2.Except(list1).Any();
使用 SetEquals(無序、無重復判斷)
bool areEqual = new HashSet<int>(list1).SetEquals(list2);
或:
HashSet<int> set1 = new HashSet<int>(list3);
HashSet<int> set2 = new HashSet<int>(list4);bool isEqual = set1.SetEquals(set2);
Console.WriteLine(isEqual); // 輸出: True
比較兩個 null 列表
List<int>? list5 = null;
List<int>? list6 = null;
Console.WriteLine(list5 == list6); // 輸出: True
比較兩個包含null元素的列表
List<string?> list7 = new List<string?> { "a", null };
List<string?> list8 = new List<string?> { "a", null };
Console.WriteLine(list7.SequenceEqual(list8)); // 輸出: True
性能優化建議
-
小規模數據:使用
SequenceEqual
或HashSet
。 -
大規模數據:
- 先檢查列表長度是否相同。
- 使用并行化處理(如
AsParallel().SequenceEqual()
)。
總結
場景 | 方法 | 是否考慮順序 | 是否考慮重復次數 |
---|---|---|---|
順序敏感且內容相同 | SequenceEqual | 是 | 是 |
順序不敏感且內容相同 | HashSet.SetEquals | 否 | 否 |
順序不敏感但重復次數相同 | 排序后使用 SequenceEqual | 否 | 是 |
自定義對象比較 | 重寫 Equals 或使用 IEqualityComparer | 可配置 | 可配置 |