2009-07-02 29 views
10

Có thể truyền lớp tùy chỉnh sang loại giá trị không?C#: Truyền tùy chỉnh thành loại giá trị

Dưới đây là một ví dụ:

var x = new Foo(); 
var y = (int) x; //Does not compile 

Có thể làm cho xảy ra ở trên không? Tôi có cần phải quá tải một số thứ trong Foo không?

+0

Bạn mong đợi điều đó sẽ làm gì? I.o.w, Foo trông như thế nào? –

Trả lời

23

Bạn sẽ phải quá tải toán tử truyền.

public class Foo 
    { 
     public Foo(double d) 
     { 
      this.X = d; 
     } 

     public double X 
     { 
      get; 
      private set; 
     } 


     public static implicit operator Foo(double d) 
     { 
      return new Foo (d); 
     } 

     public static explicit operator double(Foo f) 
     { 
      return f.X; 
     } 

    } 
+0

Bạn có thể giải thích việc sử dụng ngầm và rõ ràng trong câu trả lời của bạn không? Cảm ơn. –

+0

Plz xem MSDN: http://msdn.microsoft.com/en-us/library/xhbhezf4(VS.80).aspx http://msdn.microsoft.com/en-us/library/z5z9kes2(VS .71) .aspx (Tôi sẽ luôn thích các toán tử dàn diễn viên rõ ràng) –

+1

Tuyệt vời, chính xác những gì tôi đã tìm kiếm trong câu trả lời. Chúc mừng. –

6

Tạo một chuyển đổi rõ ràng hoặc ngầm:

public class Foo 
{ 
    public static explicit operator int(Foo instance) 
    { 
     return 0; 
    } 

    public static implicit operator double(Foo instance) 
    { 
     return 0; 
    } 
} 

Sự khác biệt là, với các chuyển đổi rõ ràng bạn sẽ phải làm loại đúc cho mình:

int i = (int) new Foo(); 

và với chuyển đổi tiềm ẩn, bạn chỉ có thể "chỉ định" mọi thứ:

double d = new Foo(); 

MSDN có điều này để nói:

"Bằng cách loại bỏ các phôi không cần thiết, chuyển đổi tiềm ẩn có thể cải thiện khả năng đọc mã nguồn. Tuy nhiên, do các chuyển đổi ngầm không yêu cầu các lập trình viên phải truyền một cách rõ ràng từ loại này sang loại khác, cần phải cẩn thận để ngăn chặn các kết quả không mong muốn. Nói chung, các nhà khai thác chuyển đổi tiềm ẩn không bao giờ nên ném ngoại lệ và không bao giờ mất thông tin để chúng có thể được sử dụng một cách an toàn mà không có sự nhận thức của người lập trình. Nếu một nhà điều hành chuyển đổi không thể đáp ứng các tiêu chí đó, nó phải được đánh dấu rõ ràng. "(tôi nhấn mạnh)

0

Một khả năng khác là để viết một Parse và phương pháp khuyến nông TryParse cho lớp học của bạn

Sau đó bạn muốn viết mã của bạn như sau:.

var x = new Foo(); 
var y = int.Parse(x); 
+2

tại sao bạn sẽ viết nó như là một phương pháp mở rộng, và không phải là một phương pháp thành viên thông thường? Đó là lớp của anh ấy, vì vậy anh ấy có quyền kiểm soát nó. –

+2

Bởi vì khi bạn có một cây búa, mọi vấn đề đều là móng tay. –

+1

@Mark: Ngay cả khi bạn đã viết một phương thức mở rộng, bạn không thể sử dụng nó với "var y = int.Parse (x);" vì các phương thức mở rộng chỉ áp dụng cho các cá thể. Bạn sẽ phải làm một cái gì đó như "var y = x.ParseToInt();" thay vào đó, và trong trường hợp đó, tại sao không chỉ đặt phương thức ParseToInt trong chính lớp đó, như Frederik nói. – LukeH

5

Bạn cần phải xác định explicit hoặc implicit đúc:

public class Foo 
{ 
    public static implicit operator int(Foo d) 
    { 
     return d.SomeIntProperty; 
    } 

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