快速搞定前端技术

171 阅读1分钟

前言:希望可以通过这篇文章,能够给你得到帮助。(感谢一键三连),前端小白不断升级打怪中...

HTML

1. 如果理解HTML语义化?

语义化以便于代码可阅读性(让人更容易读懂代码) 搜索引擎,容易分别网页主次关系SEO(让搜索引擎更容易读懂)

2. 默认情况下,哪些HTML标签是块级元素,哪些是内联元素?

  • display:block/table;有div h1 table ul ol p等
  • display:inline/inline-block; 有span img input button等

CSS

布局

1. 盒子模型

#div {

width: 100px

padding: 10px

margin: 10px

border: 1px solid $ccc

}

offsetwidth = (内容宽度+内边距+边框),无外边框

默认是: box-sizing: content-box;

122

设置

box-sizing:border-box

100

2. margin纵向重叠的问题

 p {
       margin-top: 10px;
       margin-bottom: 15px;
   }
   <p>AAA</p>
   <p></p>
   <p></p>
   <p></p>
   <p>BBB></p>

相邻元素的margin-top和margin-bottom会发生重叠 空白内容的

也会重叠 答案:15px

3. margin负值的问题

  • margin-top/margin-left 元素向上,向左移动
  • margin-right负值,右侧元素左移,自身不受影响
  • margin-bottom,下侧元素上移,自身不受影响

4. BFC理解和应用

BFC块级格式化上下文

形成BFC的常见条件:

  • float不是none
  • position是absulute或fixed
  • overflow不是visible
  • dispaly是flex inline-block等

BFC常见应用: 清除浮动

5. float布局的问题,以及clearfix

如何实现圣杯布局和双飞翼布局?

目的:

三栏布局,中间一栏最先加载和渲染(内容最重要) 两侧内容固定,中间内容随着宽度自适应 一般用于PC网页

技术总结:

使用float布局 两侧使用margin负值,以便和中间内容横向重叠 防止中间内容被两侧覆盖,一个用padding一个用margin

圣杯布局: padding

双飞翼布局: margin

手写clearfix?

.clearfix:after{
    content: '';
    display: table;
    clear: both
}
.clearfix {
    *zoom: 1; /*兼容IE低版本 */
}

6. flex画色子

flex实现一个三点的色子?

flex-direction

justify-content // 主轴对齐方式

align-items

flex-wrap // 是否换行

align-self // 交叉轴

定位

absolute relative

7. absolute和relative分别依据什么定位?

  • relative 依据自身定位
  • absolute依据最近一层的定位元素 absolute relative fixed

8. 居中对齐有哪些实现方式?

  • 水平居中 inline元素: text-align: center

block元素: margin: auto

absolute元素: left: 50% + margin-left负值

  • 垂直居中

inline元素:line-height的值等于height值

absolute元素:top: 50% + margin-top负值 前提:知道子元素的高度,宽度

absolute元素: transform:translate(-50%, -50%) 兼容性问题

absolute元素: top, left,bottom, right = 0 + margin: auto

9. line-height的继承问题

写具体数值,如30px,则继承该值

写比例,如2/1.5,则继承该比例 p的font-size*1.5 = 24px

写百分比,如200%,则继承计算出来的值 font-size * line-height百分比 20* 200% = 40px

 body {
    font-size: 20px
    line-height: 200%
  }
p{
    font-zise: 16px
}

p标签的line-height 20*200% = 40px

图文样式

响应式

10. rem是什么?

rem是一个长度单位

px:绝对长度单位,最常用

em:相对长度单位,相对于父元素,不常用

rem:相对长度单位,相对于根元素,常用于响应式布局


html{
    font-size:100px
}
div {
    font-size: 0.16rem
}

响应式布局的常见方案? media-query,根据不同的屏幕宽度设置根元素的font-size rem,基于根元素的相对单位

iphone5或者更小的尺寸 max-width:374px ---- html { font-size: 86px }

iphone6/7/8 和iphone x min-width: 374px and max-width:413px ----html { font-size: 100px }

iphone6p或者更大的尺寸 min-width: 414px ----html { font-size:110px }

body { font-size: 0.16rem; }

rem的弊端:阶梯型

网页视口尺寸

window.screen.height // 屏幕高度

window.innerHeight // 网页视口高度 去头去尾

document.body.clientHeight // body高度

vw/vh

