英文:
Usage of Mapping annotation with "this" value (@Mapping("this")) on a field while using github's dozermapper
问题
我前来观看一个类,其中的字段添加了 @Mapping("this")
,以及一个测试方法,在该方法中检查调用了 github 的 DozerMapper 中的映射方法后,源对象和结果对象不相等。
由于我无法贴出实际代码,我在下面添加了一个类似的类和测试方法。(我使用了 lombok 的 @Data
、@NoArgsConstructor
和 @AllArgsConstructor
注解,以避免显式地指定 getter、setter 和构造函数。)
@Data
@NoArgsConstructor
@AllArgsConstructor
public class TestObj
{
private int id;
@Mapping("this")
private String name;
}
测试方法:
@Test
public void testMapper() {
TestObj testObj = new TestObj(1, "test");
TestObj testCopy = DozerBeanMapperBuilder.create().build().map(testObj, TestObj.class);
Assert.assertNotEquals(testObj, testCopy);
}
测试通过了。如果我移除 @Mapping("this")
,那么同样的测试将会失败。那么 @Mapping("this")
是如何改变映射过程,使得映射后的对象和源对象不同呢?
英文:
I came to see a class in which @Mapping("this")
was added to a field and a test method which checked that the source object and resulting object are not equal after invoking the map method in github's dozermapper.
As I cannot post the actual code, I am adding a similar class and test method below. (I have used lombok's @Data
, @NoArgsConstructor
and @AllArgsConstructor
annotations to avoid explicitly specifying the getter, setter and constructors.)
@Data
@NoArgsConstructor
@AllArgsConstructor
public class TestObj
{
private int id;
@Mapping("this")
private String name;
}
Test method :
@Test
public void testMapper() {
TestObj testObj = new TestObj(1, "test");
TestObj testCopy = DozerBeanMapperBuilder.create().build().map(testObj, TestObj.class);
Assert.assertNotEquals(testObj, testCopy);
}
The test was passed. If I remove @Mapping("this")
, then the same test would fail. So how has the @Mapping("this") changed the mapping procedure so that the mapped object and source object are different?
答案1
得分: 1
@Mapping
注解用于在源类和目标类之间的字段名称不同的情况下进行映射。
例如,下面的代码将会将源类对象中的fullName
字段映射到目标类对象中的name
字段。当你需要映射两个不同类的对象时,这是特别有用的。
@Mapping("fullName")
private int name;
因此,如果我们在name
字段上使用@Mapping("this")
,那么它会将源类本身映射到name
字段。在这种情况下,由于name
是String
类型,源类的toString()
表示将被映射到name
字段。如果我们为name
字段使用了不兼容的类型,比如int
,则会引发异常。如果源对象的类型是Object
或与源对象相同的类型,那么源对象本身将存储在name
字段中。
因此,在给定的问题中,源类和目标类是相同的,但是@Mapping("this")
被应用于name
字段。因此,如果源对象类似于TestObj(id=1,name="test")
,那么映射后的对象将会是TestObj(id=1,name="TestObj(id=1,name="test"))
,即name
字段将会是源对象的toString()
结果。因此,这两个对象将不相等。
如果移除了@Mapping("this")
,测试将会失败,因为@Data
注解会添加一个equals()
方法,该方法检查各个字段的相等性,因此源对象和映射后的对象将会相等。
英文:
@Mapping
annotation is used when the field names in the source and destination class differ.
For example, The below code would map the fullName
field in the source class object to the name
field in the destination class object. This is particularly useful when you are mapping objects of two different classes.
@Mapping("fullName")
private int name;
So if we use @Mapping("this")
on the name
field, then it would map the source class itself to the name
field. Here since the name
is of type String
, the toString()
representation of the source class would be mapped to the name
field. An exception would be thrown if we have used an incompatible type like int
for the name
field. The source object itself would have been stored in the name
field, if it was of Object
type or the same type as the source object.
So, in the given question, the source and the destination class are the same, but the @Mapping("this")
is provided to the name
field. So if the source object was like TestObj(id=1,name="test")
, then the mapped object would be TestObj(id=1,name="TestObj(id=1,name="test")"
, i.e the name
field would be the toString()
of the source object. Hence both the objects would not be equal.
If the @Mapping("this")
is removed, the test would fail because, the @Data
annotation adds an equals()
method which checks the equality of individual fields and thus the source and mapped object would be equal.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论