Web前端技術(shù)由 html啃洋、css 和 javascript 三大部分構(gòu)成,是一個(gè)龐大而復(fù)雜的技術(shù)體系,其復(fù)雜程度不低于任何一門(mén)后端語(yǔ)言锐帜。而我們?cè)趯W(xué)習(xí)它的時(shí)候往往是先從某一個(gè)點(diǎn)切入瘾敢,然后不斷地接觸和學(xué)習(xí)新的知識(shí)點(diǎn)拍冠,因此對(duì)于初學(xué)者很難理清楚整個(gè)體系的脈絡(luò)結(jié)構(gòu)。本文將對(duì)Web前端知識(shí)體系進(jìn)行簡(jiǎn)單的梳理簇抵,對(duì)應(yīng)的每個(gè)知識(shí)點(diǎn)點(diǎn)到為止庆杜,不作詳細(xì)介紹。目的是幫助大家審查自己的知識(shí)結(jié)構(gòu)是否完善碟摆,如有遺漏或不正確的地方虑省,希望共勉。
JAVASCRIPT 篇
0畏陕、基礎(chǔ)語(yǔ)法
Javascript 基礎(chǔ)語(yǔ)法包括:變量聲明视卢、數(shù)據(jù)類(lèi)型、函數(shù)嘉裤、控制語(yǔ)句郑临、內(nèi)置對(duì)象等。
在ES5 中屑宠,變量聲明有兩種方式厢洞,分別是 var 和 function ,var 用于聲明普通的變量典奉,接收任意類(lèi)型躺翻,function用于聲明函數(shù)。另外卫玖,ES6 新增了 let公你、const、import 和 class 等四個(gè)命令假瞬,分別用以聲明 普通變量陕靠、靜態(tài)變量迂尝、模塊 和 類(lèi) 。
JS數(shù)據(jù)類(lèi)型共有六種剪芥,分別是 String垄开、Number、Boolean税肪、Null溉躲、Undefined 和 Object 等, 另外益兄,ES6 新增了 Symbol 類(lèi)型锻梳。其中,Object 是引用類(lèi)型偏塞,其他的都是原始類(lèi)型(Primitive Type)唱蒸。
原始類(lèi)型也稱(chēng)為基本類(lèi)型或簡(jiǎn)單類(lèi)型,因?yàn)槠湔紦?jù)空間固定灸叼,是簡(jiǎn)單的數(shù)據(jù)段神汹,為了便于提升變量查詢(xún)速度,將其存儲(chǔ)在棧(stack)中(按值訪(fǎng)問(wèn))古今。為了便于操作這類(lèi)數(shù)據(jù)屁魏,ECMAScript 提供了 3 個(gè)基本包裝類(lèi)型:Boolean、Number 和 String 捉腥∶テ矗基本包裝類(lèi)型是一種特殊的引用類(lèi)型,每當(dāng)讀取一個(gè)基本類(lèi)型值的時(shí)候抵碟,JS內(nèi)部就會(huì)創(chuàng)建一個(gè)對(duì)應(yīng)的包裝對(duì)象桃漾,從而可以調(diào)用一些方法來(lái)操作這些數(shù)據(jù)。
引用類(lèi)型由于其值的大小會(huì)改變拟逮,所以不能將其存放在棧中撬统,否則會(huì)降低變量查詢(xún)速度,因此其存儲(chǔ)在堆(heap)中敦迄,存儲(chǔ)在變量處的值是一個(gè)指針恋追,指向存儲(chǔ)對(duì)象的內(nèi)存處(按址訪(fǎng)問(wèn)),對(duì)于引用類(lèi)型的值罚屋,可以為其添加屬性和方法苦囱,也可以改變和刪除其屬性和方法;但基本類(lèi)型不可以添加屬性和方法脾猛。關(guān)于更多介紹請(qǐng)參考:詳解 ECMAScript 數(shù)據(jù)類(lèi)型
JavaScript 可以通過(guò) typeof 來(lái)判斷原始數(shù)據(jù)類(lèi)型撕彤,但不能判斷引用類(lèi)型,要知道引用類(lèi)型的具體類(lèi)型猛拴,需要通過(guò) Object 原型上的 toString 方法來(lái)判斷喉刘,關(guān)于數(shù)據(jù)類(lèi)型判斷可以參考:判斷JS數(shù)據(jù)類(lèi)型的4種方法
在 JavaScript 中瞧柔,函數(shù)有三種角色,即普通函數(shù)睦裳、構(gòu)造函數(shù) 和 對(duì)象方法。同一個(gè)函數(shù)撼唾,調(diào)用方式不同廉邑,函數(shù)的作用不一樣,所扮演的角色也不一樣倒谷。直接調(diào)用時(shí)就是普通函數(shù)蛛蒙,通過(guò)new創(chuàng)建對(duì)象時(shí)就是構(gòu)造函數(shù),通過(guò)對(duì)象調(diào)用時(shí)就是方法渤愁。
JavaScript 常用的內(nèi)置對(duì)象有 Date牵祟、Array、JSON抖格、RegExp 等等诺苹,Date 和 Array 使用場(chǎng)景最多,JSON主要用于對(duì)象的序列化和反序列化雹拄,還有一個(gè)作用就是實(shí)現(xiàn)對(duì)象的深拷貝收奔。RegExp 即正則表達(dá)式,是處理字符串的利器滓玖。 關(guān)于更多介紹請(qǐng)參考:數(shù)組常用操作方法總結(jié) 坪哄, 正則表達(dá)式基礎(chǔ)知識(shí)
順便給大家推薦一個(gè)裙,它的前面是 537势篡,中間是631翩肌,最后就是 707。想要學(xué)習(xí)前端的小伙伴可以加入我們一起學(xué)習(xí)禁悠,互相幫助念祭。群里每天晚上都有大神免費(fèi)直播上課,如果不是想學(xué)習(xí)的小伙伴就不要加啦绷蹲。
1棒卷、函數(shù)原型鏈
JS是一種基于對(duì)象的語(yǔ)言,但在 ES6 之前是不支持繼承的祝钢,為了具備繼承的能力比规,JavaScript 在函數(shù)對(duì)象上建立了原型對(duì)象 prototype,并以函數(shù)對(duì)象為主線(xiàn)拦英,從上至下蜒什,在JS內(nèi)部構(gòu)建了一條原型鏈。原型鏈把一個(gè)個(gè)獨(dú)立的對(duì)象聯(lián)系在一起疤估,Object 則是所有對(duì)象的祖宗灾常, 任何對(duì)象所建立的原型鏈最終都指向了 Object霎冯,并以 Object 終結(jié)。
簡(jiǎn)單來(lái)說(shuō)钞瀑,就是建立了變量查找機(jī)制沈撞,當(dāng)訪(fǎng)問(wèn)一個(gè)對(duì)象的屬性時(shí),先查找對(duì)象本身是否存在雕什,如果不存在就去該對(duì)象所在的原型連上去找缠俺,直到 Object 對(duì)象為止,如果都沒(méi)有找到該屬性才會(huì)返回 undefined贷岸。因此壹士,我們可以通過(guò)原型鏈來(lái)實(shí)現(xiàn)繼承機(jī)制。關(guān)于函數(shù)原型鏈請(qǐng)參考:認(rèn)識(shí)原型對(duì)象和原型鏈
2偿警、函數(shù)作用域
函數(shù)作用域就是變量在聲明它們的函數(shù)體以及這個(gè)函數(shù)體嵌套的任意函數(shù)體內(nèi)都是有定義的躏救。通俗來(lái)講就是,在一個(gè)函數(shù)里螟蒸,有些變量可以訪(fǎng)問(wèn)盒使,有些不可以訪(fǎng)問(wèn)。那些能訪(fǎng)問(wèn)的變量所形成的范圍尿庐,就是這個(gè)函數(shù)的作用域忠怖。
在 JavaScript 中,沒(méi)有塊級(jí)作用域抄瑟,只有函數(shù)作用域凡泣,也就是說(shuō) if、while皮假、for 語(yǔ)句不會(huì)形成獨(dú)立的作用域鞋拟。但有一個(gè)特殊情況,即 with 語(yǔ)句和 catch 語(yǔ)句會(huì)形成臨時(shí)作用域惹资,語(yǔ)句執(zhí)行結(jié)束后贺纲,該作用域就會(huì)被釋放。關(guān)于函數(shù)作用域請(qǐng)參考:函數(shù)作用域和作用域鏈
3褪测、this 指針
this 指針存在于函數(shù)中猴誊,用以標(biāo)識(shí)函數(shù)運(yùn)行時(shí)所處的上下文。函數(shù)的類(lèi)型不同侮措,this 指向規(guī)則也不一樣:對(duì)于普通函數(shù)懈叹,this 始終指向全局對(duì)象window;對(duì)于構(gòu)造函數(shù)分扎,this則指向新創(chuàng)建的對(duì)象澄成;對(duì)于方法,this指向調(diào)用該方法的對(duì)象。另外墨状,F(xiàn)unction 對(duì)象也提供了call卫漫、apply 和 bind 等方法來(lái)改變函數(shù)的 this 指向,其中肾砂,call 和 apply 主動(dòng)執(zhí)行函數(shù)列赎,bind 一般在事件回調(diào)中使用,而 call 和 apply 的區(qū)別只是參數(shù)的傳遞方式不同镐确。關(guān)于更多介紹請(qǐng)參考:深入理解 call,apply和 bind
如果往深的去理解粥谬,無(wú)論什么函數(shù),this 是否被改變辫塌, 本質(zhì)上,this 均指向觸發(fā)函數(shù)運(yùn)行時(shí)的那個(gè)對(duì)象派哲。而在函數(shù)運(yùn)行時(shí)臼氨,this 的值是不能被改變的。
4芭届、new 操作符
函數(shù)的創(chuàng)建有三種方式储矩,即 顯式聲明、匿名定義 和 new Function() 褂乍。前面提到持隧,JS 中的函數(shù)即可以是函數(shù),也可以是方法逃片,還可以是構(gòu)造函數(shù)屡拨。
當(dāng)使用 new 來(lái)創(chuàng)建對(duì)象時(shí),該函數(shù)就是構(gòu)造函數(shù)褥实,JS 將新對(duì)象的原型鏈指向了構(gòu)造函數(shù)的原型對(duì)象呀狼,于是就在新對(duì)象和函數(shù)對(duì)象之間建立了一條原型鏈,通過(guò)新對(duì)象可以訪(fǎng)問(wèn)到函數(shù)對(duì)象原型 prototype 中的方法和屬性损离。關(guān)于構(gòu)造函數(shù)和 new 操作符請(qǐng)參考: 深入理解 new 操作符
5哥艇、閉包
閉包不是一個(gè)孤立的概念,需要從函數(shù)作用域的角度來(lái)理解僻澎。
每個(gè)函數(shù)都有自己的作用域貌踏,如果在一個(gè)函數(shù)里定義了另一個(gè)函數(shù),那么對(duì)應(yīng)的就有兩個(gè)作用域窟勃,這兩個(gè)作用域就會(huì)形成一個(gè)鏈條祖乳,俗稱(chēng)作用域鏈。本質(zhì)上講拳恋,作用域鏈?zhǔn)且粋€(gè)自上而下的鏈表凡资, 鏈表的最頂端是內(nèi)部函數(shù)作用域,鏈表的最底端是全局作用域。內(nèi)部函數(shù)有權(quán)訪(fǎng)問(wèn)整個(gè)作用域鏈上的變量隙赁。正常情況下垦藏,每當(dāng)一個(gè)函數(shù)執(zhí)行完畢,對(duì)應(yīng)的作用域就會(huì)從該鏈表上移除伞访,然后銷(xiāo)毀掂骏。
但如果函數(shù) A 把函數(shù) B 作為返回值返回時(shí),情況又不一樣厚掷。
首先弟灼,函數(shù) A 返回的是函數(shù) B 的引用,也就是說(shuō)冒黑,B 可能會(huì)在其他地方被調(diào)用田绑。上面提到,函數(shù) B 的定義是位于函數(shù) A 內(nèi)部抡爹,因此 A 和 B 會(huì)形成一條作用域鏈掩驱,函數(shù) B 有可能會(huì)讀取 A 中的變量 。為了保證函數(shù) B 能夠在其他地方正確執(zhí)行冬竟,函數(shù) B 所在的這條作用域鏈就不能被破壞欧穴。所以,即使函數(shù) A 執(zhí)行返回后泵殴,A 的作用域也不能釋放涮帘,需要一直保存在內(nèi)存中,以確保函數(shù) B 能夠正常讀取里面的變量笑诅。函數(shù) B 具有永久訪(fǎng)問(wèn) A 作用域的特權(quán)调缨,確切說(shuō),函數(shù) B 就是閉包 苟鸯。
總而言之同蜻,閉包就是一個(gè)有權(quán)訪(fǎng)問(wèn)另一個(gè)函數(shù)作用域的函數(shù)。
6早处、單線(xiàn)程與事件循環(huán)
JavaScript 是單線(xiàn)程語(yǔ)言湾蔓。在瀏覽器中,當(dāng)JS代碼被加載時(shí)砌梆,瀏覽器會(huì)為其分配一個(gè)主線(xiàn)程來(lái)執(zhí)行任務(wù)默责,主線(xiàn)程會(huì)在棧中創(chuàng)建一個(gè)全局執(zhí)行環(huán)境 (全局作用域)。每當(dāng)有一個(gè)函數(shù)進(jìn)入執(zhí)行流時(shí)咸包,就會(huì)形成一個(gè)對(duì)應(yīng)的執(zhí)行環(huán)境(函數(shù)作用域)桃序,并將該執(zhí)行環(huán)境壓入棧中。每當(dāng)一個(gè)函數(shù)執(zhí)行完畢以后烂瘫,對(duì)應(yīng)的執(zhí)行環(huán)境就會(huì)從棧中彈出媒熊,然后被銷(xiāo)毀奇适。這就是執(zhí)行環(huán)境棧,執(zhí)行環(huán)境棧的作用就是保證所有的函數(shù)能按照正確的順序被執(zhí)行芦鳍。
但在瀏覽器中嚷往,有一些任務(wù)是非常耗時(shí)的,比如 ajax請(qǐng)求柠衅、定時(shí)器皮仁、事件等。為了保證主線(xiàn)程上的任務(wù)不被阻塞菲宴,JavaScript 內(nèi)部維護(hù)了一個(gè)任務(wù)隊(duì)列贷祈, 當(dāng)這些耗時(shí)任務(wù)結(jié)束時(shí)(Ajax 請(qǐng)求返回、定時(shí)器超時(shí)喝峦、事件被觸發(fā))势誊,就將對(duì)應(yīng)的回調(diào)函數(shù)插入隊(duì)列中進(jìn)行等待。這些任務(wù)的執(zhí)行時(shí)機(jī)并不確定谣蠢,只有當(dāng)所有同步任務(wù)執(zhí)行完畢后键科,執(zhí)行環(huán)境棧被清空(棧底的全局執(zhí)行環(huán)境會(huì)一直存在,直到進(jìn)程退出)以后漩怎,然后再?gòu)娜蝿?wù)隊(duì)列中依次讀取回調(diào)函數(shù),并將其壓入執(zhí)行環(huán)境棧中嗦嗡。于是勋锤,主線(xiàn)程開(kāi)始執(zhí)行新的同步任務(wù),執(zhí)行完畢后再?gòu)臈V袕棾鼋募溃瑮1磺蹇铡?/p>
主線(xiàn)程從任務(wù)隊(duì)列中讀取任務(wù)是不斷循環(huán)的叁执,每當(dāng)棧被清空后,主線(xiàn)程就會(huì)從任務(wù)隊(duì)列中讀取新的任務(wù)并執(zhí)行矮冬,如果沒(méi)有新的任務(wù)谈宛,就會(huì)一直等待,直到有新的任務(wù)胎署。JavaScript 的這種執(zhí)行機(jī)制就叫做任務(wù)循環(huán)吆录。因?yàn)槊總€(gè)任務(wù)都由一個(gè)事件所觸發(fā),所以也叫 “事件循環(huán)”琼牧。
7恢筝、Ajax 和 跨域技術(shù)
Ajax 是瀏覽器專(zhuān)門(mén)用來(lái)和服務(wù)器進(jìn)行交互的異步通訊技術(shù),其核心對(duì)象是 XMLHttpRequest巨坊,通過(guò)該對(duì)象可以創(chuàng)建一個(gè) Ajax 請(qǐng)求撬槽。Ajax 請(qǐng)求是一個(gè)耗時(shí)的異步操作,當(dāng)請(qǐng)求發(fā)出以后趾撵,Ajax 提供了兩個(gè)狀態(tài)位來(lái)描述請(qǐng)求在不同階段的狀態(tài)侄柔,這兩個(gè)狀態(tài)位分別是 readyState 和 status ,readyState 通過(guò) 5個(gè)狀態(tài)碼來(lái)描述一個(gè)請(qǐng)求的 5 個(gè)階段:
0 - 請(qǐng)求未發(fā)送,初始化階段
1 - 請(qǐng)求發(fā)送中暂题,服務(wù)器還未收到請(qǐng)求
2 - 請(qǐng)求發(fā)送成功移剪,服務(wù)器已收到請(qǐng)求
3 - 服務(wù)器處理完成,開(kāi)始響應(yīng)請(qǐng)求敢靡,傳輸數(shù)據(jù)
4 - 客戶(hù)端收到請(qǐng)求挂滓,并完成了數(shù)據(jù)下載,生成了響應(yīng)對(duì)象
status 用于描述服務(wù)端對(duì)請(qǐng)求處理的情況啸胧,200 表示正確響應(yīng)了請(qǐng)求赶站,404 表示服務(wù)器找不到資源,500 代表服務(wù)器內(nèi)部異常等等纺念。
Ajax 對(duì)象還可以設(shè)置一個(gè) timeout 值贝椿,代表超時(shí)時(shí)間。切記:timeout 只會(huì)影響 readyState陷谱,而不會(huì)影響 status烙博,因?yàn)槌瑫r(shí)只會(huì)中斷數(shù)據(jù)傳輸,但不會(huì)影響服務(wù)器的處理結(jié)果烟逊。 如果 timeout 設(shè)置的不合理渣窜,就會(huì)導(dǎo)致響應(yīng)碼 status 是 200,但 response里卻沒(méi)有數(shù)據(jù)宪躯,這種情況就是服務(wù)器正確響應(yīng)了請(qǐng)求乔宿,但數(shù)據(jù)的下載被超時(shí)中斷了。
為了保證用戶(hù)信息的安全访雪,瀏覽器引入了同源策略详瑞,對(duì)腳本請(qǐng)求做了限制,不允許 Ajax 跨域請(qǐng)求服務(wù)器 臣缀,只允許請(qǐng)求和當(dāng)前地址同域的服務(wù)器資源坝橡。但不限制 HTML 標(biāo)簽發(fā)送跨域請(qǐng)求,比如 script精置、img计寇、a 標(biāo)簽等,因此可以利用標(biāo)簽跨域能力來(lái)實(shí)現(xiàn)跨域請(qǐng)求脂倦,這就是 JSONP 能夠跨域的原理饲常。
JSONP 雖然可以解決跨域問(wèn)題,但只能發(fā)送 GET 請(qǐng)求狼讨,并且沒(méi)有有效的錯(cuò)誤捕獲機(jī)制 贝淤。為了解決這個(gè)問(wèn)題,W3C 在 XMLHttpRequest Level2 中提出了 CORS 規(guī)范政供,即 “跨域資源共享”播聪。它不是一個(gè)新的 API朽基,而是一個(gè)標(biāo)準(zhǔn)規(guī)范 。當(dāng)瀏覽器發(fā)現(xiàn)該請(qǐng)求需要跨域時(shí)离陶,就會(huì)自動(dòng)在頭信息中添加一個(gè) Origin 字段稼虎,用以說(shuō)明本次請(qǐng)求來(lái)自哪個(gè)源。服務(wù)器根據(jù)這個(gè)值招刨,決定是否同意這次請(qǐng)求霎俩。 關(guān)于 CORS 的詳細(xì)介紹請(qǐng)參考:跨域資源共享 CORS 詳解
順便給大家推薦一個(gè)裙,它的前面是 537沉眶,中間是631打却,最后就是 707。想要學(xué)習(xí)前端的小伙伴可以加入我們一起學(xué)習(xí)谎倔,互相幫助柳击。群里每天晚上都有大神免費(fèi)直播上課,如果不是想學(xué)習(xí)的小伙伴就不要加啦片习。
隨著移動(dòng)端的快速發(fā)展捌肴,Web 技術(shù)的應(yīng)用場(chǎng)景正在變得越來(lái)越復(fù)雜,“關(guān)注點(diǎn)分離” 原則在系統(tǒng)設(shè)計(jì)層面就顯得越來(lái)越重要藕咏,而 XMLHttpRequest 是 Ajax 最古老的一個(gè)接口状知,因而不太符合現(xiàn)代化的系統(tǒng)設(shè)計(jì)理念。因此孽查,瀏覽器提供了一個(gè)新的 Ajax 接口试幽,即 Fetch,F(xiàn)etch 是基于 ES6 的 Promise 思想設(shè)計(jì)的卦碾,更符合關(guān)注點(diǎn)分離原則。關(guān)于 Fetch 的更多介紹請(qǐng)參考:傳統(tǒng) Ajax 已死起宽,F(xiàn)etch 永生
8洲胖、模塊化
歷史上,JavaScript 規(guī)范一直沒(méi)有模塊(Module)體系坯沪,即無(wú)法將一個(gè)大程序拆分成互相依賴(lài)的小文件绿映,再用簡(jiǎn)單的方法拼裝起來(lái)。在 ES6 之前腐晾,為了實(shí)現(xiàn) JS 模塊化編程叉弦,社區(qū)制定了一些模塊加載方案,最主要有 CMD 和 AMD 兩種藻糖,分別以 commonjs 和 requirejs 為代表淹冰。ES6 在語(yǔ)言標(biāo)準(zhǔn)的層面上,實(shí)現(xiàn)了模塊化編程巨柒,其設(shè)計(jì)思想是樱拴,盡量靜態(tài)化柠衍,使得編譯時(shí)就能確定模塊的依賴(lài)關(guān)系,即編譯時(shí)加載晶乔,而 CMD 和 AMD 是在運(yùn)行時(shí)確定依賴(lài)關(guān)系珍坊,即運(yùn)行時(shí)加載。關(guān)于 ES6 模塊化請(qǐng)參考:ES6模塊化
9正罢、Node.js
Node.js 是一個(gè)基于 Chrome V8 引擎的 JavaScript 運(yùn)行環(huán)境阵漏,它的運(yùn)行不依賴(lài)于瀏覽器作為宿主環(huán)境,而是和服務(wù)端程序一樣可以獨(dú)立的運(yùn)行翻具,這使得 JavaScript 編程第一次從客戶(hù)端被帶到了服務(wù)端履怯,Node.js 在服務(wù)端的優(yōu)勢(shì)是,它采用單線(xiàn)程和異步 I/O 模型呛占,實(shí)現(xiàn)了一個(gè)高并發(fā)虑乖、高性能的運(yùn)行時(shí)環(huán)境。相比傳統(tǒng)的多線(xiàn)程模型晾虑,Node.js 實(shí)現(xiàn)簡(jiǎn)單疹味,并且可以減少資源開(kāi)銷(xiāo)。關(guān)于 Node.js單線(xiàn)程模型請(qǐng)參考:Node.js 事件循環(huán)機(jī)制
10帜篇、ES6
ES6 是 ECMAScript 6.0 的簡(jiǎn)寫(xiě)糙捺,即 JavaScript 語(yǔ)言的下一代標(biāo)準(zhǔn),已經(jīng)在 2015年6月正式發(fā)布了笙隙,它的目標(biāo)是讓JS能夠方便的開(kāi)發(fā)企業(yè)級(jí)大型應(yīng)用程序洪灯,因此,ES6的一些規(guī)范正在逐漸向Java竟痰、C# 等后端語(yǔ)言標(biāo)準(zhǔn)靠近签钩。在 ES6 規(guī)范中,比較重大的變化有以下幾個(gè)方面:
新增 let坏快、const 命令 來(lái)聲明變量铅檩,和var 相比,let 聲明的變量不存在變量提升問(wèn)題莽鸿,但沒(méi)有改變JS弱類(lèi)型的特點(diǎn)昧旨,依然可以接受任意類(lèi)型變量的聲明;const 聲明的變量不允許在后續(xù)邏輯中改變祥得,提高了JS語(yǔ)法的嚴(yán)謹(jǐn)性兔沃。
新增解構(gòu)賦值、rest 語(yǔ)法级及、箭頭函數(shù)等乒疏,這些都是為了讓代碼看起來(lái)更簡(jiǎn)潔,而包裝的語(yǔ)法糖饮焦。
新增模塊化機(jī)制缰雇,這是 JavaScript 走向規(guī)范比較重要的一步入偷,讓前端更方便的實(shí)現(xiàn)工程化。
新增類(lèi)和繼承的概念械哟,配合模塊化疏之,JavaScript 也可以實(shí)現(xiàn)高復(fù)用、高擴(kuò)展的系統(tǒng)架構(gòu)暇咆。
新增模板字符串功能锋爪,高效簡(jiǎn)潔,結(jié)束拼接字符串的時(shí)代爸业。
新增 Promise 機(jī)制其骄,解決異步回調(diào)多層嵌套的問(wèn)題。
CSS 篇
1扯旷、CSS選擇器
CSS 選擇器即通過(guò)某種規(guī)則來(lái)匹配相應(yīng)的標(biāo)簽拯爽,并為其設(shè)置 CSS 樣式,常用的有類(lèi)選擇器钧忽、標(biāo)簽選擇器毯炮、ID選擇器、后代選擇器耸黑、群組選擇器桃煎、偽類(lèi)選擇器(before/after)、兄弟選擇器(+~)大刊、屬性選擇器等等为迈。
2、CSS Reset
HTML 標(biāo)簽在不設(shè)置任何樣式的情況下缺菌,也會(huì)有一個(gè)默認(rèn)的 CSS 樣式葫辐,而不同內(nèi)核瀏覽器對(duì)于這個(gè)默認(rèn)值的設(shè)置則不盡相同,這樣可能會(huì)導(dǎo)致同一套代碼在不同瀏覽器上的顯示效果不一致伴郁,而出現(xiàn)兼容性問(wèn)題耿战。因此,在初始化時(shí)蛾绎,需要對(duì)常用標(biāo)簽的樣式進(jìn)行初始化,使其默認(rèn)樣式統(tǒng)一鸦列,這就是 CSS Reset 租冠,即 CSS 樣式重置,比如:
1
*{ margin:0; padding:0; }
就是最簡(jiǎn)單 CSS Reset薯嗤。 關(guān)于 CSS 重置請(qǐng)參考:Neat.css
3顽爹、盒子布局
盒子模型是CSS比較重要的一個(gè)概念,也是CSS 布局的基石骆姐。 常見(jiàn)的盒子模型有塊級(jí)盒子(block)和行內(nèi)盒子(inline-block)镜粤,與盒子相關(guān)的幾個(gè)屬性有:margin捏题、border、padding和content 等肉渴,這些屬性的作用是設(shè)置盒子與盒子之間的關(guān)系以及盒子與內(nèi)容之間的關(guān)系公荧,而 box-sizing 屬性會(huì)影響盒子大小的計(jì)算方式。
需要注意的是:
只有普通文檔流中塊級(jí)盒子的垂直外邊距才會(huì)發(fā)生合并同规,而具有 BFC 特性盒子的外邊距不會(huì)合并循狰。
4、浮動(dòng)布局
設(shè)置元素的 float 屬性值為 left 或 right券勺,就能使該元素脫離普通文檔流绪钥,向左或向右浮動(dòng)。一般在做宮格布局時(shí)會(huì)用到关炼,如果子元素全部設(shè)置為浮動(dòng)程腹,則父元素是塌陷的,這時(shí)就需要清除浮動(dòng)儒拂,清除浮動(dòng)的方法也很多寸潦,常用的方法是在元素末尾加空元素設(shè)置 clear: both,更高級(jí)一點(diǎn)的就給父容器設(shè)置 before/after 來(lái)模擬一個(gè)空元素侣灶,還可以直接設(shè)置 overflow 屬性為 auto/hidden 來(lái)清除浮動(dòng)甸祭。除浮動(dòng)可以實(shí)現(xiàn)宮格布局,行內(nèi)盒子(inline-block) 和 table 也可以實(shí)現(xiàn)同樣的效果褥影。
5池户、定位布局
設(shè)置元素的 position 屬性值為 relative/absolute/fixed,就可以使該元素脫離文檔流凡怎,并以某種參照坐標(biāo)進(jìn)行偏移校焦。其中,releave 是相對(duì)定位统倒,它以自己原來(lái)的位置進(jìn)行偏移寨典,偏移后,原來(lái)的空間不會(huì)被其他元素占用房匆;absolute 是絕對(duì)定位耸成,它以離自己最近的定位父容器作為參照進(jìn)行偏移;為了對(duì)某個(gè)元素進(jìn)行定位浴鸿,常用的方式就是設(shè)置父容器的 poistion:relative井氢,因?yàn)橄鄬?duì)定位元素在不設(shè)置 top 和 left 值時(shí),不會(huì)對(duì)元素位置產(chǎn)生影響岳链;fixed 即固定定位花竞,它則以瀏覽器窗口為參照物,PC網(wǎng)頁(yè)底部懸停的banner一般都可以通過(guò)fixed定位來(lái)實(shí)現(xiàn)掸哑,但fixed屬性在移動(dòng)端有兼容性問(wèn)題约急,因此不推薦使用零远,可替代的方案是:絕對(duì)定位+內(nèi)部滾動(dòng)。
6厌蔽、彈性布局
彈性布局即 Flex 布局牵辣,定義了 flex 的容器一個(gè)可伸縮容器,首先容器本身會(huì)根據(jù)容器中的元素動(dòng)態(tài)設(shè)置自身大刑烧怼服猪;然后當(dāng)Flex容器被應(yīng)用一個(gè)大小時(shí)(width和height),將會(huì)自動(dòng)調(diào)整容器中的元素適應(yīng)新大小拐云。Flex容器也可以設(shè)置伸縮比例和固定寬度罢猪,還可以設(shè)置容器中元素的排列方向(橫向和縱向)和是否支持元素的自動(dòng)換行。有了這個(gè)神器叉瘩,做頁(yè)面布局的可以方便很多了膳帕。注意,設(shè)為Flex 布局以后薇缅,子元素的 float危彩、clear、inline-block 和 vertical-align 屬性將失效泳桦。關(guān)于 flexbox 請(qǐng)參考:圖解CSS3 Flexbox屬性
7汤徽、CSS3 動(dòng)畫(huà)
CSS3 中規(guī)范引入了兩種動(dòng)畫(huà),分別是 transition 和 animation灸撰,transition 可以讓元素的 CSS 屬性值的變化在一段時(shí)間內(nèi)平滑的過(guò)渡谒府,形成動(dòng)畫(huà)效果,為了使元素的變換更加豐富多彩浮毯,CSS3 還引入了 transfrom 屬性完疫,它可以通過(guò)對(duì)元素進(jìn)行 平移(translate)、旋轉(zhuǎn)(rotate)债蓝、放大縮小(scale)壳鹤、傾斜(skew) 等操作,來(lái)實(shí)現(xiàn) 2D 和 3D 變換效果饰迹。transiton 還有一個(gè)結(jié)束事件 transitionEnd涡戳,該事件是在 CSS 完成過(guò)渡后觸發(fā)赦颇,但如果過(guò)渡在完成之前被移除塘装,則不會(huì)觸發(fā) transitionEnd 荣挨。
animation 需要設(shè)置一個(gè) @keyframes,來(lái)定義元素以哪種形式進(jìn)行變換莉掂, 然后再通過(guò)動(dòng)畫(huà)函數(shù)讓這種變換平滑的進(jìn)行葛圃,從而達(dá)到動(dòng)畫(huà)效果千扔,動(dòng)畫(huà)可以被設(shè)置為永久循環(huán)演示憎妙。設(shè)置 animation-play-state:paused 可以暫停動(dòng)畫(huà)库正,設(shè)置 animation-fill-mode:forwards 可以讓動(dòng)畫(huà)完成后定格在最后一幀。
另外厘唾,還可以通過(guò)JS 監(jiān)聽(tīng) animation 的“開(kāi)始”褥符、“結(jié)束” 和 “重復(fù)播放” 狀態(tài),分別對(duì)應(yīng)三個(gè)事件抚垃,即 animationStart喷楣、animationEnd、animationIteration 鹤树。需要注意的是:
當(dāng)播放次數(shù)設(shè)置為1時(shí)铣焊,不會(huì)觸發(fā) animationIteration 。
和 transition相比罕伯,animation 設(shè)置動(dòng)畫(huà)效果更靈活更豐富曲伊,二者還有一個(gè)區(qū)別是:transition 只能通過(guò)主動(dòng)改變?cè)氐?css 值才能觸發(fā)動(dòng)畫(huà)效果,而 animation 一旦被應(yīng)用追他,就開(kāi)始執(zhí)行動(dòng)畫(huà)坟募。
另外,HTML5 還新增了一個(gè)動(dòng)畫(huà)API邑狸,即 requestAnimationFrame懈糯,它通過(guò)JS來(lái)調(diào)用,并按照屏幕的繪制頻率來(lái)改變?cè)氐腃SS屬性单雾,從而達(dá)到動(dòng)畫(huà)效果赚哗,關(guān)于這個(gè)API的介紹請(qǐng)參考:requestAnimationFrame 知多少?
8铁坎、BFC
BFC 是頁(yè)面上的一個(gè)隔離的獨(dú)立容器蜂奸,容器里面的子元素不會(huì)影響到外面元素。比如:內(nèi)部滾動(dòng)就是一個(gè) BFC硬萍,當(dāng)一個(gè)父容器的 overflow-y 設(shè)置為 auto 時(shí)扩所,并且子容器的長(zhǎng)度大于父容器時(shí),就會(huì)出現(xiàn)內(nèi)部滾動(dòng)朴乖,無(wú)論內(nèi)部的元素怎么滾動(dòng)祖屏,都不會(huì)影響父容器以外的布局,這個(gè)父容器的渲染區(qū)域就叫 BFC买羞。滿(mǎn)足下列條件之一就可觸發(fā) BFC:
根元素袁勺,即 HTML 元素
float 的值不為 none
overflow 的值不為 visible
display 的值為 inline-block、table-cell畜普、table-caption
position 的值為 absolute 或 fixed
9期丰、Sprite,Iconfont,font-face
對(duì)于大型站點(diǎn)钝荡,為了減少 http 請(qǐng)求的次數(shù)街立,一般會(huì)將常用的小圖標(biāo)排到一個(gè)大圖中,頁(yè)面加載時(shí)只需請(qǐng)求一次網(wǎng)絡(luò)埠通, 然后在 css 中通過(guò)設(shè)置 background-position 來(lái)控制顯示所需要的小圖標(biāo)赎离,這就是 Sprite 圖。
Iconfont端辱,即字體圖標(biāo)梁剔,就是將常用的圖標(biāo)轉(zhuǎn)化為字體資源存在文件中,通過(guò)在 CSS 中引用該字體文件舞蔽,然后可以直接用控制字體的css屬性來(lái)設(shè)置圖標(biāo)的樣式荣病,字體圖標(biāo)的好處是節(jié)省網(wǎng)絡(luò)請(qǐng)求、其大小不受屏幕分辨率的影響渗柿,并且可以任意修改圖標(biāo)的顏色众雷。
font-face 是 CSS3 中的一個(gè)模塊,通過(guò) font-face 可以定義一種全新的字體做祝,然后就可以通過(guò) css 屬性 font-family 來(lái)使用這個(gè)字體了砾省,即使操作系統(tǒng)沒(méi)有安裝這種字體,網(wǎng)頁(yè)上也會(huì)正常顯示出來(lái)混槐。
10编兄、CSS HACK
早期,不同內(nèi)核瀏覽器對(duì)CSS屬性的解析存在著差異声登,導(dǎo)致顯示效果不一致狠鸳,比如 margin 屬性在 ie6 中顯示的距離會(huì)比其他瀏覽器中顯示的距離寬 2 倍,也就是說(shuō) margin-left:20px; 在ie6中距左側(cè)元素的實(shí)際顯示距離是 40px悯嗓,而在非 ie6 的瀏覽器上顯示正常件舵。因此,如果要想讓所有瀏覽器中都顯示是 20px 的寬度脯厨,就需要在CSS樣式中加入一些特殊的符號(hào)铅祸,讓不同的瀏覽器識(shí)別不同的符號(hào),以達(dá)到應(yīng)用不同的CSS樣式的目的合武,這種方式就是 “css hack”临梗, 對(duì)于 ie6 中的 margin 應(yīng)用 hack 就會(huì)變成這樣:
HTML 篇
1、BOM
BOM 是 Browser Object Model 的縮寫(xiě)稼跳,即瀏覽器對(duì)象模型盟庞,當(dāng)一個(gè)瀏覽器頁(yè)面初始化時(shí),會(huì)在內(nèi)存創(chuàng)建一個(gè)全局的對(duì)象汤善,用以描述當(dāng)前窗口的屬性和狀態(tài)什猖,這個(gè)全局對(duì)象被稱(chēng)為瀏覽器對(duì)象模型票彪,即BOM。BOM的核心對(duì)象就是 window不狮,window 對(duì)象也是BOM的頂級(jí)對(duì)象抹镊,其包含了瀏覽器的六個(gè)核心模塊:
document?- 即文檔對(duì)象,渲染引擎在解析HTML代碼時(shí)荤傲,會(huì)為每一個(gè)元素生成對(duì)應(yīng)的DOM對(duì)象,由于元素之間有層級(jí)關(guān)系颈渊,因此整個(gè)HTML代碼解析完以后遂黍,會(huì)生成一個(gè)由不同節(jié)點(diǎn)組成的樹(shù)形結(jié)構(gòu),俗稱(chēng)DOM樹(shù)俊嗽,document 用于描述DOM樹(shù)的狀態(tài)和屬性雾家,并提供了很多操作DOM的API。
frames?- HTML 子框架绍豁,即在瀏覽器里嵌入另一個(gè)窗口芯咧,父框架和子框架擁有獨(dú)立的作用域和上下文。
history?- 以棧(FIFO)的形式保存著頁(yè)面被訪(fǎng)問(wèn)的歷史記錄竹揍,頁(yè)面前進(jìn)即入棧敬飒,頁(yè)面返回即出棧。
location?- 提供了當(dāng)前窗口中加載的文檔相關(guān)信息以及一些導(dǎo)航功能芬位。
navigator?- 用來(lái)描述瀏覽器本身无拗,包括瀏覽器的名稱(chēng)、版本昧碉、語(yǔ)言英染、系統(tǒng)平臺(tái)、用戶(hù)特性字符串等信息被饿。
screen?- 提供了瀏覽器顯示屏幕的相關(guān)屬性四康,比如顯示屏幕的寬度和高度,可用寬度和高度狭握。
2闪金、DOM 系統(tǒng)
DOM 是 Document Object Model 的縮寫(xiě),即 文檔對(duì)象模型论颅,是所有瀏覽器公共遵守的標(biāo)準(zhǔn)毕泌,DOM 將HTML和XML文檔映射成一個(gè)由不同節(jié)點(diǎn)組成的樹(shù)型結(jié)構(gòu),俗稱(chēng)DOM樹(shù)嗅辣。其核心對(duì)象是document撼泛,用于描述DOM樹(shù)的狀態(tài)和屬性,并提供對(duì)應(yīng)的DOM操作API澡谭。隨著歷史的發(fā)展愿题,DOM 被劃分為1級(jí)损俭、2級(jí)、3級(jí)潘酗,共3個(gè)級(jí)別:
順便給大家推薦一個(gè)裙杆兵,它的前面是 537,中間是631仔夺,最后就是 707琐脏。想要學(xué)習(xí)前端的小伙伴可以加入我們一起學(xué)習(xí),互相幫助缸兔。群里每天晚上都有大神免費(fèi)直播上課日裙,如果不是想學(xué)習(xí)的小伙伴就不要加啦。
1級(jí)DOM - 在1998年10月份成為W3C的提議惰蜜,由 DOM 核心與 DOM HTML 兩個(gè)模塊組成昂拂。DOM核心能映射以XML為基礎(chǔ)的文檔結(jié)構(gòu),允許獲取和操作文檔的任意部分抛猖。DOM HTML通過(guò)添加HTML專(zhuān)用的對(duì)象與函數(shù)對(duì)DOM核心進(jìn)行了擴(kuò)展格侯。
2級(jí)DOM - 鑒于1級(jí)DOM僅以映射文檔結(jié)構(gòu)為目標(biāo),DOM 2級(jí)面向更為寬廣财著。通過(guò)對(duì)原有DOM的擴(kuò)展联四,2級(jí)DOM通過(guò)對(duì)象接口增加了對(duì)鼠標(biāo)和用戶(hù)界面事件(DHTML長(zhǎng)期支持鼠標(biāo)與用戶(hù)界面事件)、范圍撑教、遍歷(重復(fù)執(zhí)行DOM文檔)和層疊樣式表(CSS)的支持碎连。同時(shí)也對(duì)DOM 1的核心進(jìn)行了擴(kuò)展,從而可支持XML命名空間驮履。
3級(jí)DOM - 通過(guò)引入統(tǒng)一方式載入和保存文檔和文檔驗(yàn)證方法對(duì)DOM進(jìn)行進(jìn)一步擴(kuò)展鱼辙,DOM3包含一個(gè)名為“DOM載入與保存”的新模塊,DOM核心擴(kuò)展后可支持XML1.0的所有內(nèi)容玫镐,包括XML Infoset倒戏、 XPath、和XML Base恐似。
瀏覽器對(duì)不同級(jí)別DOM的支持情況如下所示:
從圖中可以看出杜跷,移動(dòng)端常用的 webkit 內(nèi)核瀏覽器目前只支持 DOM2,而不支持 DOM3 矫夷。
3葛闷、事件系統(tǒng)
事件是用戶(hù)與頁(yè)面交互的基礎(chǔ),到目前為止双藕,DOM事件從PC端的 鼠標(biāo)事件(mouse) 發(fā)展到了 移動(dòng)端的 觸摸事件(touch) 和 手勢(shì)事件(guesture)淑趾,touch事件描述了手指在屏幕操作的每一個(gè)細(xì)節(jié),guesture 則是描述多手指操作時(shí)更為復(fù)雜的情況忧陪,總結(jié)如下:
第一根手指放下扣泊,觸發(fā) touchstart近范,除此之外什么都不會(huì)發(fā)生
手指滑動(dòng)時(shí),觸發(fā)touchmove
第二根手指放下延蟹,觸發(fā) gesturestart
觸發(fā)第二根手指的 touchstart
立即觸發(fā) gesturechange
任意手指移動(dòng)评矩,持續(xù)觸發(fā) gesturechange
第二根手指彈起時(shí),觸發(fā) gestureend阱飘,以后將不會(huì)再觸發(fā) gesturechange
觸發(fā)第二根手指的 touchend
觸發(fā)touchstart (多根手指在屏幕上斥杜,提起一根,會(huì)刷新一次全局touch)
彈起第一根手指沥匈,觸發(fā) touchend
更多關(guān)于手勢(shì)事件的介紹請(qǐng)參考:gesture事件處理復(fù)雜手勢(shì)
DOM2.0 模型將事件處理流程分為三個(gè)階段蔗喂,即?事件捕獲階段、事件處理階段咐熙、事件冒泡階段,如圖所示:
事件捕獲:當(dāng)用戶(hù)觸發(fā)點(diǎn)擊事件后辨萍,頂層對(duì)象 document 就會(huì)發(fā)出一個(gè)事件流棋恼,從最外層的 DOM 節(jié)點(diǎn)向目標(biāo)元素節(jié)點(diǎn)傳遞,最終到達(dá)目標(biāo)元素锈玉。
事件處理:當(dāng)?shù)竭_(dá)目標(biāo)元素之后爪飘,執(zhí)行目標(biāo)元素綁定的處理函數(shù)。如果沒(méi)有綁定監(jiān)聽(tīng)函數(shù)拉背,則不做任何處理师崎。
事件冒泡:事件流從目標(biāo)元素開(kāi)始,向最外層DOM節(jié)點(diǎn)傳遞椅棺,途中如果有節(jié)點(diǎn)綁定了事件處理函數(shù)犁罩,這些函數(shù)就會(huì)被執(zhí)行。
利用事件冒泡原理可以實(shí)現(xiàn) “事件委托”两疚。
所謂事件委托床估,就是在父元素上添加事件監(jiān)聽(tīng)器,用以監(jiān)聽(tīng)和處理子元素的事件诱渤,避免重復(fù)為子元素綁定相同的事件丐巫。當(dāng)目標(biāo)元素的事件被觸發(fā)以后,這個(gè)事件就從目標(biāo)元素開(kāi)始勺美,向最外層元素傳遞递胧,最終冒泡到父元素上,父元素再通過(guò) event.target 獲取到這個(gè)目標(biāo)元素赡茸,這樣做的好處是缎脾,父元素只需綁定一個(gè)事件監(jiān)聽(tīng),就可以對(duì)所有子元素的事件進(jìn)行處理了占卧,從而減少了不必要的事件綁定赊锚,對(duì)頁(yè)面性能有一定的提升治筒。
4、HTML 渲染流程
渲染引擎一開(kāi)始會(huì)從網(wǎng)絡(luò)層獲取請(qǐng)求文檔的內(nèi)容舷蒲,內(nèi)容的大小一般限制在 8000 個(gè)塊以?xún)?nèi)耸袜。
然后進(jìn)行如下所示的基本流程:
HTML Parser 解析 HTML 文檔,并將各標(biāo)記逐個(gè)轉(zhuǎn)化為 DOM 節(jié)點(diǎn)牲平,生成 “DOM樹(shù)”堤框。
CSS Parser 解析外部 CSS 文件以及樣式元素中的樣式數(shù)據(jù),生成 “CSSOM樹(shù)”纵柿。
“DOM樹(shù)” 和 “CSSOM樹(shù)” 通過(guò) “附著” 將創(chuàng)建另一個(gè)樹(shù)結(jié)構(gòu):“渲染樹(shù)”蜈抓。
渲染樹(shù)包含多個(gè)帶有視覺(jué)屬性(如顏色和尺寸)的矩形,這些矩形的排列順序就是它們將在屏幕上顯示的順序昂儒。
渲染樹(shù)構(gòu)建完畢之后沟使,進(jìn)入“布局” 處理階段,也就是為每個(gè)節(jié)點(diǎn)分配一個(gè)應(yīng)出現(xiàn)在屏幕上的確切坐標(biāo)渊跋。
下一個(gè)階段是 “繪制”腊嗡,渲染引擎會(huì)遍歷渲染樹(shù),由用戶(hù)界面后端層將每個(gè)節(jié)點(diǎn)繪制出來(lái)拾酝。
需要注意的是:
這是一個(gè)漸進(jìn)的過(guò)程燕少。為達(dá)到更好的用戶(hù)體驗(yàn),呈現(xiàn)引擎會(huì)力求盡快將內(nèi)容顯示在屏幕上蒿囤。它不必等到整個(gè) HTML 文檔解析完畢之后客们,就會(huì)開(kāi)始構(gòu)建呈現(xiàn)樹(shù)和設(shè)置布局。在不斷接收和處理來(lái)自網(wǎng)絡(luò)的其余內(nèi)容的同時(shí)材诽,呈現(xiàn)引擎會(huì)將部分內(nèi)容解析并顯示出來(lái)底挫。
5、重繪與回流
當(dāng)渲染樹(shù)中的一部分(或全部)因?yàn)樵氐囊?guī)模尺寸脸侥、布局凄敢、隱藏等改變而需要重新構(gòu)建,就稱(chēng)為 “回流”湿痢。
當(dāng)渲染樹(shù)中的一些元素需要更新屬性涝缝,而這些屬性只是影響元素的外觀,風(fēng)格譬重,而不會(huì)影響布局拒逮,就稱(chēng)為 “重繪”。
回流必將引起重繪臀规,而重繪不一定會(huì)引起回流滩援。
引起重繪和回流的操作如下:
添加、刪除元素(回流+重繪)
隱藏元素塔嬉,display: none(回流+重繪)玩徊,visibility:hidden(只重繪租悄,不回流)
移動(dòng)元素,比如改變 top恩袱、left 的值泣棋,或者移動(dòng)元素到另外一個(gè)父元素中。(重繪+回流)
對(duì) style 的操作(對(duì)不同的屬性操作畔塔,影響不一樣)
還有一種是用戶(hù)的操作潭辈,比如改變?yōu)g覽器大小,改變?yōu)g覽器的字體大小等(回流+重繪)
注意問(wèn)題:
transform 操作不會(huì)引起重繪和回流澈吨,是一種高效率的渲染把敢。這是因?yàn)閠ransform屬于合成屬性,對(duì)合成屬性進(jìn)行transition/animation 動(dòng)畫(huà)時(shí)將會(huì)創(chuàng)建一個(gè)合成層谅辣,這使得動(dòng)畫(huà)元素在一個(gè)獨(dú)立的層中進(jìn)行渲染修赞,當(dāng)元素的內(nèi)容沒(méi)有發(fā)生改變,就沒(méi)必要進(jìn)行重繪桑阶,瀏覽器會(huì)通過(guò)重新復(fù)合來(lái)創(chuàng)建動(dòng)畫(huà)幀柏副。
6、本地存儲(chǔ)
本地存儲(chǔ)最原始的方式就是 cookie,cookie 是存放在本地瀏覽器的一段文本联逻,數(shù)據(jù)以鍵值對(duì)的形式保存搓扯,可以設(shè)置過(guò)期時(shí)間检痰。 但是 cookie 不適合大量數(shù)據(jù)的存儲(chǔ)包归,因?yàn)槊空?qǐng)求一次頁(yè)面,cookie 都會(huì)發(fā)送給服務(wù)器铅歼,這使得 cookie 速度很慢而且效率也不高公壤。因此cookie的大小被限制為4k左右(不同瀏覽器可能不同,分HOST),如下所示:
Firefox 和 Safari 允許 cookie 多達(dá) 4097 個(gè)字節(jié)椎椰,包括名(name)厦幅、值(value) 和 等號(hào)。
Opera 允許 cookie 多達(dá) 4096 個(gè)字節(jié)慨飘,包括:名(name)确憨、值(value) 和 等號(hào)。
Internet Explorer 允許 cookie 多達(dá)4095個(gè)字節(jié)瓤的,包括:名(name)休弃、值(value) 和 等號(hào)。
在所有瀏覽器中圈膏,任何 cookie 大小超過(guò)限制都被忽略塔猾,且永遠(yuǎn)不會(huì)被設(shè)置。
html5 提供了兩種在客戶(hù)端存儲(chǔ)數(shù)據(jù)的新方法:localStorage 和 sessionStorage, 它們都是以 key/value 的形式來(lái)存儲(chǔ)數(shù)據(jù)稽坤,前者是永久存儲(chǔ)丈甸,后者的存儲(chǔ)期限僅限于瀏覽器會(huì)話(huà)(session)糯俗,即當(dāng)瀏覽器窗口關(guān)閉后,sessionStorage中的數(shù)據(jù)被清除睦擂。
順便給大家推薦一個(gè)裙得湘,它的前面是 537,中間是631祈匙,最后就是 707忽刽。想要學(xué)習(xí)前端的小伙伴可以加入我們一起學(xué)習(xí),互相幫助夺欲。群里每天晚上都有大神免費(fèi)直播上課跪帝,如果不是想學(xué)習(xí)的小伙伴就不要加啦。
localStorage 的存儲(chǔ)空間大約5M左右(不同瀏覽器可能不同些阅,分 HOST)伞剑,這個(gè)相當(dāng)于一個(gè)5M大小的前端數(shù)據(jù)庫(kù),相比于cookie市埋,可以節(jié)約帶寬黎泣,但localStorage在瀏覽器隱私模式下是不可讀取的,當(dāng)存儲(chǔ)數(shù)據(jù)超過(guò)了localStorage 的存儲(chǔ)空間后會(huì)拋出異常缤谎。
此外抒倚,H5還提供了 websql 和 indexedDB,允許前端以關(guān)系型數(shù)據(jù)庫(kù)的方式來(lái)存儲(chǔ)本地?cái)?shù)據(jù)坷澡,相對(duì)來(lái)說(shuō)托呕,這個(gè)功能目前應(yīng)用的場(chǎng)景比較少,此處不作介紹频敛。
7项郊、瀏覽器緩存機(jī)制
瀏覽器緩存機(jī)制是指通過(guò) HTTP 協(xié)議頭里的 Cache-Control (或 Expires) 和 Last-Modified (或 Etag) 等字段來(lái)控制文件緩存的機(jī)制。
Cache-Control 用于控制文件在本地緩存有效時(shí)長(zhǎng)斟赚。最常見(jiàn)的着降,比如服務(wù)器回包:Cache-Control:max-age=600 表示文件在本地應(yīng)該緩存,且有效時(shí)長(zhǎng)是600秒 (從發(fā)出請(qǐng)求算起)拗军。在接下來(lái)600秒內(nèi)任洞,如果有請(qǐng)求這個(gè)資源,瀏覽器不會(huì)發(fā)出 HTTP 請(qǐng)求发侵,而是直接使用本地緩存的文件交掏。
Last-Modified 是標(biāo)識(shí)文件在服務(wù)器上的最新更新時(shí)間。下次請(qǐng)求時(shí)器紧,如果文件緩存過(guò)期耀销,瀏覽器通過(guò) If-Modified-Since 字段帶上這個(gè)時(shí)間,發(fā)送給服務(wù)器,由服務(wù)器比較時(shí)間戳來(lái)判斷文件是否有修改熊尉。如果沒(méi)有修改罐柳,服務(wù)器返回304告訴瀏覽器繼續(xù)使用緩存;如果有修改狰住,則返回200张吉,同時(shí)返回最新的文件。
Cache-Control 通常與 Last-Modified 一起使用催植。一個(gè)用于控制緩存有效時(shí)間肮蛹,一個(gè)在緩存失效后,向服務(wù)查詢(xún)是否有更新创南。
Cache-Control 還有一個(gè)同功能的字段:Expires伦忠。Expires 的值一個(gè)絕對(duì)的時(shí)間點(diǎn),如:Expires: Thu, 10 Nov 2015 08:45:11 GMT稿辙,表示在這個(gè)時(shí)間點(diǎn)之前昆码,緩存都是有效的。
Expires 是 HTTP1.0 標(biāo)準(zhǔn)中的字段邻储,Cache-Control 是 HTTP1.1 標(biāo)準(zhǔn)中新加的字段赋咽,功能一樣,都是控制緩存的有效時(shí)間吨娜。當(dāng)這兩個(gè)字段同時(shí)出現(xiàn)時(shí)脓匿,Cache-Control 是高優(yōu)化級(jí)的。
Etag 也是和 Last-Modified 一樣宦赠,對(duì)文件進(jìn)行標(biāo)識(shí)的字段陪毡。不同的是,Etag 的取值是一個(gè)對(duì)文件進(jìn)行標(biāo)識(shí)的特征字串袱瓮。在向服務(wù)器查詢(xún)文件是否有更新時(shí)缤骨,瀏覽器通過(guò) If-None-Match 字段把特征字串發(fā)送給服務(wù)器爱咬,由服務(wù)器和文件最新特征字串進(jìn)行匹配尺借,來(lái)判斷文件是否有更新。沒(méi)有更新回包304精拟,有更新回包200燎斩。Etag 和 Last-Modified 可根據(jù)需求使用一個(gè)或兩個(gè)同時(shí)使用。兩個(gè)同時(shí)使用時(shí)蜂绎,只要滿(mǎn)足基中一個(gè)條件栅表,就認(rèn)為文件沒(méi)有更新。
瀏覽緩存的基本框架如下圖所示:
關(guān)于更多瀏覽器緩存介紹請(qǐng)參考:H5 緩存機(jī)制淺析 移動(dòng)端 Web 加載性能優(yōu)化
8师枣、History
用戶(hù)訪(fǎng)問(wèn)網(wǎng)頁(yè)的歷史記錄通常會(huì)被保存在一個(gè)類(lèi)似于棧的對(duì)象中怪瓶,即 history 對(duì)象,點(diǎn)擊返回就出棧践美,跳下一頁(yè)就入棧洗贰。 它提供了以下方法來(lái)操作頁(yè)面的前進(jìn)和后退:
window.history.back( ) 返回到上一個(gè)頁(yè)面
window.history.forward( ) 進(jìn)入到下一個(gè)頁(yè)面
window.history.go( [delta] ) 跳轉(zhuǎn)到指定頁(yè)面
HTML5 對(duì)History Api 進(jìn)行了增強(qiáng)找岖,新增了兩個(gè)Api 和一個(gè)事件,分別是 pushState敛滋、replaceState 和 onpopstate:
pushState 是往 history 對(duì)象里添加一個(gè)新的歷史記錄许布。
replaceState 是替換 history 對(duì)象中的當(dāng)前歷史記錄。
onpopstate 當(dāng)點(diǎn)擊瀏覽器后退按鈕或JS調(diào)用 history.back 都會(huì)觸發(fā)該事件绎晃。
onpopstate 和 onhashchange 的區(qū)別:
onhashchange 本來(lái)是用來(lái)監(jiān)聽(tīng)hash變化的蜜唾,但可以被利用來(lái)做客戶(hù)端前進(jìn)和后退事件的監(jiān)聽(tīng),而 onpopstate 是專(zhuān)門(mén)用來(lái)監(jiān)聽(tīng)瀏覽器前進(jìn)后退的庶艾,不僅可以支持 hash袁余,非 hash 的同源 url 也支持。
9咱揍、HTML5 離線(xiàn)緩存
HTML5離線(xiàn)緩存又叫Application Cache泌霍,是從瀏覽器的緩存中分出來(lái)的一塊緩存區(qū),如果要在這個(gè)緩存中保存數(shù)據(jù)述召,可以使用一個(gè)描述文件(manifest file)朱转,列出要下載和緩存的資源。
manifest 文件是簡(jiǎn)單的文本文件积暖,它告知瀏覽器被緩存的內(nèi)容(以及不緩存的內(nèi)容)藤为。manifest 文件可分為三個(gè)部分:
CACHE MANIFEST - 在此標(biāo)題下列出的文件將在首次下載后進(jìn)行緩存
NETWORK - 在此標(biāo)題下列出的文件需要與服務(wù)器的連接,且不會(huì)被緩存
FALLBACK - 在此標(biāo)題下列出的文件規(guī)定當(dāng)頁(yè)面無(wú)法訪(fǎng)問(wèn)時(shí)的回退頁(yè)面(比如 404 頁(yè)面)
離線(xiàn)緩存為應(yīng)用帶來(lái)三個(gè)優(yōu)勢(shì):
離線(xiàn)瀏覽 - 用戶(hù)可在應(yīng)用離線(xiàn)時(shí)使用它們
速度 - 已緩存資源加載得更快
減少服務(wù)器負(fù)載 - 瀏覽器將只從服務(wù)器下載更新過(guò)或更改過(guò)的資源夺刑。
10缅疟、Web語(yǔ)義化與SEO
Web語(yǔ)義化是指使用語(yǔ)義恰當(dāng)?shù)臉?biāo)簽,使頁(yè)面有良好的結(jié)構(gòu)遍愿,頁(yè)面元素有含義存淫,能夠讓人和搜索引擎都容易理解。
SEO是指在了解搜索引擎自然排名機(jī)制的基礎(chǔ)之上沼填,對(duì)網(wǎng)站進(jìn)行內(nèi)部及外部的調(diào)整優(yōu)化桅咆,改進(jìn)網(wǎng)站在搜索引擎中關(guān)鍵詞的自然排名,獲得更多的展現(xiàn)量坞笙,吸引更多目標(biāo)客戶(hù)點(diǎn)擊訪(fǎng)問(wèn)網(wǎng)站岩饼,從而達(dá)到互聯(lián)網(wǎng)營(yíng)銷(xiāo)及品牌建設(shè)的目標(biāo)。
搜索引擎通過(guò)爬蟲(chóng)技術(shù)獲取的頁(yè)面就是由一堆 html 標(biāo)簽組成的代碼薛夜,人可以通過(guò)可視化的方式來(lái)判斷頁(yè)面上哪些內(nèi)容是重點(diǎn)籍茧,而機(jī)器做不到。 但搜索引擎會(huì)根據(jù)標(biāo)簽的含義來(lái)判斷內(nèi)容的權(quán)重梯澜,因此寞冯,在合適的位置使用恰當(dāng)?shù)臉?biāo)簽,使整個(gè)頁(yè)面的語(yǔ)義明確,結(jié)構(gòu)清晰吮龄,搜索引擎才能正確識(shí)別頁(yè)面中的重要內(nèi)容檬某,并予以較高的權(quán)值。比如h1~h6這幾個(gè)標(biāo)簽在SEO中的權(quán)值非常高螟蝙,用它們作頁(yè)面的標(biāo)題就是一個(gè)簡(jiǎn)單的SEO優(yōu)化恢恼。