vw 网页视口宽度的1/100

vh 网页视口高度的1/100

vmax取两者最大值;vmin取两者最小值 --- 横屏时

JS

1. typeof能判断哪些类型

识别所有值类型

识别函数 function

判断是否引用类型(不可再细分)Object

2. == ===

3. 值类型和引用类型的区别

值类型: Number String Boolean undefined Symbol

引用类型:null 数组 对象 函数

4. 写手深拷贝

变量类型 引用类型 typeof运算符

深拷贝

5. 类型转换

字符串拼接

==

if语句和逻辑判断

falsely变量

!!0 === false

!!NAN === false

!!null === false

!!undefined === false

!!false === false

6. 原型和原型链

7. class和继承

constructor

属性

方法

extends继承

super父类

扩展 重写

8. 类型判断instanceof

判断引用类型

Object 是所有引用类型的父类

[] instanceof Array // true

[] instanceof Object // true

{} instanceof Object // true

9. 原型

class实际是function实现的

proto

prototype

先在自身寻找属性和方法

找不到则自动去__proto__中寻找

10. 原型链

11. 作用域和闭包

this的不同场景,如何取值?

手写bind函数

实际开发中闭包应用场景?

作用域和自由变量

全局作用域,函数作用域,块级作用域

自由变量:

定义:

  1. 一个变量在当前作用域没有被定义,但被使用了
  2. 向上级作用域,一层一层依次寻找,直到找到为止
  3. 如果到全局作用域都没找到,则报错xx is not defined

闭包:

作用域应用的特殊情况,有两种表现:

函数作为参数被传递

函数作为返回值被返回

函数作为返回值被返回

 function create() {

    const a = 100

    return function() {
        console.log(a)

    }

 }

const fn = create()

const a = 200

fn() // 100

函数作为参数被传递

// 闭包:自由变量的查找,是在函数定义的地方,向上级作用域查找,不是在执行的地方

   function print(fn) {

    ​	const a = 200fn()

    }

    const a = 100

    function fn() {

    ​	console.log(a)

    }

    print(fn) // 100

this:

作为普通函数

使用call apply bind

作为对象方法被调用

在class方法中调用

箭头函数 // 箭头函数的this是取上级作用域的值

this取什么值,是在函数执行的时候决定的,不是在定义的时候决定的

bind:


    Function.prototype.bind2 = function() {

    ​	const args = Array.prototype.slice.call(arguments)

    ​	const t = args.shift() // 数组第一项   args 剩余参数const self = thisreturn function() {

    ​		return self.apply(t, args)

    ​	}

    }

    function fn(a, b) {

    ​    console.log(this)

    ​	console.log(a, b)

    }

    const fn2 = fn.bind2({ a: 2} , 2, 3 )

    fn2() //  { a: 2 }  2   3

闭包应用:

隐藏数据

12. 单线程和异步

同步和异步的区别是什么?

基于JS是单线程语言

异步不会阻塞代码执行

同步会阻塞代码执行

手写Promise加载一张图片

前端使用异步的场景有哪些?

单线程和异步

应用场景

callback hell和promise

JS是单线程语言,只能同时做一件事

浏览器和nodejs已支持JS启动进程,如Web Worker

JS和DOM渲染共用同一个线程,因为JS可修改DOM结构

遇到等待(网络请求,定时任务)

需要异步

回调callback函数形式

应用场景:

网络请求,如ajax图片加载

定时任务,如setTimeout

手写Promise加载一张图片

Promise 解决callback hell问题

  function loadImg(src) {
    return new Promise((resolve, reject) => {

        const img = document.createElement('img')

        img.onload = ()=>{

        resolve(img)

        }

    img.onerror = () => {

        reject(new Error())

        }

        img.src = src

         })

    }

    const url= ''

    const url2 = ''

    loadImg(url).then(img=> {

    ​	console.log(img.width)

    ​	return img

    }).then( img => {

    ​	console.log(img.height)

    ​	return loadImg(url2)

    }).then(img2 =>{

    }).catch(err =>{

    })

13. 异步-进阶

event loop

请描述event loop(事件循环/事件轮询)的机制?

什么是宏任务和微任务,两者有什么区别?

Promise有哪三种状态?如何变化?

async/ await 语法

promise和setTimeout执行顺序?

外加async/await的顺序问题?

14. event loop(事件循环/事件轮询)

