Java Solid 原则指南

2025-06-08

Java Solid 原则指南

在这篇文章中,我们将看到 Java 中的 5 个 SOLID 原则。

Robert C. Martin 提出了五项面向对象设计原则,并将其缩写为“SOLID”。该缩写中的每个字母都代表了Java中的原则。当您结合使用 SOLID 的所有原则时,开发易于管理的软件将变得更加容易。SOLID 的其他特性包括:

  • 避免代码异味
  • 快速折射器代码
  • 可以进行自适应或敏捷软件开发

当您在编码中使用 SOLID 原则时,您就开始编写高效且有效的代码。

SOLID 的含义是什么?

如上所述,SOLID 代表 Java 的五项原则,即:

  1. S:单一职责原则
  2. O:开放封闭原则
  3. L:里氏替换原则
  4. 一:接口隔离原则
  5. D:依赖倒置原则

本文将深入探讨这些原则。我们将从第一个原则开始,即单一职责原则。

单一职责原则(SRP)

根据单一责任原则,一个类应该只有一个需要修改的原因。这意味着一个类应该只负责一项任务。这一原则通常被称为主观原则。

举个例子,可以更好地理解这个原理。假设有一个类执行以下操作。

  • 连接到数据库
  • 从数据库表中读取一些数据
  • 最后将其写入文件。

你想象过这样的场景吗?这个类有多个需要修改的原因,其中很少一部分是修改文件输出,一部分是采用新的数据库。当我们谈论单一职责原则时,我们会说,这个类有太多需要修改的原因;因此,它并不符合单一职责原则。

开放封闭原则

根据开闭原则,实体或对象应该对扩展保持开放,但对修改保持封闭。确切地说,根据该原则,类的编写方式应使其能够完美地完成其功能,而不必假设将来有人会随意修改它。因此,类应该对修改保持封闭,但应该具有扩展的选项。扩展类的方式包括:

  • 从类继承
  • 覆盖类中所需的行为
  • 扩展类的某些行为

借助浏览器,我们可以很好地理解开放封闭原则。你还记得在 Chrome 浏览器中安装扩展程序吗?

Chrome 浏览器的基本功能是浏览不同的网站。您在使用 Chrome 浏览器撰写电子邮件时,是否想检查语法?如果是,您可以使用 Grammarly 扩展程序,它能帮您检查内容的语法。

这种通过添加功能来增强浏览器功能的机制被称为扩展。因此,浏览器是一个开放扩展、关闭修改的功能的完美例子。简而言之,您可以通过在浏览器上添加/安装插件来增强功能,但无法构建任何新的东西。

再举一个例子。
您正在使用任何 Spring 函数功能。您显然不能更改其核心逻辑,但您可以扩展 Spring 框架类并创建自己的函数。

里氏替换原则

里氏替换原则假设 q(x) 是一个属性,对于属于类型 T 的 x 的实体而言是可证明的。现在,根据该原则,q(y) 应该对于属于类型 S 的对象 y 也是可证明的,而 S 实际上是 T 的子类型。你现在是不是有点困惑,不知道里氏替换原则到底是什么意思?它的定义可能有点复杂,但实际上相当简单。唯一的区别在于,每个子类或派生类都应该可以替换它们的父类或基类。

你可以说这是一条独特的面向对象原则。理解了这条原则,就可以进一步简化这条原则;一个特定父类型的子类型应该能够替代该父类型,而不会造成任何复杂化或破坏。这条原则与里氏替换原则密切相关。

接口隔离原则

根据接口隔离原则,无论如何,客户端都不应该被强迫实现它不使用的接口,或者客户端不应该被强迫依赖于他们不使用的任何方法。

因此基本上,接口隔离原则就像您喜欢的接口一样,它们很小但特定于客户端,而不是单一且更大的接口。

简而言之,强迫客户依赖他们不需要的某些东西是有害的。

现在让我们再举一个例子来理解这一点。

让我们举一个简单的例子。您正在用 Java 实现自己的 ArrayList 和 LinkedList。您创建一个名为 List 的接口,这两个类都将实现该接口。

package org.arpit.java2blog;

public interface List<T> {
    public T get();
    public void add(T t);
    public T poll();
    public T peek();    
}
现在让我们创建 LinkedList 类。
包 org.arpit.java2blog;

