使用float + Lambda表达式C#

时间:2015-01-22 14:40:46

标签: c# lambda

var distances = new Dictionary<char, float>();
var nodes = new List<char>();

我有这条线来找到最小的距离

nodes.Sort((x, y) => distances[x] - distances[y]);

当我使用int时效果很好,但当我使用float时,我收到了一条消息

  

无法将lambda表达式转换为type   'System.Collections.Generic.IComparer',因为它不是   委托类型

你有什么想法吗?

3 个答案:

答案 0 :(得分:10)

首先,当值为整数时,原始程序是一个糟糕的编程习惯。它适用于字符,但我会避免这种糟糕的编程习惯。

传递给sort函数的委托必须具有许多属性;特别是如果x小于y则必须返回负int,如果x大于y则返回正int,如果x大于y则返回0。您的原始lambda不会对整数值执行此操作。 (看看你是否可以找到两个整数x和y,使得x小于y,但x - y是正的。)

代表还必须强加总订单。按总顺序:

  • 传递性必须成立。如果A == B且B == C则A必须等于C. B和B&lt; C然后A必须小于C.依此类推。
  • 必须是反对称的。也就是说,如果A&lt; B然后B> A等等。

减法在整数中不符合这些条件。正确的代码是实际编写比较。

nodes.Sort((x, y) => x < y ? -1 : (x > y ? 1 : 0));

然后对于字符和浮点数很有效,如果没有NaNs 。如果您有NaN,那么您需要做额外的工作来强加总订单。

我还要指出,对字符的这种序数比较通常不是你想要的比较。当然,这会正确地指出e小于z,但简单的序数比较也表示z小于é,这可能不是您想要的。字符排序取决于文化;你确定要按Unicode委员会刚刚强加的命令订购吗?

有关此主题的更多信息,请参阅我的系列文章;它从这里开始:

http://ericlippert.com/2011/01/20/bad-comparisons-part-one/

答案 1 :(得分:8)

你无法将你的lambda表达式转换为Comparison<char>(这是你想要的),因为它返回float - 你实际上有Func<char, char, float>,而{ {1}}更接近Comparison<char>

最简单的方法是使用float.CompareTo

Func<char, char, int>

或者,如果您不需要就地排序,可以使用LINQ:

nodes.Sort((x, y) => distances[x].CompareTo(distances[y]));

答案 2 :(得分:0)

重新制定lambda表达式,如下所示。

nodes.Sort((x, y) =>
  {
    float Result = distances[x] - distances[y];
    if ( Result > 0.0f )
      return 1;
    else if ( Result < 0.0f )
      return -1;
    else
      return 0;
  });