高級Web前端必會面試題知識點,不斷更新中。。。

高級Web前端工程師必會面試題,這裏只是整理一些範圍知識點,並無特別具體的面試題目,只要把這些知識點搞明白了,面試題都不是問題。
文檔持續更新中。。。加油騷年!!javascript

佈局的三種模式

參考:https://www.cnblogs.com/Renyi-Fan/p/12173366.html#_label3css

  • 彈性盒佈局 flex
    盒子是並列的,能夠設置指定寬度,輕鬆實現兩欄,三欄佈局,經典的聖盃佈局和雙飛翼佈局就是經過flex來實現的。
    可是,flexbox 佈局方式對瀏覽器的支持不太友好,有一些兼容性問題,可是,這應該是將來發展的趨勢。html

  • 浮動 float浮動
    float佈局是目前各大網站用的最多的一種佈局方式了。
    經過給元素設置float屬性來實現元素浮動,浮動的元素是脫離文檔流的,可是不脫離文本流。
    特色:
    1) 對自身:a、float元素能夠造成塊,可讓行內元素變成塊元素,也擁有寬和高;b、浮動元素的位置儘可能靠上;c、設置float:left 或 float:right,若是這一行知足不了浮動元素的寬度,則會被擠到下一行。
    2) 對兄弟:a、不影響其餘塊元素的位置;b、影響其餘塊元素的文本
    3) 對父元素:高度塌陷
    高度塌陷:(解決方案)前端

  • 響應式
    最簡單的方式是加上一個 meta 標籤, ,其中 width = device-width 這一句的意思是讓頁面的寬度等於屏幕的寬度。
    rem 是指html的font-size的大小, 根據rem來計算各個元素的寬高,而後在配合media query 就能夠實現自適應
    @media query 語法vue

1  @media screen and (max-width: 360px) {
2       html { font-size: 12px; }
3  }

 

移動端佈局適配設備的方案

參考https://www.cnblogs.com/liuXiaoDi/p/12261100.htmljava

  • rem
    rem 以根元素字體大小做爲參照的佈局方式,能夠實現等比縮放佈局,無論內容是多大的,顯示的內容是同樣的。
  • %
    頁面寬度爲100%,高度固定,當屏幕越大,顯示的內容也就越多。
    控件彈性,圖片等比例縮放,文字流式
1px邊框的解決方案
  • 原理:
    在高分辨率的顯示屏中,像素比爲2或者3,1px邊框看起來比真實的1px邊框看起來更寬
  • 方案
    1. 使用僞類添加transform:元素自己不定義邊框,給僞元素定義一個 1px 邊框,而且根據像素比值(dpr => device-pixel-ratio)設置縮放比例
    當 dpr > 2.5 時設置 scale(0.333),
    當 2.49 > dpr > 1.5 時設置 scale(0.5),
    當 dpr < 1.49 時設置 scale(1)
    2. 圖片 border-image
BFC(Block Formatting Contexts)

文檔:day0220–BFC.note
連接:http://note.youdao.com/noteshare?id=f0a95534319d2cd8f49dbe9b6f5240eb&sub=B77453B2104943B09697AF70C4CE68A5react

  • 概念
    BFC:塊級格式化上下文
  • 觸發條件
    1. 根元素 html
    2. float的值不爲none
    3. overflow的值不爲visible
    4. display的值爲inline-block/table-cell/table-caption/flex/inline-flex
    5. position 的值爲 absolute 或者 fixed
  • 特性
    1. box垂直方向的距離由margin決定,屬於同一個BFC的兩個相鄰box的margin會發生重疊
      解釋margin上下會重疊,以及解決方法的緣由
      解決方法:給第二個box添加一個父元素,而且添加overflow: hidden;屬性,使這兩個box分屬兩個不一樣的BFC,便可解決margin重疊的問題。
    2. 計算BFC高度時,浮動元素也參與計算
      解析高度塌陷 能夠用 overflow: hidden解決
    3. BFC的區域不會與float box發生重疊
    4. BFC內部的box會在垂直方向一個接一個的放置
    5. 每一個元素的margin的左邊會與包含塊border的左邊相接觸,即便存在浮動也會如此
    6. BFC就是頁面上的一個獨立容器,容器裏面的元素不會影響到外面的元素
