2010-11-12 63 views
7

问候!如何在LINQ中做一个'搜索最佳'功能?

我正在寻找一种方法来搜索最符合我的标准的对象的集合。由于我必须经常这样做,所以我一直在研究如何使用LINQ执行查询,但找不到一个简单的方法来做到这一点,不会浪费时间。

的功能的实现是:

collection.OrderByDescending(f => FitFunction(f)).First()

但这似乎不必要进行排序。我真的只需要线性扫描。 Min LINQ函数返回最佳拟合,而不是产生最佳拟合的对象,因此看起来不太有用。

为了清楚起见,非LINQ代码,我会写的传统(和已经这样做了这么多次):

T best; 
float bestFit = something very low; 

foreach (T ob in collection) 
{ 
    float fit = FitFunction(ob); 
    if (fit > bestFit) 
    { 
    bestFit = fit; 
    best = ob; 
    } 
} 
return best; 

而且我觉得我可能只是做我自己的扩展方法来做到这一点;但在我看来,LINQ中已经有一种方法可以做到这一点。

谢谢!

+0

而不是将'ob'对象传递给'FitFunction',你不能将'FitFunction'的结果作为'ob'的一个属性,因此启用'collection.Min(t => t.FitValue )'? – vlad 2010-11-12 20:45:28

+0

@vlad:不幸的是,Enumerable.Min()方法返回最小值投影...而不是对象实例't',这是OP正在寻找的东西。这就是MoreLINQ引入MinBy和MaxBy操作符的原因。 – LBushkin 2010-11-12 20:52:02

+0

困难在于Min函数会产生't.FitValue',而不是't'。除此之外,这必然将FitValue绑定到对象,我将避免保持代码松散耦合。 – 2010-11-12 20:52:37

回答

7

这主要是基于与附加约束N个总是等于1不幸的是,谓词TOPN问题,没有内置的LINQ运算符执行TOPN()操作...但正如你所指出的那样,自己写一个并不难。

MoreLINQ库有一个MaxBy()运算符的实现,它允许你指定一个谓词 - 也可以工作。

+0

Reactive Extensions(Rx)附带的'System.Interactive'程序集也有'MaxBy'的实现。 http://msdn.microsoft.com/en-us/devlabs/ee794896.aspx – bdukes 2010-11-12 21:31:07