繁体   English   中英

C#在lambda中过滤动态属性名称

[英]c# filtering dynamic property names in lambda

我遇到名称不正确的属性的麻烦:

public class Word
{
     public string Alt01 { get;set; }
     public string Alt02 { get;set; }
     public string Alt03 { get;set; }
     public string Alt04 { get;set; }
     public string Alt05 { get;set; }
}

这可能应该是List<string>类型的一个属性。 但是其他人想出了这个主意,目前我无法更改结构。

我有一个返回很多Word对象的方法。 我想做的是过滤掉一个或多个AltXX属性中具有匹配字符串的每个Word实例。

这是我到目前为止的内容:

foreach(var word in resultList) //<-- List<Word> 
{
    var alt01 = word.GetType().GetProperty("alt01").GetValue(word, null);
}

如果我稍微扩展一下,它将作为我的过滤器。 但是我的问题是:使用lambda表达式可解决吗?

因此,我们将从一个简单的辅助方法(可能是扩展方法)开始,因为我们有很多属性而不是列表:

public static IEnumerable<string> getAlts(Word word)
{
    yield return word.Alt01;
    yield return word.Alt02;
    yield return word.Alt03;
    yield return word.Alt04;
    yield return word.Alt05;
}

如果可以具有N个属性而不是五个属性,则可以将其重构为使用反射。 如果确实如此,那么上帝会帮助您。 打招呼让您处于该位置的开发人员,而不仅仅是对我使用一次List

这样,还算不错:

List<Word> words = new List<Word>();

string searchText = "foo";
var query = words.Where(word => getAlts(word).Any(alt => alt.Contains(searchText)));

我想要单词“ Where Any一个alt都包含搜索文本”。 它读起来就像它在工作一样。

您可以通过创建助手类以向后兼容的方式将类转换为List<string>

例如

class QueryFriendlyWordList
{
    public List<string> Words;

    public QueryFriendlyWordList(Word words)
    {
            Words = new List<string> {words.P1,words.P2, words.P3, words.P4};
    }
}

用法

        Word words = new Word {P1 = "abcd", P2 = "abc", P3 = "def", P4 = "qwre"};
        var queryable = new QueryFriendlyWordList(words);
        var result = queryable.Words.Where(w => w.Contains("a"));

静态甚至更容易:

static class WordConverter
{       
    public static List<string> Convert(Word words)
    {
            return new List<string> {words.P1,words.P2, words.P3, words.P4};
    }
}

最好的办法是在应用程序启动时使用反射一次来构建表达式树,将其编译为lambda,然后保存这些lambda以供重新使用。

反射缓慢的代价仅需支付一次,然后此价格就如同您从一开始就对其进行编译一样快。

但是,编写这些表达式树很麻烦,因此,如果您不关心性能(速度很慢,但不那么慢),那么您的反射应该很好。

暂无
暂无

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

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