2013-07-12 51 views
5

Tôi đang cố truy cập một đối tượng được lưu trữ trong từ điển kiểu String, UnknownClass. Tôi có chìa khóa, và biết giá trị là một trong một số lớp container. Vì giá trị được chuyển đến một phương thức nhận một đối tượng, tôi không cần biết loại của lớp được lưu trữ như một giá trị. Tôi cũng cần gọi ContainsKey để xác nhận khóa tồn tại.Lấy giá trị từ điển bằng cách sử dụng Reflection

Tôi đã thử các phương pháp sau đây không có thành công:

Dictionary<String, object> list = (Dictionary<String, object>)source.GetType().GetProperty(dictionaryName).GetValue(source, null); 
nextSource = list[key]; 

nào mang lại cho tôi một lỗi đúc, và:

nextSource = source.GetType().GetMethod("get_Item").Invoke(source, new object[] { key }); 

nào mang lại cho tôi một ngoại lệ tham khảo null.

Dưới đây là một chút về mã, mặc dù tôi không chắc chắn nó sẽ giúp ích nhiều.

private void SetValue(object source, String path, String value) 
{ 
    if (path.Contains('.')) 
    { 
     // If this is not the ending Property, continue recursing 
     int index = path.IndexOf('.'); 
     String property = path.Substring(0, index); 

     object nextSource; 
     if(property.Contains("*")) 
     { 
      path = path.Substring(index + 1); 
      index = path.IndexOf('.'); 
      String dictionaryName = path.Substring(0, index); 

      Dictionary<String, object> list = (Dictionary<String, object>)source.GetType().GetProperty(dictionaryName).GetValue(source, null); 
      nextSource = list[property.Substring(1)]; 
      //property = property.Substring(1); 
      //nextSource = source.GetType().GetMethod("Item").Invoke(source, new[] { property }); 
     } ... 

Từ điển được truy cập được định nghĩa trong lớp PersonObject như vậy:

public class PersonObject 
{ 
    public String Name { get; set; } 
    public AddressObject Address { get; set; } 
    public Dictionary<String, HobbyObject> Hobbies { get; set; } 

Giá trị của Path, ở giai đoạn này, được thiết lập để "*Hiking.Hobbies.Hobby". Về cơ bản, chuỗi đường dẫn cho phép tôi điều hướng đến một thuộc tính trong một lớp con và tôi cần từ điển để truy cập các thuộc tính cho một danh sách của cùng một lớp.

+0

Các bạn đã xác nhận rằng 'source.GetType() GetProperty (dictionaryName) .GetValue (nguồn, null) 'là trở về tham chiếu đến từ điển hoặc là nó trở về' null'? EDIT: nếu nó được trả lại từ điển đúng cách, có thể chỉ cần sử dụng 'dynamic' thay vào đó:' dynamic list = (dynamic) source.GetType(). GetProperty (dictionaryName) .GetValue (source, null); nextSource = (đối tượng) danh sách [key]; ' –

+0

am damn chắc chắn nguồn là null nếu không điều này nên làm việc –

+0

Nguồn không phải là null. Khi tôi gọi điều này, tôi nhận được một InvalidCastException. Từ điển thực mà tôi đang truy cập cho ví dụ cụ thể này là kiểu . – Tim

Trả lời

7

Các Dictionary<TKey, TValue> Class thực hiện các phi generic IDictionary Interface. Vì vậy, nếu bạn có một biến tye object chứa tham chiếu đến một trường hợp Dictionary<String, HobbyObject>, bạn có thể lấy giá trị trong từ điển như sau:.

object obj = new Dictionary<String, HobbyObject> 
{ 
    { "Hobby", new HobbyObject() } 
}; 

IDictionary dict = obj as IDictionary; 
if (dict != null) 
{ 
    object value = dict["Hobby"]; 
    // value is a HobbyObject 
} 
3

Có vẻ như bạn đang cố gắng để làm điều này:

var source = new Dictionary<string, object>(); 
var key = "some key"; 
source.Add(key, "some value"); 

var property = source.GetType().GetProperty("Item"); 
var value = property.GetValue(source, new[] { key }); 

Console.WriteLine(value.ToString()); // some value 

Cập nhật: Vấn đề là một Dictionary<string, HobbyObject> không thể được đúc để một Dictionary<string, object>. Tôi nghĩ rằng bạn sẽ phải làm điều này:

private void SetValue(object source, String path, String value) 
{ 
    if (path.Contains('.')) 
    { 
     // If this is not the ending Property, continue recursing 
     int index = path.IndexOf('.'); 
     String property = path.Substring(0, index); 

     object nextSource; 
     if(property[0] = '*') 
     { 
      path = path.Substring(index + 1); 
      index = path.IndexOf('.'); 
      String dictionaryName = path.Substring(0, index); 

      property = property.Substring(1); 

      Object list = source.GetType().GetProperty(dictionaryName) 
           .GetValue(source, null); 
      nextSource = list.GetType().GetProperty("Item") 
          .GetValue(list, new[] { property }); 
     } 
+0

Tôi đã sửa đổi mã này: nextSource = source.GetType() GetMethod ("Item"). Gọi (source, new [] {property}); Thật không may, tôi vẫn nhận được một ngoại lệ tham chiếu null.Tôi đã kiểm tra và cả "nguồn" và "thuộc tính" đều được chọn. – Tim

+0

@Tim Có lẽ tôi đã hiểu lầm vấn đề của bạn; thật khó để xem vấn đề của bạn có thể ở đâu. Vui lòng đăng thêm mã để tôi có thể xem toàn bộ ngữ cảnh. –

+0

Cảm ơn sự giúp đỡ của bạn. Tôi đã sửa đổi câu hỏi với mã bổ sung, mặc dù tôi không chắc chắn nó sẽ thực sự giúp ích như thế nào. – Tim

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