js 深切 —— 從數據類型到原型鏈

一、數據範例


javascript中的數據範例可以分為兩種範例,
基礎數據範例
援用數據範例。个中基礎數據範例包括
String,
Number,
Boolean,
null,
undefined,
Symbol(ES6)六大數據範例,援用數據範例
object

  1. 平常,數值、字符串、布爾值這三種範例,合稱為原始範例,
  2. 對象則稱為合成範例(complex type)的值,由於一個對象往往是多個原始範例的值的合成,可以看做是一個寄存種種值的容器。
  3. 至於undefined和null,平常將它們算作兩個特別值。

這裏所講的合成範例object,實在式一個廣義的對象,他包括三個子範例,[
狹義的對象
array
function]

我們平常所說的對象都是狹義的對象。

基礎數據範例是根據值舉行分派的,是寄存在了棧內存的數據片斷,可以直接訪問到。援用數據範例則是寄存在堆內存中的數據,比方: var a = {}; a只是存儲了{}的指針,這個指針指向了內存的地點。

檢測數據範例

javascript中可以運用typeof操縱符來推斷數據範例。然則typeof null = object; 這是汗青遺留的bug;

typeof 123;               // "number"
typeof "hfhan";           // "string"
typeof true;              // "boolean"
typeof null;              // "object"  獨一份的異乎尋常
typeof undefined;         // "undefined"
typeof Symbol("hfhan");   // "symbol"
typeof function(){};      // "function"   // 這裏不是object哦~~~
typeof {};                // "object"
typeof window             // "object"
typeof {}                 // "object"
typeof []                 // "object"

null是一個示意“空”的對象,轉為數值時為0undefined是一個示意”此處無定義”的原始值,轉為數值時為NaN

null和undefined的用法於寄義

null示意空值,即該處的值現在為空。挪用函數時,某個參數未設置任何值,這時候便可以傳入null,示意該參數為空。比方,某個函數吸收引擎拋出的毛病作為參數,假如運轉過程當中未失足,那末這個參數就會傳入null,示意未發作毛病。

undefined示意“未定義”,下面是返回undefined的典範場景。

// 變量聲清楚明了,但沒有賦值
var i;
i // undefined

// 挪用函數時,應當供應的參數沒有供應,該參數即是 undefined
function f(x) {
  return x;
}
f() // undefined

// 對象沒有賦值的屬性
var  o = new Object();
o.p // undefined

// 函數沒有返回值時,默許返回 undefined
function f() {}
f() // undefined

可以轉換為false的值

undefined
null
false
0
NaN
""或''(空字符串)

二、對象範例

宿主環境

平常宿主環境由外殼順序建立於保護,只如果可以供應js引擎實行環境都稱為是外殼順序。如:web 瀏覽器, 桌面運用順序等。

即由web瀏覽器、桌面運用順序等的外殼順序所作育的環境就是宿主環境

js對象的分類

js的對象可以分為三類:內部對象 宿主對象 自定義對象

1. 內部對象

1.1 當地對象

ECMA-262把當地對象定義為是: 獨立於宿主環境的ECMASCRIPT完成所供應的對象。

