null是對(duì)象原型鏈的終點(diǎn),null == undefined
undefined不是保留字缘眶,它只是全局對(duì)象的一個(gè)屬性嘱根,在低版本 IE 中能被重寫。
undefined 在 ES5 中已經(jīng)是全局對(duì)象的一個(gè)只讀(read-only)屬性了巷懈,它不能被重寫该抒。但是在局部作用域中,還是可以被重寫的顶燕。
void 0 === undefined凑保,用 void 0 代替 undefined 能節(jié)省不少字節(jié)的大小冈爹,事實(shí)上,不少 JavaScript 壓縮工具在壓縮過程中欧引,正是將 undefined 用 void 0 代替掉了频伤。
CSS
position
position: static | relative | absolute | sticky | fixed
static: 該關(guān)鍵字指定元素使用正常的布局行為,即元素在文檔常規(guī)流中當(dāng)前的布局位置芝此。此時(shí) top, right, bottom, left 和 z-index 屬性無效
relative: 相對(duì)定位的元素是在文檔中的正常位置偏移給定的值憋肖,但是不影響其他元素的偏移
absolute: 相對(duì)定位的元素并未脫離文檔流,而絕對(duì)定位的元素則脫離了文檔流癌蓖。在布置文檔流中其它元素時(shí)瞬哼,絕對(duì)定位元素不占據(jù)空間婚肆。絕對(duì)定位元素相對(duì)于最近的非 static 祖先元素定位
sticky: 粘性定位可以被認(rèn)為是相對(duì)定位和固定定位的混合租副。元素在跨越特定閾值前為相對(duì)定位,之后為固定定位
粘性定位常用于定位字母列表的頭部元素较性。標(biāo)示 B 部分開始的頭部元素在滾動(dòng) A 部分時(shí)用僧,始終處于 A 的下方。而在開始滾動(dòng) B 部分時(shí)赞咙,B 的頭部會(huì)固定在屏幕頂部责循,直到所有 B 的項(xiàng)均完成滾動(dòng)后,才被 C 的頭部替代
fixed: 固定定位與絕對(duì)定位相似攀操,但元素的包含塊為 viewport 視口院仿。該定位方式常用于創(chuàng)建在滾動(dòng)屏幕時(shí)仍固定在相同位置的元素
animation transition
animation: name | duration | timing-function | delay | iteration-count | direction | fill-mode | play-state
transition: property name | duration | timing function | delay
transition從:hover延伸出來;animation從flash延伸出來
不同點(diǎn)
觸發(fā)條件不同。transition通常和hover等事件配合使用速和,由事件觸發(fā),強(qiáng)調(diào)過渡歹垫。animation則和gif動(dòng)態(tài)圖差不多,立即播放颠放,多個(gè)關(guān)鍵幀排惨,實(shí)現(xiàn)自由動(dòng)畫。
循環(huán)碰凶。 animation可以設(shè)定循環(huán)次數(shù)暮芭。
精確性。 animation可以設(shè)定每一幀的樣式和時(shí)間欲低。tranistion 只能設(shè)定頭尾辕宏。 animation中可以設(shè)置每一幀需要單獨(dú)變化的樣式屬性,可以通過@keyframe控制當(dāng)前幀屬性砾莱,更靈活瑞筐, transition中所有樣式屬性都要一起變化
與javascript的交互。animation與js的交互不是很緊密恤磷。tranistion和js的結(jié)合更強(qiáng)大面哼。js設(shè)定要變化的樣式野宜,transition負(fù)責(zé)動(dòng)畫效果。
圣杯布局魔策,雙飛翼布局(淘寶UED)
三列布局匈子,中間寬度自適應(yīng),兩邊定寬
中間欄要在瀏覽器中優(yōu)先展示渲染
允許任意列的高度最高
區(qū)別: 圣杯布局是middle+padding闯袒,雙飛翼采用子元素+margin虎敦,最主要的還是負(fù)邊距的使用,以及浮動(dòng)布局和相對(duì)定位
因?yàn)闉g覽器渲染引擎在構(gòu)建和渲染渲染樹是異步的(誰先構(gòu)建好誰先顯示),方便SEO
回流政敢,重繪
瀏覽器使用流式布局模型其徙。瀏覽器會(huì)把HTML解析成DOM,把CSS解析成CSSOM喷户,DOM和CSSOM合并就產(chǎn)生了Render Tree唾那。有了RenderTree,我們就知道了所有節(jié)點(diǎn)的樣式褪尝,然后計(jì)算他們?cè)陧撁嫔系拇笮『臀恢媚只瘢詈蟀压?jié)點(diǎn)繪制到頁面上。由于瀏覽器使用流式布局河哑,對(duì)Render Tree的計(jì)算通常只需要遍歷一次就可以完成避诽,但table及其內(nèi)部元素除外,他們可能需要多次計(jì)算璃谨,通常要花3倍于同等元素的時(shí)間沙庐,這也是為什么要避免使用table布局的原因之一〖淹蹋回流必將引起重繪拱雏,重繪不一定會(huì)引起回流
1.當(dāng)Render Tree中部分或全部元素的尺寸、結(jié)構(gòu)容达、或某些屬性發(fā)生改變時(shí)古涧,瀏覽器重新渲染部分或全部文檔的過程稱為回流,如何引發(fā)回流
頁面首次渲染花盐,瀏覽器窗口改變大小羡滑,元素尺寸或位置發(fā)生改變,元素內(nèi)容變化(文字?jǐn)?shù)量或圖片大小等等)算芯,元素字體大小變化柒昏,DOM操作,激活CSS偽類(例如::hover)熙揍,查詢某些屬性或調(diào)用某些方法
scrollTo()职祷,getComputedStyle(),scrollIntoView()、scrollIntoViewIfNeeded()有梆,getBoundingClientRect()
2.當(dāng)頁面中元素樣式的改變并不影響它在文檔流中的位置時(shí)(例如:color是尖、background-color、visibility等)泥耀,瀏覽器會(huì)將新樣式賦予給元素并重新繪制它饺汹,這個(gè)過程稱為重繪
如何避免
1.避免使用table布局。
2.盡可能在DOM樹的最末端改變class
3.避免設(shè)置多層內(nèi)聯(lián)樣式
4.將動(dòng)畫效果應(yīng)用到position屬性為absolute或fixed的元素上痰催。
5.避免使用CSS表達(dá)式(例如:calc())
6.避免頻繁操作樣式兜辞,最好一次性重寫style屬性,或者將樣式列表定義為class并一次性更改class屬性
7.避免頻繁操作DOM夸溶,創(chuàng)建一個(gè)documentFragment逸吵,在它上面應(yīng)用所有DOM操作,最后再把它添加到文檔中
8.先為元素設(shè)置display: none缝裁,操作結(jié)束后再把它顯示出來扫皱。因?yàn)樵赿isplay屬性為none的元素上進(jìn)行的DOM操作不會(huì)引發(fā)回流和重繪
9.避免頻繁讀取會(huì)引發(fā)回流/重繪的屬性,如果確實(shí)需要多次使用压语,就用一個(gè)變量緩存起來
10.對(duì)具有復(fù)雜動(dòng)畫的元素使用絕對(duì)定位啸罢,使它脫離文檔流编检,否則會(huì)引起父元素及后續(xù)元素頻繁回流
居中
1.水平居中
<!--行內(nèi)元素:文本text胎食、圖像img、按鈕超鏈接等 -->
.center {
text-align: center;
}
<div class="center">水平居中</div>
<!--塊級(jí)定寬元素 -->
.center {
width: 200px;
margin: auto;
}
<div class="center">水平居中</div>
<!--塊級(jí)不定寬元素允懂,table -->
.center {
display: table;
margin: auto;
}
<div class="center">水平居中</div>
<!--塊級(jí)不定寬元素厕怜,inline-block -->
.center {
text-align: center;
>div {
display: inline-block;
}
}
<div class="center"><div>inline-block<div></div>
<!--塊級(jí)不定寬元素,flex -->
.center {
text-align: flex;
justify-content: center;
}
<div class="center"><div>flex<div></div>
復(fù)制代碼
2.垂直居中
<!--單行文本 line-height=height或者padding-top=padding-bottom-->
.colCenter {
height: 24px;
line-height: 24px;
}
<div class="colCenter">垂直居中</div>
<!--多行文本蕾总,利用table -->
.colCenter {
width: 200px;
height: 200px;
display: table;
>div {
display: table-cell;
vertical-align: middle;
}
}
<div class="colCenter"><div>垂直居中<div></div>
<!--塊級(jí)元素粥航,flex -->
.colCenter {
width: 200px;
height: 200px;
display: flex;
align-items: center;
}
<div class="colCenter"><div>垂直居中<div></div>
復(fù)制代碼
除此之外,還可以利用padding和margin等計(jì)算居中
塊格式化上下文(Block Formatting Context生百,BFC)
是Web頁面的可視CSS渲染的一部分递雀,是塊盒子的布局過程發(fā)生的區(qū)域,也是浮動(dòng)元素與其他元素交互的區(qū)域蚀浆。觸發(fā)條件如下:
根元素<html>
浮動(dòng)元素(元素的 float 不是 none)
overflow 值不為 visible 的塊元素
display的值為inline-block缀程、table-cell、table-caption
position的值為absolute或fixed
作用:清除浮動(dòng)市俊,浮動(dòng)塌陷杨凑,外邊距塌陷
自適應(yīng)兩欄布局
可以阻止元素被浮動(dòng)元素覆蓋
可以包含浮動(dòng)元素——清除內(nèi)部浮動(dòng)
分屬于不同的BFC時(shí)可以阻止margin重疊
canvas和svg的區(qū)別,適用場(chǎng)景
Canvas提供的功能更原始摆昧,適合像素處理撩满,動(dòng)態(tài)渲染和大數(shù)據(jù)量繪制;Canvas基于像素,提供2D繪制函數(shù)伺帘,是一種HTML元素類型昭躺,依賴于HTML,只能通過腳本繪制圖形
定制型更強(qiáng)伪嫁,可以繪制繪制自己想要的東西
非dom結(jié)構(gòu)形式窍仰,用JavaScript進(jìn)行繪制,涉及到動(dòng)畫性能較高
事件分發(fā)由canvas處理礼殊,繪制的內(nèi)容的事件需要自己做處理
依賴于像素驹吮,無法高效保真,畫布較大時(shí)候性能較低
不支持事件處理器
適合游戲應(yīng)用
SVG功能更完善晶伦,適合靜態(tài)圖片展示碟狞,高保真文檔查看和打印的應(yīng)用場(chǎng)景,不依賴于像素婚陪,無限放大后不會(huì)失真族沃;SVG為矢量,提供一系列圖形元素(Rect, Path, Circle, Line …)泌参,還有完整的動(dòng)畫脆淹,事件機(jī)制,本身就能獨(dú)立使用沽一,也可以嵌入到HTML中
矢量圖盖溺,不依賴于像素,無限放大后不會(huì)失真铣缠。
以dom的形式表示烘嘱,事件綁定由瀏覽器直接分發(fā)到節(jié)點(diǎn)上
dom形式,涉及到動(dòng)畫時(shí)候需要更新dom蝗蛙,性能較低蝇庭。
支持事件處理器
不適合游戲應(yīng)用 P
JS
數(shù)據(jù)類型:number,string,null,boolean,undefined,object(Array,Function,RegExp,Date)
類型判斷:
typeof: 1.基本數(shù)據(jù)類型除了null返回object,其他都正確;2.引用數(shù)據(jù)類型捡硅,除了function返回function哮内,其他都返回object
instanceof: A instanceof B,A是否為B的實(shí)例,instanceof 檢測(cè)的是原型壮韭;例如 []. proto ——》Array.prototype. proto ——》Object.prototype. proto ——》null
constructor: null 和 undefined 是無效的對(duì)象北发,因此是不會(huì)有 constructor 存在的,這兩種類型的數(shù)據(jù)需要通過其他方式來判斷
toString: toString() 是 Object 的原型方法,對(duì)于 Object 對(duì)象泰涂,直接調(diào)用 toString() 就能返回 [object Object] 鲫竞。而對(duì)于其他對(duì)象,則需要通過 call / apply 來調(diào)用才能返回正確的類型信息逼蒙。用法:Object.prototype.toString.call('')
內(nèi)置Symbol接口
原型鏈:
js分為函數(shù)對(duì)象和普通對(duì)象从绘,每個(gè)對(duì)象都有proto屬性,但是只有函數(shù)對(duì)象才有prototype屬性
構(gòu)造函數(shù)的proto都指向Object.prototype, 因?yàn)樵蛯?duì)象本身是普通對(duì)象
function F(){};
F.prototype.__proto__ = Object.prototype;
Array.prtotype.__proto__ = Object.prototype;
Object.prototype.__proto__ = null;
F.__proto__ = Function.prototype;
var f = new F();
f.__proto__ = F.prototype;
復(fù)制代碼
call,apply,bind
改變函數(shù)執(zhí)行時(shí)的上下文,改變函數(shù)運(yùn)行時(shí)的this指向
bind 是創(chuàng)建一個(gè)新的函數(shù)僵井,call,apply會(huì)執(zhí)行函數(shù)
參數(shù)不同
map/set,weakMap/weakSet
Set和Map都可以用來生成新的 Map
// 去重,Set接受數(shù)組或者類數(shù)組為參數(shù)
var arr = new Set([1,2,3,2,4])
[...arr] // [1,2,3,4]
// WeakSet 中的對(duì)象都是弱引用陕截,垃圾回收機(jī)制不考慮 WeakSet 對(duì)該對(duì)象的引用,WeakSet不可遍歷
const a = [[1, 2], [3, 4]];
const ws = new WeakSet(a);
// WeakSet {[1, 2], [3, 4]} 注意批什,是a數(shù)組的成員成為 WeakSet 的成員农曲,而不是a數(shù)組本身。這意味著驻债,數(shù)組的成員只能是對(duì)象乳规。
const map = new Map([
['name', '張三'],
['title', 'Author']
]);
map.set('name','jin');
// WeakMap結(jié)構(gòu)與Map結(jié)構(gòu)類似,也是用于生成鍵值對(duì)的集合
// WeakMap只接受對(duì)象作為鍵名(null除外)合呐,不接受其他類型的值作為鍵名暮的;WeakMap的鍵名所指向的對(duì)象,不計(jì)入垃圾回收機(jī)制淌实,WeakMap 弱引用的只是鍵名冻辩,而不是鍵值
// 基本上,如果你要往對(duì)象上添加數(shù)據(jù)拆祈,又不想干擾垃圾回收機(jī)制恨闪,就可以使用 WeakMap。一個(gè)典型應(yīng)用場(chǎng)景是放坏,在網(wǎng)頁的 DOM 元素上添加數(shù)據(jù)咙咽,就可以使用WeakMap結(jié)構(gòu)。當(dāng)該 DOM 元素被清除轻姿,其所對(duì)應(yīng)的WeakMap記錄就會(huì)自動(dòng)被移除犁珠。
復(fù)制代碼
堆棧:
棧內(nèi)存一般儲(chǔ)存基礎(chǔ)數(shù)據(jù)類型,遵循后進(jìn)先出的原則互亮,大小固定并且有序;堆內(nèi)存一般儲(chǔ)存引用數(shù)據(jù)類型余素,JavaScript不允許直接訪問堆內(nèi)存中的位置豹休,因此當(dāng)我們要訪問堆內(nèi)存中的引用數(shù)據(jù)類型時(shí),實(shí)際上我們首先是從棧中獲取了該對(duì)象的地址引用(或者地址指針)桨吊,然后再?gòu)亩褍?nèi)存中取得我們需要的數(shù)據(jù)
棧:存儲(chǔ)基礎(chǔ)數(shù)據(jù)類型威根;按值訪問;存儲(chǔ)的值大小固定视乐;由系統(tǒng)自動(dòng)分配內(nèi)存空間洛搀;空間小,運(yùn)行效率高佑淀;先進(jìn)后出留美,后進(jìn)先出;棧中的DOM,ajax谎砾,setTimeout會(huì)依次進(jìn)入到隊(duì)列中,當(dāng)棧中代碼執(zhí)行完畢后逢倍,再將隊(duì)列中的事件放到執(zhí)行棧中依次執(zhí)行
堆: 存儲(chǔ)引用數(shù)據(jù)類型;按引用訪問景图;存儲(chǔ)的值大小不定较雕,可動(dòng)態(tài)調(diào)整;主要用來存放對(duì)象挚币;空間大亮蒋,但是運(yùn)行效率相對(duì)較低;無序存儲(chǔ)妆毕,可根據(jù)引用直接獲取
執(zhí)行上下文
全局可執(zhí)行上下文宛蚓,函數(shù)可執(zhí)行上下文拼缝,Eval可執(zhí)行上下文
執(zhí)行棧
當(dāng)程序進(jìn)入執(zhí)行環(huán)境谅辣,將執(zhí)行上下文推入執(zhí)行棧中(入棧)
當(dāng)程序執(zhí)行完成之后,執(zhí)行上下文就會(huì)被銷毀带污,并從棧頂被推出(出棧)
eventloop事件循環(huán)
"主線程"(執(zhí)行棧)和任務(wù)隊(duì)列<先進(jìn)先出>(主要是各種I/O操作)的通信闰蛔,被稱為事件循環(huán)
node環(huán)境 還是 瀏覽器環(huán)境
任務(wù)隊(duì)列(task queue):分為3痕钢,4
宏任務(wù)task(macro-task):script(整體代碼),setTimeout序六,setInterval任连,setImmediate,I/O例诀,UI render
微任務(wù)jobs(micro-task):process.nextTick随抠,Promise,Async/Await(實(shí)際就是promise)繁涂,MutationObserver(html5新特性)
事件循環(huán)機(jī)制:主線程 ->所有微任務(wù) ->宏任務(wù)(先進(jìn)先執(zhí)行拱她,如果里面有微任務(wù),則下一步先執(zhí)行微任務(wù)扔罪,否則繼續(xù)執(zhí)行宏任務(wù))
node 11之后的特性已經(jīng)向?yàn)g覽器看齊了秉沼。兩者最主要的區(qū)別在于瀏覽器中的微任務(wù)是在每個(gè)相應(yīng)的宏任務(wù)中執(zhí)行的,而nodejs中的微任務(wù)是在不同階段之間執(zhí)行的
垃圾回收機(jī)制
1.引用計(jì)數(shù):0引用時(shí)會(huì)被回收矿酵,IE 6, 7 使用引用計(jì)數(shù)方式對(duì) DOM 對(duì)象進(jìn)行垃圾回收唬复。該方式常常造成對(duì)象被循環(huán)引用時(shí)內(nèi)存發(fā)生泄漏
2.標(biāo)記-清除算法:這個(gè)算法把“對(duì)象是否不再需要”簡(jiǎn)化定義為“對(duì)象是否可以獲得”,因?yàn)椤坝辛阋玫膶?duì)象”總是不可獲得的全肮,垃圾回收器將定期從根開始敞咧,找所有從根開始引用的對(duì)象,對(duì)堆內(nèi)存從頭到尾進(jìn)行線性的遍歷辜腺,進(jìn)行標(biāo)記休建,而沒有被標(biāo)記的對(duì)象就被清除
淺拷貝:遍歷對(duì)象賦值乍恐,只能用作基本數(shù)據(jù)類型的拷貝
深拷貝:遞歸淺拷貝
function deepCopy(a,b){
let c = b || {};
for(let i in a){
if(typeof a[i] == 'object'){
c[i] = a[i].constructor === Array ? [] : {};
deepCopy(a[i],c[i]);
}else{
c[i] = a[i];
}
}
return c;
}
var parent = {
name: 'king',
animals: {
dogs: 2,
cat: 1
},
area: ['A','B']
}
var obj = deepCopy(parent,{});
復(fù)制代碼
json序列化和反序列化的缺點(diǎn):
new
Person (){
}
var obj = new Object();
obj.__proto__ = Person.prototype;
Person.call(obj)
復(fù)制代碼
構(gòu)造函數(shù)和class(語法糖)的區(qū)別
類的內(nèi)部所有定義的方法,都是不可枚舉的
類和模塊的內(nèi)部丰包,默認(rèn)就是嚴(yán)格模式(this 實(shí)際指向的是undefined)禁熏,非嚴(yán)格模式指向window,所以不需要使用use strict指定運(yùn)行模式
類不存在變量提升(hoist)
類的方法內(nèi)部如果含有this邑彪,它默認(rèn)指向類的實(shí)例
類的靜態(tài)方法不會(huì)被實(shí)例繼承瞧毙,靜態(tài)方法里的this指的是類,而不是他的實(shí)例
類的繼承extends寄症,在constructor中使用super宙彪,讓this指向當(dāng)前類,等同于Parent.prototype.constructor.call(this)
class Parent {
constructor(name,age) {
this.name = name;
this.age = age;
}
say(){
console.log('hello')
}
}
// 等價(jià)于
function Parent(name,age){
this.name = name;
this.age = age;
}
Parent.prototype.say = function (){
console.log('hello');
}
var child = new Parent('king',12);
復(fù)制代碼
類的數(shù)據(jù)類型就是函數(shù)有巧,類本身就指向構(gòu)造函數(shù)释漆;使用的時(shí)候,也是直接對(duì)類使用new命令篮迎,跟構(gòu)造函數(shù)的用法完全一致男图;Object.assign方法可以很方便地一次向類添加多個(gè)方法;prototype對(duì)象的constructor屬性甜橱,直接指向“類”的本身逊笆,這與 ES5 的行為是一致的;
function和箭頭函數(shù)
箭頭函數(shù)體內(nèi)的this對(duì)象岂傲,就是定義時(shí)所在的對(duì)象难裆,而不是使用時(shí)所在的對(duì)象
不可以當(dāng)作構(gòu)造函數(shù),也就是說镊掖,不可以使用new命令乃戈,否則會(huì)拋出一個(gè)錯(cuò)誤
不可以使用arguments對(duì)象,該對(duì)象在函數(shù)體內(nèi)不存在亩进。如果要用症虑,可以用 rest 參數(shù)代替
箭頭函數(shù)不能用作 Generator 函數(shù)
function可以使this動(dòng)態(tài)使用(比如監(jiān)聽按鈕事件,this就會(huì)動(dòng)態(tài)指向被點(diǎn)擊的按鈕對(duì)象)镐侯,如果函數(shù)體內(nèi)有大量的讀寫操作侦讨,盡量不要使用箭頭函數(shù)
手動(dòng)實(shí)現(xiàn)字符串單詞統(tǒng)計(jì),’sdsdfdewrwescvv’苟翻,統(tǒng)計(jì)各個(gè)出現(xiàn)次數(shù)
var str = 'sdsdfdewrwescvv';
let obj = {};
for (i = 0; i<str.length; i++){
if(obj[str[i]]){
obj[str[i]]++;
}else{
obj[str[i]] = 1;
}
}
console.log(obj);
復(fù)制代碼
promise,generator骗污,async/await 對(duì)比
promise手動(dòng)實(shí)現(xiàn)
1. 設(shè)置三種狀態(tài)崇猫,一但開始不能暫停,且狀態(tài)只能被修改一次需忿,pending诅炉,rejected蜡歹,resolved(fulfilled)
2. 兩個(gè)參數(shù),resolve()涕烧,reject()月而,函數(shù)執(zhí)行之后改變狀態(tài),執(zhí)行的時(shí)候如果傳遞參數(shù)议纯,就是then的參數(shù)
3. 回調(diào)函數(shù)父款,then(resolved,rejected(可選)),返回新promise實(shí)例瞻凤,以便繼續(xù)鏈?zhǔn)秸{(diào)用憨攒,注意是異步操作,可以使用settimeout
4. catch異撤Р危回調(diào)肝集,Promise.prototype.catch()方法是.then(null, rejection)或.then(undefined, rejection)的別名,用于指定發(fā)生錯(cuò)誤時(shí)的回調(diào)函數(shù)蛛壳。
復(fù)制代碼
用async/await實(shí)現(xiàn)promise.all
1. promise.all的參數(shù)數(shù)組里面的promise杏瞻,如果自己定義了catch方法,那么它一旦被rejected衙荐,并不會(huì)觸發(fā)Promise.all()的catch方法
2. 參數(shù)數(shù)組里面的實(shí)例只要有一個(gè)變?yōu)閞ejected捞挥,或者都為fulfilled,就會(huì)調(diào)用回調(diào)函數(shù)
3. async函數(shù)返回的 Promise 對(duì)象赫模,必須等到內(nèi)部所有await命令后面的 Promise 對(duì)象執(zhí)行完树肃,才會(huì)發(fā)生狀態(tài)改變,除非遇到return語句或者拋出錯(cuò)誤瀑罗。也就是說胸嘴,只有async函數(shù)內(nèi)部的異步操作執(zhí)行完,才會(huì)執(zhí)行then方法指定的回調(diào)函數(shù)
復(fù)制代碼
在await之后增加手動(dòng)判斷斩祭,拋出異常
es 6 module和cmd中的模塊require有什么區(qū)別
Require是CommonJS的語法
export后面要跟能夠解構(gòu)的對(duì)象劣像,export 命令規(guī)定的是對(duì)外接口,必須與模塊內(nèi)部變量建立一一對(duì)應(yīng)的關(guān)系
require是動(dòng)態(tài)加載的摧玫,import是編譯的時(shí)候加載的
繼承
原型鏈繼承
function Parent(){
this.color = ['red','yellow']
}
function child() {}
child.prototype = new Parent();
var eg1 = new child();
eg1.color.push('white');
var eg2 = new child();
console.log(eg2) // ["red", "yellow", "white"]
原型鏈方案存在的缺點(diǎn):多個(gè)實(shí)例對(duì)引用類型的操作會(huì)被篡改
復(fù)制代碼
構(gòu)造函數(shù)繼承
function Person(){
this.color = ['red','yellow']
}
Person.prototype.say=function(){
console.log('hi')
}
function child(){
Person.call(this);
}
var eg1 = new child();
eg1.color.push('white');
console.log(eg1.say) // undefined
var eg2 = new child();
console.log(eg2) // ["red", "yellow"]
比前一種更耗內(nèi)存耳奕,影響性能,每次都要執(zhí)行建立Person實(shí)例
不能繼承原型方法
復(fù)制代碼
組合繼承
把前兩種組合一下
function Person(){
this.age = 11;
this.color = ['red','yellow']
}
Person.prototype.say=function(){
console.log('hi')
}
function child(){
Person.call(this);
}
child.prototype = new Parent();
child.prototype.constructor = child;
var eg1 = new child();
eg1同時(shí)繼承child 和person
缺點(diǎn): 子類實(shí)例中會(huì)存在兩份相同的屬性/方法
復(fù)制代碼
原型式繼承
即后來的Object.create內(nèi)置函數(shù)诬像,其原理為
function Person(o){
var child = function(){};
child.prototype = o;
return new child();
}
復(fù)制代碼
但實(shí)際上new具體做了什么操作
var son = new Person();
復(fù)制代碼
當(dāng)這段代碼運(yùn)行的時(shí)候屋群,內(nèi)部實(shí)際上執(zhí)行的是:
// 創(chuàng)建一個(gè)空對(duì)象
var other = new Object();
// 將空對(duì)象的原型賦值為構(gòu)造函數(shù)的原型
other.__proto__ = Person.prototype;
// 改變this指向
Person.call(other);
復(fù)制代碼
緩存 SessionStorage,localStorage坏挠,Cookie
存儲(chǔ)方式
cookie會(huì)數(shù)據(jù)始終在同源http請(qǐng)求中攜帶芍躏,在瀏覽器和服務(wù)器之間來回傳遞
sessionStroage和localStroage僅保存在本地
存儲(chǔ)大小
單個(gè)cookie不能超過4K,很多瀏覽器都限制一個(gè)站點(diǎn)最多保存20個(gè)Cookie
sessionStroage和localStroage可以達(dá)到5M
過期時(shí)間
只在設(shè)置的cookie過期時(shí)間之前有效降狠,即使窗口關(guān)閉或?yàn)g覽器關(guān)閉
sessionStorage,僅在當(dāng)前瀏覽器窗口關(guān)閉之前有效
localStorage:始終有效对竣,窗口或?yàn)g覽器關(guān)閉也一直保存庇楞,本地存儲(chǔ),因此用作持久數(shù)據(jù)
作用域
cookie和localStorage: 在所有同源窗口中都是共享的.只要瀏覽器不關(guān)閉否纬,數(shù)據(jù)仍然存在
sessionStorage:打開多個(gè)相同的URL的Tabs頁面吕晌,會(huì)創(chuàng)建各自的sessionStorage;關(guān)閉對(duì)應(yīng)瀏覽器tab临燃,會(huì)清除對(duì)應(yīng)的sessionStorage
節(jié)流和防抖
節(jié)流: 每隔一段時(shí)間睛驳,只執(zhí)行一次函數(shù)
防抖: 連續(xù)的事件,只需觸發(fā)一次回調(diào)
設(shè)計(jì)模式谬俄,觀察者柏靶,發(fā)布訂閱模式
主要是消息的處理機(jī)制不同,一個(gè)同步一個(gè)異步溃论,而異步的實(shí)現(xiàn)手段是使用MQ屎蜓,類似于Kafka
跨域
同源:協(xié)議+域名+端口都一樣;當(dāng)協(xié)議钥勋、子域名炬转、主域名、端口號(hào)中任意一個(gè)不相同時(shí)算灸,都算作不同域扼劈。不同域之間相互請(qǐng)求資源,就算作“跨域”
如果是協(xié)議和端口造成的跨域問題“前臺(tái)”是無能為力的
跨域并不是請(qǐng)求發(fā)不出去菲驴,請(qǐng)求能發(fā)出去荐吵,服務(wù)端能收到請(qǐng)求并正常返回結(jié)果,只是結(jié)果被瀏覽器攔截了
http
概念:超文本傳輸??協(xié)議(HTTP)是一個(gè)用于傳輸超媒體文檔(例如 HTML)的應(yīng)用層協(xié)議赊瞬。它是為 Web 瀏覽器與 Web 服務(wù)器之間的通信而設(shè)計(jì)的先煎,但也可以用于其他目的。HTTP 遵循經(jīng)典的客戶端-服務(wù)端模型巧涧,客戶端打開一個(gè)連接以發(fā)出請(qǐng)求薯蝎,然后等待它收到服務(wù)器端響應(yīng)。HTTP 是無狀態(tài)協(xié)議谤绳,這意味著服務(wù)器不會(huì)在兩個(gè)請(qǐng)求之間保留任何數(shù)據(jù)(狀態(tài))占锯。該協(xié)議雖然通常基于 TCP/IP 層缩筛,但可以在任何可靠的傳輸層上使用消略;也就是說,不像 UDP瞎抛,它是一個(gè)不會(huì)靜默丟失消息的協(xié)議疑俭。RUDP——作為 UDP 的可靠化升級(jí)版本——是一種合適的替代選擇
http特性:
1.HTTP 是無連接無狀態(tài)的
2.HTTP 一般構(gòu)建于 TCP/IP 協(xié)議之上,默認(rèn)端口號(hào)是 80
3.HTTP 可以分為兩個(gè)部分婿失,即請(qǐng)求和響應(yīng)钞艇。
HTTP各版本特性及區(qū)別
1.http0.9– 單行協(xié)議:請(qǐng)求由單行指令構(gòu)成,以唯一可用方法GET開頭豪硅,其后跟目標(biāo)資源的路徑(一旦連接到服務(wù)器哩照,協(xié)議、服務(wù)器懒浮、端口號(hào)這些都不是必須的);響應(yīng)也極其簡(jiǎn)單的:只包含響應(yīng)文檔本身飘弧。
2.http1.0:協(xié)議版本信息現(xiàn)在會(huì)隨著每個(gè)請(qǐng)求發(fā)送(HTTP/1.0被追加到了GET行);狀態(tài)碼會(huì)在響應(yīng)開始時(shí)發(fā)送;引入了HTTP頭的概念砚著;Content-Type讓請(qǐng)求具備了傳輸除純文本HTML文件以外其他類型文檔的能力
3.http1.1:連接可以復(fù)用次伶,節(jié)省了多次打開TCP連接加載網(wǎng)頁文檔資源的時(shí)間;增加管線化技術(shù)稽穆,允許在第一個(gè)應(yīng)答被完全發(fā)送之前就發(fā)送第二個(gè)請(qǐng)求冠王,以降低通信延遲;支持響應(yīng)分塊舌镶;引入額外的緩存控制機(jī)制柱彻;引入內(nèi)容協(xié)商機(jī)制,包括語言餐胀,編碼哟楷,類型等,并允許客戶端和服務(wù)器之間約定以最合適的內(nèi)容進(jìn)行交換否灾;感謝Host頭卖擅,能夠使不同域名配置在同一個(gè)IP地址的服務(wù)器上
4.http2.0:HTTP/2是二進(jìn)制協(xié)議而不是文本協(xié)議。不再可讀墨技,也不可無障礙的手動(dòng)創(chuàng)建惩阶,改善的優(yōu)化技術(shù)現(xiàn)在可被實(shí)施;這是一個(gè)復(fù)用協(xié)議健提。并行的請(qǐng)求能在同一個(gè)鏈接中處理琳猫,移除了HTTP/1.x中順序和阻塞的約束;壓縮了headers私痹。因?yàn)閔eaders在一系列請(qǐng)求中常常是相似的脐嫂,其移除了重復(fù)和傳輸重復(fù)數(shù)據(jù)的成本;其允許服務(wù)器在客戶端緩存中填充數(shù)據(jù)紊遵,通過一個(gè)叫服務(wù)器推送的機(jī)制來提前請(qǐng)求
5.http3.0: 將棄用TCP協(xié)議账千,改為使用基于UDP協(xié)議的QUIC協(xié)議實(shí)現(xiàn),該協(xié)議旨在使網(wǎng)頁傳輸更快
TCP暗膜,UDP
基于連接與無連接
對(duì)系統(tǒng)資源的要求(TCP較多匀奏,UDP少)
UDP程序結(jié)構(gòu)較簡(jiǎn)單
流模式與數(shù)據(jù)報(bào)模式
TCP保證數(shù)據(jù)正確性,UDP可能丟包学搜;
TCP保證數(shù)據(jù)順序娃善,UDP不保證论衍。
http請(qǐng)求:
HTTP 請(qǐng)求由 3 個(gè)部分構(gòu)成,分別是:狀態(tài)行聚磺,請(qǐng)求頭(Request Header)坯台,請(qǐng)求正文。
HTTP 響應(yīng)由 3 個(gè)部分構(gòu)成瘫寝,分別是:狀態(tài)行蜒蕾,響應(yīng)頭(Response Header),響應(yīng)正文焕阿。
HTTP 響應(yīng)中包含一個(gè)狀態(tài)碼咪啡,用來表示服務(wù)器對(duì)客戶端響應(yīng)的結(jié)果。 狀態(tài)碼一般由3位構(gòu)成:
1xx : 表示請(qǐng)求已經(jīng)接受了暮屡,繼續(xù)處理撤摸。 2xx : 表示請(qǐng)求已經(jīng)處理掉了。 3xx : 重定向栽惶。 4xx : 一般表示客戶端有錯(cuò)誤愁溜,請(qǐng)求無法實(shí)現(xiàn)。 5xx : 一般為服務(wù)器端的錯(cuò)誤外厂。
get:GET方法請(qǐng)求一個(gè)指定資源的表示形式. 使用GET的請(qǐng)求應(yīng)該只被用于獲取數(shù)據(jù).
post:POST方法用于將實(shí)體提交到指定的資源冕象,通常導(dǎo)致在服務(wù)器上的狀態(tài)變化或副作用
head: HEAD方法請(qǐng)求一個(gè)與GET請(qǐng)求的響應(yīng)相同的響應(yīng),但沒有響應(yīng)體.
put:PUT方法用請(qǐng)求有效載荷替換目標(biāo)資源的所有當(dāng)前表示汁蝶。
delete:DELETE方法刪除指定的資源渐扮。
connect:CONNECT方法建立一個(gè)到由目標(biāo)資源標(biāo)識(shí)的服務(wù)器的隧道
options:OPTIONS方法用于描述目標(biāo)資源的通信選項(xiàng)
trace:TRACE方法沿著到目標(biāo)資源的路徑執(zhí)行一個(gè)消息環(huán)回測(cè)試。
patch:PATCH方法用于對(duì)資源應(yīng)用部分修改
常見的狀態(tài)碼:
200 OK 客戶端請(qǐng)求成功掖棉。
301 Moved Permanently 請(qǐng)求永久重定向墓律。
302 Moved Temporarily 請(qǐng)求臨時(shí)重定向。
304 Not Modified 文件未修改幔亥,可以直接使用緩存的文件耻讽。
400 Bad Request 由于客戶端請(qǐng)求有語法錯(cuò)誤,不能被服務(wù)器所理解帕棉。
401 Unauthorized 請(qǐng)求未經(jīng)授權(quán)针肥,無法訪問。
403 Forbidden 服務(wù)器收到請(qǐng)求香伴,但是拒絕提供服務(wù)慰枕。服務(wù)器通常會(huì)在響應(yīng)正文中給出不提供服務(wù)的原因。
404 Not Found 請(qǐng)求的資源不存在即纲,比如輸入了錯(cuò)誤的URL具帮。
500 Internal Server Error 服務(wù)器發(fā)生不可預(yù)期的錯(cuò)誤,導(dǎo)致無法完成客戶端的請(qǐng)求。
502 Bad Gateway 是一種HTTP協(xié)議的服務(wù)器端錯(cuò)誤狀態(tài)代碼蜂厅,它表示作為網(wǎng)關(guān)或代理角色的服務(wù)器匪凡,從上游服務(wù)器(如tomcat、php-fpm)中接收到的響應(yīng)是無效的
503 Service Unavailable 服務(wù)器當(dāng)前不能夠處理客戶端的請(qǐng)求葛峻,在一段時(shí)間之后锹雏,服務(wù)器可能會(huì)恢復(fù)正常。
http與https的區(qū)別
https協(xié)議需要到ca申請(qǐng)證書术奖,一般免費(fèi)證書較少,需要付費(fèi)
http是超文本傳輸協(xié)議轻绞,信息是明文傳輸采记,https則是具有安全性的ssl加密傳輸協(xié)議
http默認(rèn)80端口,https默認(rèn)443端口
http是無狀態(tài)連接政勃;https協(xié)議是由SSL+HTTP協(xié)議構(gòu)建的可進(jìn)行加密傳輸唧龄、身份認(rèn)證的網(wǎng)絡(luò)協(xié)議,安全性更高
對(duì)稱加密奸远,非對(duì)稱加密
對(duì)稱加密:一般小于256bit既棺,密鑰越大,加密越強(qiáng)懒叛,但是加密與解密的時(shí)間越長(zhǎng)丸冕;加密與解密用的是同樣的密鑰;缺點(diǎn):密鑰的管理和分配
非對(duì)稱加密:最常用的非對(duì)稱加密算法是RSA算法薛窥;通過一堆密鑰:公鑰和私鑰胖烛,私鑰由一方安全保管,公鑰可以發(fā)送給任何請(qǐng)求他的人诅迷,只有私鑰才能解密佩番,而且不需要將私鑰通過網(wǎng)絡(luò)發(fā)送出去,大大提高網(wǎng)絡(luò)安全性
在瀏覽器地址欄輸入U(xiǎn)RL之后回車的過程
URL解析罢杉,抽出域名字段
DNS解析趟畏,域名解析成IP
瀏覽器緩存->操作系統(tǒng)緩存->路由器緩存->ISP緩存->根域名服務(wù)器->主域名服務(wù)器
TCP/IP連接,三次握手(Three-way Handshake滩租,是指建立一個(gè) TCP 連接時(shí)赋秀,需要客戶端和服務(wù)器總共發(fā)送3個(gè)包)
客戶端發(fā)送一個(gè) TCP 的 SYN 標(biāo)志位置1的包,指明客戶端打算連接的服務(wù)器的端口持际,以及初始序號(hào) X,保存在包頭的序列號(hào)(Sequence Number)字段里
服務(wù)器發(fā)回確認(rèn)包(ACK)應(yīng)答
客戶端再次發(fā)送確認(rèn)包(ACK)沃琅,SYN 標(biāo)志位為0,ACK 標(biāo)志位為1蜘欲,并且把服務(wù)器發(fā)來 ACK 的序號(hào)字段+1益眉,放在確定字段中發(fā)送給對(duì)方,并且在數(shù)據(jù)段放寫ISN的+1
發(fā)送HTTP請(qǐng)求
服務(wù)器處理請(qǐng)求并返回 HTTP 報(bào)文
瀏覽器解析渲染頁面
斷開連接:TCP 四次揮手
假設(shè)客戶端想要關(guān)閉連接,客戶端發(fā)送一個(gè) FIN 標(biāo)志位置為1的包郭脂,表示自己已經(jīng)沒有數(shù)據(jù)可以發(fā)送了年碘,但是仍然可以接受數(shù)據(jù)
服務(wù)器端確認(rèn)客戶端的 FIN 包,發(fā)送一個(gè)確認(rèn)包展鸡,表明自己接受到了客戶端關(guān)閉連接的請(qǐng)求屿衅,但還沒有準(zhǔn)備好關(guān)閉連接
服務(wù)器端準(zhǔn)備好關(guān)閉連接時(shí),向客戶端發(fā)送結(jié)束連接請(qǐng)求莹弊,F(xiàn)IN 置為1涤久。發(fā)送完畢后,服務(wù)器端進(jìn)入 LAST_ACK 狀態(tài)忍弛,等待來自客戶端的最后一個(gè)ACK
客戶端接收到來自服務(wù)器端的關(guān)閉請(qǐng)求响迂,發(fā)送一個(gè)確認(rèn)包,并進(jìn)入 TIME_WAIT狀態(tài)细疚,等待可能出現(xiàn)的要求重傳的 ACK 包蔗彤。服務(wù)器端接收到這個(gè)確認(rèn)包之后,關(guān)閉連接疯兼,進(jìn)入 CLOSED 狀態(tài)
ajax和fetch區(qū)別
ajax本質(zhì)是利用XMLHttpRequest來實(shí)現(xiàn)然遏,fetch采用了Promise的異步處理機(jī)制
cdn原理
負(fù)載均衡,緩存吧彪,dns解析
通過dns解析到全局負(fù)載均衡服務(wù)器待侵,然后再到區(qū)域的負(fù)載均衡,之后根據(jù)一些條件來找合適的緩存服務(wù)器来氧,如果第一次訪問就從源站拿過來緩存诫给。需要注意的是一切都是根據(jù)請(qǐng)求的ip來的,如果ip不合理啦扬,那么可能起不到加速效果中狂。緩存和負(fù)載均衡的思想在減輕服務(wù)器壓力方面其實(shí)是很常見的
瀏覽器緩存策略
瀏覽器在加載資源時(shí),根據(jù)請(qǐng)求頭的expires和cache-control判斷是否命中強(qiáng)緩存扑毡,是則直接從緩存讀取資源胃榕,不會(huì)發(fā)請(qǐng)求到服務(wù)器
如果沒有命中強(qiáng)緩存,瀏覽器一定會(huì)發(fā)送一個(gè)請(qǐng)求到服務(wù)器瞄摊,通過last-modified和etag驗(yàn)證資源是否命中協(xié)商緩存勋又,如果命中,服務(wù)器會(huì)將這個(gè)請(qǐng)求返回换帜,但是不會(huì)返回這個(gè)資源的數(shù)據(jù)楔壤,依然是從緩存中讀取資源
如果前面兩者都沒有命中,直接從服務(wù)器加載資源
如果命中惯驼,都是從客戶端緩存中加載資源蹲嚣,而不是從服務(wù)器加載資源數(shù)據(jù)递瑰;強(qiáng)緩存不發(fā)請(qǐng)求到服務(wù)器,協(xié)商緩存會(huì)發(fā)請(qǐng)求到服務(wù)器
react生命周期變更隙畜,以及使用方式抖部;為什么變化,為什么取消了那幾個(gè)生命周期
v16.3去掉componentWillMount议惰,componentWillReceiveProps慎颗,componentWillUpdate;新增static getDerivedStateFromProps(props, state)言询,getSnapshotBeforeUpdate(prevProps, prevState)
生命周期:set props & state --> componentWillMount(static getDerivedStateFromProps) --> render -->(getSnapshotBeforeUpdate)--> componentDidMount
propsUpdate:componentWillReceiveProps(static getDerivedStateFromProps) --> shouldComponentUpdate --> componentWillUpdate(去掉) --> render --> (getSnapshotBeforeUpdate)--> componentDidUpdate(prevProps, prevState, snapshot)
stateUpdate:shouldComponentUpdate --> componentWillUpdate(getSnapshotBeforeUpdate) --> render --> componentDidUpdate(prevProps, prevState, snapshot)
銷毀:componentWillUnmount
錯(cuò)誤處理: 當(dāng)渲染過程俯萎,生命周期,或子組件的構(gòu)造函數(shù)中拋出錯(cuò)誤時(shí)倍试,componentDidCatch讯屈,static getDerivedStateFromError()
componentWillMount是在組件掛載之前調(diào)用,在此方法中調(diào)用setstate是不會(huì)觸發(fā)render的县习,如果是初始化數(shù)據(jù)盡量寫在constructor中,如果是請(qǐng)求數(shù)據(jù)谆趾,建議放在componentDidMount中
componentWillReceiveProps:容易導(dǎo)致父子組件陷入死循環(huán)渲染躁愿,
componentWillUpdate:因?yàn)閜rops更新而引起多次調(diào)用,而componentDidUpdate就只會(huì)被調(diào)用一次
getDerivedStateFromProps 會(huì)在調(diào)用 render 方法之前調(diào)用沪蓬,并且在初始掛載及后續(xù)更新時(shí)都會(huì)被調(diào)用彤钟。它應(yīng)返回一個(gè)對(duì)象來更新 state,如果返回 null 則不更新任何內(nèi)容跷叉。
getSnapshotBeforeUpdate() 在最近一次渲染輸出(提交到 DOM 節(jié)點(diǎn))之前調(diào)用逸雹。它使得組件能在發(fā)生更改之前從 DOM 中捕獲一些信息(例如,滾動(dòng)位置)云挟。此生命周期的任何返回值將作為參數(shù)傳遞給 componentDidUpdate()梆砸。此用法并不常見,但它可能出現(xiàn)在 UI 處理中园欣,如需要以特殊方式處理滾動(dòng)位置的聊天線程等
有想了解更多的小伙伴可以加Q群鏈接里面看一下帖世,應(yīng)該對(duì)你們能夠有所幫助。