3 public int Id { get; set; }
4 public string Name { get; set; }
5 public int Age { get; set; }
6 }
8 public class UserDto
9 {
10 public string Name { get; set; }
11 public int Age { get; set; }
12 }
将User转换成UserDto也和简单
1 Mapper.Initialize(x => x.CreateMap<User, UserDto>());
2 User user = new User()
3 {
4 Id = 1,
5 Name = "caoyc",
6 Age = 20
7 };
8 var dto = Mapper.Map<UserDto>(user);
这是一种最简单的使用,AutoMapper会更加字段名称去自动对于,忽略大小写。
二、如果属性名称不同
将UserDto的Name属性改成Name2
1 Mapper.Initialize(x =>
2 x.CreateMap<User, UserDto>()
3 .ForMember(d =>d.Name2, opt => {
4 opt.MapFrom(s => s.Name);
5 })
6 );
8 User user = new User()
9 {
10 Id = 1,
11 Name = "caoyc",
12 Age = 20
13 };
15 var dto = Mapper.Map<UserDto>(user);
三、使用Profile配置
自定义一个UserProfile类继承Profile,并重写Configure方法
1 public class UserProfile : Profile
2 {
3 protected override void Configure()
4 {
5 CreateMap<User, UserDto>()
6 .ForMember(d => d.Name2, opt =>
7 {
8 opt.MapFrom(s => s.Name);
9 });
10 }
11 }
使用时就这样
1 Mapper.Initialize(x => x.AddProfile<UserProfile>());
3 User user = new User()
4 {
5 Id = 1,
6 Name = "caoyc",
7 Age = 20
8 };
10 var dto = Mapper.Map<UserDto>(user);
四、空值替换NullSubstitute
空值替换允许我们将Source对象中的空值在转换为Destination的值的时候,使用指定的值来替换空值。
1 public class UserProfile : Profile
2 {
3 protected override void Configure()
4 {
5 CreateMap<User, UserDto>()
6 .ForMember(d => d.Name2, opt => opt.MapFrom(s => s.Name))
7 .ForMember(d => d.Name2, opt => opt.NullSubstitute("值为空"));
9 }
10 }
1 Mapper.Initialize(x => x.AddProfile<UserProfile>());
3 User user = new User()
4 {
5 Id = 1,
6 Age = 20
7 };
9 var dto = Mapper.Map<UserDto>(user);
五、忽略属性Ignore
1 public class User
2 {
3 public int Id { get; set; }
4 public string Name { get; set; }
5 public int Age { get; set; }
6 }
8 public class UserDto
9 {
10 public string Name { get; set; }
11 public int Age { get; set; }
13 }
15 public class UserProfile : Profile
16 {
17 protected override void Configure()
18 {
19 CreateMap<User, UserDto>().ForMember("Name", opt => opt.Ignore());
20 }
21 }
1 Mapper.Initialize(x => x.AddProfile<UserProfile>());
3 User user = new User()
4 {
5 Id = 1,
6 Name="caoyc",
7 Age = 20
8 };
10 var dto = Mapper.Map<UserDto>(user);
六、预设值
如果目标属性多于源属性,可以进行预设值
1 public class User
2 {
3 public int Id { get; set; }
4 public string Name { get; set; }
5 public int Age { get; set; }
6 }
8 public class UserDto
9 {
10 public string Name { get; set; }
11 public int Age { get; set; }
12 public string Gender { get; set; }
14 }
16 public class UserProfile : Profile
17 {
18 protected override void Configure()
19 {
20 CreateMap<User, UserDto>();
21 }
22 }
1 Mapper.Initialize(x => x.AddProfile<UserProfile>());
3 User user = new User()
4 {
5 Id = 1,
6 Name="caoyc",
7 Age = 20
8 };
10 UserDto dto = new UserDto() {Gender = "男"};
11 Mapper.Map(user, dto);
七、类型转换ITypeConverter
如果数据中Gender存储的int类型,而DTO中Gender是String类型
1 public class User
2 {
3 public int Gender { get; set; }
4 }
6 public class UserDto
7 {
8 public string Gender { get; set; }
9 }
类型转换类,需要实现接口ITypeConverter
1 public class GenderTypeConvertert : ITypeConverter<int, string>
2 {
3 public string Convert(int source, string destination, ResolutionContext context)
4 {
5 switch (source)
6 {
7 case 0:
8 destination = "男";
9 break;
10 case 1:
11 destination = "女";
12 break;
13 default:
14 destination = "未知";
15 break;
16 }
17 return destination;
18 }
19 }
1 public class UserProfile : Profile
2 {
3 protected override void Configure()
4 {
5 CreateMap<User, UserDto>();
7 CreateMap<int, string>().ConvertUsing<GenderTypeConvertert>();
8 //也可以写这样
9 //CreateMap<int, string>().ConvertUsing(new GenderTypeConvertert());
10 }
11 }
1 Mapper.Initialize(x => x.AddProfile<UserProfile>());
3 User user0 = new User() { Gender = 0 };
4 User user1 = new User() { Gender = 1 };
5 User user2 = new User() { Gender = 2 };
6 var dto0= Mapper.Map<UserDto>(user0);
7 var dto1 = Mapper.Map<UserDto>(user1);
8 var dto2 = Mapper.Map<UserDto>(user2);
10 Console.WriteLine("dto0:{0}", dto0.Gender);
11 Console.WriteLine("dto1:{0}", dto1.Gender);
12 Console.WriteLine("dto2:{0}", dto2.Gender);
八、条件约束Condition
当满足条件时才进行映射字段,例如人类年龄,假设我们现在人类年龄范围为0-200岁(这只是假设),只有满足在这个条件才进行映射
DTO和Entity
1 public class User
2 {
3 public int Age { get; set; }
4 }
6 public class UserDto
7 {
8 public int Age { get; set; }
9 }
Profile
1 public class UserProfile : Profile
2 {
3 protected override void Configure()
4 {
5 CreateMap<User, UserDto>().ForMember(dest=>dest.Age,opt=>opt.Condition(src=>src.Age>=0 && src.Age<=200));
6 }
7 }
1 Mapper.Initialize(x => x.AddProfile<UserProfile>());
3 User user0 = new User() { Age = 1 };
4 User user1 = new User() { Age = 150 };
5 User user2 = new User() { Age = 201 };
6 var dto0= Mapper.Map<UserDto>(user0);
7 var dto1 = Mapper.Map<UserDto>(user1);
8 var dto2 = Mapper.Map<UserDto>(user2);
10 Console.WriteLine("dto0:{0}", dto0.Age);
11 Console.WriteLine("dto1:{0}", dto1.Age);
12 Console.WriteLine("dto2:{0}", dto2.Age);
近有遇到
两个
类
之间的
赋值
问题,
两个
类
的
属性
几乎都一样的,所以写了个通过反射获取
属性
的然后
赋值
的方法,把一个
类
的
属性
的值
赋值
给另一个
类
。
框架是.net 4.5
public static D Mapper<D>(S s)
D d = Activator.CreateInstance<D>();
var sType = s.GetType();
var dType = typeof(D);
foreach (PropertyInfo sP in sType.GetProperties())
foreach (PropertyInfo dP in
3 public int Id { get; set; }
4 public string Name { get; set; }
5 public int Age { get; set; }
6 ...
在我们日常的开发中,会遇到各种DTO或者是VO以及其他的划分,而这些统称为POJO,这些是基于当前业务而衍生出来的
类
,用来做数据的传输,因此我们都会经历一个必要的阶段,那就是实体
类
跟DTO或者是其他
类
型进行一个转换,在我以前接触的项目中发现很多代码是使用get/set来进行转换的,大量的这种冗余代码,看着头都大,比较好的一种方式是使用BeanUtil,但是这种方式也有缺陷,可能会要求变量名一致或者是数据
类
型一致,要是后期把某个字段的数据
类
型改了,可能会出现莫名其妙的问题!而mapstruct就是来解决上面所
var configuration = new MapperConfiguration(cfg => {
//cfg.CreateMap<Foo, Bar>();
cfg.AddProfile<
通常在一个应用程序中,我们开发人员会在
两个
不同的
类
型
对象
之间传输数据,通常我们会用DTOs(数据传输
对象
),View Models(视图模型),或者直接是一些从一个service或者Web API的一些请求或应答
对象
。一个常见的需要使用数据传输
对象
的情况是,我们想把属于一个
对象
的某些
属性
值
赋值
给另一个
对象
的某些
属性
值,但是问题是,这个
两个
对象
可能并不是完全
匹配
的,比如,两者之间的
属性
类
型,名...