也許大家對於函式的引數都不會太在意,簡單來說,把函式外部的值複製給函式內部的引數,就和把值從乙個變數複製到另乙個變數一樣。深入研究,你會發現其實沒那麼簡單,這個傳參是要分倆種情況(其實這是個錯誤的說法,ecmascript中所有函式的引數都是按值傳遞的——《高程3》原話,之所以這裡說倆種,是因為結合引用傳參更容易理解)—— 值傳參和引用傳參
。 值傳參針對基本型別,引用傳參針對引用型別,傳參可以理解為複製變數值。基本型別複製後倆個變數完全獨立,之後任何一方改變都不會影響另一方;引用型別複製的是引用(即指標),之後的任何一方改變都會對映到另一方。
不少人對引數都是按值傳遞的感到困惑,因為訪問變數有按值和按引用兩種方式
。下面就來看看有何不同:
這一段很重要:我們可以把ecmascript函式的引數想象成區域性變數。在向引數傳遞基本型別的值時,被傳遞的值被複製給乙個區域性變數(即命名引數,或者用ecmascript的概念來說,就是arguments物件中的乙個元素)。在向引數傳遞引用型別時,會把這個值在記憶體中的位址(指標)複製給乙個區域性變數,因此這個區域性變數的變化會反映在函式的外部。
1很好理解,因為是按值傳遞的,傳遞完後倆個變數各不相干!function
addten(num) 56
var count = 20;
7var result = addten(count); //
按值傳遞 num = count
8 alert(count); //
20, 沒變化
9 alert(result); //
30
1當var person = new object();時,可以用下圖表示變數和物件的關係:function
setname(obj) 45
var person = new
object();
6 setname(person); //
obj = person
7 alert(person.name); //
"nicholas" 看起來是按引用傳遞,但千萬不要以為是按引用傳遞~~~
當呼叫函式
setname(person);
時,下圖可以表示全域性變數person和區域性變數obj的關心:
以上**中建立乙個物件,並將其儲存在變數person中。然後,這個變數被傳遞到setname(obj)函式中之後就被複製給了obj。在這個函式內部,obj和person引用的是同乙個物件。換句話說,即使ecmascript說這個變數是按值傳遞的,但obj也會按引用來訪問同乙個物件。於是,在函式內部為obj新增name屬性後,函式外部的person也將有所反應;因為這時的person和obj指向同乙個堆記憶體位址。所以,很多人錯誤的認為:在區域性作用域中修改的物件會在全域性物件中反映出來,就說明引數是按引用傳遞的。
為了證明物件也是按值傳遞的,我們再來看看下面這個經過修改的例子:
1當建立obj物件function
setname(obj) 67
var person = new
object();
8 setname(person); //
你看看下面,相信我也是按值傳遞的了吧
9 alert(person.name); //
"nicholas"
obj = new object();
時,來看看這時person和obj的關係圖:
這個例子與前乙個唯一的區別,就是setname()函式中新增了兩行**: obj = new object(); 用來改變obj的指向; obj.name = "greg"; 用來給新建立的obj新增屬性。如果是按引用傳遞的,那麼person就會自動被修改為指向新建立的obj的記憶體位址,則person的name屬性值被修改為"greg"(這句話之前說的有誤,引用傳遞的是指標的值,obj=new object()改寫了自己的指向,並不會影響到person的指向,這種方式就是按引用傳遞。即使不把物件賦值給函式的引數,obj改寫指向對person也沒影響,見下面**)。但是,當訪問person.name時,顯示的結果為"nicholas"。這說明即使在函式內部修改了引數的值,但原始的引用仍然保持未變。實際上,當在函式內部重寫obj時,這個變數引用的就是乙個區域性物件了。而這個區域性物件會在函式執行完畢後被立即銷毀!
推翻以上都是按值傳遞的結論:
var person=new綜上所述,還是覺得引數傳遞物件時是按引用傳遞的,歡迎指正!object();
var obj = person; //
賦值obj.name="abc";
obj=new
object();
obj.name="bcd";
console.log(person.name);
//abc 並沒有影響person的指向
JS中函式引數值傳遞和引用傳遞
自 1 按值傳遞 1 function addten num 5 6 var count 20 7 var result addten count 按值傳遞 num count 8 alert count 20,沒變化 9 alert result 30 很好理解,因為是按值傳遞的,傳遞完後倆個變數...
C 函式引數 值傳遞與引用傳遞
以前我們在c語言中函式引數傳遞過程中,如果我們想要讓當a函式作用域中的變數經過b函式處理之後的數值仍然在a函式中生效,這個時候函式引數的傳遞時需要引用方式去傳遞,方式如下 include 函式引數為指標,通過修改指標裡面的內容達到對main中b變數的修改 void func int a int ma...
結構體作為函式引數(值傳遞,引用傳遞,指標傳遞)
一 值傳遞 include include using namespace std struct student void outcome student s 引用傳遞不會進行記憶體重新分配,因此和指標傳參類似,效率很高 void outcome student s 引用傳參 outcome stu...