我可以成功从 IDataReader 映射到对象列表,但是当我想获取一个 DataRow 时,它似乎无法按预期工作。
我在这里错过了一些简单的东西吗?
[TestFixture]
public class AutomapperTest
{
[Test]
public void TestMethod1()
{
DataTable dt = new DataTable("contact");
dt.Columns.Add("FirstName");
dt.Columns.Add("LastName");
dt.Columns.Add("Line1");
dt.Columns.Add("Line2");
dt.Columns.Add("Line3");
dt.Columns.Add("Suburb");
dt.Columns.Add("State");
dt.Columns.Add("Postcode");
DataRow row = dt.NewRow();
row.ItemArray = new [] { "Little", "Johnny",
"1 Random Place", "", "",
"Windsor", "Qld", "4030" };
var dest = Mapper.DynamicMap<myObject>(row);
Assert.AreEqual(row["FirstName"], "Little");
Assert.IsNotNull(dest);
Assert.AreEqual(dest.FirstName, "Little");
}
}
目的地类型:
public class myObject
{
public string FirstName { get; set; }
public string LastName { get; set; }
public string Line1 { get; set; }
public string Line2 { get; set; }
public string Line3 { get; set; }
public string Suburb { get; set; }
public string State { get; set; }
public string Postcode { get; set; }
}
您必须实现自己的自定义值解析器
https://github.com/AutoMapper/AutoMapper/wiki/Custom-value-resolvers
更新
public class CustomResolver : IValueResolver
{
public ResolutionResult Resolve(ResolutionResult source)
{
return source.New( Convert.ChangeType((source.Context.SourceValue as DataRow)[source.Context.MemberName], source.Context.DestinationType));
}
}
这是如何使用它
Mapper.CreateMap<DataRow,myObject>().ForAllMembers(m=>m.ResolveUsing<CustomResolver>());
var dest = Mapper.Map<myObject>(row);
我建议使用 Dapper。这样,来自数据库的数据将是强类型的或动态的,并且 Automapper 应该能够找出映射。
我相信 Dapper 可以通过 ODBC 读取 CSV 文件。但对于 CSV,我建议使用 LinqToCSV Nuget 包。
另一种方法是使用 ITypeConverter:
创建自定义 TypeConverter 类:
public class DataRowConverter : ITypeConverter<DataRow, Object>
{
Object ITypeConverter<DataRow, Object>.Convert(DataRow source, Object destination, ResolutionContext context)
{
foreach (DataColumn col in source.Table.Columns)
{
var value = source[col].ToString();
PropertyInfo prop = destination.GetType().GetProperty(
col.ColumnName,
BindingFlags.Instance | BindingFlags.Public | BindingFlags.SetProperty | BindingFlags.IgnoreCase);
if (prop != null && prop.CanWrite)
{
prop.SetValue(destination, value, null);
}
}
return destination;
}
}
然后设置配置:
cfg.CreateMap<DataRow, Object>().ConvertUsing<DataRowConverter>();
最后,照常使用映射器:
var results = new List<SearchResult>();
foreach (DataRow row in Res.data.Tables[0].Rows)
{
var obj = mapper.Map<SearchResult>(row);
results.Add(obj);
}
它应该与最新版本的 AutoMapper 一起使用。