BootStrap佈局原理
  • Bootstrap 是一個用於快速構建Web應用程序和網站的前端框架,是基於html、css、js。
  • 柵格佈局:
    Bootstrap 內置了一套響應式、移動設備優先的流式柵格系統,會隨着屏幕設備或者視口(Viewport)尺寸的增長,系統會自動分爲最多12列。
    網格系統的實現原理也是很是簡單的,只須要經過定義容器的大小,而後平分12份(也有24,32的,可是12是最多見的),再調整內外邊距,最後結合媒體查詢,就能夠實現了這種柵格佈局系統。
  • 優勢:自適應佈局,友好的移動端佈局
  • 缺點:不兼容IE,須要修改bootstrap的樣式
  • 相關問題:
    • 分辨率:xs(超小屏幕手機 < 780px)、sm(小屏幕平板 >= 780px)、md(中等屏幕桌面顯示器 >= 992px)、lg(大屏幕大桌面顯示器 >= 1200px)
    • bootstrap 柵格還有24格的 要怎麼設置:分別在十二的基礎上嵌套,每一個嵌套一個!
    • container 與 container-fluid 有什麼區別:container是文本居中、container-fluid佔整行
Sass/Less/Stylus/StyledComponents 區別,聯繫,在什麼場景下使用
  • CSS預處理器(Sass/less/stylus):就是一種專門的編程語言,爲css增長一些編程的特性,將css做爲目標生成文件,而後就可使用這種語言進行編程。可讓代碼更加簡潔、適應性更強、可讀性更強、易於代碼的維護。
  • 樣式化組件(StyledComponents):
  • 區別與聯繫:
    1. Sass與Less語法較爲嚴謹,Stylus語法比較散漫,Less上手比較快
    2. Sass和Less相互影響比較大,Sass已經全面兼容css
    3. Sass和Less都有第三方工具提供轉譯,特別是Sass和Compass是絕配
    4. Sass、Less和Stylus都具備變量、做用域、混含、嵌套、繼承、運算符、顏色函數、導入和註釋等基本特性,各自特性實現功能基本相似,只是使用規則有所不一樣
    5. Sass和Stylus具備相似的語言處理能力,好比條件語句、循環語句等,而Less須要經過when等關鍵詞模擬這些功能
  • 使用場景:
    • Sass:在編寫代碼時,須要用到變量、嵌套、混合、導入等高級操做時,能夠更好的組織管理樣式文件,更高效的開發項目。
    • Less:它更適用於皮膚、模板等總體框架固定死的網站製做,好比論壇、空間
    • Stylus:可編程
    • StyledComponents:在React中使用,編寫實際的css代碼來設計組件樣式,不須要組件和樣式之間的映射,建立成功後就是一個React組件

JavaScript 系列

變量對象+做用域鏈+this(執行上下文)
  • 變量對象:若是變量與執行上下文相關,那變量本身應該知道它的數據存儲在哪裏,而且知道如何訪問,這種機制就是變量對象(VO)。
    變量對象是一個與執行上下文相關的特殊對象,它存儲着在上下文中聲明的變量、函數聲明、函數形參等內容。
  • 全局對象:是在進入任何執行上下文以前就已經建立了的對象。
    全局對象只存在一份,它的屬性在程序中任何地方均可以訪問,全局對象的生命週期終止於程序退出那一刻。
  • 做用域鏈與原型鏈:
    • 區別:
      1.做用域鏈是對於變量而言,原型鏈是對於對象的屬性。
      2.做用域鏈頂層是window,原型鏈頂層是Object
    • 聯繫:從鏈表開始查找,直到找到爲止。
  • this指向:取決於被調用的方式
    1. 若是普通的函數調用,非嚴格模式下,this指向window,嚴格模式下,this是undefined
    2. 若是是對象調用的方式,this指向該對象
    3. 若是是call()、apply()或者bind()方式調用,this指向被綁定的對象
    4. 若是是構造函數調用方式,this指向實例化出來的新對象
    5. 若是是箭頭函數,是根據當前的詞法做用域來決定this,具體來講,箭頭函數會繼承外層函數調用的this綁定
