最近整理了一下,就決定跟大家討論一下最近對於Javascripet的型別認識。
Javascripet是一種「弱型別」的語言,所以會產生很多你意想不到噁心的事情
至於什麼是弱型別?
小弟弟我來為大家解釋一下,在程式語言的世界裡有分兩種型別系統
1.強型別 (程式所定義的變數型別=變數在執行的型別)
這類型的程式語言在宣告變數的時候就已經把資料型別指定好給變數,如果對這個變數去做錯誤的型別運算他就會直接噴錯誤給你看。 (廢話!你還想拿明朝的劍斬清朝的官啊)
舉個例子來說,以下是一段ruby的程式碼
a=2
b='3'
puts a+b #會噴錯
因為ruby是一種強型別的語言,上面的程式碼一定會給你這段
String can't be coerced into Integer (TypeError)
大概的意思就是說不能將一個字符串強制轉換為整數
2.弱型別 (語法簡潔,但是要注意型態轉換會產生非預期的錯誤)
以下是一段Javascripet的程式碼
const a = 2;
const b = '3';
console.log(a+b); //會印出5
Javascripet會判斷你使用到+號是要做運算,並透過自動轉型的特性去把字串型別轉換成數字。
所以這下你就可以拿明朝的劍斬清朝的官(喂~
接下來就是重頭戲啦,在javascript的世界中只有分基本型別(Primitives)跟物件型別(Object)兩大類。如果想要確認型別可以透過typeof()來確認。
有六種資料型別是基本型別:Boolean、Null、Undefined、Number、BigInt、String、Symbol(於EC6加入)。
字串其實就是字元的集合,字元代表一個字母的意思。字串就是一個單詞的概念。舉個例子:A是字元Apple是字串,
但在Javascript的世界裡沒有字元的概念,只有字串。字串會用' '(單引號)或是" "(雙引號)包住,切記不可以混用單引號開頭就是單引號結尾。以下用程式碼示範:
const str = 'hello world';
const str2 = "這是一個字串";
單引號內如果有用到單引號或雙引號內有用到雙引號會出錯
const str = 'I'm 18 year-old' //會出錯!
但如果改成這樣
const str = "I'm 18 year-old"; //這個沒問題
如果有非用不可的狀況就可以用跳脫字元(escape character)來處理
const str = 'I\'m 18 year-old'; //沒問題
如果想要連接字串可以使用加號
const str = 'hi!' + 'I am Eazy';
這邊補充一下ES6後加入的新語法`` 反引號(backtick)
這個超好用的東西,可以讓你在字串中直接塞變數不用在透過加號也可以讓你直接支援多行字串。這邊就不囉唆直上程式碼
const age = 18;
const str = ` hello word ! I am ${age} year-old `;
console.log(str); //可以印出 hello word ! I am 18 year-old
Javascript只有一種數值的型別,那就是Number。不管是整數(integer)或是帶有小數點的浮點數字都是屬於這一類:
const a = 10;
const b = 12.2;
除了整數與小數外,額外還有幾種特殊的數字:Infinity(無限大)
、-Infinity(負無限大)
,以及NaN(Not a Number)
。
如果用一個正數除以0會得到Infinity(無限大)
,用負數除以0會得到-Infinity(負無限大)
,那如果用0/0會得到NaN。Infinity/Infinit或Infinity(負無限大)/-Infinity(負無限大)都是NaN。
最好玩的是NaN並不等於NaN。這是什麼平行時空的概念,長得一樣的人有不一樣的人生喔
而且如果你拿NaN去跟任何數字做運算也只會得到NaN,所以它就是一個數字型別來代表不是數字。
Javascript裡還有一個特別的狀況那就是小數點運算,它是基於二進位浮點數算術標準(IEEE 754)這邊細說太複雜,有興趣的人可以看看維基百科我把連結放下方
提供個例子:
0.1+0.2 === 0.3 //false
相對其他基本型別,布林值就很簡單只有兩種,不是true就是false。通常會用在判斷式if...else用來作流程控制。這根本超級直男,不是一就是二啊
在多數程式語言都有一個這樣的設計來代表空值,在Ruby的世界裡是用nil。null型別就只有一個值就是null。
如果要比較饒舌的解釋,Null就是「這個變數(可能曾經有值,也可能沒有)但是現在起他就是沒有值。」如果要使用null可以直接宣告,以下:
const a = null;
Number(null); //用強制轉型會跑出0
如果用typeof()去檢查Null會發現他會跳出Object
啊不是跟我說他是基本型別,你有沒有搞錯啊!
其實他是一個美麗的錯誤bug,因為在Javascript的初期實作中,Javascript的值是用「型別」的標籤與實際內容的值來組成。由於Object
這個型別的標籤是0,所以跟null的標籤(慣例會以0x00表示)搞混後導致有這樣的錯誤結果。
在Javascript中如果宣告一個變數沒有賦予值就會得到這個結果,所以他跟null有點不太一樣。null是有賦予值不過是空值,undefined是尚未賦予值,所以還不知道是什麼。
const a ;
console.log(a); //會跑出undefined
Number(undefined); // NaN
但還有一個會出現的東西叫not defined
,在你還沒宣告變數就使用它會出現
console.log(b); //not defined
可以預設JS會給變數預設的值,就是undefined。這後面可以再出一篇文章細談JS宣告變數後有分建立期
與執行期
。
Javascript用來表示值太大而無法用Number表示的數值。JavaScript是雙精度浮點會留一個位置給科學記好左邊的1,所以Number最大安全表示是2的53次方-1=9,007,199,254,740,991。
const previouslyMaxSafeInteger = 9007199254740991n;
const alsoHuge = BigInt(9007199254740991); // 9007199254740991n
const hugeString = BigInt("9007199254740991"); // 9007199254740991n
所以超過這9,007,199,254,740,991,會加上bigint但是只能表示整數。
Javascript稱為Symbol值或只是一個Symbol,每一個Symbol的值都是獨一無二的。是ES6後新出的語法。
在Javascript中,除了基本型別外都可以歸類在物件型別。那什麼是物件呢?以下就來整理一下物件型別有哪些。
一個物件可以是個零或是多種屬性的集合。基本屬性上是一組Key跟value的組合而成,一個屬性的值可以是某個基本型別,也可以是物件或是一個函數。如果要宣告一個物件可以直接用{}
來宣告。
const cat = {
name: '小橘',
age: 6,
action: function(){
console.log('吃飯');
}
};
如果要將物件的屬性存取可以透.
或是[ ]
來存取,以下用上面的物件示範
const cat = {
name: '小橘',
age: 6,
action: function(){
console.log('吃飯');
}
};
cat.name // '小橘‘
cat["age"] // 6
物件並沒有先後順序,所以如果你想要獲取value,可以直接透過key來取得。
陣列也是一種物件型別,同樣是多個元素的集合體。所以一樣可以放基本型別、陣列、物件、函式。但是陣列與物件的差別在於陣列是有順序的集合體。透過[ ]
加上索引值(index),索引值(index)是由0開始。宣告一個陣列很簡單以下:
const a = [1, 2, 3];
console.log(a[0]); //可以拿到1
陣列也有很多方法可以使用,之後也可以整理出來在細談這邊就不在多贅述。
函式在javascript中也是物件型別,函式的概念有點像是我們在國中在使用的f(x)=2x+1(有參數跟引數)。
在javascript中宣告函式的方法有很多種,但不管是哪種方法,通常函式都會擁有三個部分:
function addNumber(number1, number2){
return number1 + number2;
}
addNumber(1, 2); //3
addNumber(2, 4); //6
addNumber(4, 5); //9
切記要在透過return回傳結果,不然會返還undefined
不然會像以下這個例子這樣
function echoNumber(x){
console.log(x);
}
echoNumber(1); //會跑出兩個結果 一個是1 一個是undefined
為什麼要寫function
?假設當有一段程式碼你會一直重複使用到你就可以考慮寫成一個function
。
以上是大概整理出來的Javascript的型別,當然不是像小弟弟我寫的那麼簡單而已。
只能說Javascript的世界真是博大精深,還有很多細節與設計奇妙的地方地雷之後可以在補充。
如果大家對於學Javascript有興趣,我自己本身很推薦一本書,很多觀念我也是重新看過在釐清。
我把連結放底下,我怕等等被說業配
參考文獻
0 陷阱!0 誤解!8 天重新認識 JavaScript!(iT邦幫忙鐵人賽系列書 - 02)
IEEE 754維基百科
Day04 undefined與not defined
初學者跪著學JavaScript Day8 : 資料型別:BigInt
MDN