前端面試手記

三石流浪記發表於2019-03-10

前言

面試是一個自我提升的過程,希望以下記錄能夠幫助自己在面試中有所收穫。

記錄一

第一家是一個天使輪的公司,面試沒有筆試,令我感到很無奈,面試官貌似不是技術,問了我兩個題目:

  • 手寫一個客戶登入的過程,使用原生js實現。手寫
  • 請問websocket怎麼使用。手寫

第二個題目我沒答上來,因為壓根沒用過。下面是這兩個題目的答案。

<!--第一題-->
var xhr  = new XMLHttpRquest()
xhr.send("GET","API",true)
shr.onreadystatechange = function(){
    if(xhr.readystate === 4){
        if(xhr.status === 200){
            JSON.parse(xhr.responseText)
        }
    }
}

<!--第二題-->
var ws = new websocket('http://128.12.1.2:8080')

ws.onmesage = function(e){
    console.log(e.data)
}

ws.onopen = function(e){
    ws.send('hello')
    
    if(ws.bufferedAmount  === 0){
        console.log('傳送完畢')
    }
}

ws.onclose = function(e){
  var code = event.code;
  var reason = event.reason;
  var wasClean = event.wasClean;
}


ws.onerror = function(e){
    
} 

複製程式碼

記錄二

第二家是一箇中型的公司,下面是面試過程:

筆試

寫出你熟悉的狀態碼,並寫出含義 (10)

<!--大體分為三類-->
<!--成功-->
200 成功   
201 請求成功並建立了新的連線    
202 已接收 伺服器已經接受請求,但是尚未處理
<!--請求失敗-->
400 錯誤請求
401 未授權 要求驗證身份
403 伺服器拒絕
<!--重定向-->
300 多種選擇
301 永久移動
302 臨時移動
<!--伺服器錯誤-->
500 伺服器程式碼執行出錯
503 伺服器關閉

複製程式碼

使用css3畫出一個扇形

這個題我開始使用border的特性畫出了三角形,然後使用border-raduis 使其一邊變成弧形

width:0px;
border-bottom : 100px solid red;
border-left : 30px solid transparent;
border-right: 30px solid transparent;
border-raduis : 50%
複製程式碼

但是面試官說他想要一個任意角度的扇形 我沒想出來,回來看了一波部落格,感覺這是自己理解出的最簡單的方法·····

<style>
    .r1 {
        position: absolute;
        width: 200px;
        height: 200px;
        border-radius: 50%;
        background-color: yellow;
        clip: rect(0, 100px, 200px, 0);
    }

    .r2 {
        position: absolute;
        width: 200px;
        height: 200px;
        border-radius: 50%;
        background-color: white;
        clip: rect(0, 100px, 200px, 0);
        transform: rotate(40deg);
    }
</style>

<div class="r1"></div>
<div class="r2"></div>
複製程式碼
<!--必須為position:absolute-->
clip:rect(30px 200px 200px 20px)
複製程式碼
描述
shape 設定元素的形狀。唯一合法的形狀值是:rect (top, right, bottom, left)
auto 預設值。不應用任何剪裁。
inherit 規定應該從父元素繼承 clip 屬性的值。

前端面試手記

主要是考閉包和函式引數的傳遞

function test(a,b){
    alert(b)
    return function(c){
        return test(c,a)
    }
}


複製程式碼

主要是考變數提升。

複製程式碼

寫出flex佈局的相關屬性和含義

  1. 怎麼啟用flex佈局

    • display:flex
    • 行內元素可以使用 display:inline-flex
  2. 容器的屬性

    • flex-direction: row | row-reverse | column |column-reverse //主軸的方向
    • flex-wrap: nowrap 預設 | wrap 換行第一行在上面 | wrap-reverse 換行,第一行在下面 // 在專案超過預設軸線排列數量的情況下 (使用百分比) 超出一行的容器,以什麼方式排列
    • flex-flow: <flex-direction> || <flex-wrap> 預設值 row nowrap // 前兩個屬性的綜合
    • justify-content: flex-start| flex-end | center| space-between | space-around // 主軸X軸方向的對其方式
    • align-items: flex-start | flex-end | center | baseline 基於專案裡面的文字的base-line | stretch 上下填滿 //交叉軸Y軸上面的對齊凡是

    必須對父元素設定自由盒屬性display:flex;,並且設定排列方式為橫向排列flex-direction:row;並且設定換行,flex-wrap:wrap;這樣這個屬性的設定才會起作用。

    • align-content:stretch 預設 | flex-start| flex-end | center| space-between | space-around
  3. 專案屬性

    • order:<integer> 預設0目的排序 數值越小越靠前
    • flex-grow:<integer> 預設0及在專案中佔幾份 一般為1
    • flex-shrink: <integer> 專案縮小比例 預設1 在空間不足時,為了使所有專案在一行,數值越大小放嚴重
    • flex-basis: <length> || auto預設為auto 如果設定px 則佔據實際寬度
    • flex:是上面三個值的簡寫 快捷值有auto(1 1 auto) none(0 0 auto)
    • align-self:除了 auto 都和 align-items一樣

