說說我眼中的Vue和React

雲棲直播~發表於2018-07-10

前序

我最早接觸的是reactjs,時間是在2016年,當時主要從官網學習,並且寫了一些筆記。坦白講,當時學習了一段時間,只是對裡面的概念有點印象而已。也搞不懂怎麼去具體的使用在專案裡面,裡面的思想也僅僅停留在字面上。學了一段時間以後就放下了,就這樣過了1年的時間。17年的6月,換了一份工作,直接上來就使用vue全家桶開發一個管理系統,時間一個月的時間,當時有人帶,結合官方的文件進行開發。但是這個過程仍然覺得有點痛苦,就這樣一個月的時間,總算是熬過來了。就這樣讓我第一次完整的接觸了Vue,給我印象最深的是:中文的官網,簡單的入門示例。通過這一個月的時間,讓我終於對資料驅動檢視,對從dom的繁瑣操作釋放出來是暢快感有了很真實的體驗,感謝當初帶我入門的磊哥。

 

對Vue的第一印象勝過了React

從那之後,工作也經過了短暫的動盪,有了新的工作。並且開始了大規模使用Vue或Vue全家桶開發專案,10個月的時間將近,開發了多個spa專案。從我自己獨自使用Vue-cli腳手架搭建專案,使用Vue完成各種需求和動效。收貨真的非常大,心裡面對Vue更是喜歡的很,比起之前學習React的時候,簡直覺得Vue就是最好用的。心裡也有了一點偏執的認為React比不上Vue,在公司推崇Vue勝過React。

 

最近使用React+React-Router開發了一個專案

為什麼會這樣做呢?能夠使用React開發的SPA專案,肯定能夠使用Vue開發啊,況且我心裡一直推崇Vue的嘛。其實,我只是抱著試試的心態,做技術的不能對某種技術抱有偏見,應該敞開心胸,敢於嘗試和接納新的東西,固步自封不可取,不可取,不可取(重要的事情往往說3遍)。妨礙你自己進步的往往不是技術的門檻高低,而是你那狹窄的眼光和見識。在接到公司的一個新的需求以後,我給自己定了一個小目標:那就是使用React來嘗試開發一把。話雖如此,畢竟是公司專案,而且是涉及重要的業務(購買相關),不能搞砸,遇到任何坑必須自己全力以赴的填平。我也提前進入了技術的預研,腳手架工具,React的用法,React-Router的用法等等,儘量提前去搞清楚我說完全不知道的,做一個全面的學習(快速學習)。基於create-react-app搭建demo,因為有了Vue的開發經驗,所以使用React開發需要準備和了解的東西基本心裡有數了。開發環境的配置,跨域的聯調,在不執行npm run eject的情況下新增一些配置,打包時的路徑(context如何設定),專案裡面涉及的動畫效果等等都提前進行實踐,爭取在正式開發之前心裡有數。

 

使用React以後的體驗

雖然使用React才開發了一個專案,但是卻有很多的感受是在Vue裡面沒有的,甚至我不得不重新審視兩個元件,先說說哪些東西是React裡面讓我耳目一新的:函數語言程式設計,純函式元件,jsx,css-in-js,高階元件,redux等。這裡列舉到現在還停留在我腦海的東西,不一定對,但卻是我沒有從Vue裡面發現的。

 

說說JSX

我跟很多人一樣,一開始覺得JSX完全打亂了我之前固有的觀念(HTML,CSS,JS分離),心裡各種牴觸:這是啥啊,把js和html混合到一起。儘管這樣,我也開始去思考這個背後的專案,充分發揮javascript的力量,讓HTML更富有展現力,可以說是HTML in JS吧。這種做法是好是壞,其實我沒有任何的答案,我只是覺得這是一種新的思路和想法,到後來的使用styled-components,這裡仍然在背後貫穿了一種思想:css in js。把css也寫入了js物件裡面,甚至變成了一個樣式元件了。(簡直太糟糕了——最開始的抱怨),同樣的我開始接受這種想法,覺得這樣做也有其合理性的一面。而且也找了一些相關的會議視訊來看,心裡面開始慢慢的接受了這種想法。這是在Vue裡面未曾給到我的。

 

