是否有更短的方式来编写以下内容? (在不明确写!= null
)的情况下检查null的东西
from item in list
where item.MyProperty != null
select item.MyProperty
答案 0 :(得分:56)
您可以使用OfType
operator。它忽略源序列中的空值。只需使用与MyProperty
相同的类型,它就不会过滤掉任何其他内容。
// given:
// public T MyProperty { get; }
var nonNullItems = list.Select(x => x.MyProperty).OfType<T>();
我会建议不要这样做。如果你想选择非空值,那么可能比你想要“列表中的非属性的MyProperties”更明确吗?
答案 1 :(得分:33)
您可以定义自己的扩展方法,但我不建议这样做。
public static IEnumerable<TResult> SelectNonNull<T, TResult>(this IEnumerable<T> sequence,Func<T, TResult> projection)
{
return sequence.Select(projection).Where(e => e != null);
}
我不喜欢这个,因为它混合了两个问题。使用Select
进行投影并过滤空值是单独的操作,不应合并为一个方法。
我宁愿定义一个扩展方法,只检查该项是否为null:
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。对于可以为null的值类型,它会转换为非可空等价项,因为保留可空的包装器对于不能为null的值是无用的。
使用此方法,您的代码变为:
list.Select(item => item.MyProperty).WhereNotNull()
答案 2 :(得分:11)
我倾向于为这样的情况创建一个包含基本函数的静态类。他们允许我写像
这样的表达式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;
}
}
答案 3 :(得分:4)
如果存在,则无法跳过检查。
答案 4 :(得分:1)
//如果你需要检查所有项目'MyProperty是否没有空
if (list.All(x => x.MyProperty != null))
// do something
//或者如果您需要检查至少有一个项目的属性是否没有null
if (list.Any(x => x.MyProperty != null))
// do something
但你总是要检查空
答案 5 :(得分:1)
这是从CodesInChaos的扩展方法改编而来的。名称较短(NotNull
),更重要的是,将类型(T
)限制为使用where T : class
引用类型。
public static IEnumerable<T> NotNull<T>(this IEnumerable<T> source) where T : class
{
return source.Where(item => item != null);
}
答案 6 :(得分:1)
在唯一选择中获取一列,并忽略空值:
tidyr::extract(df, Address, c("Address", "City", "State", "Zip"),
regex = "(.+) (\\w+) (\\w+) (\\w+)")
# Address City State Zip
#1 101 Marietta Street NorthWest Atlanta GA 30303
答案 7 :(得分:1)
我知道我参加聚会有点晚了,但我发现 IMO 非常优雅地解决了这个问题。我编写了一个扩展方法来链接到我的 LINQ 查询:
public static IEnumerable<T> DiscardNullValues<T>(this IEnumerable<T?> nullable)
{
foreach (var item in nullable)
{
if (item is not null) yield return item;
}
}
就像一个魅力。