更好的 JavaScript 寫法筆記

parseInt() 的第二個參數

// 建議指定第二個參數
> parseInt("123", 10)
123
> parseInt("010", 10)
10
// 如果不指定,以下的 "010" 將會被改為 8 進位,因為最前方的 0 
> parseInt("010")
8

雙等號運算子 ==(等於)會進行型態強制轉換

> "monkey" == "monkey"
true
> 1 == true
true
// 避免型態強制轉換,要用三等號運算子
> 1 === true
false
> true === true
true

while 迴圈以及 do-while 迴圈的不同

while (true) {
  // 無限迴圈!
}

do {
  // 執行至少一次,僅管條件不符合 while(false)
} while (true)

&& 以及 || 運算子「短路邏輯」檢查

// 存取一個物件的屬性前檢查物件是否為空 (null)
// 第一 o 不為空才會存取 getName() 屬性
var name = o && o.getName();

// 用來設預設值:
// 如果 otherName 為空,name 就會被設為"預設"
var name = otherName || "預設";

三元運算子 (tertiary operator)

var allowed = (age > 18) ? "是" : "否";

建立空物件的兩種基本方法

var obj = new Object();
// 以及
var obj = {};

物件屬性的兩種存取方法

obj.name = "小明"
var name = obj.name;
// 以及
obj["name"] = "小明";
var name = obj["name"];

更有效率的陣列查詢 -> 避免每迴圈一次就會查詢一次 length 屬性

// 正常方式
for (var i = 0; i < arr.length; i++) {
    //處理 arr[i]
}
// 避免每迴圈一次就會查詢一次 length 屬性,以下方式較有效率
for (var i = 0, len = arr.length; i < len; i++) {
    //處理 arr[i]
}

函式裡的參數 arguments

// 存取一個叫做 arguments 的變數,一個類似陣列的物件,內含所有遞給函式的值
function avg() {
    var sum = 0;
    for (var i = 0, j = arguments.length; i < j; i++) {
        sum += arguments[i];
    }
    return sum / arguments.length;
}
> avg(2, 3, 4, 5)
3.5

apply() 與 call()

基本上的不同在於傳入參數的方式, call() 是以逗號分開的參數, apply() 是以傳入一個陣列的方式。

fun.apply(thisArg, [argsArray])

fun.call(thisArg, arg1, arg2,...)

巢狀函式

將只有該函式會使用到的函式包括在其中。這樣便能保持全域領域 (global scope) 的函式不會太多。不在全域領界內塞太多函式是件好事情。

function betterExampleNeeded() {
    var a = 1;
    function oneMoreThanA() {
        return a + 1;
    }
    return oneMoreThanA();
}

Closures(閉包) 避免 memory leak 破壞相互參照(circular reference)的方法

// 將物件 el 直接設為 null
function addHandler() {
    var el = document.getElementById('el');
    el.onclick = function() {
        this.style.backgroundColor = 'red';
    }
    el = null;
}
// 藉由增加一個新的 closure 來解除 circular reference
function addHandler() {
    var clickHandler = function() {
        this.style.backgroundColor = 'red';
    }
    (function() {
        var el = document.getElementById('el');
        el.onclick = clickHandler;
    })();
}
// 直接避開 closure
var el = document.getElementById('el');
el.onclick = clickHandler;

var clickHandler = function() {
    this.style.backgroundColor = 'red';
}

 

整理自:https://developer.mozilla.org/zh-TW/docs/Web/JavaScript/A_re-introduction_to_JavaScript

Facebook Debug URL from JavaScript

如果客製化的圖片或影片(jpg, png, gif, video)在分享時無法被 Facebook 的發佈預覽。

可以預先做一個 url debugger 讓 Facebook 先 cache 資料。

$.post('https://graph.facebook.com', {
    id: URL,
    scrape: true
}, function(response) {

});

 

JavaScript Regular Expression

常用驗證

信用卡號:測試連結
\d{4}-?\d{4}-?\d{4}-?\d{4}

手機及電話號碼(含分機):測試連結
\d{2,4}-?\d{3,4}-?\d{3,4}#?(\d+)?

Email:測試連結
\([^.][a-z].?[a-z.]+)@(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,})

統一發票:測試連結
\^[a-zA-Z]{2}[-]?[0-9]{8}$

工具網站 https://regex101.com/ :可以很快驗證你的正規表達式。

特殊字元的使用

Single-Characters

\d0-9
\wA-Z, a-z, 0-9
\Wnot A-Z, a-z, 0-9
\swhite-space
\Snot white-space
.代表除了換行符號 (\n) 以外的任一字元。如果要包括換行符號, 請使用 [\s\S]。

Quantifiers

*0 或 更多
+ 1 或 更多
? 0 或 1
{min, max} 重複 min 到 max 次
{n} 重複 n 次

Position

^開始
$結尾
\b在邊界的字元

Character Class [ ]

[abc]抓單一個字元: a, b, or c
-[-.] 如果 - 是第一個字元,後面的 . 會是實字元 . ,而不是代表任何字元。如果是[a-z]代表 a 到 z。
^[^abc] 代表不是 a,b 或 c。[a^bc] 代表 a 或 b, c

Alternation ( )

(...)括住一群字元,將之視成一個集合, 通常用來集合表示多個檢核式。例如 (com|net)

 

詳細說明連結:MDN 正規表達式模式的編寫

CodePen 使用 GitHib 的函式庫網址

如果你的 CodePen 有使用 host 在 GitHub 的函式庫,domain 在 raw.githubusercontent.com 的會出現 MIME Type 錯誤。

例如以下網址:http://raw.githubusercontent.com/user/repo/branch/file.js

如果是在非生產環境,像是 jsFiddle請將 domain 改成 rawgit.com,成為 http://rawgit.com/user/repo/branch/file.js。

如果是生產環境,請將 domain 改成 cdn.rawgit.com,成為 http://cdn.rawgit.com/user/repo/branch/file.js。

來源為以下CodePen:

See the Pen Link and execute external JavaScript file hosted on GitHub by Jon Vadillo (@jonvadillo) on CodePen.