JS是单线程运行的

异步要基于回调来实现

event loop就是异步回调的实现原理

JS如何执行?

从前到后,一行一行执行

如果某一行执行报错,则停止下面代码

先把同步代码执行完,再执行异步

1620723935076.png

Event Loop过程:

同步代码,一行一行放在Call Stack执行

遇到异步,会先‘记录’下,等待时机(定时,网络请求等)

时机到,就移到Callback Queue

如Call Stack为空(即同步代码执行完)Event Loop开始工作

轮询查找Callback Queue, 如有则移到到Call Stack执行

然后继续轮询查找(永动机一样)

  • Call Stack:代码执行
  • Web ApIs:处理定时器,异步API
  • Callback Queue:放置待执行的定时器/网络请求返回结果
  • Event Loop 循环,从Callback Queue队列轮询,--》 进入Call Stack 执行

15. DOM事件和event loop

JS是单线程

异步(色图Timeout,ajax等)使用回调,基于event loop

DOM事件也使用回调,基于event loop,但DOM事件不是异步的

16. promise

三种状态

状态的表现和变化

then和catch对状态的影响

三种状态:

pending resolved rejected

pending-》resolved或者rejected

状态是不可逆的

pending状态,不会触发then和catch

resolved状态,会触发then

rejected状态,会触发catch

then和catch改变状态

then正常返回resolved,里面有报错则返回rejected

catch正常返回resolved,里面有报错则返回rejected

  Promise.resolve().then(() =>{
        console.log(1)
    }).catch(() =>{
        console.log(2)
    }).then(() => {
        console.log(3)
    })
    // 1
    // 3

    Promise.resolve().then(() =>{
        console.log(1)
        throw new error('err');
    }).catch(() =>{
        console.log(2)
    }).then(() => {
        console.log(3)
    })
    // 1
    // 2
    // 3

Promise.resolve().then(()  =>{
    console.log(1)
    throw new error('err');
}).catch(() =>{
    console.log(2)
}).catch(() =>{
    console.log(3)
})
// 1
// 2
    ```

```javascript
Promise.reject().then(() =>{
     console.log(1)
 }).catch(() =>{
    console.log(2)
}).then(() => {
   console.log(3)
})
// 2
// 3


Promise.reject().then(() =>{
 console.log(1)
 throw new error('err');
}).catch(() =>{
   console.log(2)
 }).then(() => {
   console.log(3)
})
// 2
// 3

Promise.reject().then(()  =>{
    console.log(1)
    throw new error('err');
}).catch(() =>{
    console.log(2)
}).catch(() =>{
    console.log(3)
})
// 2
(async function() {
    console.log('start')
    const a = await 100;
    console.log('a', a);
    const b = await Promise.resolve(200)
    console.log('b', b)
    const c = await Promise.reject(300) // 报错后面不执行
    console.log('c', c)
    console.log('end')
})()
// start
// a 100
// b 200

17. async/await

异步回调 callback hell

promise then catch链式调用,但也是基于回调函数

async/await 是同步语法编写异步代码,彻底消灭回调函数

18. async/await和Promise的关系

async/await是消灭异地回调的终极武器

但和Promise并不互斥,反而,两者相辅相成

执行async函数,返回的是Promise

await相对于Promise的then

try...catch可捕获异常,代替了Promise的catch

async function fn() {
    return 100
}

(async function() {
    const  a = fn()
    const b = await fn()
    console.log(a)
    console.log(b)
})()

// Promise { 100 }
// 100

19. 异步的本质

async/await是消灭异步回调的终极武器

JS还是单线程,还得是有异步,还得是基于event loop

async/await只是一个语法糖,但这个糖真香!

 async function async1() {

      console.log('async1 start') // 2

      await async2()

      // await 后面,都可以看成callback里的内容,即异步

      // 类似event loop ,setTimeout()

      // setTimeout(function() { console.log('async1 end')})

      // Promise.then(res => {console.log('async2 end')})

      console.log('async1 end') // 5

    }

    async function async2() {

      console.log('async2') // 3

    }

    

    console.log('start') // 1

    async1()

    console.log('end') // 4

打印:

start

async1 start

async2

end

async1 end

