1. 程式人生 > >Js基礎知識1-對象、對象屬性全解

Js基礎知識1-對象、對象屬性全解

字母 net all ini key 路徑 fun 日期函數 light

Object對象

Object對象包含如下屬性和方法,也就意味著一切對象(函數也是對象)都包含如下方法。
每種方法和屬性在不同的對象中有不同的作用,並不是每種對象都有使用每個方法的必要。

下面是Object對象的派生對象在使用這些方法和屬性時的意義。Object對象只是定義了他們,並沒有使用他們。
__proto__屬性是保存當前對象的原型對象。對象通過這個屬性產生了原型鏈,可以參考http://blog.csdn.net/luanpeng825485697/article/details/78547421。

constructor屬性

constructor屬性是保存當前對象的構造函數,js通過構造函數來實現對象的實例化。

下面的例子中,constructor保存的就是Object構造函數。

var obj1 = new Object();
obj1.id = "obj1";
var obj2 = {
  "id": "obj2"
};

console.log(obj1.constructor);//function Object(){}
console.log(obj2.constructor);//function Object(){}

hasOwnProperty(propertyName)方法

hasOwnProperty方法接收一個字符串參數,該參數表示屬性名稱,用來判斷該屬性是否在當前對象實例中,而不是在對象的原型鏈中。我們來看看下面這個例子:

var arr = [];    //實例化了一個Array對象
console.log(arr.hasOwnProperty("length"));//true
console.log(arr.hasOwnProperty("hasOwnProperty"));//false

在這個例子中,首先通過定義了一個數組對象的實例arr,我們知道數組對象實際是通過原型鏈繼承了Object對象,然後擁有自己的一些屬性,我們通過hasOwnProperty方法判斷length是arr自己的屬性,而hasOwnProperty是在原型鏈上的屬性。

isPrototypeOf(Object)方法

isPrototype方法接收一個對象,用來判斷當前對象是否在傳入的參數對象的原型鏈上,說起來有點抽象,我們來看看代碼。

*

*

*

Array數組

參考http://blog.csdn.net/luanpeng825485697/article/details/77009182

JS函數對象

任何函數function都派生於Funciton對象,而Function對象派生於Object對象。函數的詳解可以參考:http://blog.csdn.net/luanpeng825485697/article/details/77010261

可以使用關鍵字function創建函數對象;無需指定返回值類型;參數列表聲明不需var關鍵字;無函數重載;函數內部可以直接調用arguments數組(隱式定義),該數組存儲了實參列表;函數名代表一種引用類型,可用(函數名 instanceof Function)測試;打印函數引用會輸出整個函數定義。

3.1動態函數和匿名函數

1)動態函數: 動態函數是通過js的內置對象Function定義。形式為:new Function(arg1 , arg2),由於arg1和arg2為變量,所以可以動態指定。如:

var run = new Function(“x,y”,”return x+y;”);

2)匿名函數:沒有函數名,形如:var run = function(x,y){return x+y;};
註:打印動態函數的引用可以發現動態函數也是匿名函數。

3.2 全局函數

String(object) 將一個對象值轉換為一個字符串
Number(object) 將一個對象的值轉換為一個數字
Eg:sum+=Number(cell.innerText);
eval(str)接收一個字符串形式的表達式,並試圖求出表達式的值。作為參數的表達式可以采用任何合法的操作符和常數。如果參數中包含JS命令,這些命令也可以被執行,就像這些命令是JS程序的一部分一樣。
函數可計算某個字符串,並執行其中的的 JavaScript 代碼。eval(“2+3”) // 返回 5
decodeURI(URIstring) 為加密的URI進行解碼
decodeURIComponent(URIstring) 為加密的URI組件解碼
encodeURI(URIstring) 將字符串加密為URI
encodeURIComponent(URIstring) 將字符串加密為URI組件
parseInt(str) 將一個字符串解析為一個整數,不是四舍五入操作,而是切尾
試圖從一個字符串中提取一個整數。可附加一個n整數實現返回n進制整數。如果在字符串中存在除了數字、符號、小數點和指數符號以外的字符,就停止轉換,返回已有的結果。如果第一個字符就不能轉換,函數就返回NaN值。
parseFloat(str)試圖從一個字符串中提取一個浮點值。如果在字符串中存在除了數字、符號、小數點和指數符號以外的字符,就停止轉換並返回已有的結果。如果第一個字符就不能轉換,函數就返回NaN值。
isNaN()用於判斷是否為NaN值類型,如果是函數返回true。
isFinite(number)可以判斷參數number是否是一個無窮。如果是則函數返回false,否則返回true。
escape(string)對一個字符串進行解碼
接受一個字符串,這個字符串中可能含有空格、分號等字符。函數把字符串轉換成Cookie的內部表示方式。函數返回值就是這種內部的表達方式。
函數可對字符串進行編碼,這樣就可以在所有的計算機上讀取該字符串
unescape(string)接受一個Cookie,把其內部表達方式轉化成普通的字符串形式。 JS函數一共可分為常規函數、數組函數、日期函數、數學函數、字符串函數等五類。

 1 var student1 = new Object();    //定義對象引用,或者var student1 = {},new Object()。所有的包裝類都派生於Object。Object基類包含hasOwnProperty、isPrototypeOf、propertyIsEnumerable、toLocaleString、toString、valueOf方法
 2 student1.name = "student1";     //直接設置同時添加對象屬性
 3 student1["age"]=12;                 //直接設置同時添加對象屬性
 4 student1.getname = function(){      //設置添加對象方法。函數表達式,只有在執行到本行才解析
 5    return this.name;                //this表示作用對象,這裏為student1
 6 };
 7 //var {name:personname, age:personage} = student1;  //解構賦值,對應項使用副本賦值,如[value1,value2]=[value2,value1];可實現兩個基本數據交換
 8 printf(JSON.stringify(student1));   //JSON.stringify把對象轉化為JSON字符串表示
 9 
