常見vue面試題 2019-06-14

一、對于MVVM的理解?

MVVM 是 Model-View-ViewModel 的縮寫。

Model代表數據模型,也可以在Model中定義數據修改和操作的業務邏輯。

View代表UI 組件,它負責將數據模型轉化成UI 展現出來。

ViewModel監聽模型數據的改變和控制視圖行為、處理用戶交互,簡單理解就是一個同步View 和 Model的對象,連接Model和View。

在MVVM架構下,View 和 Model 之間并沒有直接的聯系,而是通過ViewModel進行交互,Model 和 ViewModel 之間的交互是雙向的, 因此View 數據的變化會同步到Model中,而Model 數據的變化也會立即反應到View 上。

ViewModel通過雙向數據綁定把 View 層和 Model 層連接了起來,而View 和 Model 之間的同步工作完全是自動的,無需人為干涉,因此開發者只需關注業務邏輯,不需要手動操作DOM, 不需要關注數據狀態的同步問題,復雜的數據狀態維護完全由 MVVM 來統一管理。

二、Vue的生命周期

beforeCreate(創建前)? ? 在數據觀測和初始化事件還未開始

created(創建后)? ? 完成數據觀測,屬性和方法的運算,初始化事件,$el屬性還沒有顯示出來

beforeMount(載入前)? ? 在掛載開始之前被調用,相關的render函數首次被調用。實例已完成以下的配置:編譯模板,把data里面的數據和模板生成html。注意此時還沒有掛載html到頁面上。

mounted(載入后)? ? 在el 被新創建的 vm.$el 替換,并掛載到實例上去之后調用。實例已完成以下的配置:用上面編譯好的html內容替換el屬性指向的DOM對象。完成模板中的html渲染到html頁面中。此過程中進行ajax交互。

beforeUpdate(更新前)? ? 在數據更新之前調用,發生在虛擬DOM重新渲染和打補丁之前。可以在該鉤子中進一步地更改狀態,不會觸發附加的重渲染過程。

updated(更新后)? ? 在由于數據更改導致的虛擬DOM重新渲染和打補丁之后調用。調用時,組件DOM已經更新,所以可以執行依賴于DOM的操作。然而在大多數情況下,應該避免在此期間更改狀態,因為這可能會導致更新無限循環。該鉤子在服務器端渲染期間不被調用。

beforeDestroy(銷毀前)? ? 在實例銷毀之前調用。實例仍然完全可用。

destroyed(銷毀后)? ? 在實例銷毀之后調用。調用后,所有的事件監聽器會被移除,所有的子實例也會被銷毀。該鉤子在服務器端渲染期間不被調用。

1.什么是vue生命周期?

答: Vue 實例從創建到銷毀的過程,就是生命周期。從開始創建、初始化數據、編譯模板、掛載Dom→渲染、更新→渲染、銷毀等一系列過程,稱之為 Vue 的生命周期。

2.vue生命周期的作用是什么?

答:它的生命周期中有多個事件鉤子,讓我們在控制整個Vue實例的過程時更容易形成好的邏輯。

3.vue生命周期總共有幾個階段?

答:它可以總共分為8個階段:創建前/后, 載入前/后,更新前/后,銷毀前/銷毀后。

4.第一次頁面加載會觸發哪幾個鉤子?

答:會觸發 下面這幾個beforeCreate, created, beforeMount, mounted 。

5.DOM 渲染在 哪個周期中就已經完成?

答:DOM 渲染在 mounted 中就已經完成了。

三、 Vue實現數據雙向綁定的原理:Object.defineProperty()

vue實現數據雙向綁定主要是:采用數據劫持結合發布者-訂閱者模式的方式,通過Object.defineProperty()來劫持各個屬性的setter,getter,在數據變動時發布消息給訂閱者,觸發相應監聽回調。當把一個普通 Javascript 對象傳給 Vue 實例來作為它的 data 選項時,Vue 將遍歷它的屬性,用 Object.defineProperty 將它們轉為 getter/setter。用戶看不到 getter/setter,但是在內部它們讓 Vue 追蹤依賴,在屬性被訪問和修改時通知變化。

vue的數據雙向綁定

