【问题标题】:Java inherance method with return type具有返回类型的 Java 继承方法
【发布时间】:2015-10-02 09:46:21
【问题描述】:

这样写我的课程是否正确?有问题的是Item 类中的方法getPrice()。每个项目都需要有一个getPrice()。但我实际上不能返回一些东西。所以我解雇了this.getPrice(),得到了ProductItem 的价格。有没有更可靠/设计更好的解决方案?

class Item {
    String description;

    public Item(String description) {
        this.description = description;
    }

    double getPrice(){return this.getPrice();} //TODO Correct like this?
}

class ProductItem extends Item {
    int amount;
    double pricePerUnit;

    public ProductItem(String description, int amount, double pricePerUnit)         {
        super(description);
        this.amount = amount;
        this.pricePerUnit = pricePerUnit;
    }

    @Override
    double getPrice(){
        return amount * pricePerUnit;
    }
}

【问题讨论】:

  • this.getPrice()Item 中不存在。你只需要做return 0。被覆盖的类返回正确的东西,因为它是 overriden

标签: java inheritance review


【解决方案1】:

听起来Item 应该是一个抽象类,getPrice() 是一个抽象方法:

public abstract class Item {
    private final String description;

    public Item(String description) {
        this.description = description;
    }

    public abstract double getPrice();

    public String getDescription() {
        return description;
    }
}

这意味着你将无法写作

Item item = new Item("foo"); // Invalid, because Item is abstract

但你可以写:

Item item = new ProductItem("foo", 10, 2.0);
double p = item.getPrice(); // 20.0

您声明的每个具体(非抽象)子类都必须覆盖 getPrice() 并提供一个实现。

有关详细信息,请参阅abstract classes and methods section of the Java tutorial

【讨论】:

    【解决方案2】:

    您需要做的是通过使getPrice 方法抽象化来使您的Itemabstract

    这会强制您的子类实现特定功能,如果不这样做,编译器会报错。

    你可以这样做:

    class Item {
        String description;
    
        public Item(String description) {
            this.description = description;
        }
    
        abstract double getPrice();
    }
    

    当子类忘记实现该函数时,您给出的实现实际上会导致对自身的循环(无限循环)调用。当子类实现了该函数时,它根本就不会被调用,因为它被子类覆盖了。

    【讨论】:

      【解决方案3】:

      为什么不能将getPrice()Itemabstract,如下:

        public abstract class Item {
          private String description;
      
          public Item(final String description) {
              this.description = description;
          }
      
          protected abstract double getPrice();
      
          public String getDescription() {
              return description;
          }
      }
      

      并在扩展类中提供实现,如下:

      public class ProductItem extends Item {
          private int amount;
          private double pricePerUnit;
      
          public ProductItem(final String description, final int amount, final double pricePerUnit) {
              super(description);
              this.amount = amount;
              this.pricePerUnit = pricePerUnit;
          }
      
          @Override
          protected double getPrice() {
              return amount * pricePerUnit;
          }
      
      }
      

      【讨论】:

        【解决方案4】:

        double getPrice(){return this.getPrice();} 基本上是一个无限循环。 你应该先设定这个价格。

        class Item {
            String description;
            double price;
            public Item(String description) {
                this.description = description;
            }
        
            public void setPrice(double price) {
                this.price = price;
            }
        
            double getPrice(){return this.price;} 
        }
        

        【讨论】:

          【解决方案5】:

          万一你错过了,Item 类存在问题,其中方法getPrice() 是递归的。所以这里new Item().getPrice()会导致StackOverflowException。

          您可以将类设为抽象类。

          abstract class Item {
            String description;
            public Item(String description) {
              this.description = description;
            }
            abstract double getPrice(); // force child classes to override this method
          }
          

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 2017-03-26
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 2020-11-20
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多