【问题标题】:Ordering of types fetched from Assembly.GetTypes()从 Assembly.GetTypes() 获取的类型的排序
【发布时间】:2019-07-13 05:37:52
【问题描述】:

我有一个要求,我需要获取以下类型

public class Class1
{
}

public class Class2 : Class1
{
}

public class Class3 : Class1
{
}

我可以在目标程序集上调用Assembly.GetTypes() 并添加从Class1 派生的所有类。我正在订购这些类型,以便下次使用该订单。 该顺序对于内部序列化和反序列化至关重要,因为内部引擎取决于类型的索引而不是类型名称。我无法更改序列化引擎。

如果将来有一个新类Class4 派生自Class1,那么它应该按Class3 之后的顺序出现。

我想不出可行的解决方案。

我需要维护一个 xml 文件,其中类型的顺序被保留,如果我遇到新类型,是否应该在 xml 末尾添加?

请帮忙

【问题讨论】:

  • 您不能依赖 GetTypes 方法返回的类型的任何顺序。如果您有一些自定义的排序规则,那么您应该将这些规则应用于方法返回的结果。
  • 基于任意索引而不是类型名称本身的类型的(反)序列化需要索引和相应类型之间的映射。这就是您对 XML 所做的基本操作,我想这种方法是这种情况下的最佳选择。这样的 XML/文本文件易于维护和验证。 (可能还有其他方法,例如创建自定义类型属性或以某种方式将序列化索引号放在类型名称中,但这些方法很麻烦且容易出错。)
  • 程序集中类的顺序是任意的,你不能依赖任何东西 stackoverflow.com/questions/11213732/… 。您将需要一个额外的机制,例如您谈到的 .xml 或下面的答案中概述的。

标签: c# reflection


【解决方案1】:

您可以为订购创建任何自定义规则:例如。模式为{ClassName}{Index}

    [Fact]
    public void Test()
    {

        Type baseClass = typeof(Class1);
        var result = (from type in Assembly.GetExecutingAssembly().GetTypes()
                      where type.IsSubclassOf(baseClass)
                      let index = Regex.Match(type.Name, @"\d+$")
                      where string.IsNullOrWhiteSpace(index.Value) == false
                      select new ResultItem { Index = int.Parse(index.Value), Type = type })
                      .OrderBy(x=>x.Index)
                      .ToList();
        result.ForEach(Console.WriteLine);
    }

    public class Class1
    {
    }

    public class Class2 : Class1
    {
    }

    public class Class3 : Class1
    {
    }

    private sealed class ResultItem
    {
        public int Index { get; set; }
        public Type Type { get; set; }

        public override string ToString()
        {
            return string.Format("Index: {0}, Type: {1}", Index, Type.Name);
        }
    }

结果输出:

Index: 2, Type: Class2
Index: 3, Type: Class3

因此,您可以添加任何新类。

【讨论】:

  • 感谢您的解决方案,但我提供的类仅用于说明目的,实际上类名可以是任何东西。在这种情况下,我需要将类型名称作为键和该类型的固定索引。
  • 如果类名可以是任何东西,那么您可以通过属性标记它们或在配置文件中创建 Key Value 部分,其中 Key 是类型,Value 是 oder。
猜你喜欢
  • 1970-01-01
  • 2011-10-23
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-12-18
  • 1970-01-01
相关资源
最近更新 更多