閉包
  • 閉包:就是可以讀取其餘函數內部變量的函數
  • 變量的做用域分爲全局變量和局部變量兩種。而js中的函數內部能夠直接讀取全局變量,可是函數外部沒法讀取函數內部的局部變量。若是想要取得函數內部的變量,就要在函數的內部再定義一個函數,將函數做爲返回值返回,就能夠在函數的外部讀取他的內部變量了。
  • 閉包的做用:
    1. 能夠讀取函數內部的變量
    2. 讓這些變量的值始終保存在內存中 => 可能致使內存泄漏
  • 閉包的this指向:外部函數的this指向調用他的對象,內部函數的this指向了全局對象。
原型
  • 原型(__proto__對象屬性):原型爲同一個構造函數new出來的實例對象提供了一個公共的區域來存放共同的屬性和方法。
    js規定,每個函數都有一個prototype對象屬性,指向另外一個對象,prototype的全部屬性和方法,都會被構造函數的實例繼承。這就意味着,咱們能夠把那些不變(公共)的屬性和方法,直接定義在 prototype對象屬性上。prototype就是調用構造函數所建立的那個實例對象的原型。
    prototype可讓全部的對象實例共享它所包含的屬性和方法。也就是說,沒必要再構造函數中定義對象信息,而是能夠直接將這些信息添加到原型中。
  • 爲何要使用原型:能夠節省必定的內存,特別是須要構建多個實例的時候。
  • 原型鏈:實例對象與原型之間的鏈接,叫作原型鏈。
    js在建立對象的時候,都有一個叫作proto的內置屬性,用於指向建立它的函數對象的原型對象prototype。
  • 內部原型(proto)和構造器原型(prototype)
    1. 每一個對象都有一個proto屬性,原型鏈上的對象正是依賴這個屬性連結在一塊兒。
    2. 做爲一個對象,當訪問其中的一個屬性或者方法的時候,若是這個對象中沒有這個方法或屬性,那麼js引擎將會訪問這個對象的proto屬性所指向的上一個對象,並在那個對象中查找指定的方法或屬性,若是不能找到,那就會繼續經過這個對象的proto屬性指向的對象進行向上查找,直到這個鏈表結束。