以vue或者react為例畫出他們的生命週期圖

前端面試手記

如果需要你轉後端你會考慮使用哪種語言,為什麼?

考樹的遍歷。

估計這個要認真學一下了

    // 還是用自己的蠢方法實現的
    var nodes = [
        { id: 10, title: 'dw10', parentId: 4 },
        { id: 2, title: 'dw2', parentId: 0 },
        { id: 4, title: 'dw4', parentId: 2 },
        { id: 12, title: 'dw12', parentId: 2 },
        { id: 8, title: 'dw8', parentId: 4 },
        { id: 9, title: 'dw8', parentId: 12 }
    ]

    nodes.sort((a, b) => {
        return a.parentId - b.parentId
    })


    function toTree(arr) {
        const root = arr[0]
        _Tree(arr, root)
        return root
    }

    function _Tree(arr, root) {
        for (let i = 0; i < arr.length; i++) {
            if (arr[i].parentId === root.id) {
                if (root.child) {
                    root.child.push(arr[i])
                } else {
                    root.child = [arr[i]]
                }
            }
        }

        var child = root.child
        if (child && child.length !== 0) {
            for (let i = 0; i < child.length; i++) {
                _Tree(arr, child[i])
            }
        }
    }

    toTree(nodes)
複製程式碼

使用es6寫一個工廠模式

自己的理解

class Man{
    constructor(name){
        this.name = name
    }
    
    getName(){
        return this.name
    }
    
    static Factory(name){
        return new Man(name)
    }
}
複製程式碼

怎麼使一個沒有長寬的div水平居中

<!--注意點:一定要在子盒子裡面新增內容,因為子盒子的div本身是沒有寬高的,如果你不加內容,根本無法實現效果-->
<style>
.one {
    position: relative;
    width: 200px;
    height: 200px;
    background-color: rebeccapurple;
}

.two {
    position: absolute;
    top: 50%;
    left: 50%;
    transform: translate(-50%,-50%);
}
</style>
<div class="one">
    <div class="two">wo</div>
</div>


<style>
.one {
    display: table-cell;
    text-align: center;
    vertical-align: middle;
    width: 100px;
    height: 100px;
    background-color: red;
}

.two {
    display: inline-block;
}
</style>
<div class="one">
    <div class="two">wo</div>
</div>

複製程式碼

10. 將'i have a dream' 裡的dream替換成apple,寫出三種方法。

var str = 'i have a dream'

<!--第一種-->
var str1 = str.replace(/d\w+m$/g,'apple')

var index_d = str.indexOf('d')
var arr = str.split('')

<!--第二種-->
var arr2 = arr.slice(0,index_d) // 0 到 d 但是不包括d 不改變原來 返回已被被擷取的目標 arr和str 都有這樣的方法 和substring 的引數一樣 起始位置
var str2 = arr2.concat('apple').join('')

<!--第三種-->
var arr3 = str.split('')
var arr4 = arr3.splice(index_d,5,'apple')   // arr3 =  'dream' 陣列專有 改變原有陣列

var str3 = arr3.join('')
<!--還有好多種...-->
複製程式碼
  • 對string 和 array的所有操作方法進行總結

    string

    • charAt(index) && chartCodeAt(index) 返回指定位置的字元 返回指定位置的字元的unicode編碼
    • substr(startIndex,length) substring(startIndex,endIndex) 擷取的字串不包括endslice() 和substring一樣,但是可以是負數 以上三種不對源字串有影響
    • toUpperCase toLowerCase
    • indexOf indexLastOf()
    • split

    array

    • indexOf()
    • push pop shift unshift
    • splice(index,length,....) 會影響原陣列
    • slice(index,end) 不會影響原陣列
    • forEach((item,index,arr)=>{}) 不產生新陣列,但是arr這個引數可以改變原陣列
    • map((item,index,arr)=>{}) return 可以產生一個新陣列 arr 不可以操控原陣列
    • reduce((prevalue,item,index,arr)=>{},startVaule) 聚合 startValue 是第一次迴圈是prevalue的初始值
    // 統計字串中字元出現的次數
    let str = 'fsadfasdfagagajkgnahjgasdjfajsfjk';
    let strArr = str.split('');
    console.log(strArr);
    let sr = strArr.reduce((preValue, curValue, curIndex, array) => {
        if (!preValue[curValue]) {
            preValue[curValue] = 0;
        }
        preValue[curValue] += 1;
        return preValue;
    }, {})
    console.log(sr);
    複製程式碼
    • flier((item,index,array)=>{ return true}) 過濾
    • sort() 排序
    arr.sort((left,right)=>{
        //升序
        return left-right
        // 降序
        return right-left
    })
    複製程式碼

