İsme göre bir özellik değeri nasıl alınır


157

Bir nesnenin bir özelliğinin değerini ismine göre almanın bir yolu var mı?

Örneğin:

public class Car : Vehicle
{
   public string Make { get; set; }
}

ve

var car = new Car { Make="Ford" };

Özellik adını geçirebileceğim bir yöntem yazmak istiyorum ve özellik değerini döndürecek. yani:

public string GetPropertyValue(string propertyName)
{
   return the value of the property;
}

Yanıtlar:


320
return car.GetType().GetProperty(propertyName).GetValue(car, null);

20
Bunun yansımayı kullandığından çok daha yavaş olduğunu unutmayın. Muhtemelen bir sorun değil, ama farkında olmak güzel.
Matt Greer

"Dizeden BindingFlags'e dönüştürülemiyor"
Christine

7
@MattGreer'ın "daha hızlı" bir yolu var mı?
FizxMike

47

Yansıma kullanmak zorundasın

public object GetPropertyValue(object car, string propertyName)
{
   return car.GetType().GetProperties()
      .Single(pi => pi.Name == propertyName)
      .GetValue(car, null);
}

Gerçekten süslü olmak istiyorsanız, bunu bir uzatma yöntemi yapabilirsiniz:

public static object GetPropertyValue(this object car, string propertyName)
{
   return car.GetType().GetProperties()
      .Single(pi => pi.Name == propertyName)
      .GetValue(car, null);
}

Ve sonra:

string makeValue = (string)car.GetPropertyValue("Make");

SetValue yerine GetValue istersiniz
Matt Greer

Bunu bir SetValue için de yapabilir miyim? Nasıl?
Piero Alberto

2
minör şey- uzatma yöntemi muhtemelen adlandırılmış değişken olması gerekmezcar
KyleMit

Özellik değerinin bir propertyName dizesine göre nasıl ayarlanacağını görmek için buradaki yanıta bakın: Özelliklerin değerini yansıma yoluyla ayarlama
nwsmith

36

Yansıma istiyorsun

Type t = typeof(Car);
PropertyInfo prop = t.GetProperty("Make");
if(null != prop)
return prop.GetValue(this, null);

7
+1 Tüm ara nesneleri gösterdiğiniz için bu en iyi cevaptır
Matt Greer

1
Özellik değerini iletmek yerine, dizini geçip özellik adını ve değerini alabilir miyim (böylece tüm mülkte döngü yapabilirim)?
singhswat

@singhswat Bunu yeni bir soru olarak sormalısınız.
Chuck Savage

7

Basit örnek (istemcide yansıma sert kodu yazmadan)

class Customer
{
    public string CustomerName { get; set; }
    public string Address { get; set; }
    // approach here
    public string GetPropertyValue(string propertyName)
    {
        try
        {
            return this.GetType().GetProperty(propertyName).GetValue(this, null) as string;
        }
        catch { return null; }
    }
}
//use sample
static void Main(string[] args)
    {
        var customer = new Customer { CustomerName = "Harvey Triana", Address = "Something..." };
        Console.WriteLine(customer.GetPropertyValue("CustomerName"));
    }

7

Buna ek olarak, diğer kişiler cevap verir, herhangi bir nesnenin özellik değerini aşağıdaki gibi Uzantı yöntemini kullanarak elde etmek kolaydır :

public static class Helper
    {
        public static object GetPropertyValue(this object T, string PropName)
        {
            return T.GetType().GetProperty(PropName) == null ? null : T.GetType().GetProperty(PropName).GetValue(T, null);
        }

    }

Kullanım:

Car foo = new Car();
var balbal = foo.GetPropertyValue("Make");

C # 6'dan itibaren boş yayma kullanabilirsiniz return T.GetType().GetProperty(PropName)?.GetValue(T, null);
Alef Duarte

7

Adam Rackis'in cevabını genişleterek - genişletme yöntemini basitçe şu şekilde genel yapabiliriz:

public static TResult GetPropertyValue<TResult>(this object t, string propertyName)
{
    object val = t.GetType().GetProperties().Single(pi => pi.Name == propertyName).GetValue(t, null);
    return (TResult)val;
}

İsterseniz bunun etrafına da bazı hatalar atabilirsiniz.


2

Yansımayı önlemek için, istediğiniz özelliklerden karşılık gelen değerleri döndüren sözlük değeri bölümünde anahtarlar ve işlevler olarak mülkiyet adlarınızı içeren bir Sözlük oluşturabilirsiniz.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.