繼承
  • 前提:提供父類(繼承誰,提供誰的屬性)
  • 分類:
  1. 原型鏈繼承:可讓新實例的原型等於父類的實例
    • 特色:實例可繼承的屬性有:實例的構造函數的屬性、父類構造函數屬性、父類原型的屬性。(新實例不會繼承父類實例的屬性)
    • 缺點:1. 新實例沒法向父類構造函數傳參
      2. 繼承單一
      3. 全部新實例都會共享父類實例的屬性(原型上的屬性是共享的,一個實例修改了原型屬性,另外一個實例的原型屬性也會被修改)
  2. 構造函數繼承:用.call().apply()將父類構造函數引入子類函數(在子類函數中作了父類的複製)
    • 特色:1. 只繼承了父類構造函數的屬性,沒有繼承父類原型的屬性
      2. 解決了原型鏈繼承的缺點
      3. 能夠繼承多個構造函數屬性(call多個)
      4. 在子實例中能夠向父實例傳參
    • 缺點:1. 只能繼承父類構造函數的屬性
      2. 沒法實現構造函數的複用(每次用都要從新調用)
      3. 每一個新實例都有父類構造函數的副本
  3. 組合繼承(原型鏈繼承+構造函數繼承):結合了兩種模式的優勢,傳參和複用
    • 特色:1. 能夠繼承父類原型上的屬性,能夠傳參,可複用
      2. 每一個新實例引入的構造函數屬性是私有的
    • 缺點:調用了兩次父類構造函數(耗內存),子類的構造函數會代替原型上的那個父類構造函數。
  4. 原型式繼承:用一個函數包裝一個對象,而後返回這個函數的調用,這個函數就變成了一個能夠隨意增添屬性的實例或對象,Object.create()就是這個原理
    • 特色:相似於複製一個對象,用函數來包裝
    • 缺點:1. 全部實例都會繼承原型上的屬性
      2. 沒法實現複用(新實例屬性都是後面添加的)
  5. 寄生式繼承:就是給原型式繼承外面套個殼子
    • 特色:沒有建立自定義類型,由於只是套了個殼子返回對象,這個函數就成了建立的新對象。
    • 缺點:沒有用到原型,沒法複用
  6. 寄生組合繼承:(經常使用)修復了組合繼承的問題
    寄生:在函數內返回對象而後調用
    組合:1. 函數的原型等於另外一個實例;2. 在函數中用apply或者call引用另外一個構造函數,可傳參
函數節流和防抖
  • 函數的節流和防抖是優化高頻率執行js代碼的一種手段,js中的一些事件在執行觸發時,會不斷調用 綁定在事件上的回調函數,極大的浪費資源,下降性能。爲了優化體驗,須要對這類事件進行調用次數的限制,此時引入函數節流防抖。
  • 節流(throttle):控制事件發生的頻率,好比控制爲1s發生一次,甚至1分鐘發生一次。
    • 應用場景:
      1. scroll事件,滾動監聽事件,每隔一段時間計算一次位置信息等
      2. 瀏覽器的播放事件,每隔1s計算一次進度信息
      3. input框實時搜索併發送請求展現下拉列表,每隔1s發送一次請求。(防抖也能夠)
      4. 高頻點擊提交,表單重複提交
    • 代碼實現:
 1  function throttle(fn, delay) {
 2      let timer;
 3      return function () {
 4          let _this = this;
 5          let args = arguments;
 6          if (timer) {
 7              return;
 8          }
 9          timer = setTimeout(function () {
10              fn.apply(_this, args);
11              timer = null; // 在delay後執行完fn以後清空timer,此時timer爲假,throttle觸發能夠進入計時器
12          }, delay)
13      }
14  }

 

  • 防抖(debounce):防止抖動,以避免把一次事件誤執行屢次,影響性能。
    • 應用場景:
      1. 登陸註冊、發短信等按鈕避免用戶點擊過快,致使屢次發送請求,須要防抖
      2. 調整瀏覽器窗口大小時,resize次數過於頻繁,形成計算過多,此時須要一次到位,須要防抖
      3. 文本編輯器實時保存,無任何更改操做一段時間後自動保存
      4. mousemovemouseover鼠標移動事件防抖
      5. 搜索框搜索輸入,只須要用戶最後一次輸入完,在發送請求防抖
      6. 手機號、郵箱驗證輸入檢測
    • 代碼實現:
 1  function debounce(fn, delay) {
 2             let timer; // 維護一個 timer
 3             return function () {
 4                 let args = arguments;
 5                 if (timer) {
 6                     clearTimeout(timer);
 7                 }
 8                 timer = setTimeout(()=> {
 9                     fn.apply(this, args); // 用apply指向調用debounce的對象,至關於this.fn(args);
10                 }, delay);
11             };
12         }

 

  • 比較:
    • 相同點:
      1. 均可以經過使用 setTimeout 實現
      2. 目的都是爲了下降回調執行頻率,節省計算資源
    • 不一樣點:
      1. 函數防抖:在一段連續操做結束後,處理回調,利用 clearTimeout 和 setTimeout 實現。
      2. 函數節流:在一段連續操做中,每一段時間只執行一次,頻率較高的事件中使用它來提升性能。
      3. 函數防抖關注必定時間連續觸發的事件只在最後執行一次,而函數節流側重於一段時間內只執行一次。
  • 總結:
    防抖:防止抖動,單位時間內事件觸發會被重置,避免事件被誤傷觸發屢次。代碼實現重在清零 clearTimeout。防抖能夠比做等電梯,只要有人進來,就須要再等一會。業務場景有避免觸發按鈕屢次重複提交。
    節流:控制流量,單位時間內事件只能觸發一次。代碼實現重在開鎖關鎖 timer=timeout;timer=null。節流能夠比做紅綠燈,每等一個紅燈時間就能夠過一批。
