定义

依赖反转原则(Dependency Inversion Principle,DIP)是面向对象编程领域中的一个重要原则,其主要目的是降低模块间的耦合度,提高代码的可维护性和重用性。

该原则主张高层次模块不应依赖于低层次模块的具体实现,而应依赖于其抽象接口。这样,低层次模块的具体实现可以独立变化,而不会影响高层次模块。

分析

react中:
高层模块指的是组件。
地层模块指的是执行具体功能的模块,比如请求数据的api

反例

下面代码中的需求请求直接采用的具体实现,当我们需要更换请求工具时,我们需要直接进入高层模块,也就是组件中进行代码修改,这可能引入风险,也不利于代码重用。

function TodosContainer() {
  const [todos, setTodos] = useState([])

  useEffect(() => {
    fetch('/getTodos').then(res => res.json()).then(res => setTodos(res));
  }, [])

  return <>{todos.map(item => <>{item.title}</>)}</>
}

正例

下面这个日常开发中经常见到的api调用,就是依赖倒置朴实无华的应用。
我们将高层模块对请求的具体进行了抽象,这样高层模块就不关心底层模块的具体实现了,当我们需要更换请求工具,比如axios,我们直接在底层模块中进行修改,也就是我们的底层模块可以独立进行变化。

// api.js

export const getTodos = () => {
    return fetch('/getTodos').then(res => res.json())
}
import { getTodos } from './api'

function TodosContainer() {
  const [todos, setTodos] = useState([])

  useEffect(() => {
    getTodos().then(res => setTodos(res));
  }, [])

  return <>{todos.map(item => <>{item.title}</>)}</>
}

结论

通过上面的代码,我们可以发现应用了依赖倒置的版本有以下优点:

可维护性:
对低层模块进行抽象会降低与高层模块的耦合度,使得代码更易于理解和维护。

重用性:
依赖反转原则鼓励对具体实现进行抽象,这使得这些抽象更易于在多个地方重用。

稳定性:
当需要添加新功能或修改现有功能时,我们只需修改相应的低层具体实现,而无需修改依赖于这些实现的高层组件。这有助于保持高层组件的稳定性。

用我自己的话来说就是,在高层模块中,不应该有具体的细节,而应该把这些细节用一个相对抽象的函数或者对象来替代,这样,当你需要替换或者修改实现细节的时候,就不用进入高层模块,也就不用担心对高层模块造成破坏(当然前提是保持接口一致)。
并且在对细节抽象的过程中会产生一个好的副作用,那就是,这些抽象的函数或者对象可以被复用。


热饭班长
3.7k 声望434 粉丝

先去做,做出一坨狗屎,再改进。