2012-04-06 36 views
14

Vì bị làm phiền trong .NET Reflection set private property, người ta có thể đặt thuộc tính với một người đặt riêng. Nhưng khi thuộc tính được định nghĩa trong một lớp cơ sở, System.ArgumentException được ném: "Không tìm thấy phương thức thuộc tính thiết lập".Phương thức thiết lập thuộc tính không được tìm thấy trong một loại có nguồn gốc

Một ví dụ có thể là:

using System; 
class Test 
{ 
    public DateTime ModifiedOn { get; private set;} 
} 

class Derived : Test 
{ 
} 

static class Program 
{ 
    static void Main() 
    { 
     Derived p = new Derived(); 
     typeof(Derived).GetProperty("ModifiedOn").SetValue(
      p, DateTime.Today, null); 
     Console.WriteLine(p.ModifiedOn); 
    } 
} 

Có ai biết một cách để giải quyết tình trạng này?

Chỉnh sửa: Ví dụ được đưa ra là minh hoạ đơn giản về sự cố. Trong kịch bản thế giới thực, tôi không biết liệu thuộc tính được định nghĩa trong một lớp cơ sở hay được định nghĩa trong cơ sở của lớp cơ sở.

Trả lời

20

Tôi gặp sự cố tương tự khi thuộc tính cá nhân của tôi được khai báo trong lớp cơ sở. Tôi đã sử dụng DeclaringType để có được xử lý trên lớp nơi thuộc tính được xác định.

using System; 
class Test 
{ 
    public DateTime ModifiedOn { get; private set;} 
} 

class Derived : Test 
{ 
} 

static class Program 
{ 
    static void Main() 
    { 
     Derived p = new Derived(); 

     PropertyInfo property = p.GetType().GetProperty("ModifiedOn"); 
     PropertyInfo goodProperty = property.DeclaringType.GetProperty("ModifiedOn"); 

     goodProperty.SetValue(p, DateTime.Today, null); 

     Console.WriteLine(p.ModifiedOn); 
    } 
} 
9

Tôi nghĩ rằng điều này sẽ làm việc:

using System; 
class Test 
{ 
    public DateTime ModifiedOn { get; private set;} 
} 

class Derived : Test 
{ 
} 

static class Program 
{ 
    static void Main() 
    { 
     Derived p = new Derived(); 
     typeof(Test).GetProperty("ModifiedOn").SetValue(
      p, DateTime.Today, null); 
     Console.WriteLine(p.ModifiedOn); 
    } 
} 

Bạn cần phải nhận được định nghĩa tài sản từ các lớp học thực sự xác định trên không phải là lớp có nguồn gốc

EDIT:

Để nhặt nó trên bất kỳ lớp cơ sở nào, bạn sẽ cần phải tìm nó trên tất cả các lớp cha.

một cái gì đó như thế này sau đó recurse đến lớp cơ sở cho đến khi bạn nhấn đối tượng hoặc tìm tài sản của bạn

typeof(Derived).GetProperties().Contains(p=>p.Name == "whatever") 
+0

Điều này chắc chắn sẽ hiệu quả nếu loại cơ sở được biết. Vui lòng xem chỉnh sửa của tôi. – tafa

7

Một tùy chọn khác hơn một @ LukeMcGregor là sử dụng BaseType

typeof(Derived) 
    .BaseType.GetProperty("ModifiedOn") 
    .SetValue(p, DateTime.Today, null); 
+0

Có, nếu cây thừa kế có chiều dài một. Vui lòng xem chỉnh sửa của tôi. – tafa

+1

Sau đó, bạn đi bộ đường dây ... Bạn có thể dừng lại tại System.Object. –

5

tôi đã thực hiện phương pháp tái sử dụng này . Nó xử lý các kịch bản của tôi.

private static void SetPropertyValue(object parent, string propertyName, object value) 
    { 
     var inherType = parent.GetType(); 
     while (inherType != null) 
     { 
      PropertyInfo propToSet = inherType.GetProperty(propertyName, BindingFlags.Public | BindingFlags.Instance); 
      if (propToSet != null && propToSet.CanWrite) 
      { 
       propToSet.SetValue(parent, value, null); 
       break; 
      } 

      inherType = inherType.BaseType; 
     } 
    } 
Các vấn đề liên quan