將MVVM作為數據綁定的入口,整合Observer,Compile和Watcher三者,通過Observer來監聽自己的model的數據變化,通過Compile來解析編譯模板指令(vue中是用來解析

{{}}),最終利用watcher搭起observer和Compile之間的通信橋梁,達到數據變化

—>視圖更新;視圖交互變化(input)—>數據model變更雙向綁定效果。

js實現簡單的雙向綁定

varobj = {}Object.defineProperty(obj,'txt', {get:function(){returnobj? ? ? ? },set:function(newValue){document.getElementById('txt').value = newValuedocument.getElementById('show').innerHTML = newValue? ? ? ? }? ? })document.addEventListener('keyup',function(e){? ? ? ? obj.txt = e.target.value? ? })

四、Vue組件間的參數傳遞

1.父組件與子組件傳值

父組件傳給子組件:子組件通過props方法接受數據;

子組件傳給父組件:$emit方法傳遞參數

2.非父子組件間的數據傳遞,兄弟組件傳值

eventBus,就是創建一個事件中心,相當于中轉站,可以用它來傳遞事件和接收事件。項目比較小時,用這個比較合適。(雖然也有不少人推薦直接用VUEX,具體來說看需求咯。技術只是手段,目的達到才是王道。)

五、Vue的路由實現:hash模式 和 history模式

hash模式:在瀏覽器中符號“#”,#以及#后面的字符稱之為hash,用window.location.hash讀取;

特點:hash雖然在URL中,但不被包括在HTTP請求中;用來指導瀏覽器動作,對服務端安全無用,hash不會重加載頁面。

hash 模式下,僅 hash 符號之前的內容會被包含在請求中,如http://www.xxx.com,因此對于后端來說,即使沒有做到對路由的全覆蓋,也不會返回 404 錯誤。

history模式:history采用HTML5的新特性;且提供了兩個新方法:pushState(),replaceState()可以對瀏覽器歷史記錄棧進行修改,以及popState事件的監聽到狀態變更。

history 模式下,前端的 URL 必須和實際向后端發起請求的 URL 一致,如http://www.xxx.com/items/id。后端如果缺少對 /items/id 的路由處理,將返回 404 錯誤。Vue-Router 官網里如此描述:“不過這種模式要玩好,還需要后臺配置支持……所以呢,你要在服務端增加一個覆蓋所有情況的候選資源:如果 URL 匹配不到任何靜態資源,則應該返回同一個 index.html 頁面,這個頁面就是你 app 依賴的頁面。”

六、Vue與Angular以及React的區別?

(版本在不斷更新,以下的區別有可能不是很正確。我工作中只用到vue,對angular和react不怎么熟)

1.與AngularJS的區別

相同點:

都支持指令:內置指令和自定義指令;都支持過濾器:內置過濾器和自定義過濾器;都支持雙向數據綁定;都不支持低端瀏覽器。

不同點:

AngularJS的學習成本高,比如增加了Dependency Injection特性,而Vue.js本身提供的API都比較簡單、直觀;在性能上,AngularJS依賴對數據做臟檢查,所以Watcher越多越慢;Vue.js使用基于依賴追蹤的觀察并且使用異步隊列更新,所有的數據都是獨立觸發的。

2.與React的區別

相同點:

React采用特殊的JSX語法,Vue.js在組件開發中也推崇編寫.vue特殊文件格式,對文件內容都有一些約定,兩者都需要編譯后使用;中心思想相同:一切都是組件,組件實例之間可以嵌套;都提供合理的鉤子函數,可以讓開發者定制化地去處理需求;都不內置列數AJAX,Route等功能到核心包,而是以插件的方式加載;在組件開發中都支持mixins的特性。

不同點:

React采用的Virtual DOM會對渲染出來的結果做臟檢查;Vue.js在模板中提供了指令,過濾器等,可以非常方便,快捷地操作Virtual DOM。

七、vue路由的鉤子函數

首頁可以控制導航跳轉,beforeEach,afterEach等,一般用于頁面title的修改。一些需要登錄才能調整頁面的重定向功能。

beforeEach主要有3個參數to,from,next:

to:route即將進入的目標路由對象,

from:route當前導航正要離開的路由

