I can’t get a container from the class field using reflection. I tried the method below, but got an exception:
Exception in thread "main" java.lang.UnsupportedOperationException at java.util.AbstractList.add(AbstractList.java:148) at java.util.AbstractList.add(AbstractList.java:108) at java.util.Collections.addAll(Collections.java:5455)
public static void copy(Object from, Object to) throws NoSuchFieldException, IllegalAccessException { Class<?> fromClass = from.getClass(); Class<?> toClass = to.getClass(); Field[] sourceFields = fromClass.getDeclaredFields(); for (Field fromField : sourceFields) { Field toField = toClass.getDeclaredField(fromField.getName()); toField.setAccessible(true); fromField.setAccessible(true); if (fromField.getType().equals(toField.getType())) { if (!(fromField.getType() == String.class || fromField.getType().isPrimitive())) { if (fromField.getType().isAssignableFrom(List.class)) { List list = (List) fromField.get(from); List list1 = (List) toField.get(to); Collections.addAll(list1,list); toField.set(to, fromField.get(from)); } else if (fromField.getType().isAssignableFrom(Set.class)) { Set set = (Set) fromField.get(from); Set set1 = (Set) toField.get(to); set1.clear(); set.addAll(set1); toField.set(to, fromField.get(from)); } } else { toField.set(to, fromField.get(from)); } } } }
I don’t want to use methods of copying via serialization, I’m interested in reflection.
Advertisement
Answer
You are doing this for training I hope? If not then use some opensource library, it’s a lot harder than you think – check this.
Your problem is that you are adding to the to
list, and the to
list is an implementation that does not support adding (btw then you are ignoring the result). I suggest creating a new list and reassiging it, instead of adding to the existing one.
List list = (List) fromField.get(from); List list1 = (List) toField.get(to); List newList = new ArrayList(); if(list != null) Collections.addAll(newList,list); if(list1 != null) Collections.addAll(newList,list1); toField.set(to, newList);
Similar thing with Set
– your current code for Set
doesn’t make any sense, it operates on Class
objects.