我目前正在处理使用dynamic-linq的代码,使用$('a[title="' + $title '"]').css("color", "red");
时遇到问题,其中列表实际上包含List<BaseClass>
类的列表。
当我执行以下代码时,我得到Person
:
ParseException
和例外:
请参阅下面的var list = new List<BaseClass>();
list.Add(new Person
{
FirstName = "Joe",
Surname = "Bloggs"
});
list.Where("FirstName == @0", "Joe");
:
BaseClass
public class BaseClass
{
public int Id { get; set; }
}
类:
Person
我可以通过实施以下代码克服错误:
public class Person : BaseClass
{
public string FirstName { get; set; }
public string Surname { get; set; }
}
请参阅以下var list = new List<BaseClass>();
list.Add(new Person
{
FirstName = "Joe",
Surname = "Bloggs"
});
var newList = CreateListOfCorrectType<BaseClass>(list);
newList.Where("FirstName == @0", "Joe");
方法:
CreateListOfCorrectType<T>
我的问题是否使用private IList CreateListOfCorrectType<T>(
List<T> list)
{
if (list.Count == 0)
{
return list;
}
var typeInfo = list.FirstOrDefault().GetType();
var correctListType = typeof(List<>).MakeGenericType(typeInfo.UnderlyingSystemType);
var listOfCorrectType = (Activator.CreateInstance(correctListType)) as IList;
list.ForEach(x => listOfCorrectType.Add(x));
return listOfCorrectType;
}
是克服问题的最佳方式?如果没有,我有什么选择让CreateListOfCorrectType
得到正确的类型。
我希望将其与现有代码一起使用,并且无法更改现有的List<BaseClass>
类型。并且List<>
方法不了解CreateListOfCorrectType
类。
请注意,类名和变量仅用于演示目的。
更新
以下乐观主义者的回答让我找到了解决问题的方法,请参阅下面使用的扩展方法:
Person
public static IList ToDerivedListType(this IList list)
{
if (list == null || list.Count == 0)
{
return list;
}
var type = list.Cast<object>().FirstOrDefault().GetType();
var castedList = typeof(Enumerable).GetMethod("Cast", System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Public)
.MakeGenericMethod(type)
.Invoke(null, new[] { list });
return typeof(Enumerable).GetMethod("ToList", System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Public)
.MakeGenericMethod(type)
.Invoke(null, new[] { castedList }) as IList;
}
和System.Linq.Enumerable.Cast
是关键。
答案 0 :(得分:2)
如何使用OfType linq方法:
list.OfType<Person>().Where("FirstName == @0", "Joe");
请参阅https://msdn.microsoft.com/en-us/library/vstudio/bb360913(v=vs.100).aspx
答案 1 :(得分:0)
根据实际使用情况,可以改进一些事项:
CreateListOfCorrectType
函数将所有元素复制到一个新集合中,如果只从返回的集合中取出一个子集,则会导致不必要的费用。IEnumerable
一起使用。 System.Linq.Enumerable.Cast
和MakeGenericMethod
来实现这一目标:
static public class Extension
{
static public IEnumerable CastDynamic(this IEnumerable Source, Type Type)
{
return
(IEnumerable)
typeof(Enumerable)
.GetMethod("Cast", System.Reflection.BindingFlags.Static | System.Reflection.BindingFlags.Public)
.MakeGenericMethod(Type)
.Invoke(null, new[] { Source });
}
static public IEnumerable CastToFirstType(this IEnumerable Source)
{
if (0 == Source.Take(1).Count())
{
return Source;
}
return CastDynamic(Source, Source.Cast<object>().FirstOrDefault().GetType());
}
static public IEnumerable WhereCastToFirstType(this IEnumerable Source, string Predicate, params object[] values)
{
return Source.CastToFirstType().Where(Predicate, values);
}
}
如果尝试模仿您在抛出的异常方面显示的功能。有一点不同,因为在映射函数返回后完成了转换。