10 student1 = {
11     name:"student1",
12     _age:12,                        //前面有下滑線是一種常用的標記,用於表示只能通過對象方法訪問的屬性,只是對開發者的一種標記習慣,並不是真的私有變量
13     getname:function(){
14         return this.name;
15     }
16 };
17 Object.defineProperty(student1,"name1",{  //可以用於定義新數據屬性,也可以修改原有數據屬性。也可以不使用defineProperty可以直接定義數據屬性。也可以使用defineProperties同時定義多個數據或訪問器屬性
18     writable:true,                  //對象屬性的數據屬性,是否可修改
19     enumerable:true,                //對象屬性的數據屬性,通過for-in遍歷到
20     configurable:true,              //對象屬性的數據屬性,能否通過delete刪除屬性,configurable屬性在定義為false以後,就不能再被設置
21     value:"sst"                     //對象屬性的值屬性,默認為underfined
22 });
23 Object.defineProperty(student1,"age",{   //訪問器屬性,不能直接定義,必須通過defineProperty定義,不包含數據值,設置時調用set函數,讀取時調用get函數。訪問器屬性名稱不要和數據屬性名稱相同
24      get:function(){return this._age},
25     set:function(newvalue){this._age=newvalue;this.name="xxt";}
26 });
27 student1.age=22;                //age不是數據屬性,而是訪問屬性。這裏是調用了set函數,
28 Object.preventExtensions(student1);//設置對象不可被擴展,以後再添加屬性都是underfined,防止被篡改
29 Object.seal(student1);              //密封對象,對象不能添加刪除屬性。
30 Object.freeze(student1);            //凍結對象,屬性不可修改。只能通過set訪問器修改
31 printf(JSON.stringify(student1)); //將JSON格式轉化為字符串。JSON格式即KEY-VALUE格式
32 for(var myproperty in student1){ //for in遍歷對象屬性
33     console.log(myproperty,":",student1[myproperty]);
34 }
35 
36 
37 
38 
39 function Student(name,age){         //自定義函數,構造函數,等同於java中的自定義類。所有的類型派生於Object
40     var sex="男";                //函數內部為私有屬性
41     this.name=name;                 //通過this創建的是可以被實例對象訪問的
42     this.age=age;
43     this.getName=function(){
44         return this.name;       //函數內部this表示此函數引用的擁有者,不是傳入參數。當作為全局函數時,this表示window
45     };
46     this.setName= function(name){  //函數不關心傳入或者定義的參數數量和類型,因此所有函數沒有重載
47         if(typeof name=="string")  //基本數據類型,做類型檢驗,避免參數傳遞錯誤
48             this.name = name;      //沒有指定返回值,實際返回的是undefined
49     };
50     this.getAge =function (){
51         if(this.age.toFixed(2)<<2) //轉化為false的值:"",0,NaN,null,underfined。其他轉化為true,類型首字母大寫,變量首字母小寫,<<按位移動,<<<無符號按位移動,toFixed(2)表示保留2位小數
52             return -~this.age;     //~按位取非,&按位取與,|按位取或 ^按位取異或,一元減號,表示取負
53         return this.age;            //保證所有路徑都有返回值,雖然不加也不會出錯,因為有默認返回值undefined
54     };
55     this.setAge= function(age){     //函數參數總是按值傳遞,無論基本類型還是引用類型,引用類型傳遞引用的值,不傳遞指向對象的值
56         if(age instanceof Number){ //包裝類型,做類型檢驗,避免參數傳遞錯誤
57             this.age = parseInt(age.toString(16),16);//parseInt將字符串化為整數,支持識別多進制和轉化為多進制,toString()轉化為字符串,支持多進制轉化
58         }
59         //typeof判斷基本類型,underfined聲明未定義(underfined類型只有一個值),boolean布爾型,string字符串,number數值,object對象或null(null類也只有一個值),function函數
60         //instanceof判斷包裝類型,基本類型對象的包裝類型為Underfined,Boolean,String,Number,Object,
61         typestr = typeof("getAge"); //省略var的變量為全局變量
62     }
63 }
64 student1=new Student("小明",12);          //new是創建了一個新對象,構造函數將屬性和方法綁定到這個新對象上
65 Student("小紅",13);                   //作為全局函數。通過構造函數將屬性綁定到window上
66 var student2 = new Object();
67 Student.call(student2,"小剛",14);     //call和apply通過構造函數,將屬性綁定到以存在對象student2上
68 if(student2 instanceof Student)         //instanceof判斷變量是否是某個類型或其派生類型實例的,student1是Student類,同時也是Object
69      printf(student2.name);
70 
71 
72 //js的繼承有多重方式。每種方式的內存操作都是不同。下面展示其中一種。
73 // js的類型繼承原理和java、c#相同。派生類繼承基類時,會實例化(淺復制)一個基類對象和保留引用在派生類空間。派生類內的實例的基類和派生類自定義的函數分別操控各自的屬性。在函數和屬性操作中時,會自動先派生後基類的順序查找,不用手動查找
74 //關於實例化:只復制且全部復制在構造函數中開辟了內存的變量,包括引用變量。派生類實例化時基類對象進行淺復制。
75 function Monitor(){   //自定義函數,相當於自定義一個類,類名Monitor。在文件中多稱為構造函數,相當於c++和java中的自定義類。每個函數類,都有基類Object
76     this.task=["學習"];
77 }
78 Monitor.prototype.data = "原型數據";  //prototype獲取派生類的基類對象引用,通過基類對象引用直接為基類添加屬性。系統會為派生類提供默認原型,也可以通過繼承自定義原型
79 person1 = new Monitor();                //通過函數類實例化對象
80 person2 = new Monitor();                //實例化對象
81 Object.getPrototypeOf(person1).data="原型數據1";  //通過實例修改原型。Object.getPrototypeOf()獲取對象原型。實例對象包含對原型的引用,但需要使用getPrototypeOf函數獲取
82 person1.data="派生數據";            //修改派生類屬性,這樣當查找data數據會先自動搜索派生類,再自動搜素基類。
83 
84 printf(person1.hasOwnProperty("data"));     //是否擁有指定屬性(不算基類屬性)。true因為自定義了該屬性
85 printf(person1.data);                           //讀取自定義屬性
86 
87 var keys = Object.keys(Monitor.prototype);      //獲取對象所擁有(不包括繼承的)的可枚舉實例,Monitor是類,Monitor.prototype是基類實例。如果換成person1,則只能獲取派生類的自定義屬性。getOwnPropertyNames可獲取對象擁有的所有屬性
88 printf(keys);
89 delete person1.data;                            //刪除派生類自定義的屬性
90 printf(person1.hasOwnProperty("data"));         //是否擁有指定屬性。false,因為該屬性在派生類中被刪除了,只有基類中存在,雖然可以訪問,但是是繼承過來的,不是自己擁有的
91 printf("data" in person1);                  //是否包含指定屬性。true包含,只是不擁有
92 printf(person1.data);                           //基類屬性
93 Monitor.prototype.sex=["男"];                //通過派生類向基類添加數組引用變量
94 person1.sex.push("女");                          //在實例對象中保留了基類的引用和淺復制了基類對象。這裏的sex是經過了一次從派生類到基類的向上查詢。
95 printf("基類中的引用:"+person2.sex);          //實例對象連帶更新。所以構造函數用於指定專屬屬性,原型用於存放共享屬性
96 person1.task.push("工作");                    //修改構造函數中引用指向的對象
97 printf("派生類中的引用:"+person2.task);        //實例對象不連帶更新構造函數中的數據。因為實例化時會深復制構造函數中的所有數據,在實例化時為每個對象都創建
98 
99 Monitor.prototype=new Student("組長",12);     //繼承,派生類Person設置基類為Student。在繼承中會為淺復制一個基類實例放在派生類空間中,同時將引用存儲為prototype,放在派生類Person中

Js基礎知識1-對象、對象屬性全解