一位同事要我写一个衬纸来代替以下方法:
public static bool IsResourceAvailableToUser(IEnumerable<string> resourceRoles, IEnumerable<string> userRoles) { foreach (var userRole in userRoles) foreach (var resourceRole in resourceRoles) if (resourceRole == userRole) return true; return false; }
Resharper和我想出了这个:
public static bool IsResourceAvailableToUser(IEnumerable<string> resourceRoles, IEnumerable<string> userRoles) { return userRoles.Where(resourceRoles.Contains).Count() > 0; }
有没有更好的办法?
您可以编写可处理许多情况的通用扩展方法。该功能本身的实质是一行。
/// <summary> /// Compares both lists to see if any item in the enumerable /// equals any item in the other enumerable. /// </summary> public static bool AnyItem<T>(this IEnumerable<T> source, IEnumerable<T> other, IEqualityComparer<T> comparer = null) { return (comparer == null ? source.Intersect(other) : source.Intersect(other, comparer)).Any(); }
public static bool AnyItem<T>(this IEnumerable<T> source, IEnumerable<T> other) { return source.Any(s => other.Any(o => EqualityComparer<T>.Default.Equals(s, o))); }
我 认为 这也比当前答案更有效(不是)。我将不得不检查获取EqualityComparer是否昂贵,但我对此表示怀疑。
您也可以扩展此函数以接受一个表达式,该表达式将评估要比较包含对象的可枚举的哪些属性。
public static bool AnyItem<T, TResult>( this IEnumerable<T> source, IEnumerable<T> other, Expression<Func<T, TResult>> compareProperty = null) { if (compareProperty == null) { return source.Any(s => other.Any(o => EqualityComparer<T>.Default.Equals(s, o))); } return source.Any(s => other.Any(o => EqualityComparer<TResult>.Default.Equals( s.GetPropertyValue(compareProperty), o.GetPropertyValue(compareProperty)))); } public static TValue GetPropertyValue<TTarget, TValue>( this TTarget target, Expression<Func<TTarget, TValue>> memberLamda) { var memberSelectorExpression = memberLamda.Body as MemberExpression; var property = memberSelectorExpression?.Member as PropertyInfo; return (TValue)property?.GetValue(target); }