next:function一定要調用該方法resolve這個鉤子。執行效果依賴next方法的調用參數。可以控制網頁的跳轉。

八、vuex是什么?怎么使用?哪種功能場景使用它?

只用來讀取的狀態集中放在store中; 改變狀態的方式是提交mutations,這是個同步的事物; 異步邏輯應該封裝在action中。

在main.js引入store,注入。新建了一個目錄store,….. export 。

場景有:單頁應用中,組件之間的狀態、音樂播放、登錄狀態、加入購物車


state

Vuex 使用單一狀態樹,即每個應用將僅僅包含一個store 實例,但單一狀態樹和模塊化并不沖突。存放的數據狀態,不可以直接修改里面的數據。

mutations

mutations定義的方法動態修改Vuex 的 store 中的狀態或數據。

getters

類似vue的計算屬性,主要用來過濾一些數據。

action

actions可以理解為通過將mutations里面處里數據的方法變成可異步的處理數據的方法,簡單的說就是異步操作數據。view 層通過 store.dispath 來分發 action。

conststore = new Vuex.Store({ //store實例state:{count:0},mutations:{? ? ? ? ? ? ? ? increment(state) {state.count++}},actions:{ increment(context) {context.commit('increment')}}})

modules

項目特別復雜的時候,可以讓每一個模塊擁有自己的state、mutation、action、getters,使得結構非常清晰,方便管理。

constmoduleA = {state:{ ... },mutations:{ ... },actions:{ ... },getters:{ ... }}constmoduleB = {state:{ ... },mutations:{ ... },actions:{ ... }}conststore = new Vuex.Store({modules:{a:moduleA,b:moduleB})

九、vue-cli如何新增自定義指令?

1.創建局部指令

varapp =newVue({? ? el:'#app',? ? data: {? ? ? ? },// 創建指令(可以多個)directives: {// 指令名稱dir1: {? ? ? ? ? ? inserted(el) {// 指令中第一個參數是當前使用指令的DOMconsole.log(el);console.log(arguments);// 對DOM進行操作el.style.width ='200px';? ? ? ? ? ? ? ? el.style.height ='200px';? ? ? ? ? ? ? ? el.style.background ='#000';? ? ? ? ? ? }? ? ? ? }? ? }})

2.全局指令

Vue.directive('dir2', {? ? inserted(el) {console.log(el);? ? }})

3.指令的使用

十、vue如何自定義一個過濾器?

html代碼:

{{msg| capitalize }}

JS代碼:

varvm=newVue({? ? el:"#app",? ? data:{? ? ? ? msg:''},? ? filters: {? ? ? capitalize: function (value) {if(!value)return''value=value.toString()returnvalue.charAt(0).toUpperCase() +value.slice(1)? ? ? }? ? }})

全局定義過濾器

Vue.filter('capitalize', function (value) {if(!value)return''value=value.toString()returnvalue.charAt(0).toUpperCase() +value.slice(1)})

過濾器接收表達式的值 (msg) 作為第一個參數。capitalize 過濾器將會收到 msg的值作為第一個參數。

十一、對keep-alive 的了解?

keep-alive是 Vue 內置的一個組件,可以使被包含的組件保留狀態,或避免重新渲染。

在vue 2.1.0 版本之后,keep-alive新加入了兩個屬性: include(包含的組件緩存) 與 exclude(排除的組件不緩存,優先級大于include) 。

使用方法

<!-- 該組件是否緩存取決于include和exclude屬性 -->

參數解釋

include - 字符串或正則表達式,只有名稱匹配的組件會被緩存

exclude - 字符串或正則表達式,任何名稱匹配的組件都不會被緩存

include 和 exclude 的屬性允許組件有條件地緩存。二者都可以用“,”分隔字符串、正則表達式、數組。當使用正則或者是數組時,要記得使用v-bind 。

使用示例

<!-- 逗號分隔字符串,只有組件a與b被緩存。 --><!-- 正則表達式 (需要使用 v-bind,符合匹配規則的都會被緩存) --><!-- Array (需要使用 v-bind,被包含的都會被緩存) -->

十二、一句話就能回答的面試題

1.css只在當前組件起作用

答:在style標簽中寫入scoped即可 例如:

2.v-if 和 v-show 區別

答:v-if按照條件是否渲染,v-show是display的block或none;

3.$route和$router的區別

答:$route是“路由信息對象”,包括path,params,hash,query,fullPath,matched,name等路由信息參數。而$router是“路由實例”對象包括了路由的跳轉方法,鉤子函數等。

4.vue.js的兩個核心是什么?

答:數據驅動、組件系統

5.vue幾種常用的指令

答:v-for 、 v-if 、v-bind、v-on、v-show、v-else

6.vue常用的修飾符?

答:.prevent: 提交事件不再重載頁面;.stop: 阻止單擊事件冒泡;.self: 當事件發生在該元素本身而不是子元素的時候會觸發;.capture: 事件偵聽,事件發生的時候會調用

7.v-on 可以綁定多個方法嗎?

答:可以

8.vue中 key 值的作用?

答:當 Vue.js 用 v-for 正在更新已渲染過的元素列表時,它默認用“就地復用”策略。如果數據項的順序被改變,Vue 將不會移動 DOM 元素來匹配數據項的順序, 而是簡單復用此處每個元素,并且確保它在特定索引下顯示已被渲染過的每個元素。key的作用主要是為了高效的更新虛擬DOM。

9.什么是vue的計算屬性?

答:在模板中放入太多的邏輯會讓模板過重且難以維護,在需要對數據進行復雜處理,且可能多次使用的情況下,盡量采取計算屬性的方式。好處:①使得數據處理結構清晰;②依賴于數據,數據更新,處理結果自動更新;③計算屬性內部this指向vm實例;④在template調用時,直接寫計算屬性名即可;⑤常用的是getter方法,獲取數據,也可以使用set方法改變數據;⑥相較于methods,不管依賴的數據變不變,methods都會重新計算,但是依賴數據不變的時候computed從緩存中獲取,不會重新計算。

10.vue等單頁面應用及其優缺點

答:優點:Vue 的目標是通過盡可能簡單的 API 實現響應的數據綁定和組合的視圖組件,核心是一個響應的數據綁定系統。MVVM、數據驅動、組件化、輕量、簡潔、高效、快速、模塊友好。

缺點:不支持低版本的瀏覽器,最低只支持到IE9;不利于SEO的優化(如果要支持SEO,建議通過服務端來進行渲染組件);第一次加載首頁耗時相對長一些;不可以使用瀏覽器的導航按鈕需要自行實現前進、后退。



1、active-class是哪個組件的屬性?嵌套路由怎么定義?

答:vue-router模塊的router-link組件。

2、怎么定義vue-router的動態路由?怎么獲取傳過來的動態參數??

答:在router目錄下的index.js文件中,對path屬性加上/:id。? 使用router對象的params.id

3、vue-router有哪幾種導航鉤子??? ?

答:三種,一種是全局導航鉤子:router.beforeEach(to,from,next),作用:跳轉前進行判斷攔截。第二種:組件內的鉤子;第三種:單獨路由獨享組件

4、scss是什么?安裝使用的步驟是?有哪幾大特性?

答:預處理css,把css當前函數編寫,定義變量,嵌套。 先裝css-loader、node-loader、sass-loader等加載器模塊,在webpack-base.config.js配置文件中加多一個拓展:extenstion,再加多一個模塊:module里面test、loader

4.1、scss是什么?在vue.cli中的安裝使用步驟是?有哪幾大特性?

答:css的預編譯。

使用步驟:

第一步:用npm 下三個loader(sass-loader、css-loader、node-sass)

第二步:在build目錄找到webpack.base.config.js,在那個extends屬性中加一個拓展.scss

第三步:還是在同一個文件,配置一個module屬性

第四步:然后在組件的style標簽加上lang屬性 ,例如:lang=”scss”

有哪幾大特性:

1、可以用變量,例如($變量名稱=值);

2、可以用混合器,例如()

3、可以嵌套

5、mint-ui是什么?怎么使用?說出至少三個組件使用方法?

答:基于vue的前端組件庫。npm安裝,然后import樣式和js,vue.use(mintUi)全局引入。在單個組件局部引入:import {Toast} from ‘mint-ui’。組件一:Toast(‘登錄成功’);組件二:mint-header;組件三:mint-swiper

6、v-model是什么?怎么使用? vue中標簽怎么綁定事件?

答:可以實現雙向綁定,指令(v-class、v-for、v-if、v-show、v-on)。vue的model層的data屬性。綁定事件:

7、axios是什么?怎么使用?描述使用它實現登錄功能的流程?

答:請求后臺資源的模塊。npm install axios

-S裝好,然后發送的是跨域,需在配置文件中config/index.js進行設置。后臺如果是Tp5則定義一個資源路由。js中使用import進來,然后.get或.post。返回在.then函數中如果成功,失敗則是在.catch函數中


8、axios+tp5進階中,調用axios.post(‘api/user’)是進行的什么操作?axios.put(‘api/user/8′)呢?

答:跨域,添加用戶操作,更新操作。

9、什么是RESTful API?怎么使用?

答:是一個api的標準,無狀態請求。請求的路由地址是固定的,如果是tp5則先路由配置中把資源路由配置好。標準有:.post .put .delete

10、vuex是什么?怎么使用?哪種功能場景使用它?

答:vue框架中狀態管理。在main.js引入store,注入。新建了一個目錄store,….. export 。場景有:單頁應用中,組件之間的狀態。音樂播放、登錄狀態、加入購物車

11、mvvm框架是什么?它和其它框架(jquery)的區別是什么?哪些場景適合?

答:一個model+view+viewModel框架,數據模型model,viewModel連接兩個

區別:vue數據驅動,通過數據來顯示視圖層而不是節點操作。

場景:數據操作比較多的場景,更加便捷

12、自定義指令(v-check、v-focus)的方法有哪些?它有哪些鉤子函數?還有哪些鉤子函數參數?

答:全局定義指令:在vue對象的directive方法里面有兩個參數,一個是指令名稱,另外一個是函數。組件內定義指令:directives

鉤子函數:bind(綁定事件觸發)、inserted(節點插入的時候觸發)、update(組件內相關更新)

鉤子函數參數:el、binding

13、說出至少4種vue當中的指令和它的用法?

答:v-if:判斷是否隱藏;v-for:數據循環出來;v-bind:class:綁定一個屬性;v-model:實現雙向綁定

14、vue-router是什么?它有哪些組件?

答:vue用來寫路由一個插件。router-link、router-view

15、導航鉤子有哪些?它們有哪些參數?

答:導航鉤子有:a/全局鉤子和組件內獨享的鉤子。b/beforeRouteEnter、afterEnter、beforeRouterUpdate、beforeRouteLeave

參數:有to(去的那個路由)、from(離開的路由)、next(一定要用這個函數才能去到下一個路由,如果不用就攔截)最常用就這幾種

16、Vue的雙向數據綁定原理是什么?

答:vue.js 是采用數據劫持結合發布者-訂閱者模式的方式,通過Object.defineProperty()來劫持各個屬性的setter,getter,在數據變動時發布消息給訂閱者,觸發相應的監聽回調。

具體步驟:

第一步:需要observe的數據對象進行遞歸遍歷,包括子屬性對象的屬性,都加上setter和getter

這樣的話,給這個對象的某個值賦值,就會觸發setter,那么就能監聽到了數據變化

第二步:compile解析模板指令,將模板中的變量替換成數據,然后初始化渲染頁面視圖,并將每個指令對應的節點綁定更新函數,添加監聽數據的訂閱者,一旦數據有變動,收到通知,更新視圖

第三步:Watcher訂閱者是Observer和Compile之間通信的橋梁,主要做的事情是:

1、在自身實例化時往屬性訂閱器(dep)里面添加自己

2、自身必須有一個update()方法

3、待屬性變動dep.notice()通知時,能調用自身的update()方法,并觸發Compile中綁定的回調,則功成身退。

第四步:MVVM作為數據綁定的入口,整合Observer、Compile和Watcher三者,通過Observer來監聽自己的model數據變化,通過Compile來解析編譯模板指令,最終利用Watcher搭起Observer和Compile之間的通信橋梁,達到數據變化 -> 視圖更新;視圖交互變化(input) -> 數據model變更的雙向綁定效果。

ps:16題答案同樣適合”vue data是怎么實現的?”此面試題

17、請詳細說下你對vue生命周期的理解?

答:總共分為8個階段創建前/后,載入前/后,更新前/后,銷毀前/后。

創建前/后:在beforeCreated階段,vue實例的掛載元素$el和數據對象data都為undefined,還未初始化。在created階段,vue實例的數據對象data有了,$el還沒有。

載入前/后:在beforeMount階段,vue實例的$el和data都初始化了,但還是掛載之前為虛擬的dom節點,data.message還未替換。在mounted階段,vue實例掛載完成,data.message成功渲染。

更新前/后:當data變化時,會觸發beforeUpdate和updated方法。

銷毀前/后:在執行destroy方法后,對data的改變不會再觸發周期函數,說明此時vue實例已經解除了事件監聽以及和dom的綁定,但是dom結構依然存在

18、請說下封裝?vue?組件的過程?

答:首先,組件可以提升整個項目的開發效率。能夠把頁面抽象成多個相對獨立的模塊,解決了我們傳統項目開發:效率低難維護復用性等問題。

然后,使用Vue.extend方法創建一個組件,然后使用Vue.component方法注冊組件。子組件需要數據,可以在props中接受定義。而子組件修改好數據后,想把數據傳遞給父組件。可以采用emit方法。

19、你是怎么認識vuex的?

答:vuex可以理解為一種開發模式或框架。比如PHP有thinkphp,java有spring等。

通過狀態(數據源)集中管理驅動組件的變化(好比spring的IOC容器對bean進行集中管理)。

應用級的狀態集中放在store中; 改變狀態的方式是提交mutations,這是個同步的事物; 異步邏輯應該封裝在action中。

20、vue-loader是什么?使用它的用途有哪些?

答:解析.vue文件的一個加載器,跟template/js/style轉換成js模塊。

用途:js可以寫es6、style樣式可以scss或less、template可以加jade等

21、請說出vue.cli項目中src目錄每個文件夾和文件的用法?

答:assets文件夾是放靜態資源;components是放組件;router是定義路由相關的配置;view視圖;app.vue是一個應用主組件;main.js是入口文件

22、vue.cli中怎樣使用自定義的組件?有遇到過哪些問題嗎?

答:第一步:在components目錄新建你的組件文件(smithButton.vue),script一定要export default {

第二步:在需要用的頁面(組件)中導入:import smithButton from ‘../components/smithButton.vue’

第三步:注入到vue的子組件的components屬性上面,components:{smithButton}

第四步:在template視圖view中使用,?

問題有:smithButton命名,使用的時候則smith-button。

23、聊聊你對Vue.js的template編譯的理解?

答:簡而言之,就是先轉化成AST樹,再得到的render函數返回VNode(Vue的虛擬DOM節點)

詳情步驟:

首先,通過compile編譯器把template編譯成AST語法樹(abstract syntax tree 即

源代碼的抽象語法結構的樹狀表現形式),compile是createCompiler的返回值,createCompiler是用以創建編譯器的。另外compile還負責合并option。

然后,AST會經過generate(將AST語法樹轉化成render funtion字符串的過程)得到render函數,render的返回值是VNode,VNode是Vue的虛擬DOM節點,里面有(標簽名、子節點、文本等等)



VUE面試題

v-show 與 v-if 區別

動態綁定class的方法

計算屬性和 watch 的區別

怎樣理解單向數據流

keep-alive

自定義組件的語法糖 v-model 是怎樣實現的

生命周期

組件通信

路由跳轉

vue-router 有哪幾種導航鉤子

Vue.js 2.x 雙向綁定原理

什么是 MVVM,與 MVC 有什么區別

vuex

this.$nextTick()

vue的原理

理解Vue中的Render渲染函數

slot插槽

v-show 與 v-if 區別

v-hsow和v-if的區別:

v-show是css切換,v-if是完整的銷毀和重新創建。

使用

頻繁切換時用v-show,運行時較少改變時用v-if

v-if=‘false’ v-if是條件渲染,當false的時候不會渲染

綁定 class 的數組用法

對象方法v-bind:class="{'orange': isRipe, 'green': isNotRipe}"

數組方法v-bind:class="[class1, class2]"

行內v-bind:style="{color: color, fontSize: fontSize+'px' }"

計算屬性和 watch 的區別

計算屬性是自動監聽依賴值的變化,從而動態返回內容,監聽是一個過程,在監聽的值變化時,可以觸發一個回調,并做一些事情。

所以區別來源于用法,只是需要動態值,那就用計算屬性;需要知道值的改變后執行業務邏輯,才用 watch,用反或混用雖然可行,但都是不正確的用法。

說出一下區別會加分

computed 是一個對象時,它有哪些選項?

computed 和 methods 有什么區別?

computed 是否能依賴其它組件的數據?

watch 是一個對象時,它有哪些選項?

有get和set兩個選項

methods是一個方法,它可以接受參數,而computed不能,computed是可以緩存的,methods不會。

computed可以依賴其他computed,甚至是其他組件的data

watch 配置

handler

deep 是否深度

immeditate 是否立即執行

總結

當有一些數據需要隨著另外一些數據變化時,建議使用computed。

當有一個通用的響應數據變化的時候,要執行一些業務邏輯或異步操作的時候建議使用watcher

事件修飾符

綁定一個原生的click事件, 加native,

其他事件修飾符

stop prevent? self

組合鍵

click.ctrl.exact 只有ctrl被按下的時候才觸發

組件中 data 為什么是函數

為什么組件中的 data 必須是一個函數,然后 return 一個對象,而 new Vue 實例里,data 可以直接是一個對象?

因為組件是用來復用的,JS 里對象是引用關系,這樣作用域沒有隔離,而 new Vue 的實例,是不會被復用的,因此不存在引用對象的問題。

keep-alive

https://cn.vuejs.org/v2/guide...

自定義組件的語法糖 v-model 是怎樣實現的

https://www.cnblogs.com/attac...

根據官方文檔介紹,v-model本質上就是語法糖,即利用v-model綁定數據后,其實就是既綁定了數據,又添加了一個input事件監聽,如下:


怎樣理解單向數據流

這個概念出現在組件通信。父組件是通過 prop 把數據傳遞到子組件的,但是這個 prop 只能由父組件修改,子組件不能修改,否則會報錯。子組件想修改時,只能通過 $emit 派發一個自定義事件,父組件接收到后,由父組件修改。

一般來說,對于子組件想要更改父組件狀態的場景,可以有兩種方案:

在子組件的 data 中拷貝一份 prop,data 是可以修改的,但 prop 不能:

exportdefault{props: {value:String},? data () {return{currentValue:this.value? ? }? }}

如果是對 prop 值的轉換,可以使用計算屬性:

exportdefault{props: ['size'],? computed: {? ? normalizedSize: function () {? ? ? return this.size.trim().toLowerCase();? ? }? }}

生命周期

創建前后 beforeCreate/created

在beforeCreate 階段,vue實例的掛載元素el和數據對象data都為undefined,還未初始化。在created階段,vue實例的數據對象有了,el還沒有。

載入前后 beforeMount/mounted

在beforeMount階段,vue實例的$el和data都初始化了,但還是掛載之前未虛擬的DOM節點,data尚未替換。

在mounted階段,vue實例掛載完成,data成功渲染。

更新前后 beforeUpdate/updated

當data變化時,會觸發beforeUpdate和updated方法。這兩個不常用,不推薦使用。

銷毀前后beforeDestory/destoryed

beforeDestory是在vue實例銷毀前觸發,一般在這里要通過removeEventListener解除手動綁定的事件。實例銷毀后,觸發的destroyed。

組件間的通信

父子 props/event? $parent/$children? ? ref? provide/inject

兄弟? bus vuex

跨級 bus? vuex provide.inject

路由的跳轉方式

一般有兩種

<router-link to='home'> router-link標簽會渲染為<a>標簽,咋填template中的跳轉都是這種;

另一種是編程是導航? 也就是通過js跳轉? 比如router.push('/home')

Vue.js 2.x 雙向綁定原理

這個問題幾乎是面試必問的,回答也是有深有淺。基本上要知道核心的 API 是通過Object.defineProperty()來劫持各個屬性的 setter / getter,在數據變動時發布消息給訂閱者,觸發相應的監聽回調,這也是為什么 Vue.js 2.x 不支持 IE8 的原因(IE 8 不支持此 API,且無法通過 polyfill 實現)。

https://cn.vuejs.org/v2/guide...

什么是 MVVM,與 MVC 有什么區別

http://www.ruanyifeng.com/blo...

nextTick()

在下次 DOM 更新循環結束之后執行延遲回調。在修改數據之后,立即使用這個回調函數,獲取更新后的 DOM。

// 修改數據vm.msg ='Hello'// DOM 還未更新Vue.nextTick(function(){// DOM 更新})

vue的原理

https://segmentfault.com/a/11...


Vue的模式是m-v-vm模式,即(model-view-modelView),通過modelView作為中間層(即vm的實例),進行雙向數據的綁定與變化。

通過建立虛擬dom樹document.createDocumentFragment(),方法創建虛擬dom樹。

一旦被監測的數據改變,會通過Object.defineProperty定義的數據攔截,截取到數據的變化。

截取到的數據變化,從而通過訂閱——發布者模式,觸發Watcher(觀察者),從而改變虛擬dom的中的具體數據。

最后,通過更新虛擬dom的元素值,從而改變最后渲染dom樹的值,完成雙向綁定

雙向綁定的實現

object.defineProperty 方法會直接在一個對象上定義一個新屬性,或者修改一個對象的現有屬性, 并返回這個對象。語法:Object.defineProperty(obj, prop, descriptor)varobj = {};Object.defineProperty(obj,'hello',{get:function(){//我們在這里攔截到了數據console.log("get方法被調用");? },set:function(newValue){//改變數據的值,攔截下來額console.log("set方法被調用");? }});obj.hello//輸出為“get方法被調用”,輸出了值。obj.hello ='new Hello';//輸出為set方法被調用,修改了新值

我們可以做到數據的雙向綁定:

varobj = {};Object.defineProperty(obj,'hello',{get:function(){//我們在這里攔截到了數據console.log("get方法被調用");? },set:function(newValue){//改變數據的值,攔截下來額console.log("set方法被調用");document.getElementById('test').value = newValue;document.getElementById('test1').innerHTML = newValue;? }});//obj.hello;//obj.hello = '123';document.getElementById('test').addEventListener('input',function(e){? obj.hello = e.target.value;//觸發它的set方法})

理解Vue中的Render渲染函數

https://www.cnblogs.com/tugen...

VUE一般使用template來創建HTML,然后在有的時候,我們需要使用javascript來創建html,這時候我們需要使用render函數。

render函數return一個createElement組件中的子元素存儲在組件實列中$slots.default中。

return createElement('h1', this.title);createElement返回的是包含的信息會告訴VUE頁面上需要渲染什么樣的節點及其子節點。我們稱這樣的節點為虛擬DOM,可以簡寫為VNode。

createElement 參數

{String|Object|Function}

一個HTML標簽字符串,組件選項對象,或者一個返回值類型為String/Object的函數。該參數是? 必須的

子節點

子節點,可選,String 或 Array

Vue.component('anchored-heading', {render:function(createElement){returncreateElement('h'+this.level,// 標簽名稱this.$slots.default// 由子節點構成的數組)? },props: {level: {type:Number,required:true}? }})

slot插槽

http://www.lxweimin.com/p/316...

https://vue.docschina.org/v2/...

單個插槽

當子組件模板只有一個沒有屬性的插槽時,父組件傳入的整個內容片段將插入到插槽所在的 DOM 位置,并替換掉插槽標簽本身。

最初在 <slot> 標簽中的任何內容都被視為備用內容。備用內容在子組件的作用域內編譯,并且只有在宿主元素為空,且沒有要插入的內容時才顯示備用內容。

命名插槽

solt元素可以用一個特殊的特性name來進一步配置如何分發內容。多個插槽可以有不同的名字。

這樣可以將父組件模板中 slot 位置,和子組件 slot 元素產生關聯,便于插槽內容對應傳遞

作用域插槽scoped slots

可以訪問組件內部數據的可復用插槽(reusable slot)

在父級中,具有特殊特性slot-scope的<template>元素必須存在,表示它是作用域插槽的模板。slot-scope 的值將被用作一個臨時變量名,此變量接收從子組件傳遞過來的 prop 對象。

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。