阴影最终战场

时间:2017-06-25 13:14:52

标签: java inheritance field final

所以我想创造一个房子(此时这是一个非常简单的房子)我有这个类:

public class Probability {
    public final int MinWindows = 0;
    public final int MaxWindows = 0;
    //double values represend the percent chance for a specific attribute to 
    //generate
    public final double hasBackDoor = 0;
    public final double hasSecondFloor = 0;
    public final double hasChimny = 0;
    public final double hasGarage = 0;
    public final double hasPorch = 0;
}

这个类然后由不同类型的房屋的子类继承:

public class LowClassHouseProbability extends Probability{
    public final int MinWindows = 5;
    public final int MaxWindows = 10;
    public final double hasBackDoor = 55.0;
    public final double hasSecondFloor = 10.0;
    public final double hasChimny = 5.5;
    public final double hasGarage = 30.0;
    public final double hasPorch = 60.0;
}

public class MiddleClassHouseProbability extends Probability{
    public final int MinWindows = 20;
    public final int MaxWindows = 50;
    public final double hasBackDoor = 80.0;
    public final double hasSecondFloor = 70.0;
    public final double hasChimny = 10.0;
    public final double hasGarage = 90.0;
    public final double hasPorch = 85.0;
}

public class UpperClassHouseProbability extends Probability{
    public final int MinWindows = 50;
    public final int MaxWindows = 100;
    public final double hasBackDoor = 100.0;
    public final double hasSecondFloor = 100.0;
    public final double hasChimny = 80.0;
    public final double hasGarage = 99.0;
    public final double hasPorch = 100.0;
}

因此概率的所有子类都会影响其所有字段,这些字段在我的意见中看起来很邋and并且有点令人讨厌,但是我需要它们来扩展概率因为当我实际必须使用该对象时它会使它变得更容易,因为它看起来更好:

public class House {
    public House(Probability prob){

    }
}

如果我没有概率课并且做了这个:

public class House {
    public House(LowClassHouseProbability prob){

    }
    public House(MiddleClassHouseProbability prob){

    }
    public House(UpperClassHouseProbability prob){

    }
}

对于我创建的子类越多,这种情况就越糟糕。 所以我的问题是有没有更好的方法来做到这一点,我没想到,或者我只需要按照我想到的两种解决方案中的一种或另一种方式来做。

3 个答案:

答案 0 :(得分:1)