async function async1() {

      console.log('async1 start') // 2

      await async2()

      // await 后面,下面三行都可以看成callback里的内容,即异步

      console.log('async1 end') // 5

      await async3()

    // await,下面一行看成callback里的内容

      console.log('async1 end2') // 7

    }

    async function async2() {

      console.log('async2') // 3

    }

    

    async function async3() {

      console.log('async3') // 6

    }

    

    console.log('start') // 1

    async1()

    console.log('end') // 4

打印:

start

async1 start

async2

end

async1 end

async3

async1 end2

20. for...of的使用

for... in(以及forEach for)是常规的同步遍历

for...of常用于异步的遍历

function muti(num) {

  return new Promise(resolve =>{

​    setTimeout(() =>{

​      resolve(num*num)

​    }, 1000)

  })

}


const nums = [1, 2, 3]

nums.forEach(async (i) =>{

  const res = await muti(i)

  console.log(res)

})

一秒钟同时打印 1 4 9

forEach同步执行muti,一秒钟后打印

function muti(num) {
return new Promise(resolve =>{
    setTimeout(() =>{
        resolve(num*num)
    }, 1000)
})
}

const nums = [1, 2, 3]
// nums.forEach(async (i) =>{
//     const res = await muti(i)
//     console.log(res)
// })
!(async function() {
for(let i of nums) {
    const res = await muti(i)
    console.log(res)
}
})()

// 1 4 9
// for of 先执行完再执行下一个

21. 宏任务macroTask和微任务microTask

什么是宏任务,什么是微任务

event loop和DOM渲染

微任务和宏任务的区别

  • 宏任务:setTimeout,setInterval,Ajax, DOM事件

  • 微任务: Promise async/await

微任务执行时机比宏任务要早

console.log(100)
setTimeout(() =>{
    console.log(200)
})

Promise.resolve().then(res =>{
    console.log(300)
})

console.log(400)
// 100 400 300 200

event loop和DOM渲染

JS是单线程的,而且和DOM渲染共用一个线程

JS执行的时候,得留一些时机供DOM渲染

1620786592877.png

每次Call Stack清空(即每次轮询结果),即同步任务执行完

都是DOM重新渲染的机会,DOM结构如有改变则重新渲染

然后再去触发下一次Event Loop

宏任务:DOM渲染后触发,如setTimout

微任务:DOM渲染前触发,如Promise

<div id="content"></div>
    <script>
        let p = document.createElement('p');
        p.innerHTML = '我是p标签';
        document.getElementById('content').append(p);

        // 宏任务:DOM渲染之后
        setTimeout(() =>{
            console.log('length', document.getElementById('content').children.length); // 1
            alert('setTimeout'); // DOM渲染了吗--yes
        })

        // 微任务:DOM渲染之前
        Promise.resolve().then(() =>{
            console.log('length', document.getElementById('content').children.length); // 1
            alert('Promise then'); // DOM渲染了吗? ---No
        })
    </script>

为什么微任务执行更早

1620788871033.png

微任务是ES6语法规定的

宏任务是由浏览器规定的

1620788949811.png

micro task queue 微任务队列

callback queue 宏任务队列

async function async1() {
    console.log('async1 start') // 2
    await async2()
    // await 后面作为回调内容  --微任务
    console.log('async2 end')  // 6
}

async function async2() {
    console.log('async2') // 3
}

console.log('script start') // 1


setTimeout(() =>{ // 宏任务 setTimeout
    console.log('setTimeout') // 8
}, 0)

async1()

// 初始化promise时,传入的函数会被立刻执行
new Promise(function(resolve){
    console.log('promise1')  // 4
    resolve()
}).then(function() { // 微任务
    console.log('promise2') // 7
})

console.log('script end') // 5


// 1-5 同步代码执行完毕(event loop --call stack 被清空)
// 执行微任务
// 尝试触发DOM渲染
// 触发event loop , 执行宏任务

22. 描述event loop机制(可画图)

23. 从JS基础知识到JS Web Api

JS基础知识,规定语法(ECMA 261标准)

JS Web API,网页操作的API(WC标准)-- 添加DOM元素,文字,设置css样式,监听事件,获取浏览器信息

前者是后者的基础,两者结合才能真正实际应用

JS基础知识:

变量的类型和计算

原型和原型链

作用域和闭包

JS Web API:

DOM操作

BOM操作 浏览器上的操作

事件绑定

ajax

存储

24. 存储:

cookie

localStorage

sessionStorage

cookie:

本身用于浏览器和server通讯

被借用到本地存储来

