js基礎(chǔ)

JS的單線程模型和事件循環(huán)機(jī)制

JS的單線程模型意味著签杈,在執(zhí)行JS時(shí)只有一個(gè)主線程,每個(gè)任務(wù)必須順序執(zhí)行汞斧。如果當(dāng)前任務(wù)執(zhí)行時(shí)間過長滔驶,會導(dǎo)致接下來的所有任務(wù)都處于阻塞狀態(tài)遇革,進(jìn)而導(dǎo)致瀏覽器卡死等我們不希望看到的狀況。為了解決這一問題,事件循環(huán)機(jī)制(Event Loop)被發(fā)明出來萝快。

事件循環(huán)機(jī)制中锻霎,負(fù)責(zé)執(zhí)行JS腳本的單線程我們稱為主線程,在內(nèi)存中表現(xiàn)為一個(gè)執(zhí)行棧揪漩,JS只通過主線程執(zhí)行任務(wù)旋恼。異步任務(wù)被掛起,存儲在堆中氢拥,當(dāng)異步任務(wù)準(zhǔn)備就緒,它對應(yīng)的事件便進(jìn)入任務(wù)隊(duì)列锨侯。主線程首先執(zhí)行同步任務(wù)嫩海,然后查看任務(wù)隊(duì)列是否有就緒的異步任務(wù)(或者時(shí)間到了的異步任務(wù)),調(diào)用相應(yīng)的回調(diào)函數(shù)執(zhí)行囚痴,直到任務(wù)隊(duì)列為空叁怪。至此即完成一個(gè)事件循環(huán)。

數(shù)組扁平化

將多層次的數(shù)組轉(zhuǎn)變成單層的數(shù)組

function flatten(arr) {

return arr.reduce(function (pre,item) {

return pre.concat(item instanceof Array?flatten(item):item)

},[])

}

.sort()

默認(rèn)按字典序排序深滚。如果要對數(shù)值排序:.sort(function(a,b){ return a-b })

獲取dom節(jié)點(diǎn)的兄弟節(jié)點(diǎn)

firstChild,lastChild,nextSibling,previousSibling都會將空格或者換行當(dāng)做節(jié)點(diǎn)處理奕谭,但是有代替屬性

所以為了準(zhǔn)確地找到相應(yīng)的元素,會用

firstElementChild,

lastElementChild,

nextElementSibling,

previousElementSibling

兼容的寫法痴荐,這是JavaScript自帶的屬性血柳。

但壞消息是IE6,7,8不兼容這些屬性。IE9以上和火狐谷歌支持生兆。

js實(shí)現(xiàn)二叉查找樹