由于你无法覆盖java中超类的字段,所以这些类根本不需要定义字段..

 public class LowClassHouseProbability extends Probability{
     //public final int MinWindows = 50;
     //public final int MaxWindows = 100;

这些都是最终声明的,所以你需要在构造函数中设置它们......

LowClassHouseProbability(int minW, int maxW,...){
    super(minW, maxW, ....);

MiddleClassHouseProbability(int minW, int maxW,...){
    super(minW, maxW, ....);

UpperClassHouseProbability(int minW, int maxW,...){
    super(minW, maxW, ....);

并在超类Probability中定义构造函数:

Probability(int minW, int maxW,...){
    MinWindows = minW;
    MaxWindows = maxW;
    // .... etc etc

答案 1 :(得分:1)

最好完全删除子类,并定义与您的房屋类型相关的Worksheets("Sheet2").Range("E" & i).Value = rngName.Value 类的实例,并构建一个多参数构造函数便于实例构建。

或者,您可以将其重构为界面

Probability

然后,

public interface Probability {
    int getMinWindwsMinWindows();
    /*and so on*/
}

答案 2 :(得分:0)

使用步骤构建器可以解决管理具有太多字段的构造函数的问题。步骤构建器的工作原理是为每个步骤创建一个接口,然后让构建器实现所有步骤。这样,在完成每个构建步骤后,只有下一步可用于完成。

以下是一个例子:

package mcve;

public class Probability {
    public final int    minWindows;
    public final int    maxWindows;
    public final double hasBackDoor;
    public final double hasSecondFloor;
    public final double hasChimny;
    public final double hasGarage;
    public final double hasPorch;
    private Probability(final int    minWindows,
                        final int    maxWindows,
                        final double hasBackDoor,
                        final double hasSecondFloor,
                        final double hasChimny,
                        final double hasGarage,
                        final double hasPorch) {
        this.minWindows     = minWindows;
        this.maxWindows     = maxWindows;
        this.hasBackDoor    = hasBackDoor;
        this.hasSecondFloor = hasSecondFloor;
        this.hasChimny      = hasChimny;
        this.hasGarage      = hasGarage;
        this.hasPorch       = hasPorch;
    }

    public static final Probability LOW_CLASS =
        builder().setMinWindows(5)
                 .setMaxWindows(10)
                 .setHasBackDoor(55.0)
                 .setHasSecondFloor(10.0)
                 .setHasChimny(5.5)
                 .setHasGarage(30.0)
                 .setHasPorch(60.0)
                 .build();
    // public static final Probability MIDDLE_CLASS = ...;
    // public static final Probability UPPER_CLASS  = ...;

    public static MinWindowsStep builder() {
        return new Builder();
    }

    public interface MinWindowsStep     { MaxWindowsStep     setMinWindows(int n);        }
    public interface MaxWindowsStep     { HasBackDoorStep    setMaxWindows(int n);        }
    public interface HasBackDoorStep    { HasSecondFloorStep setHasBackDoor(double n);    }
    public interface HasSecondFloorStep { HasChimnyStep      setHasSecondFloor(double n); }
    public interface HasChimnyStep      { HasGarageStep      setHasChimny(double n);      }
    public interface HasGarageStep      { HasPorchStep       setHasGarage(double n);      }
    public interface HasPorchStep       { BuildStep          setHasPorch(double n);       }
    public interface BuildStep          { Probability        build();                     }

    private static final class Builder
    implements MinWindowsStep,
               MaxWindowsStep,
               HasBackDoorStep,
               HasSecondFloorStep,
               HasChimnyStep,
               HasGarageStep,
               HasPorchStep,
               BuildStep {
        private int    minWindows;
        private int    maxWindows;
        private double hasBackDoor;
        private double hasSecondFloor;
        private double hasChimny;
        private double hasGarage;
        private double hasPorch;

        @Override
        public MaxWindowsStep setMinWindows(int minWindows) {
            this.minWindows = minWindows;
            return this;
        }
        @Override
        public HasBackDoorStep setMaxWindows(int maxWindows) {
            this.maxWindows = maxWindows;
            return this;
        }
        @Override
        public HasSecondFloorStep setHasBackDoor(double hasBackDoor) {
            this.hasBackDoor = hasBackDoor;
            return this;
        }
        @Override
        public HasChimnyStep setHasSecondFloor(double hasSecondFloor) {
            this.hasSecondFloor = hasSecondFloor;
            return this;
        }
        @Override
        public HasGarageStep setHasChimny(double hasChimny) {
            this.hasChimny = hasChimny;
            return this;
        }
        @Override
        public HasPorchStep setHasGarage(double hasGarage) {
            this.hasGarage = hasGarage;
            return this;
        }
        @Override
        public BuildStep setHasPorch(double hasPorch) {
            this.hasPorch = hasPorch;
            return this;
        }
        @Override
        public Probability build() {
            return new Probability(minWindows,
                                   maxWindows,
                                   hasBackDoor,
                                   hasSecondFloor,
                                   hasChimny,
                                   hasGarage,
                                   hasPorch);
        }
    }
}

必须按名称分配字段,如果您忘记了所在的步骤,编译器错误将告诉您:

// This will cause an error with a message something like
// "Cannot find symbol method build() in interface MinWindowsStep".
Probability p = Probability.builder()
                           .build();

如果事实证明您确实需要使用继承,那么构建器模式可以通过以下方式进行调整:具有多个实现的抽象构建步骤。