如何转换列表List< ClassName>
本文关键字:List ClassName 列表 何转换 转换 | 更新日期: 2023-09-27 18:15:06
我使用泛型方法填充所有类型的下拉列表
下面的是我的代码。
实体类型如下
public class Role
{
public string Id { get; set; }
public string Name { get; set; }
}
public class DropDown
{
public string Id { get; set; }
public string Name { get; set; }
}
我能够在
成功地获取数据var data = DataFetcher.FetchData<T>();
private static void Main( string[] args )
{
List<DropDown> cities = BLL.GetDataList<City>();
List<DropDown> states = BLL.GetDataList<State>();
List<DropDown> roles = BLL.GetDataList<Role>();
}
public static class BLL
{
public static List<DropDown> GetDataList<T>() where T : class ,new()
{
var data = DataFetcher.FetchData<T>();
return data as List<DropDown>;
}
}
我知道这个强制转换data as List<DropDown>
会失败,这就是为什么它返回null回调用方法,
如何将泛型列表转换为已知类型列表?
您必须问自己:我想如何将T
转换为DropDown
?如果你不能回答这个问题,那么答案是:你不能。
我猜你的DropDown
类有一个object Value
属性,它持有下拉值,你希望将数据实体分配给该属性。
然后,您可以将数据实体列表投影到 DropDown
s,如下所示:
var data = DataFetcher.FetchData<T>();
return data.Select(d => new DropDown { Value = d }).ToList();
对于您的编辑:因此您至少有一种类型,即显示的Role
,具有Id
和Name
属性。但是类型T
不能保证这一点,所以您需要引入一个接口:
public interface INamedIdentifyableEntity
{
string Id { get; set; }
string Name { get; set; }
}
并将其应用于您的实体。然后将其作为泛型约束引入并执行映射:
return data.Select(d => new DropDown
{
Id = d.Id,
Name = d.Name,
}).ToList();
但是你不希望这样,因为这里你将这两个属性绑定到下拉列表。明天你会想要一个Code
而不是Id
和Text
而不是Name
的实体,所以你必须添加更多的接口,更多的重载,等等。
相反,您可能希望使用反射,可以在调用中指定成员名:
List<DropDown> cities = BLL.GetDataList<City>(valueMember: c => c.CityCode, displayMember: c => c.FullCityname);
并使用这些成员表达式查找data
的值,并将这些值填充到DropDown
中。
然而,你在重新发明轮子。完全省略DropDown
类,并将下拉生成留给前端,在本例中为MVC:
var cities = DataFetcher.FetchData<City>();
var selectList = new SelectList(cities.Select(c => new SelectListItem
{
Selected = (c.Id == selectedCityId),
Text = c.FullCityName,
Value = c.CityCode,
});
或:
var selectList = new SelectList(cities, "CityCode" , "FullCityName", selectedCityId);
一个解决方案是使用AutoMapper。
首先像这样在你的模型之间创建一个映射:
AutoMapper.Mapper.CreateMap<Role, DropDown>();
如果需要,对City
和State
类做同样的事情。
然后你可以使用AutpMapper将你的对象转换为DropDown
,像这样:
public static List<DropDown> GetDataList<T>() where T : class ,new()
{
var data = DataFetcher.FetchData<T>();
return data.Select(x => AutoMapper.Mapper.Map<DropDown>(x)).ToList();
}
如果我正确理解了这个问题,您可以像下面这样使用Linq。
return data.Cast<DropDown>().ToList();