繁体   English   中英

如何在C#中传递多个函数作为约束参数?

[英]How do you pass multiple functions as constrainment parameters in C#?

对于我要学习的东西,这可能是一个措辞不佳的问题,因此我将解释我要做什么。 我使用以下表达式创建以下列表:

var showIndexes = from item in lItems
                               where WildcardString.IsMatch(item.RecordId.ToString(), filter) ||
                                     WildcardString.IsMatch(item.Tokens.ToString(), filter) ||
                                     WildcardString.IsMatch(string.Format("{0}:{1}", item.OwnerID.SystemName, item.OwnerID.Port.ToString()), filter) ||
                                     WildcardString.IsMatch(item.ChildID.UserName, filter) ||
                                     WildcardString.IsMatch(item.TypeOfLicense.ToString(), filter) ||
                                     WildcardString.IsMatch(item.ExpiryTime.DateTime.ToLocalTime().ToString(), filter)
                               select item.RecordId.ToString();

我想将此表达式放入函数中,并将在“ where”中使用的约束作为单个参数传递。 我该如何实现? 在使用文件属性时(当您选择不同的属性枚举时),我已经看到了使用按位OR的类似功能,因此,我相信应该可以编写自己的函数,该函数将一组委托作为“ where”规则。

如果相关,则WildcardString.IsMatch(string,string)是一个布尔函数。 另外,我有三个不同的函数执行完全相同的操作,但在不同的列表上,这就是为什么我想学习如何将其简化为一个函数,并仅将列表和选择规则传入。

只需定义一个谓词:一个接受item并返回布尔值的函数。

假设该item属于Record类型,并且该filter在范围内:

Func<Record, bool> predicate = r =>
    WildCardString.IsMatch(r.RecordId.ToString(), filter) ||
    WildCardString.IsMatch(...);

然后,您可以将predicate视为一等值(将其存储,将其作为参数传递,等等)并使用过滤任何IEnumerable<Record>

var filtered = enumerable.Where(predicate);

好吧,只需将where部分重构为函数即可:

public bool MyIsMatch(MyType item, String filter)
{
    return
    WildcardString.IsMatch(item.RecordId.ToString(), filter) ||
    WildcardString.IsMatch(item.Tokens.ToString(), filter) ||
    WildcardString.IsMatch(string.Format("{0}:{1}", item.OwnerID.SystemName, item.OwnerID.Port.ToString()), filter) ||
    WildcardString.IsMatch(item.ChildID.UserName, filter) ||
    WildcardString.IsMatch(item.TypeOfLicense.ToString(), filter) ||
    WildcardString.IsMatch(item.ExpiryTime.DateTime.ToLocalTime().ToString(), filter);
}

然后调用它:

var showIndexes = from item in lItems where MyIsMatch(item, filter) select item.ToString();

您可以创建一个Is.Match版本,该版本采用有效值列表

public static bool IsMatch(IEnumerable<object> values, filter) {
    return values.All(v => IsMatch(v.ToString(),filter))
}

在您的情况下,您将像这样使用它

var values = new object[]{
                    item.RecordId,
                    item.Tokens,
                    string.Format("{0}:{1}", item.OwnerID.SystemName, item.OwnerID.Port),
                    item.ChildID.UserName
                    item.TypeOfLicense
                    item.ExpiryTime.DateTime};

var showIndexes = from item in lItems
                  where WildcardString.IsMatch(values,filter)
                           select item.RecordId.ToString();

我选择使用IEnumerable<object>而不是IEnumerable<string>从每个项目中删除.ToString() ,但这确实要花很多钱,因为您将要装箱和拆箱任何ValueTyped值。 如果它位于确定的性能关键路径上,则应改用IEnumerable<string>

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM