2012-01-19 33 views
6

Tôi có một phương thức cố gắng so khớp chuỗi với DescriptionAttribute của các giá trị enum và sau đó trả về giá trị enum. Trong trường hợp không tìm thấy kết quả phù hợp, nó sẽ trả lại giá trị mặc định, mà tôi nghĩ rằng tôi có thể trả lại 0. Nhưng nó sẽ không xảy ra ...Trả về giá trị mặc định Enum khi loại Enum không được biết

private Enum GetEnumFromDescription(Type enumType, string description) 
{ 
     var enumValues = Enum.GetValues(enumType); 

     foreach (Enum e in enumValues) 
     { 
      if (string.Compare(description, GetDescription(e), true) == 0) 
        return e; 
     } 

     return 0; // not compiling 
} 

Làm cách nào để viết mã trên?

+0

Tại sao không chuyển thông số loại bằng cách sử dụng Generics? – millimoose

+0

Tại sao bạn đã gắn thẻ thẻ này với "iterator" và "yield-return"? –

+0

@Inerdial Tôi có thể? enumType của tôi đến từ Type.GetReflectionOnlyType (somestringfromdatabase). – Jake

Trả lời

13

Bạn có thể sử dụng

return (Enum) Activator.CreateInstance(enumType); 

này sẽ cung cấp cho bạn các giá trị mặc định cho các loại - đó là những gì bạn muốn.

EDIT: Tôi mong rằng bạn sẽ biết loại thời gian biên dịch, trong trường hợp đó, generics là một cách tiếp cận tốt. Mặc dù điều đó có vẻ không đúng, nhưng tôi sẽ để lại phần còn lại của câu trả lời này trong trường hợp nó sử dụng cho người khác.

Ngoài ra, bạn có thể sử dụng Unconstrained Melody mà đã có chứa một cái gì đó giống như chức năng này trong một loại an toàn, hình thức hiệu quả hơn :)

MyEnum value; 
if (Enums.TryParseDescription<MyEnum>(description, out value)) 
{ 
    // Parse successful 
} 

value sẽ được thiết lập với giá trị "0" nếu isn hoạt động phân tích cú pháp không thành công.

Hiện tại phân biệt chữ hoa chữ thường, nhưng bạn có thể dễ dàng tạo phiên bản phân biệt chữ hoa chữ thường. (Hoặc cho tôi biết và tôi có thể làm như vậy.)

+0

'Enum.ToObject (enumType, 0)' nên được sử dụng. – hazzik

+0

@hazzik: * Nên * là? Tại sao * nên *? Bạn nghĩ gì về lợi thế của điều đó là qua cách tiếp cận mà tôi đã đề xuất? Tôi không nói nó sẽ không hoạt động - chỉ có nhiều thứ sẽ hoạt động, và nếu bạn định tuyên bố rằng ai đó * nên * sử dụng một cách tiếp cận khác, bạn nên biện minh cho điều đó. –

+1

Tôi không phải là người bản xứ, và đối với tôi không có nhiều khác biệt giữa các động từ này, vì vậy xin lỗi, nếu tôi xúc phạm một ai đó. Nhưng để biện minh, tôi nghĩ nó tốt hơn vì 'Activator.CreateInstance' là một giải pháp chung cho các kiểu giá trị _all_, nhưng' Enum.ToObject' là đặc trưng cho enums. Và nó cũng _probably_ hoạt động nhanh hơn kích hoạt. Ngoài ra, 'Enum.ToObject' được sử dụng bên trong' Enum.GetValues ​​(t) ' – hazzik

0

lẽ điều này sẽ làm việc

return (Enum)enumValues[0]; 
+2

Không, điều đó sẽ không hoạt động nếu enum không xác định một giá trị tương ứng với 0. Nó cũng sẽ ném một ngoại lệ nếu enum doesn 't define * any * values. –

+1

@JonSkeet hmm ... làm thế nào để bạn biết được chi tiết về phút trên đầu của bạn? Nó chắc chắn không phải là một cái gì đó xảy ra thường xuyên? – Jake

+0

@Jon Tôi không hiểu tại sao nó không hoạt động. Nó chỉ lấy ra phần tử đầu tiên tạo thành mảng. – clearpath

1

tôi tin rằng phương pháp đúng là

(Enum)Enum.ToObject(enumType, 0) 

  • Activator.CreateInstance là giải pháp chung cho tất cả các loại giá trị và Enum.ToObject là giải pháp cụ thể cho enums, do đó, Enum.ToObject de clares rõ ràng ý định của mã.
  • Enum.ToObjectlẽ hoạt động nhanh hơn so với Activator.CreateInstance
  • Enum.ToObject được sử dụng bên trong Enum.GetValues để lấy giá trị.
Các vấn đề liên quan