對外的,面對編譯器segmentfault
包括數組
存放位置:內存中的棧區域。
值的不可變性,稱這些類型的值爲原始值。
基本數據類型的值是按值訪問的,基本類型的值是不可變的。
比較:基本數據類型的比較是值的比較,只判斷是否相等。
拷貝:都是值的複製,相互沒有影響。數據結構
包括函數
存放位置:內存中的棧存放指向堆區域的指針,內容在堆區域中
值的可變性:引用類型的值是按引用訪問的,引用類型的值是動態可變的
比較: 引用類型的比較是引用地址的比較,判斷是否指向同一對象。
拷貝:spa
undefined:是一個沒有設置值的變量。JavaScript特有的。沒有返回值的函數返回爲undefined,沒有實參的形參也是undefined。
null:它是一個空對象指針。
null 和 undefined 的值相等,但類型不等:prototype
typeof undefined // undefined typeof null // object null === undefined // false null == undefined // true
基本數據類型:數據存於內存中的棧區域。
應用數據類型:內存中的棧存放指向堆區域的指針,內容在堆區域中。指針
若是是基本數據類型,直接賦值,會拷貝其自己,不存在淺拷貝和深拷貝。
若是是引用類型:code
賦值
let obj1 = { color: 'red', age: 20, address: { city: 'beijing', }, arr: ['a', 'b', 'c'] }; //賦值 let obj2 = obj1; obj1.age = 21; obj1.address.city = "shanghai"; console.log(obj2.age);//21 console.log(obj2.address.city);//shanghai
淺拷貝
let obj1 = { color: 'red', age: 20, address: { city: 'beijing', }, arr: ['a', 'b', 'c'] }; //淺拷貝 let obj3 = shallowCopy(obj1); obj1.age = 21; obj1.address.city = "shanghai"; console.log(obj3.age); //20 console.log(obj3.address.city); //shanghai //自定義淺拷貝函數 function shallowCopy(obj) { if (typeof obj !== 'object' || obj == null) { return obj; } let result; if (obj instanceof Array) { result = []; } else { result = {}; } for (let key in obj) { if (obj.hasOwnProperty(key)) { result[key] = obj[key]; } } return result; }
深拷貝
let obj1 = { color: 'red', age: 20, address: { city: 'beijing', }, arr: ['a', 'b', 'c'] }; //深拷貝 let obj4 = deepCopy(obj1); obj1.age = 21; obj1.address.city = "shanghai"; console.log(obj4.age);//20 console.log(obj4.address.city);//shanghai //自定義深拷貝函數 function deepCopy(obj) { // obj 是 null 或者不是對象和數組,直接返回 if (typeof obj !== 'object' || obj == null) { return obj; } // 初始化返回結果 let result; if (obj instanceof Array) { result = []; } else { result = {}; } for (let key in obj) { if (obj.hasOwnProperty(key)) { result[key] = deepCopy(obj[key]); } } return result; }
對內的,供開發者使用
包裝類型對象對象
引用類型blog
內置對象
在腳本程序初始化時被建立,沒必要實例化這兩個對象。
在實際中每讀取一個基本數據值的時候,後臺就會建立一個對應的基本包裝類型對象,從而讓咱們可以調用一些方法操做這些數據。
let s1 = "some text"; //值類型沒有方法。 let s2 = s1.substring(2); console.log(s1); //some text console.log(s2); //me text
引用類型與基本包裝類型的區別
它們的對象生命週期不一樣:
引用類型:使用new建立引用類型的實例,在執行數據流離開當前做用域時會一直存儲在內存中。
基本包裝類型:自動建立基本包裝類型的對象,只執行一行代碼的瞬間以後就會當即銷燬。
這意味着在運行時爲基本包裝類型值添加屬性和方法是無效的。
let s1 = 'some text'; s1.color = 'red'; s1.color // undefined // 可是這樣是能夠的 let s1 = new String('some text'); s1.color = 'red'; s1.color // red
不建議顯式的建立基本包裝類型的對象,由於在不少時候會形成一些讓人很迷惑的東西。
let b = new Boolean(false); //b 這個變量就是 Boolean 對象 let c = b && true; console.log(c); // true
let str = 'hello'; // str 本質上是一個原始值,並不存在 prototype 屬性 console.log(typeof str); // string console.log(str instanceof String); // false
參考文章:https://segmentfault.com/a/11...
相較於JS基本數據類型少null多function。
console.log(typeof null); //object console.log(typeof undefined); //undefined console.log(typeof 123); //number console.log(typeof "123"); //string console.log(typeof true); //boolean console.log(typeof function a() {}); //function console.log(typeof [1, 2, 3]); //object console.log(typeof {a: "a"}); //object
- 肯定原型指向關係。只適用於對象,由於值類型沒有原型。
- 不能判斷一個對象實例具體屬於哪一種類型。
let a = []; console.log(a instanceof Array);//true console.log(a instanceof Object);//true
- Object 的原型方法,返回"[object type]",其中type是對象的類型。
- toString()調用null返回[object, Null],undefined返回[object Undefined]。
- 沒法識別自定義的對象類型。
console.log(Object.prototype.toString.call(123)); //[object Number]
function optc(obj) { return Object.prototype.toString.call(obj).slice(8, -1); } console.log(optc(123)); //Number console.log(optc('123')); //String console.log(optc(true)); //Boolean console.log(optc(undefined)); //Undefined console.log(optc(null)); //Null console.log(optc({})); //Object console.log(optc([])); //Array console.log(optc(function () {})); //Function console.log(optc(/\d/)); //RegExp console.log(optc(new Date())); //Date
利用構造函數判斷數據類型。
- 對象的構造函數名就是該數據類型。
- 除Null和Undefined外,全部的數據類型都是/能夠轉化爲對象,而若是是對象,就確定有構造函數。
function A() {} let a = new A(); console.log(a.constructor.toString()); //function A() {}
準確判斷數據類型包括自定義的對象類型
function dataType(data) { if (!data) { //判斷null、undefined return Object.prototype.toString.call(data).slice(8, -1); } else { return data.constructor.toString().match(/function\s*([^(]*)/)[1]; } } console.log(dataType(null)); //null console.log(dataType(undefined)); //Undefined console.log(dataType(123)); //Number console.log(dataType([])); //Array function Point(x, y) {} console.log(dataType(new Point(1, 2))); //Point
String()
此方法經常使用於null和undefined轉換成字符串類型
toString()
此方法不適合用於null和undefined
對象 | 返回值 |
---|---|
Number | 返回當前數值的字符串 |
String | 字符串自己 |
Boolean | false-->"false" |
Array | [1,2,3]-->"1,2,3" |
Function | 返回當前函數源代碼的字符串 |
Object | "[object object]" |
Date | 返回表示UTC的字符串 |
Symbol | "Symbol()" |
Number()
Number方法只要字符串中有一個字母則返回NaN,而且能夠轉換boolear類型。Number()能夠用於任何數據類型。
parseInt()和parseFloat()
parseInt方法在字符串中遇到數值轉換成數字,若是遇到非數字就會返回,不能轉換boolear類型。parseInt()和parseFloat()則專門用於字符串。
let str1 = "123"; let str2 = "abc"; let str3 = "123abc"; let a = true; console.log(Number(str1)); // 123 console.log(Number(str2)); // NaN console.log(Number(str3)); //NaN console.log(Number(a)); //1 console.log(parseInt(str1)); // 123 console.log(parseInt(str2)); //NaN console.log(parseInt(str3)); //123 console.log(parseInt(a)); //NaN
Boolean()
五種轉換爲false的狀況:null
,undefined
,''(空字符串)
,0
,NaN
。其他爲true。
轉換規則
加法運算:
一方是字符串,另外一方也會被轉換爲字符串類型。加法運算會觸發3種類型轉換
其餘運算:雙方會被轉爲數字進行運算。
console.log(1 + "1"); //1 console.log(1 * "2"); //2 console.log([1, 2] + [3, 4]); //1,23,4 console.log('a' + +'b'); //aNaN /* 轉換步驟 * +'b' -> 'NaN' * 'a' + 'NaN' -> 'aNaN' */
==
會發生類型轉換,使兩邊儘可能相等。類型(x) | 類型(y) | 結果 |
---|---|---|
null | undefined | true |
number | string | 把y轉化爲number,再與x進行比較 |
boolean | 任何類型 | 把x轉換爲number,再與x進行比較 |
string或number | object | 把y轉換爲原始值,再與x進行比較 |
object | object | 若是它們指向同一個對象,則返回true;不然返回false |
==
的狀況:除了==null以外,其餘一概都用 ===
const obj = {x: 100}; if (obj.a == null) {} //至關於: //if (obj.a === null || obj.a === undefined) {}
if 語句中就是判斷 truly
變量和 falsely
變量。
//如下是falsely 變量。除此以外都是 truly 變量 console.log(!!0 === false); console.log(!!NaN === false); console.log(!!null === false); console.log(!!undefined === false); console.log(!!false === false);
邏輯判斷(隱式轉換成Boolean值)
console.log((10 && 0)); //0 console.log(("" || "abc")); //abc console.log((!global.abc)); //true