0

好的,我有一个抽象类“订单”:

public abstract class Order {
protected String location;
protected double price;

public Order(double price, String location){
    this.price = price;
    this.location = location;
}
public abstract double calculateBill();

public String getLocation() {
    return location;
}
public double getPrice() {
    return price;
}
public abstract String printOrder(String format);   
}

我也有 3 个实现它的类,它们是相似的,当然,它们根据税收、关税等不同地计算账单。

现在我正在尝试创建 OrderManager 类来管理它们。这是我到目前为止所拥有的

public class OrderManager {
private ArrayList<Order> orders;

public OrderManager() {     
}   
public OrderManager(ArrayList<Order> orders) {
    this.orders = orders;   
}   
public void addOrder(Order o) {
    orders.add(o);
}   
public ArrayList<Order> getOrdersAbove(double val) {
    for (Order o : orders) {
        double bill = o.calculateBill();
        if (bill > val)
            orders.add(o);
    }
    return orders;
}

我在使用 getOrdersAbove 方法时遇到问题,该方法应该返回账单高于 val 的订单的数组列表。作为calculateBill 是抽象的,并在订单的每个子类中实现,我应该能够称它为正确吗?此外,如果是这种情况,那么 OrderManager 不应该扩展 Order 吗?或者只是在同一个包中可以让我调用它的方法?还是我做错了?

感谢您的任何帮助!

4

4 回答 4

0

作为calculateBill 是抽象的,并在订单的每个子类中实现,我应该能够称它为正确吗?

该方法声明为public,您将能够在Order实例上调用它。

此外,如果是这种情况,那么 OrderManager 不应该扩展 Order 吗?

问问自己:OrderManager 是 Order 吗?不?所以不要让它扩展Order

或者只是在同一个包中可以让我调用它的方法?

同样,该方法是公共的,因此您可以从任何地方调用它,只要您有一个实例可以调用它。

所以在你的for循环中

public ArrayList<Order> getOrdersAbove(double val) {
    for (Order o : orders) {
        double bill = o.calculateBill();
        // do logic
    }
}

在调用时calculateBill(),Java 会使用后期绑定(多态性)来解析要使用的方法的实际实现。

于 2013-09-18T21:55:53.930 回答
0

OrderManager不需要知道任何calculateBill关于Order.

只要该方法被覆盖,您就可以确保如果它是公共的(或者它们在同一个包中),您将被允许调用它,因为您不能降低继承方法的可见性。

即使OrderisabstractcalculateBillisabstract在那个不禁止您调用该方法的类中。应用于abstract类的唯一限制是你不能实例化它们,一旦你有一个实例(即使它的运行时类型更窄)那么你就不应该担心任何事情。

于 2013-09-18T21:58:52.603 回答
0

作为calculateBill 是抽象的,并在订单的每个子类中实现,我应该能够称它为正确吗?

Java Runtime 并不真正关心 in 中没有calculateBill()方法的实现Order,只是Order“知道”(或者更好的是,“已声明”)一个被调用的方法calculateBill(),它不接受任何参数并返回一个双精度值——它之所以这样做是因为你的行:

public abstract double calculateBill();

确保具体子类实际实现抽象方法是在编译时完成的检查。只要您覆盖了calculateBill()子类中的方法(编译代码需要这样做),您就可以调用它(从任何地方,因为您将其声明为public)。将在运行时根据您调用它的特定子类实例为您选择具体的实现calculateBill()——无论是class Foo' 的实现还是' 的。class Bar

此外,如果是这种情况,那么 OrderManager 不应该扩展 Order 吗?

不,我不明白为什么应该这样做。这似乎没有多大意义。如果你这样做了,你必须有一个具体的calculateBill()内部实现OrderManager,同样似乎没有多大意义。

或者只是在同一个包中可以让我调用它的方法?

任何拥有该类实例的人都可以调用公共(非静态)方法calculateBill(),无论调用类是否在同一个包中。

还是我做错了?

您似乎在子类中的抽象方法和实现的正确轨道上,以及在抽象类中提供各种方法的默认实现(例如getPrice(), getLocation()

于 2013-09-18T22:02:31.987 回答
0

getOrdersAbove 应该创建一个新的 ArrayList 来保存高于 val 的订单。

您正在将选定的订单添加回您正在迭代的列表中,这将导致迭代器失败。

于 2013-09-18T22:19:08.987 回答