我遇到了Delegate和OrderBy扩展方法的问题。 谁能告诉我为什么?提前致谢。 以下是整个代码:
namespace StudyDemo
{
public class MyDelegate
{
public delegate TResult DelegateOrder<in T, out TResult>(T arg);
}
public class Product
{
public string Name { get; private set; }
public decimal? Price { get; set; }
public Product(string name, decimal price)
{
Name = name;
Price = price;
}
/* private parameterless constructor for the sake of the new property-based initialization. */
Product() { }
public static List<Product> GetSampleProducts()
{
return new List<Product>
{
new Product { Name="West Side Story", Price=9.99m },
new Product { Name="Assassins", Price=14.99m },
new Product { Name="Frogs", Price=13.99m },
new Product { Name="Sweeney Todd", Price=10.99m }
};
}
public override string ToString()
{
return string.Format("{0}: {1}", Name, Price);
}
}
public partial class FrmMain : Form
{
public FrmMain()
{
InitializeComponent();
}
public string myOrder(Product p)
{
return p.Name;
}
private void button2_Click(object sender, EventArgs e)
{
List<Product> products = Product.GetSampleProducts();
Func<Product, string> orderDelegate2 = myOrder;
foreach (Product product in products.OrderBy(orderDelegate2))
{
/* Do something */
}
MyDelegate.DelegateOrder<Product, string> myOrder2 = myOrder;
foreach (Product product in products.OrderBy(myOrder2)) /* not functioning, why? */
{
/* Do something */
}
}
}
}
下面的注意: DelegateOrder 委托和Func委托是相同的。 我只是将 Func 委托复制到 DelegateOrder 委托。
在上面的代码示例中,行foreach (Product product in products.OrderBy(myOrder2))
不起作用,有人可以告诉我为什么吗?
编译代码时出现错误:
The type arguments for method 'System.Linq.Enumerable.OrderBy<TSource,TKey>(System.Collections.Generic.IEnumerable<TSource>, System.Func<TSource,TKey>)' cannot be inferred from the usage. Try specifying the type arguments explicitly.
答案 0 :(得分:2)
OrderBy 需要Type Func的委托。您的委托不属于Func类型,这就是为什么它在抱怨。即使它们的签名相同,Func和DelegateOrder也不相同。委托声明定义了一个派生自System.Delegate类的类。
答案 1 :(得分:2)
编译器无法将自定义委托类型DelegateOrder转换为System.Func(这是IEnumerable.OrderBy所期望的参数)。
尽管两者基本上具有相同的签名。首选使用System.Func是因为它提供了具有相同签名的委托之间的互操作。
如果我是你,我只会使用内联匿名函数来处理排序:
foreach(Product product in products.OrderBy((Product source)=>source.Name))
{
// Do something...
}
有趣的是 - 对于奖励积分 - 如果您确实想要使用委托对象,则以下方法可行:
foreach(Product product in products.OrderBy((x)=>myOrder2(x)))
{
// Do something...
}