java中的工厂类设计问题

时间:2011-03-02 13:41:59

标签: java design-patterns

我有两个班级

public class PrepaidPackage {

    private String name;
    private String serviceClassID;
    private boolean isTranferable;

    public boolean isTranferable() {
        return isTranferable;
    }
    public void setTranferable(boolean isTranferable) {
        this.isTranferable = isTranferable;
    }
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
    public String getServiceClassID() {
        return serviceClassID;
    }
    public void setServiceClassID(String serviceClassID) {
        this.serviceClassID = serviceClassID;
    }
}

其他课程

public class PostpaidPackage {
    private String name;
    private boolean isTranferable;
    public boolean isTranferable() {
        return isTranferable;
    }
    public void setTranferable(boolean isTranferable) {
        this.isTranferable = isTranferable;
    }
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
}

我想创建一个基于包类型创建相关类的工厂类。但是如果你看看上面的clasess,他们没有相同类型的方法和变量。那么请指导如何为上面的类创建接口或抽象类?

现在工厂将返回类名包。我能否调用其他类中不存在的方法。

更新

请建议我是否将我的套餐分为两类,如

public abstract class MyPackage {
    public abstract PackageSpec getSpec();
    public abstract PackagePrepaidDetails getDetail();
}

现在常见的属性将出现在PackageSpec和packageDetails中的预付费内容。

它是一种抽象的工厂模式。

public class PrepaidPackage extends MyPackage{
    PackageSpec spec;
    public Spec getSpec() {
      spec = new PackageSpec();
      spec.setTranferable(true)
      spec.setName("abc");
      return spec;
    }
    public PackagePrepaidDetails getDetails() {
      details = new PackagePrepaidDetails ();
      details.setServiceClassID(123)
      return details;
    }
}

public class PostpaidPackage extends MyPackage{
    PackageSpec spec;
    public Spec getSpec() {
        spec = new PackageSpec();
        spec.setTranferable(true)
        spec.setName("abc");
        return spec;
    }
}

4 个答案:

答案 0 :(得分:0)

快速解决方案,不是理想的解决方案,是拥有一个代表Prepaid类中所有方法的接口,并在Postpaid中保留未实现的方法。这将在短期内解决问题。我建议您重新查看类和用法,以避免代码中未实现的方法。

答案 1 :(得分:0)

对于一个抽象的超级班,你必须将两者共同的一切分组:

public abstract class MyPackage { // not sure you can call a class just "Package"
    private String name;
    private boolean isTranferable;

    public boolean isTranferable() {
        return isTranferable;
    }
    public void setTranferable(boolean isTranferable) {
        this.isTranferable = isTranferable;
    }
    public String getName() {
       return name;
    }
    public void setName(String name) {
        this.name = name;
    }
}

然后两者都从它继承(第一个添加serviceClassID而第二个没有)

您的工厂函数将返回MyPackage(或AbstractPackage,无论如何),但要访问您在instanceof测试后必须投射的特定函数。

答案 2 :(得分:0)

如果您还没有接口,我建议您使用界面。你并不一定需要它,但如果它们如此相似,这是一个很好的做法:

public interface Package {
    public boolean isTranferable();
    public void setTranferable(boolean isTranferable);
    public String getName();
    public void setName(String name);
}

然后在您的呼叫代码中,您有一个来自您工厂的包裹:

Package p = myFactory.nextPackage();    // or something
if (p instanceof PrepaidPackage) {
    PrepaidPackage prepaid = (PrefpaidPackage)p;
    // and do the thing you want
} else if (p instanceof PostpaidPackage) {
    PostpaidPackage postpaid = (PostpaidPackage)p;
    // amd do the other things
}

建议您进入llok的是 instanceof 运算符和类型转换

答案 3 :(得分:0)

您可以做出两种可能的设计选择:

  1. 预付费套餐会延期 后付运包和你的工厂 然后返回类型的对象 后付包,代码 那时叫工厂 负责检查类型。

  2. 有一个包接口 定义所有方法并具有 postpaid包定义方法 扔一个 UnsupportedOperationException(ala 集合定义的方式 操作为可选。)或返回 某种哨兵价值(即无效)

  3. 对于上述任何一种情况,您可以添加另一个方法getType(),该方法返回您希望实现的各种包类型的枚举,然后可以在访问工厂对象的代码中使用它来确定哪些方法可用