开发者

jQuery object passed as argument to function is value copy not reference?

My understanding: in Javascript objects and arrays get passed as references not values for function arguments. A jQuery group is an object and hence should be passed as reference.

However I'm finding in the test script below that something strange is going on; the jQuery group is behaving like a value not a reference unless wrapped in another object ... can anyone explain this?

<html>
<head>
 <script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.4.2/jquery.min.js"></script>
</head>
<body>
<script>

 function test(arg){
   arg = arg.add($('<span/>'))
   console.log(arg);
 };

 ele = $('<div/>');
 test(ele);  // div + span in the group as expected
 console.l开发者_开发百科og(ele); // only the div - the 'arg' param in function was a copy

 function test2(arg){
   arg.a = arg.a.add($('<span/>'));
   console.log(arg.a);
 };

 obj = {a:ele};
 test2(obj); // div + span in the group as expected
 console.log(obj.a); // both in the group - arg acted like a reference!

</script>
</body>
</html>


This is a "feature" of the .add() method. It does not modify the original jQuery object, but rather returns a new object with the added value.

Given your first example, you would need to return the arg variable and overwrite ele.

 function test(arg){
   arg = arg.add($('<span/>'))
   console.log(arg);
   return arg;  // return the new jQuery object stored in "arg"
 };

 ele = $('<div/>');
 ele = test(ele);  // overwrite the original "ele" with the returned value
 console.log(ele); 

EDIT: To give another illustration, using your code, but with .push() which modifies the original object, you will see the correct value updated in ele.

 function test(arg){
   arg = arg.push($('<span/>')[0])
   console.log(arg);  // Because .push() is being used, "arg" will reference 
                      //   the new length of the array.
 };

 ele = $('<div/>');
 test(ele);  
 console.log(ele); // Will reference jQuery object with both elements

EDIT: Once last illustration. Because .add() returns a new object, you could update both variables to point to the same value like this:

ele = arg = arg.add($('<span/>'));

Now instead of ele referencing the original, and arg referencing the new Object that was created, both variables hold a reference to the same Object in memory.


The two tests you performed aren't the same. The first one sets a variable arg to the value arg.add(...), while the second one set's a property on arg named a to the value arg.a.add(...). Passing "by reference" in JavaScript isn't really the same as it is in other languages (in fact, some would disagree that it is really pass-by-reference). When you pass an variable whose type is an object, you have a reference to its value and not to the original variable.

When you set arg = arg.add(...), you are setting a new value for the arg variable and overriding its previous value. This will not modify the variable that was passed in, because you don't have a reference to it, you only have a reference to its value (the object).

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