函數柯里化與反柯里化
  • 柯里化(currying):是一種編程技術,主要就是把本來接收多個參數的函數變成只接受一個參數的函數,而且返回一個接收剩餘參數的函數。
    • 應用場景:
      1. 封裝一些含有環境判斷的方法時,函數柯里化能夠幫助咱們減小判斷條件執行的次數;
      2. 在封裝函數節流、防抖、bind此類返回值是函數的方法時,會用到函數柯里化;
      3. 可用與 vue、react、小程序中的事件傳參,在事件綁定時就執行回調函數傳參,根據傳參值返回真正的事件 callback函數。
  • 反柯里化:擴大方法的適用範圍。
    1. 可讓任何對象擁有其餘對象的方法(改變原來方法上下文)
    2. 增長被反柯里化方法接收的參數

設計模式

設計模式是一套被反覆使用的、多數人知曉的、通過分類編目的、代碼設計經驗的總結。使用設計模式是爲了重用代碼、讓代碼更容易被他人理解、保證代碼可靠性。webpack

  1. 工廠模式
    工廠模式定義了一個用於建立對象的接口,用戶只負責傳遞須要的參數,不須要關心內部的邏輯,隱藏了建立實例的複雜度,最後返回一個實例。
  2. 單例模式
    單例模式是指在內存中只會建立且僅建立一次對象的設計模式。單例模式很經常使用,好比全局緩存、全局狀態管理等,這些只須要一個對象,就可使用單例模式。好比 Redux、Vuex的store。
  3. 觀察者模式(發佈-訂閱模式)
    觀察者模式中通常都須要實現三個接口: subscribe()接收觀察者,使其訂閱;unsubscribe()取消訂閱;fire()觸發事件,通知到全部觀察者。
  4. 裝飾器模式
    裝飾器模式不須要改變已有的接口,它的做用是給對象添加功能。好比 react裏的高階組件。
  5. 適配器模式
    適配器用來解決兩個接口不兼容的問題,不須要改變已有的接口,經過包裝一層的方式實現兩個接口的正常協做。咱們其實常用到適配器模式。好比父組件傳遞給子組件一個屬性,組件內部須要使用 computed計算屬性來作處理,這個過程就用到了適配器模式。