function BinarySearchTree () {

? ? ? ? var Node = function(key) {

? ? ? ? ? ? this.key = key,

? ? ? ? ? ? this.left = null,

? ? ? ? ? ? this.right = null

? ? ? ? }

? ? ? ? var root = null


? ? ? ? //插入節(jié)點(diǎn)

? ? ? ? this.insert = function(key) {

? ? ? ? ? ? var newNode = new Node(key)

? ? ? ? ? ? if(root === null) {

? ? ? ? ? ? ? ? root = newNode

? ? ? ? ? ? } else {

? ? ? ? ? ? ? ? insertNode(root, newNode)

? ? ? ? ? ? }

? ? ? ? }

? ? ? ? var insertNode = function(node, newNode) {

? ? ? ? ? ? if (newNode.key <= node.key) {

? ? ? ? ? ? ? ? if (node.left === null) {

? ? ? ? ? ? ? ? ? ? node.left = newNode

? ? ? ? ? ? ? ? }else {

? ? ? ? ? ? ? ? ? ? insertNode(node.left, newNode)

? ? ? ? ? ? ? ? }

? ? ? ? ? ? }else {

? ? ? ? ? ? ? ? if (node.right === null) {

? ? ? ? ? ? ? ? ? ? node.right = newNode

? ? ? ? ? ? ? ? }else {

? ? ? ? ? ? ? ? ? ? insertNode(node.right, newNode)

? ? ? ? ? ? ? ? }

? ? ? ? ? ? }

? ? ? ? }


? ? ? ? //實(shí)現(xiàn)中序遍歷

? ? ? ? this.inOrderTraverse = function() {

? ? ? ? ? ? inOrderTraverseNode(root)

? ? ? ? }

? ? ? ? var inOrderTraverseNode = function(node) {

? ? ? ? ? ? if (node !== null) {

? ? ? ? ? ? ? ? inOrderTraverseNode(node.left)

? ? ? ? ? ? ? ? console.log(node.key)

? ? ? ? ? ? ? ? inOrderTraverseNode(node.right)

? ? ? ? ? ? }

? ? ? ? }

? ? ? ? // 實(shí)現(xiàn)先序遍歷

? ? ? ? this.preOrderTraverse = function() {

? ? ? ? ? ? preOrderTraverseNode(root)

? ? ? ? }

? ? ? ? var preOrderTraverseNode = function(node) {

? ? ? ? ? ? if (node !== null) {

? ? ? ? ? ? ? ? console.log(node.key)

? ? ? ? ? ? ? ? preOrderTraverseNode(node.left)

? ? ? ? ? ? ? ? preOrderTraverseNode(node.right)

? ? ? ? ? ? }

? ? ? ? }

? ? ? ? // 實(shí)現(xiàn)后序遍歷

? ? ? ? this.postOrderTraverse = function() {

? ? ? ? ? ? postOrderTraverseNode(root)

? ? ? ? }

? ? ? ? var postOrderTraverseNode = function(node) {

? ? ? ? ? ? if (node !== null) {

? ? ? ? ? ? ? ? postOrderTraverseNode(node.left)

? ? ? ? ? ? ? ? postOrderTraverseNode(node.right)

? ? ? ? ? ? ? ? console.log(node.key)

? ? ? ? ? ? }

? ? ? ? }

? ? }

Null和Undefined

var?oValue;

alert(oValue?==?undefined);//output?"true"??

這段代碼顯示為true,代表oVlaue的值即為undefined难捌,因?yàn)槲覀儧]有初始化它。

alert(null==?document.getElementById('notExistElement'));

當(dāng)頁面上不存在id為"notExistElement"的DOM節(jié)點(diǎn)時(shí)鸦难,這段代碼顯示為"true"根吁,因?yàn)槲覀儑L試獲取一個(gè)不存在的對象。

JS實(shí)現(xiàn)快速排序

大致分三步:

1合蔽、找基準(zhǔn)(一般是以中間項(xiàng)為基準(zhǔn))

2击敌、遍歷數(shù)組,小于基準(zhǔn)的放在left拴事,大于基準(zhǔn)的放在right

3沃斤、遞歸

function quickSort(arr){

? ? ? ? ? ? //如果數(shù)組<=1,則直接返回if(arr.length<=1){return arr;}

? ? ? ? ? ? var pivotIndex=Math.floor(arr.length/2);//找基準(zhǔn),并把基準(zhǔn)從原數(shù)組刪除varpivot=arr.splice(pivotIndex,1)[0];

? ? ? ? ? ? //定義左右數(shù)組va rleft=[];

? ? ? ? ? ? var right=[];

? ? ? ? ? ? //比基準(zhǔn)小的放在left刃宵,比基準(zhǔn)大的放在rightfor(vari=0;i

? ? ? ? ? ? ? ? if(arr[i]<=pivot){

? ? ? ? ? ? ? ? ? ? left.push(arr[i]);

? ? ? ? ? ? ? ? }

? ? ? ? ? ? ? ? else{

? ? ? ? ? ? ? ? ? ? right.push(arr[i]);

? ? ? ? ? ? ? ? }

? ? ? ? ? ? }

? ? ? ? ? ? //遞歸return quickSort(left).concat([pivot],quickSort(right));

? ? ? ? }? ? ? ? ? ? ? ?

js手動實(shí)現(xiàn)call轰枝,apply,bind

