js小技巧--摘錄1
原文地址https://github.com/loverajoel/jstips
1、數組中插入元素
a.尾部追加
var arr = [1,2,3,4,5]; var arr2 = []; arr.push(6); arr[arr.length] = 6; arr2 = arr.concat([6]);
//快慢排序
1. arr[arr.length] = 6; // 平均42 345 449 ops/sec 2. arr.push(6); // 慢34.66% 3. arr2 = arr.concat([6]); // 慢85.79%
b.頭部追加
ar arr = [1,2,3,4,5]; arr.unshift(0); [0].concat(arr);
//最快的為 1. [0].concat(arr); // 平均4 972 622 ops/sec 2. arr.unshift(0); // 慢64.70%
c.數組中間插入元素
var items = [‘one‘, ‘two‘, ‘three‘, ‘four‘]; items.splice(items.length / 2, 0, ‘hello‘);
2、if嵌套語句的優化
if (color) { if (color === ‘black‘) { printBlackBackground(); } else if (color === ‘red‘) { printRedBackground(); }else if (color === ‘blue‘) { printBlueBackground(); } else if (color === ‘green‘) { printGreenBackground(); } else { printYellowBackground(); } } //可以改寫為 var colorObj = { ‘black‘: printBlackBackground, ‘red‘: printRedBackground, ‘blue‘: printBlueBackground, ‘green‘: printGreenBackground,‘yellow‘: printYellowBackground }; if (color in colorObj) { colorObj[color](); }
3、sort排序含音節字符的字符串
Javascript有一個原生方法sort可以排列數組。一次簡單的array.sort()
將每一個數組元素視為字符串並按照字母表排列。你也可以提供自定義排列方法
[‘Shanghai‘, ‘New York‘, ‘Mumbai‘, ‘Buenos Aires‘].sort(); // ["Buenos Aires", "Mumbai", "New York", "Shanghai"] //下面非ASCLL元素失效,sort只在英文下生效 // 西班牙語 [‘único‘,‘árbol‘, ‘cosas‘, ‘fútbol‘].sort(); // ["cosas", "fútbol", "árbol", "único"] // bad order // 德語 [‘Woche‘, ‘w?chentlich‘, ‘w?re‘, ‘Wann‘].sort(); // ["Wann", "Woche", "w?re", "w?chentlich"] // bad order
處理辦法:由ECMAScript國際化API提供的localeCompare和Intl.Collator。
[‘único‘,‘árbol‘, ‘cosas‘, ‘fútbol‘].sort(function (a, b) { return a.localeCompare(b); }); // ["árbol", "cosas", "fútbol", "único"] [‘Woche‘, ‘w?chentlich‘, ‘w?re‘, ‘Wann‘].sort(function (a, b) { return a.localeCompare(b); }); // ["Wann", "w?re", "Woche", "w?chentlich"] [‘único‘,‘árbol‘, ‘cosas‘, ‘fútbol‘].sort(Intl.Collator().compare); // ["árbol", "cosas", "fútbol", "único"] [‘Woche‘, ‘w?chentlich‘, ‘w?re‘, ‘Wann‘].sort(Intl.Collator().compare); // ["Wann", "w?re", "Woche", "w?chentlich"]
4、使用嚴格模式
程序員喜歡電腦幫我們做一些無聊的工作,喜歡它自動的檢查我們工作上的錯誤。這就是”use strict”幫我們做的,它把我們的錯誤轉變為了JavaScript錯誤。
// 全腳本嚴格模式 "use strict"; var v = "Hi! I‘m a strict mode script!"; //或者 function f() { // 方法級嚴格模式 ‘use strict‘; function nested() { return "And so am I!"; } return "Hi! I‘m a strict mode function! " + nested(); } function f2() { return "I‘m not strict."; }
通過在JavaScript文件或方法內引入此指令,使JavaScript引擎運行在嚴格模式下,這直接禁止了許多大項目中不受歡迎的操作。另外,嚴格模式也改變了以下行為:
- 只有被”var”聲明過的變量才可以引用
- 試圖寫只讀變量時將會報錯
- 只能通過”new”關鍵字調用構造方法
- “this”不再隱式的指向全局變量
- 對eval()有更嚴格的限制
- 防止你使用預保留關鍵字命名變量
嚴格模式對於新項目來說是很棒的,但對於一些並沒有使用它的老項目來說,引入它也是很有挑戰性的。如果你把所有js文件都連接到一個大文件中的話,可能導致所有文件都運行在嚴格模式下,這可能也會有一些問題。
它不是一個聲明,而是一個表達式,被低版本的JavaScript忽略。 嚴格模式的支持情況:
- Internet Explorer 10+
- Firefox 4+
- Chrome 13+
- Safari 5.1+
- Opera 12+
5、將node list轉為數組
querySelectorAll
方法返回一個類數組對象稱為node list。這些數據結構被稱為“類數組
const nodelist = document.querySelectorAll(‘div‘); const nodelistToArray = Array.apply(null, nodelist); //或者 const nodelistToArray = Array.prototype.slice.call(nodelist);
const nodelist
ToArray= [...document.querySelectorAll(‘div‘)]; // 返回一個真正的數組
//之後 ..
nodelistToArray.forEach(...);
nodelistToArray.map(...);
nodelistToArray.slice(...);
6、檢查對象是否存在某屬性
var myObject = { name: ‘@tips_js‘ }; if (myObject.name) { ... } //這樣可以 //同時用hasOwnProperty和in操作符可以區分屬性是繼承的還是自身的 var myObject = { name: ‘@tips_js‘ }; myObject.hasOwnProperty(‘name‘); // true ‘name‘ in myObject; // true myObject.hasOwnProperty(‘valueOf‘); // false, valueOf 繼承自原型鏈 ‘valueOf‘ in myObject; // true
7、contains功能
位操作符 ~, “按位操作符操作數字的二進制形式,但是返回值依然是標準的JavaScript數值。”
它將-1
轉換為0
,而0
在javascript為false
,所以:
var someText = ‘text‘; !!~someText.indexOf(‘tex‘); // someText contains "tex" - true !~someText.indexOf(‘tex‘); // someText NOT contains "tex" - false ~someText.indexOf(‘asd‘); // someText doesn‘t contain "asd" - false ~someText.indexOf(‘ext‘); // someText contains "ext" - true //在ES6中提供了includes() 方法供我們判斷一個字符串是否包含了另一個字符串: ‘something‘.includes(‘thing‘); // true //在ECMAScript 2016 (ES7)甚至可能將其應用於數組,像indexOf一樣: !!~[1, 2, 3].indexOf(1); // true [1, 2, 3].includes(1); // true
8、快速但是危險的取整方法(~~)
一個按位非操作符~
首先將輸入input
截取為32位,然後將其轉換為-(input+1)
。因此雙按位非操作符將輸入轉換為-(-(input + 1)+1)
,使其成為一個趨向於0取整的好工具。對於數字的輸入,它很像Math.trunc()
。失敗時返回0
,這可能在解決Math.trunc()
轉換錯誤返回NaN
時是一個很好的替代。
console.log(~~47.11) // -> 47 console.log(~~1.9999) // -> 1 console.log(~~3) // -> 3 console.log(~~-3.66) // -> -3
當處理大數時
因為~
首先將數組轉換為32位,~~
的結果偽值在 ±2.15*10^12左右。如果你沒有明確的檢查輸入值的範圍,當轉換的值最終與原始值有很大差距時,用戶就可能觸發未知的行為:
a = 2147483647.123 // 比32位最大正數,再多一點 console.log(~~a) // -> 2147483647 (ok) a += 10000 // -> 2147493647.123 (ok) console.log(~~a) // -> -2147483648 (huh?)
9.安全拼接字符串
var one = 1; var two = 2; var three = ‘3‘; var result = ‘‘.concat(one, two, three); //"123"
10、對數組進行洗牌
這段代碼運用了優秀的Fisher-Yates Shuffling算法對數組進行洗牌
const shuffle = arr => { for (let i = arr.length - 1; i > 0; i--) { let j = ~~(Math.random() * (i + 1)); [arr[i],arr[j]] = [arr[j],arr[i]] } return arr; } var a = [1, 2, 3, 4, 5, 6, 7, 8]; var b = shuffle(a); console.log(b); // [2, 7, 8, 6, 5, 3, 1, 4]
11、清空數組的兩種方法
// 定義一個數組 var list = [1, 2, 3, 4]; //清空數組 list = []; //或者 list.length = 0;
-
list = []
將一個新的數組的引用賦值給變量,其他引用並不受影響。 這意味著以前數組的內容被引用的話將依舊存在於內存中,這將導致內存泄漏。 -
list.length = 0
刪除數組裏的所有內容,也將影響到其他引用。
然而,如果你復制了一個數組(A 和 Copy-A),如果你用list.length = 0
清空了它的內容,復制的數組也會清空它的內容。
var foo = [1,2,3]; var bar = [1,2,3]; var foo2 = foo; var bar2 = bar; foo = []; bar.length = 0; console.log(foo, bar, foo2, bar2); //[] [] [1, 2, 3] []
js小技巧--摘錄1