摘要:js的數據類型有種劃分方式爲 原始數據類型和 引用數據類型。javascript
原始數據類型 存儲在棧(stack)中的簡單數據段,也就是說,它們的值直接存儲在變量訪問的位置。棧區包括了 變量的標識符和變量的值。php
引用數據類型 存儲在堆(heap)中的對象,也就是說,存儲在變量處的值是一個指針(point),指向存儲對象的內存處。放在棧空間中的值是該對象存儲在堆中的地址。html
按值傳遞(call by value)是最經常使用的求值策略:函數的形參是被調用時所傳實參的副本。修改形參的值並不會影響實參。java
按引用傳遞(call by reference)時,函數的形參接收實參的隱式引用,而再也不是副本。這意味着函數形參的值若是被修改,實參也會被修改。同時二者指向相同的值。ajax
按引用傳遞會使函數調用的追蹤更加困難,有時也會引發一些微妙的BUG。json
按值傳遞因爲每次都須要克隆副本,對一些複雜類型,性能較低。兩種傳值方式都有各自的問題。數組
typeof 運算符,返回一個字符串,
指示未經
計算的操做數的類型。
函數
var person,name; person = 'kn'; name=person; person='黑白'; console.log(person,name,typeof person)//黑白 kn string
person的改變沒有改變name,說明 string 是按值傳遞的。賦值時建立一塊新的內存空間oop
true
和 false
.null
與 Null
、NULL
或其餘變量徹底不一樣。42
或者 3.14159。
基本類型是不可變的(immutable),只有對象是可變的(mutable). 有時咱們會嘗試「改變」字符串的內容,但在JS中,任何看似對string值的」修改」操做,實際都是建立新的string值。任何方法都沒法改變一個基本類型的值, 性能
1 var str = "abc"; 2 str[0]; // "a" 3 str[0] = "d"; 4 console.log(str); //abc 5 6 var name = 'jozo'; 7 var upName=name.toUpperCase(); 8 console.log(upName,name); // 輸出 'JOZO' 'jozo'
方法操做沒法改變一個基本類型的值
1 var person = 'kn'; 2 person.age = 24; 3 person.method = function(){}; 4 5 console.log(person.age); // undefined 6 console.log(person.method); // undefined
上面代碼可知,咱們不能給基本類型添加屬性和方法
引用類型的值是可變的
1 var obj = {x : 0}; 2 obj.x = 100; 3 var o = obj; 4 o.x = 1; 5 console.log(obj.x)// 1, 被修改 6 o = {x:100}; //等同於從新賦值,從新開闢內存,不是修改 7 console.log(JSON.stringify(obj),JSON.stringify(o))//{"x":1} {"x":100} 8 obj.x; // 1, 不會因o = {"x":100}改變
引用類型的值是同時保存在棧內存和堆內存中的對象
javascript和其餘語言不一樣,其不容許直接訪問內存中的位置,也就是說不能直接操做對象的內存空間,那咱們操做啥呢? 實際上,是操做對象的引用,
因此引用類型的值是按引用訪問的。
準確地說,引用類型的存儲須要內存的棧區和堆區(堆區是指內存裏的堆內存)共同完成,棧區內存保存變量標識符和指向堆內存中該對象的指針,
也能夠說是該對象在堆內存的地址。
假若有如下幾個對象:
var person1 = {name:'jozo'};
var person2 = {name:'xiaom'};
var person3 = {name:'xiaoq'};
則這三個對象的在內存中保存的狀況以下圖:
var person1 = {}; var person2 = {}; console.log(person1 == person2); // false
引用類型時按引用訪問的,換句話說就是比較兩個對象的堆內存中的地址是否相同,那很明顯,person1和person2在堆內存中地址是不一樣的。
首先要明白什麼實參什麼是形參。
實參:能夠是常量、變量、表達式、函數等, 不管實參是何種類型的量,在進行函數調用時,它們都必須具備肯定的值, 以便把這些值傳送給形參。 所以應預先用賦值,輸入等辦法使實參得到肯定值。
形參:全稱爲「形式參數」是在定義函數名和函數體的時候使用的參數,目的是用來接收調用該函數時傳遞的參數。
形參的做用是實現主調函數與被調函數之間的聯繫,一般將函數所處理的數據,影響函數功能的因素或者函數處理的結果做爲形參。
function addNum(param) //相對於addNum方法來講 param是形參 { param+=10; return param; } var num=10; var result=addNum(num); //相對於addNum方法來講 num是實參 console.log(num); //10 console.log(result);//20
上面的例子中,當將 num做爲實參傳入方法 addNum是 param做爲形參接受 並在方法體內使用,且num在全局中沒用改變,但當實參爲引用類型時
1 function fun(param) //相對於fun方法來講 param是形參 2 { 3 param[0]=99; 4 return param; 5 } 6 var num=[10]; 7 var result=fun(num); //相對於fun方法來講 num是實參 8 console.log(num[0]); //99 9 console.log(result);//[99]
在方法體內改變 形參將同時改變實參。這個是其餘語言中不會存在的,例如php,須要操做引用時,使用 &地址符 在形參的時候聲明
1 <?php 2 function fun($param) //相對於fun方法來講 param是形參 function fun(&$param){} 3 { 4 $param[0]=99; 5 // return $; 6 } 7 $num=[10]; 8 fun($num); //相對於fun方法來講 num是實參 9 var_dump($num); 10 /* 11 array (size=1) 12 0 => int 10 13 */ 14 15 ?>
思考: 正由於js中 function的形參若爲引用類型時,能夠影響實參! 推斷 callback中參數原理
1 function fun(data,callback){ 2 var json=[1,2,3]; 3 callback(json) 4 } 5 6 var data=[]; 7 fun(data,function(result){ 8 data=result; 9 }) 10 console.log(data)//[1, 2, 3]
如上例子 在回調函數中修改了 變量 data
知識點一、 function 是一種數據類型,能夠當作參數傳遞 二、數組是引用類型 三、引用類型的形參會影響實參
1 <body> 2 <button onclick='log()'>ajax</button> 3 </body> 4 <script> 5 function fun(data,callback){ 6 setTimeout(function(){ 7 var json=[1,2,3]; 8 callback(json) 9 },4000) 10 11 } 12 13 var data=[]; 14 fun(data,function(res){ 15 data=res; 16 }) 17 console.log(data)//[] 18 function log(){ 19 console.log(data)//[1, 2, 3] 4秒後輸出 20 } 21 22 </script>
使用 setTimeout 模擬ajax請求!
參考地址: http://www.w3school.com.cn/js/pro_js_value.asp
http://www.qdfuns.com/notes/17660/7f82003c5ce92d39d19d6be0403f3f3b.html