2011-01-28 22 views
6

Tôi đang thử các cách sau:Không thể so sánh T giá trị 1 với giá trị T2 = mặc định (T). Tại sao và làm thế nào để làm điều đó trên C#?

T value1 = el.value; // it's of type T already 
T value2 = default(T); 
if (value1 != value2) // gives the following error: Operator '!=' cannot be applied to operands of type 'T' and 'T' 
{ 
    // ... 
} 

Vì vậy, làm cách nào tôi có thể so sánh cả hai giá trị? Và tại sao lỗi này xảy ra?

Cảm ơn trước!

+0

Hãy chắc chắn rằng T thực hiện các lớp học kiểu ICompare-ish, và các phương pháp hoặc lớp định nghĩa T có những tài liệu tham khảo trong việc kê khai. – asawyer

Trả lời

11

Bạn có thể sử dụng một hạn chế của where T : IEquatable<T> như Henk đã đề cập, hoặc bỏ qua những hạn chế và sử dụng:

if (!EqualityComparer<T>.Default.Equals(value1, value2)) 
+0

Tôi đã nhìn thấy khuôn khổ sử dụng phương pháp đó để kiểm tra sự bình đẳng, có vẻ như là một cách tốt để đi, ngay cả khi nó là một chút tiết. –

+0

Tôi nghĩ đây là cách đơn giản nhất. Cảm ơn! – Girardi

+0

@Ani: Bạn nói đúng. Tôi đã quên không có giao diện IEquatable không chung chung. Sẽ chỉnh sửa. –

3

của bạn xung quanh lớp generic nên liệt kê một hạn chế: T : IEquatable<T>

Và sau đó bạn phải sử dụng value1.Equals(value2)

Lý do cho tất cả điều này là không phải tất cả các loại định nghĩa toán tử ==

+0

@ani: Bạn nói đúng, tôi đã xóa nó. Hình tượng của trí tưởng tượng của tôi. –

+0

Bạn sẽ nhận được 'NullReferenceException' nếu' value1' là 'null'. – nicodemus13

2

Có gì sai với điều này ?

if (!value1.Equals(value2)) 

nên là "chéo đối tượng" .. :)

+2

Cá nhân tôi không thích sự bất đối xứng của điều đó. Và tất nhiên nó ném nếu 'value1 == null' – CodesInChaos

0

Một điều mà bạn có thể làm là xác định toán tử so sánh (trên thực tế, toán tử khác biệt ở đây) để có thể so sánh các phần tử của kiểu T. Chính nó, trình biên dịch không thể biết ý bạn là gì khi viết value1 != value2, trừ khi toán tử đã được định nghĩa trước đó .

Để xác định một nhà điều hành, bạn muốn sử dụng

public operator!=(T a, T b) { 
    // Comparison code; returns true or false 
} 
+0

Tôi nghĩ 'T' là một tham số chung, vì vậy điều này có thể là không thể. – CodesInChaos

+0

Điều đó chỉ hoạt động khi trình biên dịch biết (chính xác) T là gì. –

1

nếu bạn sử dụng value1.equals (value2) sau đó bạn có một vấn đề với các giá trị null. Better:
Object.equals (value1, value2)

Hoặc với nhiều loại tài liệu tham khảo (cẩn thận):
object.referenceEquals (value1, value2)

1

Không phải tất cả các loại có một thực hiện mặc định của người điều khiển == . Đối với các lớp, hoạt động mặc định là == là để so sánh các tham chiếu. Đối với các cấu trúc, không có triển khai mặc định nào tồn tại.

Bạn có thể thêm các ràng buộc kiểu vào các tham số kiểu chung trong C#. Thật không may, bạn không thể xác định ràng buộc buộc loại phải thực hiện toán tử ==. Điều tốt nhất bạn có thể làm là buộc loại phải là một lớp: where T: class. An article about type parameter constraints in C#

1

thử

Equals(value1, value2) 

Một cách tốt để tránh vô ref của

Các vấn đề liên quan