公共类 LinkedList 实现 List{

    @Override
    公共整数获取(){
        // 实现此方法
        返回 null;
    }

    @Override
    公共无效添加(整数t){
        // 实现此方法
    }

    @Override
    公共整数轮询(){
        // 实现此方法
        返回 null;
    }

    @Override
    公共整数 peek() {
        // 实现此方法
        返回 null;
    }
}

现在让我们创建 ArrayList 类。

包 org.arpit.java2blog;

公共类 ArrayList 实现 List{

    @Override
    公共整数获取(){
        // 实现此方法
        返回 null;
    }

    @Override
    公共无效添加(整数t){
        // 实现此方法
    }

    @Override
    公共整数轮询(){
        // ArrayList 不需要此方法
        返回 null;
    }

    @Override
    公共整数 peek() {
        // ArrayList 不需要此方法
        返回 null;
    }
}

你发现问题了吗?即使你不需要 ArrayList 中的 poll 和 peek 方法,我们也实现了它们。
上述问题的正确解决方案是:
创建另一个名为 Deque 的接口,并使其包含 peek 和 poll 方法。

包 org.arpit.java2blog;

公共接口 Deque<T> {
    公共T投票();
    公共 T peek();    
}

并从列表界面中删除 peek 和 poll。

包 org.arpit.java2blog;

公共接口列表<T> {
    公共 T 获取();
    公共无效添加(T t);   
}

现在让我们改变 LinkedList 类。

包 org.arpit.java2blog;

公共类 LinkedList 实现 List,双端队列{

    @Override
    公共整数获取(){
        // 实现此方法
        返回 null;
    }

    @Override
    公共无效添加(整数t){
        // 实现此方法
    }

    @Override
    公共整数轮询(){
        // 实现此方法
        返回 null;
    }

    @Override
    公共整数 peek() {
        // 实现此方法
        返回 null;
    }
}

现在让我们改变 ArrayList 类。

包 org.arpit.java2blog;

公共类 ArrayList 实现 List{

    @Override
    公共整数获取(){
        // 实现此方法
        返回 null;
    }

    @Override
    公共无效添加(整数t){
        // 实现此方法
    }
}

如您所见,我们已经分离了两个接口来实现所需的功能。

依赖倒置原则

根据依赖倒置原则,实体应该只依赖于抽象,而不依赖于具体。根据该原则,高级模块绝不能依赖任何低级模块,而应该依赖于抽象。让我们通过另一个实际的例子来再次理解这一点。

你去当地一家商店买东西,决定用借记卡付款。所以,当你把卡交给店员付款时,店员不会费心去检查你给的是什么卡。即使你给了一张Visa卡,店员也不会拿出Visa刷卡机来刷你的卡。你用的是信用卡还是借记卡,这根本不重要;他们只会刷卡。所以,在这个例子中,你和店员都依赖于信用卡抽象,而你并不关心卡的具体细节。这就是依赖倒置原则。

包起来

我希望现在你了解了 SOLID 五个组成部分的基本定义,即单一职责原则、开放封闭原则、里氏替换原则、接口隔离原则和依赖倒置原则。所以,基本上,无论何时编写代码,你都必须牢记这些核心原则。实际上,说实话,你必须以这些原则为蓝本,才能编写出高效且有效的代码。

使用这些原则来管理代码也是一件很容易的事情。最初在编码中运用这些原则可能看起来有些奇怪,但你需要练习使用这些原则编写代码,逐渐地,它们就会成为你的一部分。这样,你编写的代码就可以根据你遇到的需求轻松地进行修改、扩展、重构或测试,而不会遇到任何问题。所以,尽可能地实践这些原则,让你的编码更优秀。
来源:Java 中的可靠原则

您可能还喜欢:
Java 中的 xms 和 xmx 参数
Java 解析时到达文件末尾
Java 中的 NumberFormatException
Java 中的 FileNotFoundException
检查 Java 中的数字是否为数字

鏂囩珷鏉ユ簮锛�https://dev.to/arpitmandliya/a-guide-to-solid-principles-in-java-17ne
PREV
Java AWS Security LIVE 中的 100 多个顶级数据结构和算法面试问题!
NEXT
GraphQL 比 Rest 更好吗?