Lambda表达式替代了几个if语句

nev*_*ova 1 c# lambda expression predicate

我正在尝试完成表达式功能替代方案

private static Expression<Func<UserProfile, bool>> CompareFilter(FilterViewModel f)
{
       ...
}
Run Code Online (Sandbox Code Playgroud)

在这一个:

private static bool CompareFilter(UserProfile profile, FilterViewModel filter)
{
        if (filter.FirstName != null)
        {
            if (profile.FirstName != null)
            {
                if (profile.FirstName.CompareTo(filter.FirstName) != 0)
                {
                    return false;
                }
            }
            else
            {
                return false;
            }
        }

        if (filter.TownId != null)
        {
            if (profile.TownId != filter.TownId)
            {
                return false;
            }
        }

        // true if at least one of the filter interests match
        if (filter.InterestsIds != null)
        {
            var firstInterestFound = profile.Interests
                 .Where(i => filter.InterestsIds.Contains(i.Id))
                 .FirstOrDefault();

            if (firstInterestFound == null)
            {
                return false;
            }
        }
        ...

        return true;
}
Run Code Online (Sandbox Code Playgroud)

有没有办法将这些嵌套的if语句适用于lambda表达式或其他适用于表达式函数的东西?这个想法是通过所有if语句进行验证,并且只有在所有if语句都没有返回false时才返回true.

提前致谢!

JLR*_*she 5

首先,您当前的方法是如此之长,因为您没有充分利用布尔逻辑.它可以简化为:

private static bool CompareFilter(UserProfile profile, FilterViewModel filter)
{
    if (filter.FirstName != null && filter.FirstName != profile.FirstName)
    {
        return false;
    }

    if (filter.TownId != null && filter.TownId != profile.TownId)
    {
        return false;
    }

    // true if at least one of the filter interests match
    if (filter.InterestsIds != null &&
        !profile.Interests.Any(i => filter.InterestsIds.Contains(i.Id)))
    {
        return false;
    }
    ...

    return true;
}
Run Code Online (Sandbox Code Playgroud)

您可以通过反转所有逻辑1将其转换为一个巨大的笨重表达式:

private static bool CompareFilter(UserProfile profile, FilterViewModel filter)
{
    return (filter.FirstName == null || filter.FirstName == profile.FirstName) &&

           (filter.TownId == null || filter.TownId == profile.TownId) &&

           (filter.InterestsIds == null ||
            profile.Interests.Any(i => filter.Interests.Contains(i.Id)));

    // etc. etc.
}
Run Code Online (Sandbox Code Playgroud)

一旦你有这个,将它变成一个lambda并获得你的Expression<T>:是一块蛋糕:

private static Expression<Func<UserProfile, bool>> CompareFilter(FilterViewModel f)
{
    return profile => 
           (filter.FirstName == null || filter.FirstName == profile.FirstName) &&

           (filter.TownId == null || filter.TownId == profile.TownId) &&

           (filter.InterestsIds == null ||
            profile.Interests.Any(i => filter.Interests.Contains(i.Id)));
}
Run Code Online (Sandbox Code Playgroud)
  1. 从技术上讲,你可以||将第一种方法中的所有条件放在一起并!( )对其进行大量改进:return !( (...) || (...) || (...));但是反转一切并加入条件&&要好得多.