2011-11-02 49 views
6

Tôi đã tuyên bố Enum sau:Nhận tên Enum dựa trên giá trị Enum

public enum AfpRecordId 
{ 
    BRG = 0xD3A8C6, 
    ERG = 0xD3A9C6 
} 

và tôi muốn lấy đối tượng enum từ là giá trị:

private AfpRecordId GetAfpRecordId(byte[] data) 
{ 
    ...      
} 

Gọi Ví dụ:

byte[] tempData = new byte { 0xD3, 0xA8, 0xC6 }; 
AfpRecordId tempId = GetAfpRecordId(tempData); 

//tempId should be equals to AfpRecordId.BRG 

Tôi cũng muốn sử dụng LINQ hoặc lambda, chỉ khi chúng có thể cho hiệu suất tốt hơn hoặc bằng.

+0

có thể trùng lặp của [Nhận tên enum khi giá trị được biết] (http://stackoverflow.com/questions/3327883/get-enum-name-when-value-is-known) – Heinzi

Trả lời

9

đơn giản:

  • Chuyển đổi mảng byte thành một int (hoặc bằng tay, hoặc bằng cách tạo một mảng Bốn byte và sử dụng BitConverter.ToInt32)
  • Cast int để AfpRecordId
  • Gọi ToString vào kết quả nếu cần thiết (dòng chủ đề của bạn gợi ý tên, nhưng chữ ký phương thức của bạn chỉ nói về giá trị)

Ví dụ:

private static AfpRecordId GetAfpRecordId(byte[] data) 
{ 
    // Alternatively, switch on data.Length and hard-code the conversion 
    // for lengths 1, 2, 3, 4 and throw an exception otherwise... 
    int value = 0; 
    foreach (byte b in data) 
    { 
     value = (value << 8) | b; 
    } 
    return (AfpRecordId) value; 
} 

Bạn có thể sử dụng Enum.IsDefined để kiểm tra xem các dữ liệu nhất định thực sự là một hợp lệ ID.

Đối với hiệu suất - hãy kiểm tra xem điều gì đó đơn giản mang đến cho bạn hiệu suất đủ tốt trước khi bạn tìm kiếm điều gì đó nhanh hơn.

+0

Tôi buộc phải chuyển đổi byte mảng đến một int? Nếu tôi hiểu đúng giá trị "BRG = 0xD3A8C6" không được nhận dạng dưới dạng một byte []? –

+0

Tôi không nghĩ rằng anh ta thực sự đang tìm kiếm một chuỗi (tôi nghĩ rằng ban đầu là tốt) Nếu bạn nhìn vào kiểu trả về của phương pháp tấm nồi hơi của mình, nó trả về giá trị của enum –

+3

@Duncan_McCloud: Thật vậy, '0xd3a8c6' là một 'int' chữ, không phải mảng byte. Trong khi có thể có những cách khác ngoài việc chuyển đổi mảng byte thành một int, chúng có hiệu quả đun sôi xuống một cái gì đó tương tự, và phức tạp hơn. Mã này nên cực kỳ nhanh, và nó đẹp và đơn giản - bạn không thích gì về nó? –

1

Nếu mảng là có kích thước được biết đến (tôi sẽ giả định kích thước là 3 theo ví dụ của bạn), bạn có thể thêm các yếu tố với nhau và các diễn viên kết quả để enum

private AfpRecordId GetAfpRecordId(byte[] tempData){ 
    var temp = tempData[0] * 256*256 + tempData[1] * 256 +tempData[2]; 
    return (AfpRecordId)temp; 
} 

một khác nhau cách tiếp cận sẽ được sử dụng toán tử chuyển đổi thay vì

private AfpRecordId GetAfpRecordId(byte[] tempData){ 
    var temp = (int)tempData[0]<<16 + (int)tempData[1] * 8 +tempData[2]; 
    return (AfpRecordId)temp; 
} 
+2

Lưu ý rằng điều này giả định 'tempData' có ba phần tử. Đó * có thể * là một giả định hợp lệ, nhưng nó có thể không. –

+0

Đó là một giả định hợp lệ :) –

+0

@JonSkeet có nó giả định rằng (dựa trên mã mẫu. Tôi đã cập nhật để câu trả lời làm nổi bật giả định. –

1

Giả sử rằng tempData có 3 yếu tố sử dụng Enum.GetName (typeof (AfpRecordId), tempData[0] * 256*256 + tempData[1] * 256 +tempData[2]).