說說純函式元件

在React中,一個普通的函式就可以作為元件使用,返回JSX。只是沒有生命週期函式,做一個展示元件使用,從外界接收屬性資料,沒有任何問題。React就是這樣不斷的向外界傳遞發揮javascript的最大能效——All in js

 

說說高階元件

相對高階函式,傳入一個函式作為引數,返回一個函式作為結果。這裡是傳入的是元件,返回的是元件。函式式的變成思想貫穿其中,不侵入的想法貫穿其中。我想點個贊

 

說說redux thunk saga

我就不說redux是幹什麼的,只是有一點,redux裡面提到了thunk時(非同步的action),說這個是例外,因為action是個普通Object,thunk裡面變成了函式。為什麼說saga好了呢,他更好的貫穿了action是個純物件的思想。既然說好的,我們們就不要隨便例外。

 

說說Vue和React相通的地方

虛擬DOM

使用js來實現一個DOM結構,DOM變化通過使用Diff演算法比較js物件(記憶體中),找出不一樣的地方,然後更新,只更新發生變化的,提高了重繪效能。

為什麼呢?因為DOM的操作時耗效能的,而JS執行效率更好,所以兩者都選擇了使用vdom。Vue借鑑了一個虛擬dom的庫snabbdom,h函式就是來建立虛擬dom的。

var vnode= h(`div#div1`,{},[h(`span`,{},`Hello`),h(`span`,{},`world`)]) // h函式接收三個引數:標籤,屬性,標籤包含的children複製程式碼

Diff實現過程

patch(container,vnode)和patch(vnode,newVnode)複製程式碼

首次渲染的時候使用前一個path進行render(createElement),data屬性發生變化時使用後一個path進行rerender(updateChildren)

 

Vue資料響應式

Vue裡面初始化時定義在data裡面的屬性會被重新定義(代理)到vm物件上,使用Object.defineProperty,所以我們才可以使用this(指向vm)訪問定義在data裡面的屬性。首次渲染以後顯示頁面,並且這裡會繫結依賴,為啥是這裡才繫結呢?因為只針對在頁面上顯示的屬性(get時)進行set監聽,如果沒有使用過,那麼也就沒必要監聽set了,資料發生變化時,set裡面會呼叫updateComponent方法,裡面呼叫vm._update方法,重新執行vm._render方法,裡面執行patch(prevVnode,newVnode)提高效能。

 

React資料響應式

首次渲染ReactDOM.render時,會觸發patch(container,vnode)。其次就是在呼叫setState時會觸發patch(vnode,newVnode)。注意下setState是非同步的。每個React元件都有一個renderComponent方法,setState會執行該方法重新渲染render,render函式會返回新的newVnode,然後跟prevVNode比較(Diff)執行對應的patch(prevVNode,newVnode).

 

為什麼setState是非同步的?

無法限制使用者執行setState的次數,沒必要每次都渲染,只需要對最終的一次更改進行渲染,提高效能

 

說說Vue和React區別

Vue是一個mvvm的框架,React是前端元件化框架

Vue使用模板,React使用JSX

Vue通過單檔案元件,擴充套件方法的方式實現元件化; React本身就是元件化的。

所以元件化來講React更徹底

 

React的入門門檻確實要高一些,Vue相對容易一些。但是React更加發揮js的作用,比如屬性(可以是資料,可以是函式),父子元件的互動方式更加單純。Vue需要採用屬性和事件的方式。

我所持的態度

實現專案需求的角度來說,Vue和React都能夠實現,沒有什麼問題。從生態來看,React無疑更加豐富,而且出現一些新的框架常常能夠引起我很多的思考,新的一些思想會衝擊我,從不能接受到慢慢欣賞。同時學習和使用不同的框架能夠相互促進,不建議二者好像只能取其一。就像多學習一門不同的語言,也能夠體驗更豐富的程式設計思想,最終能夠融會貫通,提高自己。

原文釋出時間為:2018年07月02日

原文作者:掘金

本文來源:掘金 如需轉載請聯絡原作者


相關文章