可用document.cookie = ''来修改

缺点:

存储大小,最大4kb

http请求时需要发送到服务端,增加请求数据量

只能用document.cookie=''来存储

localStorage和sessionStorage:

html5专门为存储而设计,最大可存5M

api简单用setTtem,getItem

不会随着http请求被发送出去

localStorage:

数据会永久存储,除非代码或代码删除

sessionStorage:

数据只操作当前会话,浏览器关闭则请求

一般用localStorage会更多一些

25. DOM

vue和react框架应用广泛,封装了DOM操作

但DOM操作一直都会前端工程师的基础,必备知识

只会vue而不懂DOM操作的前端程序员,不会长久

DOM是哪种数据结构

DOM操作的常用API

attr和property的区别

一次性插入多个DOM节点,考虑性能

DOM本质

DOM节点操作

DOM结构操作

DOM性能

26. DOM本质

树形结构

27. DOM节点操作

获取DOM节点

attribute

property: 修改对象属性,不会体现到html结构中

attribute:修改html属性,会改变html结构中

两者都有可能引起DOM重新渲染

const div = document.getElementById('content')
// property
div.style.color = ''

// attribute
div.getAttribute('index')
div.setAttribute('index', '1')

新增/插入节点

获取子元素列表,获取父元素

删除子元素

const div = document.getElementById('content')
const div2 = document.getElementById('content2')
const p = document.createElement('p')
// 插入标签
div.appendChild(p)

// 移动标签
div2.appendChild(p)  // div下p移动动到div2

// 获取父节点
p.parentNode

// 获取子元素
div2.childNodes // 包括文本节点需要筛出掉
div2.childNodes
Array.prototype.slice.call(div2.childNodes).filter(child =>{
return child.nodeType === 1  // 标签节点  
// nodeType === 3 // 文本节点
})

28. DOM性能

DOM操作非常‘昂贵’,避免频繁操作DOM

对DOM查询做缓存

将频繁操作改为一次性操作

    // 不缓存DOM查询结果
for (let i = 0; i < document.getElementsByTagName('p').length; i++){
        // 每次循环,都会计算length,频繁进行DOM查询
    }
    
    // 缓存DOM查询结果
    const pList = document.getElementsByTagName('p');
    const length = pList.length
    for( let i =0; i < length;i++){
        // 缓存length,只进行一次DOM查询
    }
    

// 频繁操作改成一次性操作

const listNode = document.getElementById('list')

// 创建一个文档片段,此时还没有插入到DOM树中

const frag = document.createDocumentFragment()
    
// 执行插入
for(let x = 0;x<10;x++){
const li = document.createElement('li');
    li.innerHTML = 'list item' + x;
    frag.appendChild(li)
}

listNode.appendChild(frag)

29. BOM操作

识别浏览器类型

navigator

screen

location

history

const ua = navigator.useAgent
ua.indexOf('Chrome')

screen.width

loaction.href //网址
loaction.protocal // 协议
loaction.host // 端口号
location.hostname // 
loaction.search
loaction.hash
loaction.pathname


history.back()
hitory.forward()

30. 事件

事件绑定

事件冒泡

事件代理

// 事件绑定
function bindEvent(elem, type, fn) {
    elem.addEventListener(type, fn)
}

const a = document.getElementById('a')
bindEvent(a, 'click', e => {
    e.preventDefault() // 阻止默认行为
    alert('clicked')
})
// 事件冒泡
// 事件绑定
function bindEvent(elem, type, fn) {
    elem.addEventListener(type, fn)
}

const a = document.getElementById('a')
bindEvent(a, 'click', e => {
e.stopProgation() // 阻止默认行为
    alert('clicked')

})

事件冒泡的原理:

基于DOM树形结构

事件会顺着触发元素往上冒泡

应用场景:代理

// 事件代理
// 事件绑定在父级标签,默认行为
const btn = document.getElementById('btn')
bindEvent(btn, 'click','a',  function(event) {
    event.preventDefault()
    alert(this.innerHTML)
})

function bindEvent(elem, type,selector, fn) {
    if (fn == null) {
        fn = selector
        selector = null
    }
    elem.addEventListener(type, event =>{
        const target = event.target
        if (selector) {
            // 代理绑定
            if (target.matchs(selector)) {
                fn.call(target, event)
            }
        } else {
            // 普通绑定
            fn.call(target, event)
        }
    })
}

