OOP:在同一个类中调用公共方法

Ale*_*erc 5 java oop methods encapsulation public

当我的程序员介意让我以面向对象的方式思考这个概念时,我正在读一些关于汽车防撞系统的文章,这让我想知道这些系统是否尊重面向对象的编程模型.

作为一名Java开发人员,我在Java环境中转换了这个问题,并提出了一个特殊问题:在同一个类(在非静态上下文中)调用公共方法是否尊重并遵循面向对象的方式?

我的意思是,采取这个简短的假设汽车课:

public class Car {
    // Class attributes.

    // Constructors.

    public void accelerate(final double amplitude) {
        // Accelerate according to the amplitude.
    }

    public void brake(final double amplitude) {
        // Brake according to the amplitude.
    }

    // Other useful methods.

    private void collisionPreventionActions() {
        // Some actions.

        brake(100.0);

        // Some other actions.
    }
}
Run Code Online (Sandbox Code Playgroud)

假设一些Thread负责检测碰撞并在检测到碰撞时采取措施,其中一个动作就是制动.显然,该brake(...)方法成为一个有趣的选择,但这不是打破面向对象的做事方式吗?这不只是刹车.如果这个类中的防撞系统使用方向盘来避免事故怎么办?我觉得很奇怪汽车会从内部角度使用自己的输入......

在更一般的范围内,假设您有一个通用对象,我喜欢将其视为黑盒子.公共方法将相当于控制其行为的黑匣子上的杠杆.在此对象中调用公共方法意味着黑盒子将从其内部机制激活其自己的控制杆.

我问,因为我知道这样做是合法的,并且我已经看到公共方法在我的生活中多次在同一个类中被调用,但它是合法的并不一定意味着它是正确的OO方式它.

在非静态上下文中使用同一类中的公共方法是否遵循面向对象编程和封装的规则?如果没有,那么这样做的正确方法是什么,或者解决方法是什么?

das*_*ght 6

从OOP的角度来看,这个选择没有任何问题:对于一个执行需要其他方法组合的方法的方法来说,这是完全正确的.

但实际上,一种常见的方法是将功能分为公共部分和私有部分,如下所示:

public void brake(final double amplitude) {
    // check preconditions
    if (speed == 0) throw new IllegalStateException("cannot brake when standing");
    if (amplitude <= 0) throw new IllegalArgumentException("amplitude must be positive");
    // ... do other important checks
    doBrake(amplitude);
}
private void doBrake(final double amplitude) {
    // The real code goes here
}
Run Code Online (Sandbox Code Playgroud)

现在你collisionPreventionActions可以打电话doBrake而不是brake,假设你在打电话之前检查了所有必要的前提条件.

注意:doBrake还应检查其前提条件.但是,不要在不满足前提条件时抛出异常,而是使用断言.不同之处在于异常表示其他人滥用您的公共方法,而断言表明您或其他人维护您的代码时滥用您的封装方法.

  • 好答案.但是,最好在`doBrake`方法中包含任何强制性的前置条件检查,以确保始终检查它们.我将在"刹车"中进行的唯一检查是那些只需要检查外部班级何时呼叫的检查.我想这就是你所暗示的,但可能值得明确说明. (3认同)
  • 那很有意思。因此,在实际的汽车中,doBrake(...)将是制动液压系统,制动器(...)将是制动踏板,而冲撞防撞动作(...)将使用某种电动机来激活水力学,是吗? (2认同)