面試

說一下盒子模型,盒模型會產生哪些問題。

盒子模型會有那些問題:

  • margin上下重合的問題
種類 解決方法
上下兩個div 底部元素產生bfc,使用position:absolute
父子元素div 父級元素加上border:1px solid transparent或者overflow:hidden

能描述一下vue的生命週期中什麼時候掛載的dom樹。

http中的304經歷那些過程。

重定向和轉發的區別。

如果現在要做一個日曆元件你會使用什麼佈局來解決。

操作在短時間內很多次操作vue的資料,vue會怎麼重新整理。

有沒有了解過jquery的原始碼,你對jquery這種操作方式有什麼看法,vue是怎麼解決dom平凡操作的這種問題的。

對自己的職業1-3年內職業規劃有哪些?

解釋一下作用域鏈。

說一下對this的理解。

記錄三

電話面試

解釋一下vue的響應原理,並解釋怎麼從資料更新到檢視層的。

function observer(obj){
    // 遞迴邊界
    if(!obj || typeof obj !== 'object'){
        return
    }

    Object.keys(obj).forEach((item,index,arr)=>{
        defineReactive(obj,item,obj[item])
        observer(obj[item])
    })
}

function defineReactive(data,key,val){
    Object.defineProperty(data,key ,{
        enumerable:true,
        configurale:true,
        get:function(){
            // 需要在這裡新增訂閱者
            return val
        },
        set:function(newValue){
            val = newValue
            console.log('屬性'+key+'被監聽了'+'現在的值為'+newValue)

            // 在這裡通知訂閱者去更新檢視
        }
    })
}


var library = {
    book1: {
        name: ''
    },
    book2: ''
};

observer(library)

library.book1.name = 'vue權威指南'; 
library.book2 = '沒有此書籍';

// 再往下面的東西不想啃了  這裡用到的是 釋出-訂閱者模式
複製程式碼

快取 cookie 頭資訊的控制等等

  • http 頭資訊
請求頭欄位 作用
Cache-control 控制cookie 的快取
Connection 瀏覽器想要的連線方式 比如keep-alive
Date 報文建立報文時間
If-Modified-Since 對應響應頭裡面的 Last-Modofied 控制快取
If-None-Match 配合響應頭ETag使用
Host 請求的伺服器域名
響應頭 作用
Location 客戶端重定向的uri
server 伺服器的名字
ETag 指紋
Last-Modofied 上一次伺服器檔案修改的時間

下面是http請求中cache-conctrol

前端面試手記
響應頭的選項
前端面試手記

怎麼解決父級塌陷,overflow:hidden怎麼產生bfc的,產生bfc的方式還有哪些。

清除浮動

  • 當子元素浮動時,給父元素新增overflow:hidden,按照它的第一個特性,應該將子元素超出的部分截掉,但是因為子元素有浮動,無法裁剪,所有隻能由父元素增加高度去包裹住子元素,使得父元素擁有了高度,而這個高度是跟隨子元素自適應的高度,這樣就把浮動的子元素包含在父元素內了。

怎麼產生bfc?

  • 根元素
  • float的值不為none
  • overflow的值不為visible
  • display的值為inline-block、table-cell、table-caption
  • position的值為absolute或fixed

看到有道友文章中把display:table也認為可以生成BFC,其實這裡的主要原因在於Table會預設生成一個匿名的table-cell,正是這個匿名的table-ccell生成了BFC

有哪些佈局方式。

element UI,antd的響應式佈局是根據什麼原理來的

為什麼css執行順序是從右至左比較快

瀏覽器專門建立了一個反常規思維的從右往左的匹配規則就是為了避免對所有元素進行遍歷 遍歷的節點會變少

瀏覽器的優化 script defer 和async的差別

<script async src="script.js"></script>
複製程式碼

 當瀏覽器遇到 script 標籤時,文件的解析不會停止,其他執行緒將下載指令碼,指令碼下載完成後開始執行指令碼,指令碼執行的過程中文件將停止解析,直到指令碼執行完畢

<script defer src="myscript.js"></script>
複製程式碼

當瀏覽器遇到 script 標籤時,文件的解析不會停止,其他執行緒將下載指令碼,待到文件解析完成,指令碼才會執行。

相關文章