2016-11-30 53 views
3

頂層應用程序組件訂閱在構造函數方法的終極版商店:爲什麼使用react-redux而不僅僅是redux?

constructor() { 
    super() 
    this.state = store.getState() 
    store.subscribe(() => { 
    this.setState(store.getState()) 
    }) 
} 

它傳遞到子組件作爲道具的狀態的部件。如果某些子組件需要更新狀態,它只是分派一個動作:

<button onClick={() => { 
    store.dispatch({type: 'INCREMENT'}) } 
}>increment</button> 

什麼是使用react-redux在此設置的優勢呢?換句話說,我爲什麼需要react-redux

+0

通過react-redux,您可以使用'connect'功能將任何組件連接到應用商店。如果沒有連接,你必須手動完成。而且,一般來說,任何圖書館的目的都是爲了減少手工工作量。 –

+1

由於您在Redux中創建的任何訂閱都會在每次狀態更改時被調用,無論您是否需要在該狀態片上進行操作。 'react-redux'允許我們指定某些組件應該訂閱的商店的哪些部分,因此我們只需「訂閱」我們想要的更改。 – lux

回答

0

它的要點是關注點分離 - react-redux允許訪問和更改組件需要訪問和更改的狀態部分。

@勒克斯的評論回答我的問題最好的,所以我會貼在這裏(重點煤礦):

你在終極版中創建的任何訂閱將被調用每個狀態變化,不管你是否需要在那個狀態切片上工作或沒有。 react-redux允許我們specifiy該商店的某些組件的部分應該訂閱,因此我們只有「訂閱」的變化,我們希望

+0

這是不正確的,因爲在Redux中也可以做同樣的事情,所以不應該接受答案。 – kushalvm

3

如果你的組件樹不是很深,那麼你是對的。優勢並不明顯。然而,大多數不是簡單示例的React應用程序都會很快產生長樹,特別是在組合許多組件時。

假設你有一個樹去

App -> HomePage -> BlogContainer -> PostList -> Post -> CustomCard -> Card -> LikeButton 

LikeButton組件需要訪問當前選定的職位的血統,並希望派遣一個動作,以更新後的樣數。

在您的設置中,AppLikeButton之間的每個組件都需要傳遞該信息,即使它們從未使用過它。使用react-reduxconnect功能,您可以直接將LikeButton連接到redux商店,並有權訪問dispatch。 YMMV,但一般來說這是一個很好的利用模式。

+0

難道你仍然需要將數據傳遞給Post子樹嗎?這是對原始的改進,但類似的按鈕仍然需要知道關於該文章的東西或對其進行回調。 –

+0

'PostList'可能會將帖子ID傳遞給'Post',後者可能會將它傳遞給'LikeButton'。不過,絕對不是'App'需要了解的任何內容。 – markerikson

3

一些原因。

首先,每Redux FAQ answer on connecting multiple components:在Redux的例子

強調「頂部一個容器組件」是一個錯誤。不要把這當成一句格言。儘量讓您的演示文稿組件分開。在方便時通過連接來創建容器組件。每當你覺得你正在複製父組件中的代碼來爲相同種類的孩子提供數據時,就需要花費時間來提取一個容器。一般情況下,只要您覺得父母對孩子的「個人」數據或行爲知之甚多,就有時間提取容器。

換句話說,一個有意義的應用程序將在組件樹中的不同位置連接多個組件。

更多的組件意味着它更容易推理什麼給定組件在做什麼。它聲明它需要從狀態獲得什麼數據,以及它想要分派什麼樣的動作,並且你不必爲了讓它們到達組件而從根傳遞道具。

此外,具有多個連接的組件已經被證明是一種整體的性能提高。更多的mapState調用的成本已被證明超過重組渲染浪費較少的組件。

從繼:陣營 - 終極版已優化工作投入它的很多(和即將到來的React-Redux v5是一個完整的內部重寫與主要性能增強)。

換句話說,如果你使用的是與Redux的反應,你應該使用作出反應,終極版和connect功能來構建你的UI。

0

您可以通過終極版做到這一點,仍然避免更新所有組件。是的,你可以調整你的當前組件是否應該更新。這裏的示例代碼

class VisibleTodos extends Component{ 
    componentDidMount(){ 
     this.unsubscribe = store.subscribe(() => { 
      this.forceUpdate(); 
     }); 
    } 

    componentWillUnmount() { 
     this.unsubscribe(); 
    } 


    render(){ 


     const state = store.getState(); 

     return(
      <TodoList 
       todos = {getVisibleTodos(
        state.todos, 
       state.visibilityFilter 
      )} 
       onTodoClick = {id => { 
        store.dispatch({ 
         type: 'TOGGLE_TODO', 
        id 
       }) 
       }} 
      > 
      </TodoList> 
     ) 
    } 
} 

與反應,終極版庫同樣的事情會做的

const mapStateToProps = (state) => { 


return { 
    todos: getVisibleTodos(
     state.todos, 
     state.visibilityFilter 
    ) 
    }; 
}; 

const mapDispatchToProps = (dispatch) => { 
    return { 
    onTodoClick: (id) => { 
     dispatch({ 
     type: 'TOGGLE_TODO', 
     id 
     }); 
    } 
    }; 
}; 

const { connect } = ReactRedux; 
const VisibleTodoList = connect(
    mapStateToProps, 
    mapDispatchToProps 
)(TodoList); 

所以,想象一下有與此類似,並在前者的情況下其他幾個組件,調用this.forceUpdate()this.unsubscribe()會是多餘的。因此,它使我們免於手動工作。

相關問題