Function.prototype.myCall =function(obj, ...args){

//我們要讓傳入的obj成為, 函數(shù)調(diào)用時(shí)的this值.

obj._fn_ =this;//在obj上添加_fn_屬性组去,值是this(要調(diào)用此方法的那個(gè)函數(shù)對象)鞍陨。

obj._fn_(...args);//在obj上調(diào)用函數(shù),那函數(shù)的this值就是obj.

deleteobj._fn_;// 再刪除obj的_fn_屬性,去除影響.

//_fn_ 只是個(gè)屬性名 你可以隨意起名,但是要注意可能會覆蓋obj上本來就有的屬性

}

Function.prototype.myApply =function(obj, ...args){

//我們要讓傳入的obj成為, 函數(shù)調(diào)用時(shí)的this值.

obj._fn_ =this;//在obj上添加_fn_屬性,值是this(要調(diào)用此方法的那個(gè)函數(shù)對象)诚撵。

obj._fn_(args);//在obj上調(diào)用函數(shù),那函數(shù)的this值就是obj.

deleteobj._fn_;// 再刪除obj的_fn_屬性,去除影響.

//_fn_ 只是個(gè)屬性名 你可以隨意起名缭裆,但是要注意可能會覆蓋obj上本來就有的屬性

}

Function.prototype.es6Bind = function(context, ...rest) {

? if (typeof this !== 'function') throw new TypeError('invalid invoked!');

? var self = this;

? return function F(...args) {

? ? if (this instanceof F) {

? ? ? return new self(...rest, ...args)

? ? }

? ? return self.apply(context, rest.concat(args))

? }

}

new的簡單實(shí)現(xiàn)

function newFunc(constructor){

? ? ? //第一步:創(chuàng)建一個(gè)空對象obj

? ? ? ? var obj = {};

? ? ? //第二步:將構(gòu)造函數(shù) constructor的原型對象賦給obj的原型

? ? ? ? obj.__proto__ = constructor.prototype;

? ? ? //第三步:將構(gòu)造函數(shù) constructor中的this指向obj,并立即執(zhí)行構(gòu)造函數(shù)內(nèi)部的操作

? ? ? ? constructor.apply(obj);

? ? ? //第四步:返回這個(gè)對象

? ? ? ? return obj;

}

保留小數(shù)

varnum =2.446242342;

num = num.toFixed(2); // 輸出結(jié)果為 2.45

let、const寿烟、var 的區(qū)別

是否存在變量提升澈驼?

var聲明的變量存在變量提升(將變量提升到當(dāng)前作用域的頂部)。即變量可以在聲明之前調(diào)用筛武,值為undefined缝其。

let和const不存在變量提升。即它們所聲明的變量一定要在聲明后使用徘六,否則報(bào)ReferenceError錯内边。

是否存在暫時(shí)性死區(qū)

let和const存在暫時(shí)性死區(qū)。即只要塊級作用域內(nèi)存在let命令待锈,它所聲明的變量就“綁定”(binding)這個(gè)區(qū)域漠其,不再受外部的影響。

是否允許重復(fù)聲明變量

var允許重復(fù)聲明變量竿音。let和const在同一作用域不允許重復(fù)聲明變量和屎。

是否存在塊級作用域

var不存在塊級作用域(內(nèi)層變量可能會覆蓋外層變量,計(jì)數(shù)的循環(huán)變量泄露為全局變量)春瞬。let和const存在塊級作用域柴信。

是否能修改聲明的變量

var和let可以。const聲明一個(gè)只讀的常量宽气。


DOM事件流


即比如點(diǎn)擊td元素時(shí)颠印,由外至內(nèi)層會經(jīng)歷捕獲階段,目標(biāo)階段抹竹,冒泡階段三個(gè)階段线罕,相應(yīng)地會觸發(fā)路徑元素上的事件?

此外,addEventListener(type, listener[, useCapture])函數(shù)默認(rèn)設(shè)置在冒泡階段窃判。

事件委托

在父元素上監(jiān)聽事件钞楼;通過event.target確定觸發(fā)源。

substring和substr的區(qū)別

兩者都是截取字符串袄琳。

相同點(diǎn):如果只是寫一個(gè)參數(shù)询件,兩者的作用都一樣:都是是截取字符串從當(dāng)前下標(biāo)以后直到字符串最后的字符串片段。

substr(startIndex);

substring(startIndex);

