如何将属性从一个 Java bean 复制到另一个?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/835416/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How to copy properties from one Java bean to another?
提问by paulgreg
I have a simple Java POJO that I would copy properties to another instance of same POJO class.
我有一个简单的 Java POJO,我会将属性复制到同一 POJO 类的另一个实例。
I know I can do that with BeanUtils.copyProperties() but I would like to avoid use of a third-party library.
我知道我可以用 BeanUtils.copyProperties() 做到这一点,但我想避免使用第三方库。
So, how to do that simply, the proper and safer way ?
那么,如何简单、正确且安全地做到这一点?
By the way, I'm using Java 6.
顺便说一下,我使用的是 Java 6。
采纳答案by Dónal
I guess if you look at the source code of BeanUtils, it will show you how to do this without actually using BeanUtils.
我想如果您查看 BeanUtils 的源代码,它将向您展示如何在不实际使用 BeanUtils 的情况下执行此操作。
If you simply want to create a copy of a POJO (not quite the same thing as copying the properties from one POJO to another), you could change the source bean to implement the clone() method and the Cloneable interface.
如果您只想创建 POJO 的副本(与将属性从一个 POJO 复制到另一个 POJO 不完全相同),您可以更改源 bean 以实现 clone() 方法和 Cloneable 接口。
回答by McDowell
Have a look at the JavaBeans API, in particular the Introspectorclass. You can use the BeanInfo metadata to getand setproperties. It is a good idea to read up on the JavaBeans specificationif you haven't already. It also helps to have a passing familiarity with the reflection API.
查看JavaBeans API,特别是Introspector类。您可以使用 BeanInfo 元数据来获取和设置属性。如果您还没有阅读JavaBeans 规范,这是一个好主意。熟悉反射 API也有帮助。
回答by MetroidFan2002
There isno simple way to do it. Introspector and the Java beans libraries are monolithic - BeanUtils is a simple wrapper around this and works well. Not having libraries just to not have libraries is a bad idea in general - there's a reason it's commons to begin with - common functionality that should exist with Java, but doesn't.
这里是没有简单的方法来做到这一点。Introspector 和 Java bean 库是整体式的 - BeanUtils 是一个简单的包装器,并且运行良好。没有库只是为了没有库一般来说是一个坏主意 - 它是公共的开始是有原因的 - Java 应该存在的公共功能,但没有。
回答by Efthymis
I had the same problem when developing an app for Google App Engine, where I couldn't use BeanUtils due to commons Logging restrictions. Anyway, I came up with this solution and worked just fine for me.
我在为 Google App Engine 开发应用程序时遇到了同样的问题,由于公共日志记录限制,我无法使用 BeanUtils。无论如何,我想出了这个解决方案并且对我来说效果很好。
public static void copyProperties(Object fromObj, Object toObj) {
Class<? extends Object> fromClass = fromObj.getClass();
Class<? extends Object> toClass = toObj.getClass();
try {
BeanInfo fromBean = Introspector.getBeanInfo(fromClass);
BeanInfo toBean = Introspector.getBeanInfo(toClass);
PropertyDescriptor[] toPd = toBean.getPropertyDescriptors();
List<PropertyDescriptor> fromPd = Arrays.asList(fromBean
.getPropertyDescriptors());
for (PropertyDescriptor propertyDescriptor : toPd) {
propertyDescriptor.getDisplayName();
PropertyDescriptor pd = fromPd.get(fromPd
.indexOf(propertyDescriptor));
if (pd.getDisplayName().equals(
propertyDescriptor.getDisplayName())
&& !pd.getDisplayName().equals("class")) {
if(propertyDescriptor.getWriteMethod() != null)
propertyDescriptor.getWriteMethod().invoke(toObj, pd.getReadMethod().invoke(fromObj, null));
}
}
} catch (IntrospectionException e) {
e.printStackTrace();
} catch (IllegalArgumentException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
}
}
Any enhancements or recomendations are really welcome.
任何改进或建议都非常受欢迎。
回答by ripper234
I ran into some problems with Introspector.getBeanInfo
not returning all the properties, so I ended up implementing a field copy instead of property copy.
我遇到了一些Introspector.getBeanInfo
没有返回所有属性的问题,所以我最终实现了一个字段副本而不是属性副本。
public static <T> void copyFields(T target, T source) throws Exception{
Class<?> clazz = source.getClass();
for (Field field : clazz.getFields()) {
Object value = field.get(source);
field.set(target, value);
}
}
回答by Gunnar
回答by Vijay Shegokar
Hey friends just use my created ReflectionUtil class for copy one bean values to another similar bean.
This class will also copy Collections object.
https://github.com/vijayshegokar/Java/blob/master/Utility/src/common/util/reflection/ReflectionUtil.java
嘿朋友们只需使用我创建的 ReflectionUtil 类将一个 bean 值复制到另一个类似的 bean。该类还将复制 Collections 对象。https://github.com/vijayshegokar/Java/blob/master/Utility/src/common/util/reflection/ReflectionUtil.java
Note:This bean must have similar variables name with type and have getter and setters for them.
注意:此 bean 必须具有与类型相似的变量名称,并为它们提供 getter 和 setter。
Now more functionalities are added. You can also copy one entity data to its bean. If one entity has another entity in it then you can pass map option for runtime change of inner entity to its related bean.
现在添加了更多功能。您还可以将一个实体数据复制到其 bean 中。如果一个实体中有另一个实体,那么您可以将内部实体的运行时更改的映射选项传递给其相关 bean。
Eg.
例如。
ParentEntity parentEntityObject = getParentDataFromDB();
Map<Class<?>, Class<?>> map = new HashMap<Class<?>, Class<?>>();
map.put(InnerBean1.class, InnerEntity1.class);
map.put(InnerBean2.class, InnerEntity2.class);
ParentBean parent = ReflectionUtil.copy(ParentBean.class, parentEntityObject, map);
This case is very useful when your Entities contains relationship.
当您的实体包含关系时,这种情况非常有用。
回答by Piyush Chaudhari
You can achieve it using Java Reflection API.
您可以使用Java Reflection API来实现它。
public static <T> void copy(T target, T source) throws Exception {
Class<?> clazz = source.getClass();
for (Field field : clazz.getDeclaredFields()) {
if (Modifier.isPrivate(field.getModifiers()))
field.setAccessible(true);
Object value = field.get(source);
field.set(target, value);
}
}