将对象复制到对象(使用Automapper?)

时间:2011-04-19 08:24:37

标签: c# automapper

我有一个班级:

public class Person {
    public string FirstName { get; set; }
    public string LastName { get; set; }
}

我有两个Person实例(person1和person2)。我想将person2的内容复制到person1。我想在一个指令中创建此副本,并且按属性属性:

person1.LastName = person2.LastName;

在doc中,我看到将对象复制到另一个对象但类型不同。如何在类型相同时复制对象?

5 个答案:

答案 0 :(得分:71)

据我所知,OP不想将 person2 克隆到 Person 的新实例中,而是要求如何复制的内容person2 进入 Person 已存在的实例 person1 )。 AutoMapper的Mapper.Map方法有一个重载,可以为您完成此任务:

Mapper.CreateMap<Person, Person>();
Mapper.Map<Person, Person>(person2, person1);
//This copies member content from person2 into the _existing_ person1 instance.

注1: @ alexl的答案会创建实例。如果您对 person1 指向的实例有其他引用,则如果将 person1 变量重定向到新实例,则这些引用将无法获得(可能)所需的数据更新。 / p>

注2:您需要注意(递归)复制深度取决于AutoMapper在映射时知道的映射!
如果 Person 类的成员说的是 Brain 类,并且您在复制数据Mapper.CreateMap<Brain, Brain>();调用之前已经完成了Mapper.Map<Person, Person>(person2, person1);,那么< em> person1 将保留其当前的 Brain 实例,但此 Brain 将收到 person2 Brain的成员值实例。那就是你有一个深层拷贝 但是如果AutoMapper在复制之前没有Brain-Brain映射,那么 person1 Brain 成员将引用相同的 Brain 实例作为一个 person2 引用。那就是你会得到一个浅拷贝 这会递归地应用于所有成员,因此您最好确保AutoMapper具有要进行深层复制的成员类的映射,并且没有要进行浅层复制的成员类的映射。

使用AutoMapper的另一种方法是使用an approach using reflection。 (请注意,链接中的代码执行复制!)

“支持填充现有对象,而不是AutoMapper创建目标对象本身”是added in AutoMapper version 0.2

答案 1 :(得分:25)

既然你问With Automapper?我建议你不要使用AutoMapper吗?

而是在Clone方法中使用MemberwiseClone(),例如

public class Person
{
    public string FirstName { get; set; }
    public string LastName { get; set; }

    public Person Clone()
    {
        return (Person) MemberwiseClone();
    }
}

<强>更新

重要的是要注意这并没有实现原始海报希望将person1 复制到 person2

然而,如果您只需要制作对象的副本(克隆),则优先使用MemberwiseClone()(以及@Jimmy Bogard指出)。

例如,如果您这样做:

//I need a copy of person1 please! I'll make a new person object 
//and automapper everything into it!
var person2 = new Person2();
Mapper.Map<Person, Person>(person1, person2)

那么你真的应该/可以使用

//oh wait, i can just use this!
var person2 = person1.Clone()

答案 2 :(得分:17)

Mapper.CreateMap<Person, Person>();

// Perform mapping

var person1 = Mapper.Map<Person, Person>(person2);

希望这有帮助。

答案 3 :(得分:2)

为什么要为此使用Automapper?一个简单的克隆就能为你完成这项工作。

在此处阅读更多内容:Deep cloning objects

答案 4 :(得分:0)

在当前版本的AutoMapper中,不能使用静态的AutoMapper.Mapper.Map方法。而是像这样初始化一个新的映射器:

var config = new MapperConfiguration(cfg =>
{
    cfg.CreateMap<Person, Person>();
});

var mapper = new Mapper(config);

var clone = mapper.Map<Person>(person);

通常,您希望在Startup.cs文件中注册映射器以进行依赖项注入,并将其注入您的业务类中:

public void ConfigureServices(IServiceCollection services)
{
    var config = new MapperConfiguration(cfg =>
    {
        cfg.CreateMap<Person, Person>();
    });

    var mapper = new Mapper(config);

    services.AddSingleton(mapper);

    // ...
}

重要提示不要在您的实体类中创建或插入映射器!

当然,在简单的情况下,您应该首选使用MemberwiseClone()