不同點(diǎn):第二個(gè)參數(shù)

substr(startIndex,lenth): 第二個(gè)參數(shù)是截取字符串的長度(從起始點(diǎn)截取某個(gè)長度的字符串)唆樊;

substring(startIndex, endIndex): 第二個(gè)參數(shù)是截取字符串最終的下標(biāo) (截取2個(gè)位置之間的字符串,‘含頭不含尾’)宛琅。

window對象

子對象:

navigator對象(了解即可)

瀏覽器對象,通過這個(gè)對象可以判定用戶所使用的瀏覽器逗旁,包含了瀏覽器相關(guān)信息嘿辟。

?screen對象(了解即可)

屏幕對象舆瘪,不常用。

history對象(了解即可)

window.history 對象包含瀏覽器的歷史红伦。

location對象

window.location 對象用于獲得當(dāng)前頁面的地址 (URL)英古,并把瀏覽器重定向到新的頁面。

localstorage和sessionstorage

前端路由

前端路由的兩種模式: hash 模式和 history 模式

hash模式

這里的 hash 就是指 url 尾巴后的 # 號以及后面的字符昙读。這里的 # 和 css 里的 # 是一個(gè)意思召调。hash 也 稱作 錨點(diǎn),本身是用來做頁面定位的蛮浑,她可以使對應(yīng) id 的元素顯示在可視區(qū)域內(nèi)唠叛。

由于 hash 值變化不會導(dǎo)致瀏覽器向服務(wù)器發(fā)出請求,而且 hash 改變會觸發(fā) hashchange 事件沮稚,瀏覽器的進(jìn)后退也能對其進(jìn)行控制艺沼,所以人們在 html5 的 history 出現(xiàn)前,基本都是使用 hash 來實(shí)現(xiàn)前端路由的壮虫。

使用到的api:

window.location.hash ='qq'// 設(shè)置 url 的 hash澳厢,會在當(dāng)前url后加上 '#qq'

varhash =window.location.hash// '#qq'??