31. http

http常见状态码

http常见headers

Resrful API

http缓存机制

http状态码

1xx 服务器收到请求

2xx请求成功, 如200

3xx重定向, 如302

4xx客户端错误, 如404

5xx服务端错误,如500

301永久重定向,浏览器是永久的老地址不用了,直接访问返回的重定向地址

302临时重定向, 浏览器还是访问老地址

304资源未被修改

403没有权限

504网关超时

methods

get 获取数据

post 新建数据

patch/put 更新数据

delete 删除数据

Restful API

传统API设计: 把每个url当做一个功能

Restful API设计:把每个url当做一个唯一的资源

尽量不用url参数

用method表示操作类型

传统API设计:/api/list?pageIndex = 2

Restful API设计:/api/list/2

http常见headers

request headers

Accept 浏览器可接收的数据格式

Accept-Encoding浏览器可接收的压缩算法

Accept_Languange浏览器可接收的语言,如zh-CN

Connection: keep-alive一次TCP连续重复使用

cookie:同域浏览器自动携带

Host:域名

User-Agent(UA)浏览器信息

Content-type发送数据的格式:如application/json

response headers:

Content-type: 返回数据的格式

Content-length:返回数据的大小

Content-encoding:返回数据的压缩算法:肉gzip

Set-Cookie:设置cookie

header自定义header

缓存相关的header

Cache-Control Expires

Last-Modified IF-Modified-Since

Etag If-None_match

32. http缓存

http缓存策略(强制缓存+协商缓存)

什么是缓存?

为什么需要缓存?

哪些资源可以被缓存?-静态资源(js css img)

http缓存:强制缓存

Cache-Control

在Response Headers中

控制强制缓存的逻辑

例如Cache-Control: max-age = 31536000(单位是秒)

1620906815993.png

cache-control的值:

max-age

no-cache

no-store

private

public

Expires

同在Responese Headers

同为控制缓存过期

已被Cache-Control代替

http缓存-协商缓存

服务器端缓存策略

服务器判断客户端资源,是否贺服务器资源一样

一致则返回304,否则返回200和最新的资源

1620907354771.png

资源标识

在Response Headers中,有两种:

Last-Modified资源的最后修改时间

Etag资源的唯一标识(一个字符串,类似人类的指纹)

1620907560883.png

1620907796635.png

共存会优先使用Etag

last-Modified只能精确到秒级

如果资源被重复生产,而内容不变,则Etag更精确

1620908012231.png

三种刷新操作:

正常操作:地址栏输入url,跳转链接,前进后退等

手动刷新:F5,点击刷新按钮,右击菜单刷新

强制刷新:ctrl+F5

不同刷新操作,不同的缓存策略

正常操作:强制缓存有效,协商缓存有效

手动刷新:强制缓存失效,协商缓存有效

强制刷新:强制缓存失效,协商缓存失效

33. 开发环境

git

调试工具

抓包

webpack babel

linux常用命令

34. git

git服务端常见的有github coding.net等

git add.

git checkout xxx // 撤销

git commit -m 'xxx'

git push origin master

git pull origin master

git branch // 查分支

git checkout -b xxx // 切新分支

git checkout xxx 切换分支

git fetch // 当前拉所有分支

git merge xxx // 合并当前分支

git diff /git diff xxx    ----修改内容

git status // 查需要提交内容

git log

git stash // 当前改的东西放在一边

git stash pop // 放在一边放出

git show xxx // 提交内容

git config user.name xxx

git config user.email xxx





新建项目

https // 输入用户名,密码

ssh // 需要生成ssh公钥

35. chrome调试工具

36. 抓包

移动端h5页,查看网络请求,需要用工具抓包

windows一般用fiddler

Mac OS一般用charles

手机和电脑连同一个局域网

将手机代理到电脑上

手机浏览网页,即可抓包

查看网络请求

网址代理

https

37. webpack 和babel

ES6模块化,浏览器暂不支持

ES6语法,浏览器并不完全支持

压缩代码,整合代码,以让网页加载更快

38. linux命令

ssh 用户名@IP地址

输入密码

ls // 查看文件夹/文件

ls -a // 查看所有文件

ll // 看列表的形式

clear // 清除

mkdir dir // 创建文件夹

rm -rf dir // 删除文件夹/文件

cd dist/ // 进入目录

../   // 回到上级目录

