【问题标题】:iterate .net dictionary as object将 .net 字典迭代为对象
【发布时间】:2014-07-29 11:11:18
【问题描述】:

我有一个有趣的问题。我需要编写一个通用(我会使用“通用”一词,但这会与我所追求的内容相冲突)例程,我可以将一个字典对象实例的实例交给一个字典,并将所述对象的内容作为字典进行迭代并将内容作为文字值返回。困难在于方法参数将是“对象”类型,而不是字典。

我现在需要但不知道该怎么做,是一种迭代任意键和值的Dictionary<K, V> 的方法。如果您知道输入的类型,这很容易做到,但正如我所说,字典的起源将作为 object.GetType().GetInterfaces() 在结果中具有 typeof(IDictionary) 的对象。我不知道(也不应该知道)字典键类型或值类型。

我目前的需要是处理Dictionary<string, SomeClass>;。一旦我得到键列表,我就可以在每个实例上使用一个 foreach,找出它是一个字符串并从那里继续。使用 Values ,它将成为某个类的实例(该类会发生变化,但我可以将其传递给另一组方法来提取类、提取类的属性并提取这些值)。

请求的主要目的是获得一个方法(或两个或多个),它允许我遍历未知类型的字典并提取键和值,所有这些都不需要在编译时知道类型。上述词典;只是一个例子,我需要能够通过任何字典。目前,我并不担心像 Dictionary<Tuple<int, string, SomeOtherClass>, SomeClass>> 这样的边缘情况,如果我可以从 Dictionary<string, SomeClass>; 开始,我可能可以从那里着手。

它以一种我可以处理但我还没有弄清楚如何去做的形式获取键和值。

【问题讨论】:

  • foreach over 字典有什么问题,它将为您提供键/值对
  • 想想你的问题。 “foreach”通常是“foreach(可枚举类型项目)”,其中项目是键或值。特别是因为我知道实例是字典的唯一方法是检查接口,所以我知道没有一种方法可以将对象声明为字典然后引用键和值。由于我不知道类型,我该如何声明一个 foreach?如果我可以使用接口声明一个变量并在运行时将其转换为所需的接口,那么问题就解决了。我不知道有什么方法可以做到这一点,你呢?
  • foreach(var keyValue in (Dictionary)someObject)... metacubed (+1) 的回答展示了如何直接获取键/值,并且可能更适合您的情况。

标签: c# loops object dictionary key


【解决方案1】:

您提到您可以访问对象上的IDictionary<K,V> 接口。然后您可以使用get_Keysget_Values 分别访问键和值。

此外,IDictionary<K,V> 派生自 IEnumerable<KeyValuePair<K,V>>,因此您还可以使用类似于列表的 for 循环访问键值对列表。

编辑 - 澄清:

IDictionary inputAsDictionary = input as IDictionary;
if (inputAsDictionary != null)
{
    // Valid :  input is a dictionary.
    ICollection dictKeys = inputAsDictionary.Keys; // This is a list of all keys
    ICollection dictValues = inputAsDictionary.Values; // This is a list of all values

    // Iterate over all keys
    for(var dictKey in dictKeys)
    {
        Console.WriteLine(dictKey); // Print the key
        Type dictKeyType = dictKey.GetType(); // Get the type of key if required
        // ...
    }

    // Similarly, iterate over all values
    for(var dictValue in dictValues)
    {
        Console.WriteLine(dictValue); // Print the value
        Type dictValueType = dictValue.GetType(); // Get the type of value if required
        // ...
    }
}

您也可以使用通用的Dictionary<K,V> 接口来执行此操作,但获取类型会变得更加复杂。您需要致电Type.GenericTypeArguments 并从那里开始。我展示的示例似乎更简单。

【讨论】:

  • 您能详细说明一下吗?我认为我知道你要去哪里,但是以代码 sn-p 为例会有很大帮助。在接口列表中,我可以看到(调试模式 - 查看来自“propertyType.GetInterfaces()”的调用内容)“IDictionary”和“IDictionary`2”都在列表中,但我不在当然,如果有的话,我可以用它们做什么。
  • 好的,这对于获取键和值的类型非常有用,但是(抱歉在这里很密集),我需要的不是类型,而是构成列表的实际值键或值。例如,如果我有一个 Dictionary<string, int>包含两个条目 {{"Key1", 1}, {"Key2", 2}},我需要能够从键和值中取出“Key1”和“Key2”以及 1 和 2。
  • @Fred 哦,您已经在上面的示例中拥有了这些。每个dictKey 是键的实际值,即“Key1”、“Key2”。每个dictValue 同样是实际值,即 1、2 等。
  • (用手拍打额头的声音)!谢谢 - 我离问题太近了,完全错过了。
  • 对于延迟将其标记为“答案”表示歉意,我需要在此处介绍的基础上进行扩展以实现我的目标 - 这是一种我称之为“ToCode”的方法,它将获取一个对象并吐出必要的 C# 代码,以便稍后初始化所述对象的实例。这有利于开发棕地开发测试模拟数据。感谢指导,真的很有帮助!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2018-11-24
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-07-05
  • 2018-12-14
相关资源
最近更新 更多