简体   繁体   中英

Better way to do this code

A and AService are base classes.

B and BService extend these classes.

A and B are beans containing parameters for the services.

BService expects a B typed argument in the execute method.

public class A
{
    private int a1;

    public int getA1() { return a1; }
    public void setA1(int a1) { this.a1 = a1; }
}

public class B extends A
{
    private int b1;

    public int getB1() { return b1; }
    public void setB1(int b1) { this.b1 = b1; }
}

public abstract class AService
{
    public int execute(A a)
    {
        return a.getA1() + getValue();
    }

    public abstract int getValue(A a);
}

public class BService extends AService
{
    public int getValue(A a)
    {
        B b = (A) a;

        return b.getB1();
    }
}

Is there a better way to do this code ? In particular, is there a way to avoid to cast objects ?

It sounds like generics are what you're looking for. Typically, whenever you have a concrete class which can always safely cast a value, you can usually express this via generic parameters (and have it checked at compile time).

In this particular example, you'd declare the AService with a generic parameter which must be some subclass of A. Then you use that parameter to make some methods specific to the particular type - in this case the getValue method, as something like

public class AService<T extends A> {

   // Now this takes a T - i.e. the type that a subclass is parameterised on
   public abstract int getValue(T a)

   // Execute will have to take a T as well to pass into getValue - an A
   // wouldn't work as it might not be the right type
   public int execute(T a)
   {
      return a.getA1() + getValue(a);
   }
}

where the T is a type parameter (conventionally a single uppercase letter). Then you can declare the BService as

public class BService extends AService<B> {

   // The type is checked by the compiler; anyone trying to pass an instance
   // of A into this class would get a compile-time exception (not a class cast
   // at runtime)
   public int getValue(B b) {
       return b.getB1();
   }
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM