在LINQ中,select属性X的所有值,其中X!= null

有没有更简单的方法来编写以下内容? (有些东西会检查null而不明确写入!= null

 from item in list where item.MyProperty != null select item.MyProperty 

您可以使用OfType运算符 。 它会忽略源序列中的空值。 只要使用与MyProperty相同的types,它不会过滤掉其他任何东西。

 // given: // public T MyProperty { get; } var nonNullItems = list.Select(x => x.MyProperty).OfType<T>(); 

我会build议反对这个。 如果你想select非空值,比说你想从列表中不是空的MyProperties什么可以更明确?

你可以定义你自己的扩展方法,但是我不会推荐这个方法。

 public static IEnumerable<TResult> SelectNonNull<T, TResult>(this IEnumerable<T> sequence,Func<T, TResult> projection) { return sequence.Select(projection).Where(e => e != null); } 

我不喜欢这个,因为它混合了两个问题。 使用Select和筛选空值进行投影是单独的操作,不应将其合并为一个方法。


我宁愿定义一个扩展方法,只检查该项目是否不为空:

 public static IEnumerable<T> WhereNotNull<T>(this IEnumerable<T> sequence) { return sequence.Where(e => e != null); } public static IEnumerable<T> WhereNotNull<T>(this IEnumerable<T?> sequence) where T : struct { return sequence.Where(e => e != null).Select(e => e.Value); } 

这只有一个目的,检查null。 对于可为空的值types,它将转换为不可为空的等价物,因为对于不能为null的值保留可以为null的包装器是无用的。

用这个方法,你的代码变成:

 list.Select(item => item.MyProperty).WhereNotNull() 

我倾向于创build一个静态类,包含像这些情况下的基本function。 他们让我写expression式

 var myValues myItems.Select(x => x.Value).Where(Predicates.IsNotNull); 

谓词函数的集合:

 public static class Predicates { public static bool IsNull<T>(T value) where T : class { return value == null; } public static bool IsNotNull<T>(T value) where T : class { return value != null; } public static bool IsNull<T>(T? nullableValue) where T : struct { return !nullableValue.HasValue; } public static bool IsNotNull<T>(T? nullableValue) where T : struct { return nullableValue.HasValue; } public static bool HasValue<T>(T? nullableValue) where T : struct { return nullableValue.HasValue; } public static bool HasNoValue<T>(T? nullableValue) where T : struct { return !nullableValue.HasValue; } } 

如果存在,则无法跳过检查。

//如果你需要检查是否所有项目的MyProperty都没有null

 if (list.All(x => x.MyProperty != null)) // do something 

//或者如果您需要检查是否至less有一个项目的属性没有null

 if (list.Any(x => x.MyProperty != null)) // do something 

但是你总是要检查null

这是从CodesInChaos的扩展方法改编的。 名称更短( NotNull ),更重要的是,将types( T )限制为where T : class引用types。

  public static IEnumerable<T> NotNull<T>(this IEnumerable<T> source) where T : class { return source.Where(item => item != null); }