ES6新增API(Proxy, Reflect, Promise, Generator, async, Decorator, Class)
  • Proxy:用於修改某些操做的默認行爲,也能夠理解爲在目標對象以前架設一層攔截,外部全部的訪問都必須先經過這層攔截,所以提供了一種機制,能夠對外部的訪問進行過濾和修改。這個詞的原理爲代理,在這裏能夠表示由它來「代理」某些操做,譯爲「代理器」。web

    • 基本用法:ES6原生提供給了Proxy構造函數,用來生成Proxy實例。
      var proxy = new Proxy(target, handler); 
      Proxy對象的全部用法,都是經過這種形式。不一樣的只是handle參數的寫法。其中new Proxy用來生成Proxy實例,target是表示所要攔截的對象,handle是用來定製攔截行爲的對象。
  • Reflect:是一個全局的普通的對象,原型是Object。面試

    • 目的:
      1. 將Object對象的一些屬於語言內部的方法放到Reflect對象上,從Reflect上能拿到語言內部的方法。如:Object.defineProperty;
      2. 修改某些object方法返回的結果。如:Object.defineProperty(obj, name, desc)在沒法定義屬性的時候會報錯,而Reflect.defineProperty(obj, name, desc)則會返回false;
      3. 讓Object的操做都變成函數行爲。如object的命令式:name in obj和delete obj[name] 則與 Reflect.has(obj, name)、Reflect.deleteProperty(obj, name)相等;
      4. Reflect對象的方法與Proxy對象的方法一一對應,只要proxy對象上有的方法reflect也能找到。
  • Promise:是一個專門解決異步回調地獄的問題。

    • 所謂 Promise,簡單點來講就是一個容器,裏面保存着某個將來纔會結束的事件(一般是一個異步操做)的結果,promise是一個對象,它能夠從獲取異步操做的消息,promise提供了統一的API,各類異步操做均可以用一樣的方法進行處理。

      • 特色:
      1. 對象的狀態不受外界影響,promise對象表明一個異步操做,有三種狀態:pending(進行中)、fulfilled(已成功)、rejected(失敗)。只有異步操做的結果,能夠決定當前是哪種狀態,任何其餘操做都沒法改變這個狀態。
      2. 一旦狀態改變就不會再變,任什麼時候候均可以獲得這個結果,promise對象的狀態改變,只有兩種可能:從 pending => fulfilled,從pending => rejected。這個就稱爲 resolved。若是改變已經發生,再對 promise 對象添加回調函數,也會當即獲得這個結果,這與事件(event)徹底不一樣,事件的特色是:若是你錯過了它,再去監聽是得不到結果的。
      • 用法:
      1. Promise 是一個構造函數,這個構造函數有兩個參數,分別是 resolve(成功以後的回調函數)和 reject(失敗以後的回調函數)
        由於 Promise 表示的是一個異步操做,每當咱們 new 一個 promise 實例,就表示一個具體的異步操做,那麼這個異步操做的結果就只能有兩種狀態:成功/失敗,二者都須要回調函數 resolve/reject返回。因此內部拿到操做結果後,沒法使用 return 把操做結果返回給調用者,這個時候只能用回調函數的形式來吧成功或者失敗的結果返回給調用者。
      2. promise 實例生成之後,能夠用 then方法分別指定 resolved 狀態和 rejected 狀態的回調函數,then方法能夠接收兩個回調函數做爲參數,第一個回調函數是 promise 對象的狀態變成 resolved 時調用,第二個回調函數是 promise 對象的狀態變爲 rejected 時調用。第二個回調函數是可選的,這兩個函數都接受 promise 對象傳出的值做爲參數。
  • Generator:與日常的函數不一樣,它能夠理解爲是一個分佈執行的函數,返回值是一個遍歷器。

    • 用法:
      1. 外部能夠經過next(),thow()和return()調用,只是調用的形式不一樣。
      2. 在應用方面主要是異步調用,不一樣於之前的回調函數和Promise(Promise算是對回調函數解決嵌套繁瑣問題提出的)
      3. 它在每個yield中部署本身的異步操做,等到須要執行的時候再調用。
      4. generator函數和Ajax能夠一塊兒進行同步操做。
      5. 它的分佈執行的特性決定了它對耗時大的多步操做有很大的改進(generator若是你不執行,那以後的程序系統不會編譯)。
      6. 部署Iterator接口:generator函數能夠再任何對象上部署Iterator接口。
  • async/await:回調地獄的終極解決方案,使用它能夠把異步代碼寫的看起來像同步代碼。

    • await 是一個函數中的關鍵字,要求函數必須是 async 聲明的函數。當 await 中的方法執行完畢或者返回後執行後續代碼。
  • Decorator:修飾器,是一個函數,用來修飾類的行爲。不過目前主流瀏覽器都沒有很好的支持,咱們須要用babel來轉換爲瀏覽器能識別的語言。

    • 裝飾器在javascript 中僅僅能夠修飾類和屬性,不能修飾函數。
    • 裝飾器對類的行爲的改變,是表明編譯時發生的,而不是在運行時。
    • 裝飾器能在編譯階段運行代碼。
    • 裝飾器是經典的AOP模式的一種實現方式。
    • 執行順序:同一處的多個裝飾器是按照洋蔥模型,由外到內進入,再由內到外執行。
  • Class:類,經過class關鍵字能夠定義類。

    • class 關鍵字的出現使得其在對象寫法上更加清晰,更像是一種面向對象的語言。
    • 注意:
      1. 在類中聲明方法的時候,千萬不要給該方法加上 function 關鍵字
      2. 方法之間不要用逗號分割,不然會報錯
    • 用法:
      1. 類自身指向的就是構造函數,因此能夠認爲 ES6 中的類其實就是構造函數的另外一種寫法。
      2. 類的全部方法都定義在類的prototype屬性上,也能夠經過prototype屬性對類添加方法。
      3. 能夠經過 Object.assign() 來爲對象動態增長方法。
      4. constructor方法是類的構造函數的默認方法,經過new命令生成對象實例時,自動調用該方法。
      5. constructor方法若是沒有顯式定義,會隱式生成一個constructor方法。因此即便你沒有添加構造函數,構造函數也是存在的。constructor方法默認返回實例對象this,可是也能夠指定constructor方法返回一個全新的對象,讓返回的實例對象不是該類的實例。
      6. 類的全部實例共享一個原型對象,他們的原型都是 Person.prototype,因此proto屬性是相等的。
      7. class不存在變量提高,因此須要先定義再使用。
