Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/334.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/oop/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 最大化代码重用的最佳方法,同时避免实现继承和维护内部化_Java_Oop_Design Patterns - Fatal编程技术网

Java 最大化代码重用的最佳方法,同时避免实现继承和维护内部化

Java 最大化代码重用的最佳方法,同时避免实现继承和维护内部化,java,oop,design-patterns,Java,Oop,Design Patterns,对于代码重用和代码结构,我在几种不同的OOP方法之间左右为难,无法找到适合我的情况的最佳选择 目前,我有一个名为“Plot”(一块土地)的基类,它处理标准Plot类型和任何其他Plot类型的核心功能。所以我认为有任何其他使用核心Plot功能来扩展Plot的Plot类型都是有意义的。然而,我现在意识到这种方法有很多缺点。以下是我的代码(java)的当前基本结构: 我不喜欢这种方法有几个原因 有些情况下,我需要重写一个方法以提供更多功能,但我不想执行父方法中的所有代码。(即:对代码重用没有控制或精

对于代码重用和代码结构,我在几种不同的OOP方法之间左右为难,无法找到适合我的情况的最佳选择

目前,我有一个名为“Plot”(一块土地)的基类,它处理标准Plot类型和任何其他Plot类型的核心功能。所以我认为有任何其他使用核心Plot功能来扩展Plot的Plot类型都是有意义的。然而,我现在意识到这种方法有很多缺点。以下是我的代码(java)的当前基本结构:

我不喜欢这种方法有几个原因

  • 有些情况下,我需要重写一个方法以提供更多功能,但我不想执行父方法中的所有代码。(即:对代码重用没有控制或精确性)
  • 类之间存在功能的强耦合。(即:基图类可能对任何子类的行为产生不期望的影响,因为它们是紧密耦合的。这称为脆弱基类问题)
我认为这种方法不可取的更多原因可以在这里找到()

我考虑过使用合成,但我意识到这也不是一个好的选择,因为我仍然需要重写基图类的功能

所以在这一点上,我知道我应该使用接口继承而不是实现继承。也许我可以让Plot成为一个界面,为所有绘图类型(标准、地产等)定义核心功能。现在这就是我被困的地方,因为我面临着代码重用的问题。我不想为所有绘图类型实现相同的标准功能,因此我考虑使用一种过程类(我们称之为PlotHelper),该类定义了公共静态方法来处理给定绘图对象的许多核心功能。以下是一个例子:

public interface Plot {
    public void doStuff();
}

public class StandardPlot implements Plot {

    @Override
    public void doStuff() {
        PlotHelper.handleStuff(this);
    }
}

public class EstatePlot implements Plot {
    @Override
    public void doStuff() {
        // Make sure we still handle the base functionality (code reuse)
        PlotHelper.handleStuff(this);
        
        // Make sure we also do stuff specific to the Estate plot type
    }
    
    public void extendedFunctionality() {
        // Do stuff that only applies to the Estate plot type
    }
}

public class PlotHelper {
    public static void handleStuff(Plot plot) {
        // Do stuff for Standard plot type
    }
}
我的问题是,现在核心功能不再被内部化。PlotHelper中的公共静态方法中现在的功能的位和段过去在基图类中一起处理,这意味着更模块化和内部化的代码

最后,既然您知道了我被困的地方和原因,有没有更好的解决方案可以避免实现继承并保持特定类型代码的内部化?或者,你可以想出一种完全不同的方法,对这种情况很好

谢谢你的时间

可能适用于您?

允许您实现方法(代码可重用性)和声明抽象方法(接口继承)

然后可以在
Plot
抽象类中实现
doStuff()
方法,并创建一个类似
doSpecificStuff()
的抽象方法,以便在
PlotType
中实现

public abstract class Plot {
    protected void doStuff(){
        //Implement general stuff for Plot
    };

    abstract void doSpecificStuff();
}

public class StandardPlot extends Plot {

    @Override
    public void doSpecificStuff() {
        // Make sure we still handle the base functionality (code reuse)
        doStuff(); //if needed. You can call standardPlot.doStuff() and then
                   //standardPlot.doSpecificStuff();

        // Make sure we also do stuff specific to the Estate plot type
    }

    public void extendedFunctionality() {
        // Do stuff that only applies to this plot type
    }
}

抽象类不能实例化,所以您仍然需要
StandardPlot
类。还将
doStuff()
声明为
protected
可以确保该方法仅由
Plot
类及其子类调用。

在某些情况下,我需要重写一个方法以提供更多功能,但我不希望在父方法中执行所有代码。那就不要调用
super.xyz()
?或者我误解了你的意思?如果你有一堆代码需要重用,那么继承本质上并不坏。如果您的方法不够精细,不允许合理的重用,那么这就是实现问题。如果您使用的是Java8,那么您就能够提供接口功能的标准实现。底线是Java的抽象模型有些贫乏,没有字节码操作(例如AOP),您的选择是有限的。在任何情况下,这可能更适合codereview或程序员。@ifLoop我指的是super.doStuff();可以做子类需要做的所有事情,除了一行。我宁愿不复制super.doStuff()中减去那一行的所有代码。我也不希望用这种方法分割不同的代码片段,因为这样会破坏内部化和模块化。@Weasel。。。但是,除了可测试性之外,小型方法的目的是可组合性。如果需要扩展点,则需要扩展点。另一个选择是将
这个
传递给助手类,这些助手类知道如何处理
这个
的实例。我非常熟悉抽象类。Plot类实际上扩展了一个名为“Region”的抽象类,但在查看我的代码之后,我认为将Plot抽象化也是有意义的。甚至可能使用像user1598503这样的模板模式
public abstract class Plot {
    protected void doStuff(){
        //Implement general stuff for Plot
    };

    abstract void doSpecificStuff();
}

public class StandardPlot extends Plot {

    @Override
    public void doSpecificStuff() {
        // Make sure we still handle the base functionality (code reuse)
        doStuff(); //if needed. You can call standardPlot.doStuff() and then
                   //standardPlot.doSpecificStuff();

        // Make sure we also do stuff specific to the Estate plot type
    }

    public void extendedFunctionality() {
        // Do stuff that only applies to this plot type
    }
}