當地對象包括Object Function Boolean String Array Date RegExp Number 以及各種毛病對象(Error、EvalError、RangeError、ReferenceError、SyntaxError、TypeError、URIError

1.2 內置對象

ECMA-262把內置對象定義為是: 由 ECMAScript 完成供應的、獨立於宿主環境的一切對象,在 ECMAScript 順序最先實行時湧現。意味着你不須要明白實例化便可所以直接運用。

包括由 Global Math兩個內置對象。

global

global對象算是一個比較特別的對象了吧,由於不論你從哪一個角度看,它都是不存在的。全局作用域下的一些屬性和要領比方: isNaN parseInt等。都是global的屬性和要領。
JavaScript 全局對象參考手冊

2. 宿主對象

宿主對象就是實行JS劇本的環境供應的對象。關於嵌入到網頁中的JS來講,其宿主對象就是瀏覽器供應的對象,所以又稱為瀏覽器對象(BOM)

差別的瀏覽器供應的宿主對象能夠差別,縱然供應的對象雷同,實在現體式格局也天差地別!這會帶來瀏覽器兼容問題,增添開闢難度。

瀏覽器對象有許多,如WindowDocument等等。

關於web瀏覽器而言,
Global有一個代言人
window,然則window並非ECMAScripta劃定的內置對象,由於window對象是相關於web瀏覽器而言的,而js不單單議可以用在瀏覽器中。

document對象是window對象的一個屬性,是顯現於窗口內的一個文檔。而window對象則是一個頂層對象,它不是另一個對象的屬性。document可以理解為文檔,就是你的網頁,而window是你的窗口,就是你的瀏覽器翻開所顯現的哪一個窗口。

3. 自定義對象

望文生義,就是開闢人員本身定義的對象。JavaScrip許可運用自定義對象,使JavaScript運用及功用獲得擴大

三、推斷對象的範例

運用Object.prototype.toString()來推斷。

Object.prototype.toString.apply(new Function); // "[object Function]"
Object.prototype.toString.apply(new Object);       // "[object Object]"
Object.prototype.toString.apply(new Date);         // "[object Date]"
Object.prototype.toString.apply(new Array);        // "[object Array]"
Object.prototype.toString.apply(new RegExp);       // "[object RegExp]"
Object.prototype.toString.apply(new ArrayBuffer);  // "[object ArrayBuffer]"
Object.prototype.toString.apply(Math);             // "[object Math]"
Object.prototype.toString.apply(JSON);             // "[object JSON]"
var promise = new Promise(function(resolve, reject) {
    resolve();
});
Object.prototype.toString.apply(promise);          // "[object Promise]"

下面正式進入我們的正題

四、組織函數

在javascript中對象的建立有兩種體式格局,對象字面量組織函數

4.1 對象字面量

var o1 = {  
    p:”I’m in Object literal”,  
    alertP:function(){  
        alert(this.p);  
    }  
}  
// 這類寫法不須要定義組織函數,因而不在本文的議論局限以內。這類寫法的瑕玷是,每建立一個新的對象都須要寫出完全的定義語句,不便於建立大批雷同範例的對象,不利於運用繼承等高等特徵。

4.2 組織函數(組織器)

new表達式是合營組織函數運用,可以完成更好的效果

new String(“a string”)
// 挪用內置的String()要領來構建了一個字符串對象。



function CO(){  
    this.p = “I’m in constructed object”;  
    this.alertP = function(){  
        alert(this.p);  
    }  
}  
var o2 = new CO();  

針對new操縱標記在挪用組織函數,我們來刨析一下詳細發作了什麼

發作了四件事

var obj = {}; // 第一步建立一個空對象
obj.__proto__ = CO.prototype; // 讓空對象的成員指向組織函數的prototype成員對象
CO.call(obj); // 第三步,將組織函數的作用域賦值給新的對象
return obj; // 返回新的對象
  • 注重
function C2(a, b){  
    this.p = a + b;  
    this.alertP = function(){  
        alert(this.p);  
    }  
    return this.p;//此返回語句在C2作為組織函數時沒有意義  
}  
var c2 = new C2(2,3);  
c2.alertP();//效果為5  
alert(C2(2, 3)); //效果為5  

// 該實例是可行的,然則不引薦哦,
// 該函數既可以用作組織函數來組織一個對象,也可以作為一般的函數來運用。用作一般函數時,它吸收兩個參數,並返回二者的相加的效果。為了代碼的可讀性和可保護性,發起作為組織函數的函數不要攙雜除組織作用以外的代碼;一樣的,平常的功用函數也不要用作組織對象。

以上兩種體式格局中展示的都是我們自定義的對象,看了兩種建立對象對的體式格局,我們來連繫內部對象來繼承剖析:

4.3 一般建立法

一個函數可以經由過程下面的體式格局直接建立。

function a(){

}

建立一個對象比方是object 可所以 {} ,建立數組可所以[], 建立正則可所以/.*/

4.4 組織函數建立對象

var a = new Function(){

}
var b = new Object({a:1})
var c = new Array(10)
var d = new Date()
var e = new Set()

我們直接(new)運用內部對象的組織函數便可以建立一個對象了。

// 除了內置的一些對象以外,我們還可以運用一般的函數來構建對象。

function person (){
}

var p1 = new Person();
  • 我們商定一般函數以小寫字母開首,組織函數以大寫字母開首。

五、原型以及原型鏈

未完待續

    原文作者:Meils
    原文地址: https://segmentfault.com/a/1190000014452455
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