2010-10-26 38 views

Trả lời

103

Không có sự khác biệt.

int? chỉ là viết tắt của Nullable<int>, chính nó là viết tắt của Nullable<Int32>.

Mã được biên dịch sẽ hoàn toàn giống với bất kỳ mã nào bạn chọn sử dụng.

+1

... trừ khi bạn đang sử dụng mã EF trước. Xem câu trả lời của tôi dưới đây. – Maciej

+1

Thật không may có một số trường hợp góc khi điều này không đúng. Xem [answer] này (http://stackoverflow.com/a/24738380/1552016). – qqbenq

19

Biểu mẫu ? chỉ là viết tắt cho loại đầy đủ. Sở thích cá nhân là lý do duy nhất để chọn một người khác.

Chi tiết đầy đủ here.

Cú pháp T? là viết tắt cho Nullable<T>, nơi T là một loại giá trị. Hai hình thức có thể hoán đổi cho nhau.

+4

... hoặc khả năng đọc. – adrianbanks

+0

@adrianbanks - chắc chắn –

4

Có vẻ như là một sự khác biệt giữa hai khi sử dụng mã đầu tiên Entity Framework (EF) thế hệ:

Khi tổ chức của bạn có chứa một tài sản tuyên bố như:

public class MyEntity 
{ 
    public Nullable<int> MyNullableInt { get; set; } 
} 

EF sẽ không tạo một tài sản không có giá trị và bạn sẽ phải buộc máy phát điện làm cho nó không hoạt động như vậy:

public class YourContext : DbContext 
{ 
    public DbSet<MyEntity> MyEntities{ get; set; } 

    protected override void OnModelCreating(DbModelBuilder modelBuilder) 
    { 
     base.OnModelCreating(modelBuilder); 
     modelBuilder.Entity<MyEntity>().Property(x => x.MyNullableInt).IsOptional(); 
    } 
} 

Bật Mặt khác, nếu bạn khai báo thực thể của bạn như:

public class MyEntity 
{ 
    public int? MyNullableInt { get; set; } 
} 

máy phát điện EF bất động sản sẽ tạo ra một tài sản nullable với một lĩnh vực nullable trong bảng cơ sở dữ liệu tương ứng.

+2

Điều đó thực sự không may. – siride

+7

Điều đó cho thấy bạn có một số định nghĩa 'Nullable' khác ở đâu đó, bởi vì với' Nullable 'được xây dựng sẵn, nó không thể cho EF thấy sự khác biệt giữa hai. Ngay cả khi người dân EF muốn đối xử với họ khác đi, họ vẫn không thể. – hvd

+1

Có ai đó xác nhận trường hợp này không? (chỉ cần thận trọng một chút vì phiếu bầu tiêu cực) – RayLoveless

15

Mặc dù tôi hoàn toàn đồng ý rằng trong hầu hết các trường hợp, chúng cũng giống nhau, gần đây tôi đã gặp một tình huống, khi có sự khác biệt giữa hai trường hợp đó. Đối với các chi tiết đẫm máu thấy this question, nhưng để cung cấp cho bạn một ví dụ nhanh ở đây:

void Test<T>(T a, bool b) 
{ 
    var test = a is int? & b;    // does not compile 
    var test2 = a is Nullable<int> & b; // does compile 
} 

Dòng đầu tiên cho các thông báo lỗi sau:

error CS1003: Syntax error, ':' expected 
error CS1525: Invalid expression term ';' 

Nếu bạn tò mò về lý do chính xác cho điều này , Tôi thực sự khuyên bạn nên kiểm tra xem đã có linked question chưa, nhưng vấn đề cơ bản là trong giai đoạn phân tích sau một toán tử is (hoặc as), khi chúng tôi gặp mã thông báo ?, chúng tôi kiểm tra xem tiếp theo token có thể được hiểu là toán tử đơn nhất (& có thể là một) và nếu như vậy: trình phân tích cú pháp không quan tâm đến khả năng mã thông báo ? là công cụ sửa đổi loại, nó đơn giản sử dụng loại trước nó và phân tích cú pháp phần còn lại như thể mã thông báo ? là một toán tử bậc ba (do đó việc phân tích cú pháp sẽ thất bại).Vì vậy, trong khi nói chung, int?Nullable<int> có thể hoán đổi cho nhau, có một số trường hợp góc khi chúng tạo ra các kết quả hoàn toàn khác nhau, vì cách trình phân tích cú pháp nhìn thấy mã của bạn.

+1

Trường hợp đầu tiên, 'test', được cố định bằng dấu ngoặc đơn, vì vậy' var test = (a is int?) & b; '. Cũng có thể được sửa với 'var test = a is int? && b; ', và cho rằng' b' là một tham số giá trị đơn giản (không có tác dụng phụ trên đánh giá) có vẻ lạ để thích '&' hơn '&&'. –

+0

Trong cú pháp cụ thể đó, '?' Là một ký tự chính. –

+0

Xem câu hỏi và trả lời được liên kết, nhận xét của bạn đều được giải quyết ở đó :) Tôi chỉ thêm thông tin ở đây, vì tôi cảm thấy nó có liên quan, vì nó đưa ra sự khác biệt giữa hai hình thức và chứng minh rằng nó không chỉ là cú pháp – qqbenq

0

Nullable là loại chung, nhưng int? thì không.

Có một số trường hợp trong đó Nullable nên được sử dụng trên int?

ví dụ: tại đây bạn không thể thay thế Nullable với int?

cách bạn có thể thay đổi mã bên dưới mà không cần sử dụng Nullable?

class LazyValue<T> where T : struct 
{ 
    private Nullable<T> val; 
    private Func<T> getValue; 

    // Constructor. 
    public LazyValue(Func<T> func) 
    { 
     val = null; 
     getValue = func; 
    } 

    public T Value 
    { 
     get 
     { 
     if (val == null) 
      // Execute the delegate. 
      val = getValue(); 
     return (T)val; 
     } 
    } 
} 
+1

'T riêng tư? val' hoạt động tốt. – johnnyRose

+0

Điều gì có thể quan trọng nếu câu hỏi đã được hỏi về các loại chung chung, nhưng câu hỏi đã chỉ định int, vì vậy nó không phải là 'Nullable ' nó 'Nullable ' – Andrew

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