mv index.html index1.html // 修改文件名

mv index.html  dist/index.html // 移动到dist文件夹下

touch index.js // 新建文件

vim index.js // 新建文件并且打开     点esc键  :w 保存   :q  退出 :q! //强制退出

cat pacakage.json // 查看文件

head package.json // 查看文件头

grep "babel" package.json // 查看关键字

39. 运行环境

运行环境即浏览器(server 有nodejs)

下载网页代码,渲染出页面,期间会执行若干JS

保证代码在浏览器总,高效稳定

网页加载过程

性能优化

安全

从输入url到渲染页面的整个过程

window.onload和DOMContentLoaded的区别

加载资源的形式:

html代码

媒体文件,如图片,视频等

javascript css

加载资源的过程:

DNS解析:域名-》IP地址

浏览器根据IP地址向服务器发起HTTP请求(三次握手)

服务器处理http请求,并返回给浏览器

加载资源的渲染

根据HTML代码生成DOM TREE

根据css代码生成CSSOM

将DOM Tree和CSSOM整合形成Render Tree

根据Render Tree渲染页面

遇到

直至把Render Tree渲染完成

为什么建议把css放在head里?

渲染完发现CSSOM,会重新形成Render Tree,重新渲染,网速卡的情况下会感官不好

放head里,好处,生成DOM Tree和CSSOM整合形成Render Tree,一次性渲染完成

为何把建议js放在body最后?

Render Tree渲染页面,遇到

load:页面的全部资源加载完才会执行,包括图片视频等

DOMContentLoaded: DOM渲染即可执行,此时图片视频还可能没有加载完成

DOMContentLoaded比load好

40. 性能优化

多使用内存缓存或者其他方法

减少CPU计算量,减少网络加载耗时

适用于所有编程的性能优化-空间换时间

怎么优化。从何入手?

让加载更快:

减小资源体积:压缩代码

减少访问次数:合并代码,SSR服务器渲染,缓存

使用更快的网络:CDN

缓存:

静态资源加hash后缀,根据文件内容计算hash

文件内容不变,则hash不变,则url不变

url和文件不变,则会自动触发http缓存机制,则返回304

CDN:

SSR:

服务器渲染:将网页和数据一起加载:

非SSR(前后端分离):先加载网页,再加载数据,再渲染数据

让渲染更快:

CSS放在head,JS放在body下面

尽早开始执行JS,用DOMContentLoadad触发

懒加载(图片懒加载,上滑加载更多)

对DOM查询进行缓存

减少频繁DOM操作,合并到一起插入DOM结构

节流throttle防抖debounce

防抖debounce:

function debounce(fn, delay = 500) {
    // timer是在闭包中
    let timer = null
    return function() {
        if (timer) {
            clearTimeout(timer)
        }
        timer = setTimeout(() =>{
            fn.apply(this, arguments)
            timer = null
        }, delay)
    }
}

节流throttle:

drag事件,频繁触发,很容易卡顿

function throttle(fn, delay = 500) {
    let timer = null
    return function() {
        if (timer) {
            return
        }
        timer = setTimeout(() => {
            fn.apply(this, arguments)
            timer = null
        }, delay)
    }
}
div.addEventListener('drag', throttle(function(e){
    console.log(e)
}))

41. 安全

问题:常见的web前端攻击方式有哪些?

XSS跨站请求攻击:

XSRF跨站请求伪造

XSS攻击:

<script>变为lt;scriptlt;script lt; 不会作为脚本被攻击

xss工具,替换

XSRF:

预防:

使用post接口

增加验证。例如密码,短信验证码,指纹

42. 同源策略

源(origin)就是协议、域名和端口号

地址里面的协议、域名和端口号均相同则属于同源

什么是同源策略? 同源策略是浏览器的一个安全功能,不同源的客户端脚本在没有明确授权的情况下,不能读写对方资源。所以a.com下的js脚本采用ajax读取b.com里面的文件数据是会报错的

不受同源策略限制的:

页面中的链接,重定向以及表单提交是不会受到同源策略限制的。 跨域资源的引入是可以的。但是js不能读写加载的内容。

如嵌入到页面中的<script src="..."></script><img><link><iframe>

43. 跨域的实现形式

www.cnblogs.com/rockmadman/…

44. 轮询、长轮询、长连接、websocket

www.cnblogs.com/huchong/p/8…