2010-06-22 16 views
8

tengo los siguientes dos clases:constructor de copia en el niño, pero no de Padres

public class User { 
    public Integer userId; 
    // ...another 50-60 fields 
} 

public class SuperUser extends User { 
} 

me gustaría tener un constructor de superusuario que toma un objeto de tipo de usuario y crea un objeto de tipo superusuario. Por ejemplo:

public SuperUser(User theUser) { 
    // not legal -> but I am looking for a one-liner to initialize this with values from theUser 
    this = theUser; 
} 

Si el objeto de usuario carece de la constructor de usuario (User existingUser), ¿hay alguna manera automática para inicializar el objeto SuperUser con todos los campos de objeto de usuario existente? Estoy tratando de evitar 50 líneas de:

public SuperUser(User theUser) { 
    this.firstName = theUser.getFirstName(); 
    this.lastName = theUser.getLastName(); 
    // and so on.... 
} 

Si esto no se puede hacer, hay una refactorización como "Crear copia Constructor?"

Gracias!

Respuesta

9

Tome un vistazo a commons-beanutils 's BeanUtils.copyProperties(..):

SuperUser superUser = new SuperUser(); 
BeanUtils.copyProperties(superUser, originalUser); 

alternativa, se puede colocar esto en el constructor de copia:

public SuperUser(User originalUser) { 
    BeanUtils.copyProperties(this, originalUser); 
} 
1

Reflexión & BeanUtils son muy útiles, pero lento. Puede valer la compensación en su caso, pero los evitaría. Además, Object.clone() no le dará lo que desea ... porque el método clone() del usuario (si se implementó ... y probablemente no) le dará un Usuario ... no un Superusuario.

clone() se usa raramente. El constructor de copias o un método de fábrica son patrones razonables.

Editar: He olvidado responder la pregunta. Sí, implemente manualmente el constructor de copia. Java == Mucha escritura.

+1

No creo que usted está respondiendo a la pregunta;) – Bozho

+0

Pero, si no recuerdo mal, no hay verdaderos constructores de copia dedicados en Java, por lo que ¿cómo se puede usar? – AndrejaKo

+0

Usted las implementa manualmente. – royal

0

java.beans El paquete puede manejar estas cosas:

User u = ...; 
SuperUser su = ...; 
BeanInfo bi = Introspector.getBeanInfo(User.class); 
for (PropertyDescriptor pd : bi.getPropertyDescriptors()) { 
    Method getter = bi.getReadMethod(), setter = bi.getWriteMethod(); 
    if (getter == null || setter == null) continue; 
    setter.invoke(su, getter.invoke(u)); 
} 
0

// ...another 50-60 fields.
En lugar de String firstName etc, el usuario debe tener campos como Name name, que tiene nombre, apellido, título, etc.

Usted podría hacer lo mismo para sus direcciones, detalles de contacto, etc. Esto haría que un constructor de copias sea bastante más fácil.

Por cierto, ya superusuario extiende usuario, su constructor sería

public SuperUser(User user){ 
    super(user); //the User constructor would do the copy 
    //initialize other fields... 
} 
+0

que asume que tengo un constructor: usuario público (usuario existente) No tengo tal constructor ...... – David

+0

En realidad, supone que puede crear un superconstructor 'protegido' (' usuario protegido (Usuario) existente) '). – Stephen

4

Mientras que usted podría utilizar algo como BeanUtils para hacer lo que está tratando de hacer, si es necesario promover un usuario a superusuario o degradar un SuperUser para un usuario, ¿está utilizando la abstracción correcta?

¿Podría usted refactorizar su código para que el usuario tenga permisos o privilegios? En general, cuando siento que necesito cambiar un objeto por un objeto diferente en la jerarquía, reorganizo la jerarquía.

Por ejemplo:

public class User { 
    public Integer userId; 
    // ...another 50-60 fields 
    public Role role; 
} 

public interface Role { 
} 
public SuperUserRole implements Role { 
} 

Si no quiere hacer este cambio, entonces la respuesta de Bozho funcionaría.

0

Si quieres usar BeanUtils en Android pero no hay suerte, prueba con android-java-air-bridge. https://code.google.com/p/android-java-air-bridge/

Simplemente descargue android-java-air-bridge.jar.zip, extraiga el .jar e importe en su proyecto, sin necesidad de cambiar ningún código.

Ejemplo:

import javadz.beanutils.BeanUtils; 

BeanUtils.copyProperties(superUser, originalUser); 
Cuestiones relacionadas