瀏覽器渲染頁面的過程

https://www.jianshu.com/p/b6b42fd3f80e

  • 瀏覽器從服務器那收到的HTML,CSS,JavaScript等相關資源,而後通過一系列處理後渲染出來的web頁面。

  • 過程:

    1. 瀏覽器將獲取的HTML文檔並解析成DOM樹。
    2. 處理CSS標記,構成層疊樣式表模型CSSOM(CSS Object Model)。
    3. 將DOM和CSSOM合併爲渲染樹(rendering tree)將會被建立,表明一系列將被渲染的對象。
    4. 渲染樹的每一個元素包含的內容都是計算過的,它被稱之爲佈局layout。瀏覽器使用一種流式處理的方法,只須要一次pass繪製操做就能夠佈局全部的元素。
    5. 將渲染樹的各個節點繪製到屏幕上,這一步被稱爲繪製painting。

    以上五個步驟並不必定一次性順序完成,好比DOM或CSSOM被修改時,亦或是哪一個過程會重複執行,這樣才能計算出哪些像素須要在屏幕上進行從新渲染。而在實際狀況中,JavaScript和CSS的某些操做每每會屢次修改DOM或者CSSOM。

瀏覽器緩存(強緩存,協商緩存)
  • 緩存:就是一個資源副本,當咱們向服務器請求資源後,會根據狀況將資源copy一份副本存在本地,方便下次讀取。緩存最根本的做用是減小不必的請求,使用緩存能夠減小時長,從而優化用戶體驗,減小流量消耗,減輕服務器的壓力。
  • 強緩存:直接從本地副本比對讀取,不去請求服務器,返回的狀態碼是 200(expires 和 cache-control)
  • 協商緩存:會去服務器比對,若沒改變才直接讀取本地緩存,返回的狀態碼是 304(last-modified 和 etag)
  • 獲取緩存的流程:
    1. 先根據這個資源的 http header 判斷它是否命中強緩存,若是命中,則直接從本地緩存中獲取資源,不會則向服務器請求 資源。
    2. 當強緩存沒有命中時,客戶端會發送請求到服務器,服務器經過另外一些request header驗證這個資源是否命中協商緩存,這個過程成爲http再驗證,若是命中,服務器直接返回請求而不返回資源,而是告訴客戶端之間從緩存中獲取,客戶端收到返回後就直接從客戶端獲取資源。
    3. 強緩存和協商緩存的共同之處在於:若是命中緩存,服務器不會返回資源;區別是:強緩存不發送請求打服務器,可是協商緩存會發送請求到服務器。
    4. 當協商緩存沒有命中時,服務器會返回資源給客戶端。
    5. 當ctrl+F5強制刷新網頁時,直接從服務器加載,跳過強緩存和協商緩存。
    6. 當F5刷新頁面時,跳過強緩存但會檢查協商緩存
