【问题标题】:How to get specific items from List<object> when all the object are different types of EventArgs当所有对象都是不同类型的 EventArgs 时如何从 List<object> 获取特定项目
【发布时间】:2019-07-08 15:15:48
【问题描述】:

我有一个名为eventQueue 的对象列表,其中存储了在后台执行的任务产生的所有事件。现在,我需要处理这个列表,从中提取特定事件。我想主要使用 LINQ 来提高代码的可读性(我不想编写多个 foreach),我的问题是我不完全知道如何进行。假设我有一个自定义 EventArgsnamed FirstEventArgs 的多个实例,我想从列表中提取一个特定的实例,做一个我会写的 foreach

foreach(object o in eventQueue)
{
   if( o is FirstEventArgs)
   {
       FirstEventArgs ev = o as FirstEventArgs ;
       if( ev.MyProperty == desiredValue)
       {
          // you got it 
       }
   }
}

目前我可以在 LINQ 中编写以下代码

FirstEventArgs ev = eventQueue.Where(x => x.GetType() == typeof(FirstEventArgs )).SingleOrDefault() as FirstEventArgs;

我的问题是。我如何修改前面的以在 Where if x is of type object 中添加条件ev.MyProperty = desiredValue

【问题讨论】:

    标签: c# linq


    【解决方案1】:

    您可以在 LINQ 查询中使用模式匹配将对象转换为您的类型:

    FirstEventArgs ev = eventQueue.Where(x => x is FirstEventArgs fea && fea.MyProperty == desiredValue)
                                  .SingleOrDefault() as FirstEventArgs;
    

    感谢@Slappywag 检查它是否有效!

    【讨论】:

    • 这很整洁。我不知道你会做这样的事情。我会把接受的答案留给另一个人,因为他速度更快,但你的答案更具可读性
    【解决方案2】:

    您可以使用&amp;&amp; 运算符,然后强制转换为所需的类型。仅当前半部分为真时才会评估 AND 语句的后半部分,因此您不会从转换中得到任何错误。这称为短路评估,根据此答案 (Is relying on && short-circuiting safe in .NET?) 可以在 C# 中依赖。

    FirstEventArgs ev = eventQueue.Where(x => x.GetType() == typeof(FirstEventArgs) 
                                           && ((FirstEventArgs)x).MyProperty == desiredValue)
                                  .SingleOrDefault() as FirstEventArgs;
    

    【讨论】:

    • 模式匹配在 LINQ 查询中是否有效,例如,eventQueue.Where(x =&gt; x is FirstEventArgs fea &amp;&amp; fea.MyProperty == desiredValue)?
    • @mmathis 我刚刚检查过 - 是的,请随时添加它作为答案。比我的好:)
    • 我很接近。我做错的是 && (FirstEventArgs)x.MyProperty == desiredValue 而不是 &&((FirstEventArgs)x).MyProperty == desiredValue。谢谢
    【解决方案3】:

    OfType 可让您进行类型测试并免费加入演员阵容:

    FirstEventArgs ev = eventQueue
                         .OfType<FirstEventArgs>()
                         .SingleOrDefault(fea=>fea.MyProperty==desiredValue);
    

    (我还将剩余的过滤移到了SingleOrDefault 调用中,因为,为什么不呢?)

    是的,其他答案也有效,但我的口味仍然有点“机制”,而不是仅仅声明我们想要什么

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2021-08-24
      • 2013-03-04
      • 1970-01-01
      • 1970-01-01
      • 2019-04-21
      • 1970-01-01
      相关资源
      最近更新 更多