鍍金池/ 問答/HTML/ React中高階組件的意義是什么?

React中高階組件的意義是什么?

背景部分是我對高階組件的理解,確保在繼續(xù)具體問題前,我們的理解是一致的。

背景:

React中高階組件是一個普通的函數(shù)。之所說它是“普通”的函數(shù),是想和組件類區(qū)分開,因?yàn)镴S中的類本質(zhì)上也是函數(shù)。所以高階組件雖然叫組件,但它并不是普通意義的 React 組件,而是一個函數(shù)。

這個函數(shù)接收一個React 組件類(姑且稱為“被包裝組件”)或其他可選參數(shù),并返回一個新的組件類(姑且稱為“增強(qiáng)型組件”)。所以你可以認(rèn)為高階組件是一個組件工廠函數(shù)。返回的組件類在 render 時往往使用“被包裝組件”進(jìn)行渲染。

其實(shí),高階組件的函數(shù)體的實(shí)現(xiàn)大部分都是“增強(qiáng)型組件”的實(shí)現(xiàn),在實(shí)現(xiàn)中利用傳遞給高階組件的參數(shù)定制化“增強(qiáng)型組件”的實(shí)現(xiàn)。

“增強(qiáng)型組件”是“被包裝組件”的容器組件。所以 React 文檔上說

You can think of HOCs as parameterized container component
definitions.(你可以把 HOC 看作是參數(shù)化的容器組件的定義)

具體問題:

那么問題來了,既然 hoc 可看做是參數(shù)化的容器組件的定義,那么 hoc 的獨(dú)特意義何在呢?如果需要對一個 React 組件進(jìn)行功能增強(qiáng),我給它在外面套一層容器組件不就行了嗎?同時容器組件也可以通過接收props 來進(jìn)行實(shí)現(xiàn)過程的定制化,props中也可包含組件類,即“被包裝組件”。高階組件對容器組件進(jìn)行定制化實(shí)現(xiàn)只不過是通過函數(shù)的參數(shù),這和容器組件本身使用 props 來定制化沒有本質(zhì)區(qū)別。

拿 React 文檔中的例子來說,文檔中將 withSubscription 實(shí)現(xiàn)為一個高階組件。那么我覺得就這個例子來說,withSubscription 實(shí)現(xiàn)為一個普通的 React 組件效果也是完全一樣的。只要把 withSubscription 的函數(shù)參數(shù)變?yōu)?WithSubscription 這個普通 React 組件的 props 即可。WithSubscription 的實(shí)現(xiàn)也就直接是“被包裝組件”的容器組件的實(shí)現(xiàn)了,而無需像 withSubscription 那樣返回一個容器組件類。
文檔上舉的例子確實(shí)說明了高階組件應(yīng)用的情境,但就這個例子而言,似乎不是非高階組件不可。那么,高階組件這種設(shè)計模式的獨(dú)特性在哪里,意義是什么?

回答
編輯回答
陪她鬧

如果需要對一個 React 組件進(jìn)行功能增強(qiáng),我給它在外面套一層容器組件不就行了嗎?同時容器組件也可以通過接收props 來進(jìn)行實(shí)現(xiàn)過程的定制化,props中也可包含組件類,即“被包裝組件”。高階組件對容器組件進(jìn)行定制化實(shí)現(xiàn)只不過是通過函數(shù)的參數(shù),這和容器組件本身使用 props 來定制化沒有本質(zhì)區(qū)別。

其實(shí)你說的這就是高階組件的實(shí)現(xiàn)方式了。高階組件只是將組件(函數(shù))作為參數(shù)的一個函數(shù)罷了。更加 fp。一般高階函數(shù)什么的,不就是因?yàn)槟芙邮芎瘮?shù)作為參數(shù)么。所以取名為高階。。。比如react-redux connect 其實(shí)就是高階組件。 寫法上來看,你覺得
const App = <Enhance><Main/></Enhance>
好還是
const App = Enhance(Main)
更好?

2018年3月12日 10:16
編輯回答
焚音

就和裝飾器一樣 可以看下裝飾器模式復(fù)用已有類的功能

2018年8月10日 05:34
編輯回答
裸橙

比如說你要給每個組件(Table、Slider等等)外面都加個Loading

如果說照著題主的想法,可能是給Table或者Slider外面套一層方法,最后返回個新組件就得了

但這樣Table或者Slider本身就寫死了而不是一個靈活的參數(shù),如果我下次有個Table1呢,又得寫一遍

這還不算,萬一我這是個狀態(tài)深沉的Loading呢...

具體的情況可以去看看antd的Form,如果不抽象一下真的欲仙欲死

這玩意就是為了少寫重復(fù)的代碼的,獨(dú)特性倒還真沒覺得

題主也說了這是個設(shè)計模式,沒碰上實(shí)際場景的時候它的確沒用,并不是什么非它不用的東西

碰見了,知道有這個東西了,那問題就會簡單很多了


以上是我出來的,并沒有實(shí)際操作過,只是知道有這么個東西

我實(shí)際操作過的所謂的“高階組件”反而是用在了以下場景:

原先的組件不成熟,但又急著上線,后來有時間了要重寫

改成成熟版本以后和原先版本用法差異很大,但又要兼容之前項(xiàng)目的用法

于是干脆組件本體改個名字,然后外面包一層跟原先一樣的名字的皮,就這么將就用著先的這么一種“被動高階”


仔細(xì)查了下,我發(fā)現(xiàn)對高階組件的理解還是片面了

2018年8月10日 23:07
編輯回答
乖乖噠

簡單點(diǎn)說就是組件復(fù)用, 簡單的組件組合成你所需要的組件

2017年10月16日 16:27