【问题标题】:Find index of a list of keyvalue pair by key -updated通过 key -updated 查找键值对列表的索引
【发布时间】:2020-12-17 22:36:51
【问题描述】:

我正在创建一个键值对列表。

var myList = new List<KeyValuePair<string, int>>();
myList.Add(new KeyValuePair<string, int>("A", 1));
myList.Add(new KeyValuePair<string, int>("B", 2));
myList.Add(new KeyValuePair<string, int>("A", 1));
myList.Add(new KeyValuePair<string, int>("C", 3));
myList.Add(new KeyValuePair<string, int>("A", 5));
myList.Add(new KeyValuePair<string, int>("X", 9));
myList.Add(new KeyValuePair<string, int>("Z", 7));

我想通过键值对的键找出这个列表的索引。 因此,A 的索引为 0,2 和 4,Z 的索引为 6。

要查找只存在一次的索引,我可以执行以下操作..

int o = myList.IndexOf((from val in myList where val.Key == "Z" select val).SingleOrDefault());

但是如何获取 val.Key == "A" 的索引。

有人建议我查看Get indexes of all matching values from list using Linq 的问题并结束我的问题,尽管我的问题是关于键值对列表和上述关于字符串列表的问题......

基于我尝试失败..

var result = Enumerable.Range(0, myList.Count)
             .Where(kvp => kvp.Key == "A")
             .ToList();

var result1 =   myList.Select((x, i) => new {x, i})
                  .Where(x => x.Key == "A")
                  .Select(x => x.i);

收到的错误:

编译错误:“int”不包含“Key”的定义,并且找不到接受“int”类型的第一个参数的扩展方法“Key”(您是否缺少 using 指令或程序集引用?) 编译错误:“AnonymousType#1”不包含“Key”的定义,并且找不到接受“AnonymousType#1”类型的第一个参数的扩展方法“Key”(您是否缺少 using 指令或程序集引用? )

非常感谢人们回答问题或允许其他人回答而不是关闭它们..

【问题讨论】:

  • 要一行行吗?
  • 一行很棒.. 多条也行.. Tx..
  • 为什么不用字典呢?

标签: c#


【解决方案1】:

您可以通过执行以下操作来实现此目的:

public List<int> GetIndices(List<KeyValuePair<string, int>> myList, string query)
{
    List<int> indices = new List<int>();
    for (int i = 0; i < myList.Count; i++)
    {
        if (myList[i].Key == query) indices.Add(i);
    }

    return indices;
}

以下适用于任何类型:

public List<int> GetIndices<T, K>(List<KeyValuePair<T, K>> myList, T query)
{
    List<int> indices = new List<int>();
    int i = 0;
    myList.ForEach((pair) => { if (pair.Key.Equals(query)) indices.Add(i); i++; });
    return indices;
}

【讨论】:

    【解决方案2】:

    您似乎并没有真正理解链接问题中的代码,所以我会尝试解释一下。

    Enumerable.Range 的方法创建一个从 0(myList 的第一个索引)到myList.Count - 1myList 的最后一个索引)的数字序列,然后您使用Where 过滤这些索引,基于一个条件。

    真的,这里的 lambda 参数 kvp 是一个索引,而不是 KeyValuePair。在=&gt; 之后,您应该编写一个表达式,如果该索引应包含在最终列表中(即该索引处的 KVP 具有您想要的键),则计算结果为 true,所以让我们这样做:

    .Where(index => myList[index].Key == "A")
    

    第二种方法使用Select 的重载,它采用Func&lt;TSource, int, TResult&gt;,因此在Select lambda 中,您可以访问KVP 和索引。在这里,我们将两个参数转换为一个(匿名类的)对象。这样我们就可以只选择使用最后一个Select 的索引,但根据Where 中的KVP 进行过滤。

    您的错误是您没有意识到其中涉及匿名类。在Where lambda 中,您需要访问.x 才能访问匿名对象的KVP 部分,而不是索引I

    .Where(x => x.x.Key == "A") // the first x is the anonymous object, the second x is the KVP
    

    【讨论】:

      猜你喜欢
      • 2018-09-22
      • 2017-05-10
      • 1970-01-01
      • 2016-09-06
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-01-28
      相关资源
      最近更新 更多