Javascript作為前端開發必須掌握的一門語言,因為語言的靈活性,有些知識點看起來簡單,在真正遇到的時候,卻不一定會直接做出來,今天我們就一起來看看幾道題目吧 題目1 var val = 'smtg'; console.log(' Value is' + (val 'smtg') ? 'Some ...
Javascript作為前端開發必須掌握的一門語言,因為語言的靈活性,有些知識點看起來簡單,在真正遇到的時候,卻不一定會直接做出來,今天我們就一起來看看幾道題目吧
題目1
var val = 'smtg';
console.log(' Value is' + (val === 'smtg') ? 'Something' : 'Nothing');
這道題考察的知識點是運算符的優先順序。
首先,小括弧的優先順序是最高的,所以首先會做判斷,val與smtg相等返回true。因此最後這道題等價於判斷是執行下麵的語句1還是語句2.
//語句1
'Value is' + (true ? 'Something' : 'Nothing');
//語句2
'Value is true' ? 'Something' : 'Nothing';
根據運算符優先順序我們知道,連接元算符+的優先順序要高於條件運算符?的優先順序,因此實際執行的是語句2,所以最後返回的結果是
'Something'.
題目2
我們再來看看下麵這道題。
var ary = [0,1,2];
ary[6] = 6;
var result = ary.filter(function(x){
return x === undefined;
});
console.log(result);
這道題考察的時候數組的初始化和filter方法。
第一眼看上去,以為會輸出[undefined,undefined,undefined],但是實際輸出卻是undefined,為什麼會這樣?
這是因為在JavaScript里存在稀疏數組的概念,數組在初始化時,只會對已經確定索引的選項進行初始化,對於不存在索引的選項不進行初始化,通過以下代碼可以確定。
0 in ary;//true
1 in ary;//true
3 in ary;//false
4 in ary;//false
6 in ary;//true
對數組使用in運算符時,是通過枚舉數組的索引,通過3和4返回false可以知道,ary[3]和ary[4]實際是不存在的,未進行初始化。
我們再來看看 Array.prototype.filter方法和polyfill,註意代碼中標註的地方。
Array.prototype.filter = function(fun /*thisArg*/){
if(this === void 0 || this === null){
throw new TypeError();
}
var t = Object(this);
var len = t.length >>> 0;
if(typeof fun !== 'function'){
throw new TypeError();
}
var res = [];
var thisArg = arguments.length >=2 ? arguments[1]:void 0;
for(var i = 0;i<len;i++){
if(i in t){ //註意這裡,使用的是in運算符
var val = t[i];
if(fun.call(thisArg,val,i,t)){
res.push(val);
}
}
}
return res;
}
在filter方法源碼中,我發現使用了in運算符,而arg數組沒有對索引為3,4,5的值進行初始化,因此會直接跳過執行,所以最後返回undefined。
題3
function caseshow(val){
switch(val){
switch(value){
case 'A':
console.log('A');
break;
case 'B':
console.log('B');
break;
case 'C':
console.log('C');
break;
default:
console.log('do not know!');
}
}
}
caseshow(new String('A'));
咋一看,很多人會以為輸出'case A',但實際輸出'do not know'。why?
這道題考察的知識點是:switch和string,我們需要知道一下兩點:
1,JavaScript中switch執行的是嚴格相等(===)。
2,字元串和string的實例不一樣。
第二點我們可以測試下。
var s_p = 'foo';
var s_o = new String(s_p)
console.log(typeof s_p) //'string'
onsole.log(typeof s_o) //'object'
onsole.log(s_p === s_o) //'false'
因此針對題目中的'A'與String('A')並不嚴格相等,最終會返回‘do not know’
題4
針對上面的題目3,我們稍作一點改動,成為下麵的題目4,再看看結果輸出什麼?
function caseshow2(val){
switch(val){
case 'A':
console.log('A');
break;
case 'B':
console.log('B');
break;
case undefined:
console.log('undefined');
break;
default:
console.log('do not know!');
}
}
caseshow2(String('A'));
題目4相對於題目3,只是在最後調用的時候傳入的參數是String('A'),它的結果就變成了'Case A'。這是為什麼呢?
其實很簡單,String(X)返回的是一個字元串而不會生成一個新的String實例,因此與'A'是嚴格相等的。