瀏覽器端 Event loop

https://segmentfault.com/a/1190000018181334

  • 事件循環(event-loop):主線程從"任務隊列"中讀取執行事件,這個過程是循環不斷的,這個機制被稱爲事件循環。此機制具體以下:主線程會不斷從任務隊列中按順序取任務執行,每執行完一個任務都會檢查microtask隊列是否爲空(執行完一個任務的具體標誌是函數執行棧爲空),若是不爲空則會一次性執行完全部microtask。而後再進入下一個循環去任務隊列中取下一個任務執行。
  • 什麼須要:由於JavaScript是單線程的。單線程就意味着,全部任務須要排隊,前一個任務結束,纔會執行後一個任務。若是前一個任務耗時很長,後一個任務就不得不一直等着。爲了協調事件(event),用戶交互(user interaction),腳本(script),渲染(rendering),網絡(networking)等,用戶代理(user agent)必須使用事件循環(event loops)。

 

webpack 細節
  • webpack中在使用babel插件處理js代碼的時候,爲何使用polyfill,如何使用polyfill?
    • 緣由:由於在使用preset_env 處理js代碼時,沒法將全部的ES6的語法所有轉換成ES5語法,就好比promise、array.from以及實例方法都沒法轉換,這個時候須要加入墊片。
    • 使用:
      1. 在入口文件引入@babel/polyfill ,會污染全局環境
      2. 在配置文件中的entry中寫 ,也會污染全局環境
      3. 能夠配置@babel/preset-env useBuiltIns接收3個參數
      entry:無論代碼 有沒有用到,只要目標瀏覽器不支持的都會引入對應的polyfill;自動引入polyfill模塊;
      usage: 根據代碼的使用狀況,按需引入;自動引入polyfill模塊;
      false:不會自動引入polyfill模塊;
      4. corejs 3.0之後的版本; 若是參數爲entry,則須要在入口文件中引入兩個包
webpack 和 gulp 的區別
  • webpack是一個模塊打包器,強調的是一個前端模塊化方案,更側重模塊打包,咱們能夠把開發中的全部資源都當作是模塊,經過loader和plugin對資源進行處理。
  • gulp是一個前端自動化構建工具,強調的是前端開發的工做流程,能夠經過配置一系列的task,第一task處理的事情(如代碼壓縮,合併,編譯以及瀏覽器實時更新等)。而後定義這些執行順序,來讓glup執行這些task,從而構建項目的整個開發流程。自動化構建工具並不能把全部的模塊打包到一塊兒,也不能構建不一樣模塊之間的依賴關係。
webpack 從啓動構建到輸出結果經歷了一系列過程
    1. 解析webpack配置參數,合併從shell傳入和webpack.config.js文件裏配置的參數,生產最後的配置結果。
    2. 註冊全部配置的插件,好讓插件監聽webpack構建生命週期的事件節點,以作出對應的反應。
    3. 從配置的entry入口文件開始解析文件構建AST語法樹,找出每一個文件所依賴的文件,遞歸下去。
    4. 在解析文件遞歸的過程當中根據文件類型和loader配置找出合適的loader用來對文件進行轉換。
    5. 遞歸完後獲得每一個文件的最終結果,根據entry配置生成代碼塊chunk。
    6. 輸出全部chunk到文件系統。

文檔持續更新中。。。每日更新,加油騷年!!

相關文章
相關標籤/搜索