如何在C#中获取所有者属性类

时间:2014-01-16 13:11:12

标签: c# properties base-class owner

我需要分析我的对象并在列表中显示它的一些属性。 我的对象有一些属性,它们来自基类“ObjectBaseClass”,这些属性不应该显示在我的列表中。

我怎么知道,房产是否来自基层?

即我有一个IDisposableExtended接口,这个接口将在我的对象类中实现。但在我的列表中,我不想显示这两个属性“Disposable”和“Disposed”。我该如何过滤它们?

public interface IDisposableExtended : IDisposable
{
    bool Disposable { get; }
    bool Disposed { get; }
}

非常感谢!

p.s属性可以来自基类(级别1),基类(级别1)也可以来自他自己的基类(级别2)。是这样,当我使用包含BindingFlags.DeclaredOnly的GetProperties(flags)时,所有来自基类(级别1和级别2)的属性都将被过滤掉?我可以过滤基级1级或2级吗? 这意味着,我希望首先获取所有属性,然后根据其基类手动过滤。然后我完全控制它们以显示我需要的属性。

3 个答案:

答案 0 :(得分:1)

首先,这些属性的“所有者”实际上是类,而不是接口。接口为这些属性提供访问,但这些属性的声明类型仍然是类。

但是,当您通过反射发现它们时,您继承的属性将具有不同的声明类型。这是一个LINQPad程序,演示了:

void Main()
{
    var derivedType = typeof(Derived);
    derivedType.GetProperties().Dump("All");
    derivedType.GetProperties(BindingFlags.DeclaredOnly
        | BindingFlags.Public | BindingFlags.Instance).Dump("Declared only");
}

public class Base
{
    public string BaseProperty { get; set; }
}

public class Derived : Base
{
    public string DerivedProperty { get; set; }
}

请注意,如果您还在Derived中实现了一个接口,那么在转储Derived的属性时也会显示这些方法/属性,因为它们是由该类型声明的。是的,它们用于实现接口,但它们也被类型声明(“拥有”)。

答案 1 :(得分:0)

您应该使用Type.GetProperty(String, BindingFlags)方法重载并包含BindingFlags.DeclaredOnly来限制搜索到未继承的成员。

在此处阅读更多内容:http://msdn.microsoft.com/en-us/library/kz0a8sxy(v=vs.110).aspx

回应评论(即使我不确定我是否理解正确)。这是一个快速程序,它将遍历类型层次结构并显示在类型本身上声明的属性,不包括每个级别的继承类型。

namespace ConsoleApplication1
{
    class ClassA
    {
        public string ClassAProp { get; set; }
    }

    class ClassB : ClassA
    {
        public string ClassBProp { get; set; }
    }

    class ClassC : ClassB
    {
        public string ClassCProp { get; set; }
    }

    class Program
    {
        static void Main(string[] args)
        {
            var c = new ClassC();
            var t = c.GetType();
            while (t.BaseType != null)
            {
                var cProps = t.GetProperties(BindingFlags.DeclaredOnly | BindingFlags.Instance | BindingFlags.Public);
                foreach (var p in cProps)
                {
                    Console.WriteLine("{0} defines {1}", t.Name, p.Name);
                }
                t = t.BaseType;
            }
            Console.ReadLine();
        }
    }
}

因此,您可以看到'BindingFlags.DeclaredOnly'仅返回在类上声明的属性。希望这有助于实现您的目标。

注意: Type.BaseType对于object类型将为null,因为它是根类型。如果您希望循环停止在任何其他类型,您应该能够说出while (t != TypeYouWantToStopAt.GetType())

答案 2 :(得分:0)

这稍微偏离了您的问题,但可能会让您了解所描述问题的不同方法。

您可以声明一个自定义属性,用于标记您不想列出的任何属性(或任何成员)。当您枚举对象的属性时,您可以检查它的属性并跳过已标记的任何内容。这类似于.NET属性Editor控件的工作方式。