window.addEventListener('hashchange',function(){// 監(jiān)聽hash變化环础,點(diǎn)擊瀏覽器的前進(jìn)后退會觸發(fā)})

history模式

已經(jīng)有 hash 模式了囚似,而且 hash 能兼容到IE8, history 只能兼容到 IE10线得,為什么還要搞個(gè) history 呢饶唤?

首先,hash 本來是拿來做頁面定位的贯钩,如果拿來做路由的話募狂,原來的錨點(diǎn)功能就不能用了。其次角雷,hash 的傳參是基于 url 的祸穷,如果要傳遞復(fù)雜的數(shù)據(jù),會有體積的限制勺三,而 history 模式不僅可以在url里放參數(shù)雷滚,還可以將數(shù)據(jù)存放在一個(gè)特定的對象中。

相關(guān)API:

window.history.pushState(state, title, url)// state:需要保存的數(shù)據(jù)吗坚,這個(gè)數(shù)據(jù)在觸發(fā)popstate事件時(shí)祈远,可以在event.state里獲取// title:標(biāo)題,基本沒用商源,一般傳 null// url:設(shè)定新的歷史記錄的 url车份。新的 url 與當(dāng)前 url 的 origin 必須是一樣的,否則會拋出錯誤牡彻。url可以是絕對路徑扎附,也可以是相對路徑怀酷。//如 當(dāng)前url是 https://www.baidu.com/a/,執(zhí)行history.pushState(null, null, './qq/')蚌成,則變成 https://www.baidu.com/a/qq/配喳,//執(zhí)行history.pushState(null, null, '/qq/'),則變成 https://www.baidu.com/qq/

window.history.replaceState(state, title, url)// 與 pushState 基本相同囱桨,但她是修改當(dāng)前歷史記錄,而 pushState 是創(chuàng)建新的歷史記錄

window.addEventListener("popstate",function(){// 監(jiān)聽瀏覽器前進(jìn)后退事件,pushState 與 replaceState 方法不會觸發(fā)? ? ? ? ? ? ? });

window.history.back()// 后退

window.history.forward()// 前進(jìn)

window.history.go(1)// 前進(jìn)一步盈蛮,-2為后退兩步,window.history.lengthk可以查看當(dāng)前歷史堆棧中頁面的數(shù)量

history 模式改變 url 的方式會導(dǎo)致瀏覽器向服務(wù)器發(fā)送請求技矮,這不是我們想看到的抖誉,我們需要在服務(wù)器端做處理:如果匹配不到任何靜態(tài)資源,則應(yīng)該始終返回同一個(gè) html 頁面衰倦。

用發(fā)布訂閱監(jiān)聽pushstate和replacestate

class Dep{

constructor(name){

this.id =new Date()

this.subs = []

}

defined(){

this.subs.push(Dep.watch)

}

notify(){

this.subs.forEach(item=>{

item.update()

})

}

}

Dep.watch =null

class watcher{

constructor(name,fn){

this.name =name

this.callback = fn

}

update(){

this.callback()

}

}

var addHistoryMethod = (function (){

var mydep =new Dep()

return function (name) {

if(name =='historychange'){

return function (name,fn) {

var watch =new watcher(name,fn)

Dep.watch = watch

mydep.defined()

Dep.watch =null

? ? ? }

}

else if(name ==='pushState' || name ==='replaceState'){

var method = history[name];

? ? ? return function(){

method.apply(history, arguments);

? ? ? ? mydep.notify()

}

}

}

}())

window.addHistoryListener = addHistoryMethod('historychange');

history.pushState =? addHistoryMethod('pushState');

history.replaceState =? addHistoryMethod('replaceState');

window.addHistoryListener('history',function(){

console.log('窗口的history改變了');

})

window.addHistoryListener('history',function(){

console.log('窗口的history改變了-我也聽到了');

})

history.pushState({first:'first'}, "page2", "/first")

獲得table里的行或列

var table = document.getElementById('mytable')

var tr = table.getElementsByTagName('tr')

js ascall碼轉(zhuǎn)換

str="A";

code = str.charCodeAt();//65

str2 = String.fromCharCode(code);//A

str3 = String.fromCharCode(0x60+26);//Z

添加或刪除類名

添加:節(jié)點(diǎn).classList.add("類名")袒炉;

刪除:節(jié)點(diǎn).classList.remove("類名");

js中判斷數(shù)組中是否包含某元素的方法

方法一:arr.indexOf(某元素):未找到則返回 -1樊零。

arr.includes()? ?數(shù)組中含有某值返回true我磁,沒有返回false

event.x和event.clientX和event.offsetX

event.x和event.clientX為相對與窗口的位置。

event.offsetX為相對于目標(biāo)對象的padding外邊緣的位置驻襟,如果點(diǎn)擊在border中的話夺艰,會取到負(fù)值

.concat()合并數(shù)組不會改變原數(shù)組,而是返回一個(gè)新數(shù)組

JS深拷貝

function deepCopy(obj) {

? ? ? varresult = Array.isArray(obj) ? [] : {};

? ? ? for(var key in obj) {

? ? ? ? if (obj.hasOwnProperty(key)) {

? ? ? ? ? if(typeofobj[key] ==='object' && obj[key]!==null) {

? ? ? ? ? ? result[key] = deepCopy(obj[key]);? //遞歸復(fù)制

? ? ? ? ? } else {

? ? ? ? ? ? result[key] = obj[key];

? ? ? ? ? }

? ? ? ? }

? ? ? }

? ? ? return result;

? ? }

js堆排序

// 交換兩個(gè)節(jié)點(diǎn)

function swap(A, i, j) {

? let temp = A[i];

? A[i] = A[j];

? A[j] = temp;

}

// 將 i 結(jié)點(diǎn)以下的堆整理為大頂堆沉衣,注意這一步實(shí)現(xiàn)的基礎(chǔ)實(shí)際上是:

// 假設(shè) 結(jié)點(diǎn) i 以下的子堆已經(jīng)是一個(gè)大頂堆郁副,shiftDown函數(shù)實(shí)現(xiàn)的

// 功能是實(shí)際上是:找到 結(jié)點(diǎn) i 在包括結(jié)點(diǎn) i 的堆中的正確位置。后面

// 將寫一個(gè) for 循環(huán)豌习,從第一個(gè)非葉子結(jié)點(diǎn)開始存谎,對每一個(gè)非葉子結(jié)點(diǎn)

// 都執(zhí)行 shiftDown操作,所以就滿足了結(jié)點(diǎn) i 以下的子堆已經(jīng)是一大

//頂堆

function shiftDown(A, i, length) {

? let temp = A[i]; // 當(dāng)前父節(jié)點(diǎn)

// j<length 的目的是對結(jié)點(diǎn) i 以下的結(jié)點(diǎn)全部做順序調(diào)整

? for(let j = 2*i+1; j<length; j = 2*j+1) {

? ? temp = A[i];? // 將 A[i] 取出肥隆,整個(gè)過程相當(dāng)于找到 A[i] 應(yīng)處于的位置

? ? if(j+1 < length && A[j] < A[j+1]) {

? ? ? j++;? // 找到兩個(gè)孩子中較大的一個(gè)既荚,再與父節(jié)點(diǎn)比較

? ? }

? ? if(temp < A[j]) {

? ? ? swap(A, i, j) // 如果父節(jié)點(diǎn)小于子節(jié)點(diǎn):交換;否則跳出

? ? ? i = j;? // 交換后栋艳,temp 的下標(biāo)變?yōu)?j

? ? } else {

? ? ? break;

? ? }

? }

}

// 堆排序

function heapSort(A) {

? // 初始化大頂堆恰聘,從第一個(gè)非葉子結(jié)點(diǎn)開始

? for(let i = Math.floor(A.length/2-1); i>=0; i--) {

? ? shiftDown(A, i, A.length);

? }

? // 排序,每一次for循環(huán)找出一個(gè)當(dāng)前最大值嘱巾,數(shù)組長度減一

? for(let i = Math.floor(A.length-1); i>0; i--) {

? ? swap(A, 0, i); // 根節(jié)點(diǎn)與最后一個(gè)節(jié)點(diǎn)交換

? ? shiftDown(A, 0, i); // 從根節(jié)點(diǎn)開始調(diào)整憨琳,并且最后一個(gè)結(jié)點(diǎn)已經(jīng)為當(dāng)

? ? ? ? ? ? ? ? ? ? ? ? // 前最大值,不需要再參與比較旬昭,所以第三個(gè)參數(shù)

? ? ? ? ? ? ? ? ? ? ? ? // 為 i篙螟,即比較到最后一個(gè)結(jié)點(diǎn)前一個(gè)即可

? }

}

let Arr = [4, 6, 8, 5, 9, 1, 2, 5, 3, 2];

heapSort(Arr);

alert(Arr);

希爾排序(增量排序)

//shellSort

function shellSort(arr) {

? for(let gap = Math.floor(arr.length/2); gap > 0; gap = Math.floor(gap/2)) {

??? // 內(nèi)層循環(huán)與插入排序的寫法基本一致,只是每次移動的步長變?yōu)?gap

??? for(let i = gap; i < arr.length;

i++) {

????? let j =i;

????? let temp =arr[j];

????? for(; j> 0; j -=gap) {

??????? if(temp >= arr[j-gap]) {

????????? break;

??????? }

??????? arr[j]= arr[j-gap];

????? }

????? arr[j]=temp;

??? }

? }

? return arr;

}

// example

let arr = [2,5,10,7,10,32,90,9,11,1,0,10];

alert(shellSort(arr));

判斷dom節(jié)點(diǎn)的是否包含某個(gè)子節(jié)點(diǎn)

contains?自帶方法问拘,判斷一個(gè)元是不是另一個(gè)元的子集

document.documentElement.contains(document.body)

數(shù)組深拷貝

1.var arr = arr2.concat()

2.var arr = arr2.map(item=>return item)

JS-設(shè)計(jì)模式

工廠模式

工廠函數(shù)就是做一個(gè)對象創(chuàng)建的封裝遍略,并將創(chuàng)建的對象return出去

?function newObj(name,age){

??? var o = new Object();

??? o.name=name;

??? o.age=age;

??? returno;

}

var obj = newObj();

單例模式:只允許存在一個(gè)實(shí)例的模式

?var Instance = (function(){

??? varobj;

??? return function(){

??????? if(obj === undefined) obj = new Date();

??????? returnobj;

??? }

})();

var ibs = Instance();

觀察者模式

又稱發(fā)布訂閱者模式惧所,經(jīng)典案例:事件監(jiān)聽,一個(gè)元素同時(shí)監(jiān)聽多個(gè)同類型事件绪杏,元素對象即為發(fā)布者下愈,每一個(gè)事件處理函數(shù)即為訂閱者。

策略模式

策略模式的定義是:定義一系列的算法蕾久,把它們一個(gè)個(gè)封裝起來势似,并且使它們可以相互替換,從而避免很多if語句僧著,曾經(jīng)學(xué)過最簡單的策略模式雛形就是使用數(shù)組的方式解決傳入數(shù)字得到對應(yīng)星期幾問題的算法履因。

比如公司的年終獎是根據(jù)員工的工資和績效來考核的,績效為A的人盹愚,年終獎為工資的4倍栅迄,績效為B的人,年終獎為工資的3倍皆怕,績效為C的人毅舆,年終獎為工資的2倍

?var obj ={

??? "A": function(salary) {

??????? return salary * 4;

??? },

??? "B" : function(salary) {

??????? return salary * 3;

??? },

??? "C" : function(salary) {

??????? return salary * 2;

??? }

};

var calculateBouns =function(level,salary){

??? returnobj[level](salary);

};

console.log(calculateBouns('A',10000)); // 40000

代理模式

代理模式(Proxy),為其他對象提供一種代理以控制對這個(gè)對象的訪問愈腾,為了不暴露執(zhí)行對象的部分代碼

?//三個(gè)對象

//用戶委托快捷方式打開exe

//為了不暴露執(zhí)行對象的部分代碼

//男孩委托快遞小哥給女孩送禮物

var girl = function(name){

??? this.name =name;

}

//隱藏復(fù)雜憋活,不愿意修改的的方法

var boy = function(girl){

??? this.girl =girl;

??? this.send = function(gift){

??????? alert("你好:"+this.girl.name+",給你一個(gè)"+gift);

??? }

}

var proxyBro = function(girl){

??? this.send = function(gift){

??????? new boy(girl).send(gift);

??? }

}

var pro = new proxyBro(new girl("Lisa"));

pro.send("么么噠");

pro.send("玫瑰花");

模塊模式:

在立即執(zhí)行函數(shù)表達(dá)式中定義的變量和方法在外界是訪問不到的,只能通過其向外部提供的接口,"有限制"地訪問.通過函數(shù)作用域解決了屬性和方法的封裝問題.

var?Person = (function(){

??var?name =?"xin";

??var?age = 22;

??function?getName(){

????return?name;

??}

??function?getAge(){

????return?age;

??}

??return?{

????getName: getName,

????getAge: getAge

??}

})();

console.log(age);?// 報(bào)錯:age未定義

console.log(name);?// 報(bào)錯:name未定義

console.log(Person.age);?// undefined

console.log(Person.name);?// undefined

// 只能通過Person提供的接口訪問相應(yīng)的變量

console.log(Person.getName());?// xin

console.log(Person.getAge());?// 22

構(gòu)造函數(shù)模式

混合模式

function?Person(name,age){

??this.name = name;

??this.age = age;

};

Person.prototype.printName =?function(){

??console.log(this.name);

}

function?Student(name,age){

??// 繼承 Person 的屬性

??Person.call(this,name,age);

}

function?create(prototype){

??function?F(){};

??F.prototype = prototype;

??return?new?F();

}


// 讓Student的原型指向一個(gè)對象,該對象的原型指向了Person.prototype,通過這種方式繼承 Person 的方法

Student.prototype = create(Person.prototype);

Student.prototype.printAge =?function(){

??console.log(this.age);

}

var?student =?new?Student('xin',22);

student.printName();?// "xin"


進(jìn)制轉(zhuǎn)換

parseInt(num,8); //八進(jìn)制轉(zhuǎn)十進(jìn)制

parseInt(num,16);? //十六進(jìn)制轉(zhuǎn)十進(jìn)制

parseInt(num).toString(8)//十進(jìn)制轉(zhuǎn)八進(jìn)制

parseInt(num).toString(16)//十進(jìn)制轉(zhuǎn)十六進(jìn)制

parseInt(num,2).toString(8)//二進(jìn)制轉(zhuǎn)八進(jìn)制

parseInt(num,2).toString(16)//二進(jìn)制轉(zhuǎn)十六進(jìn)制

parseInt(num,8).toString(2)//八進(jìn)制轉(zhuǎn)二進(jìn)制

parseInt(num,8).toString(16)//八進(jìn)制轉(zhuǎn)十六進(jìn)制

parseInt(num,16).toString(2)//十六進(jìn)制轉(zhuǎn)二進(jìn)制

parseInt(num,16).toString(8)//十六進(jìn)制轉(zhuǎn)八進(jìn)制

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市顶滩,隨后出現(xiàn)的幾起案子余掖,更是在濱河造成了極大的恐慌寸爆,老刑警劉巖礁鲁,帶你破解...
    沈念sama閱讀 221,695評論 6 515
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異赁豆,居然都是意外死亡仅醇,警方通過查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,569評論 3 399
  • 文/潘曉璐 我一進(jìn)店門魔种,熙熙樓的掌柜王于貴愁眉苦臉地迎上來析二,“玉大人,你說我怎么就攤上這事节预∫渡悖” “怎么了?”我有些...
    開封第一講書人閱讀 168,130評論 0 360
  • 文/不壞的土叔 我叫張陵安拟,是天一觀的道長蛤吓。 經(jīng)常有香客問我,道長糠赦,這世上最難降的妖魔是什么会傲? 我笑而不...
    開封第一講書人閱讀 59,648評論 1 297
  • 正文 為了忘掉前任锅棕,我火速辦了婚禮,結(jié)果婚禮上淌山,老公的妹妹穿的比我還像新娘裸燎。我一直安慰自己,他們只是感情好泼疑,可當(dāng)我...
    茶點(diǎn)故事閱讀 68,655評論 6 397
  • 文/花漫 我一把揭開白布德绿。 她就那樣靜靜地躺著,像睡著了一般退渗。 火紅的嫁衣襯著肌膚如雪脆炎。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 52,268評論 1 309
  • 那天氓辣,我揣著相機(jī)與錄音秒裕,去河邊找鬼。 笑死钞啸,一個(gè)胖子當(dāng)著我的面吹牛几蜻,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播体斩,決...
    沈念sama閱讀 40,835評論 3 421
  • 文/蒼蘭香墨 我猛地睜開眼梭稚,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了絮吵?” 一聲冷哼從身側(cè)響起弧烤,我...
    開封第一講書人閱讀 39,740評論 0 276
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎蹬敲,沒想到半個(gè)月后暇昂,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 46,286評論 1 318
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡伴嗡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 38,375評論 3 340
  • 正文 我和宋清朗相戀三年急波,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片瘪校。...
    茶點(diǎn)故事閱讀 40,505評論 1 352
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡澄暮,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出阱扬,到底是詐尸還是另有隱情泣懊,我是刑警寧澤,帶...
    沈念sama閱讀 36,185評論 5 350
  • 正文 年R本政府宣布麻惶,位于F島的核電站馍刮,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏用踩。R本人自食惡果不足惜渠退,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,873評論 3 333
  • 文/蒙蒙 一忙迁、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧碎乃,春花似錦姊扔、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,357評論 0 24
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至梗掰,卻和暖如春嵌言,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背及穗。 一陣腳步聲響...
    開封第一講書人閱讀 33,466評論 1 272
  • 我被黑心中介騙來泰國打工摧茴, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人埂陆。 一個(gè)月前我還...
    沈念sama閱讀 48,921評論 3 376
  • 正文 我出身青樓苛白,卻偏偏與公主長得像,于是被迫代替她去往敵國和親焚虱。 傳聞我的和親對象是個(gè)殘疾皇子购裙,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,515評論 2 359

推薦閱讀更多精彩內(nèi)容