Reputation: 351
Here is the code,when the function change the attribute of the object,it works,but redefine the object, nothing happened, why? I have found some answers,but I still don't know what's happened when the object as a parameter inside a function.
var person = {name: "tom"};
function changeName(person) {
person.name = "new tom";
person = {};
}
changeName(person);
console.log(person); //{name: "new tom"}
Upvotes: 2
Views: 63
Reputation: 28742
This has to do with scoping.
A function has its own scope to edit in and from.
your var person
is defined against window. In actuality it's window.person={name:'tom'};
now you enter your function. You create a new scope, a blank slate sort to say where you define a parameter person.
This means you have no more access to the global object person in that object because you have a scoped variable named that way.
Note that htis variable is merely an "Address" that tells the function where to find the actual object Person. It's called a reference.
Imagine this: Your computer memory is like houses on the street
/-\ /-\ /-\ /-\ /-\ /-\ /-\ /-\ /-\
[ ] [ ] [ ] [ ] [ ] [ ] [ ] [ ] [ ]
1 2 3 4 5 6 7 8 9
Now, in your window object you create an object named person. We shall call it p for short in the houses. person needs memory to live in otherwise he'll get swept away so he's put in a house
/-\ /-\ /-\ /-\ /-\ /-\ /-\ /-\ /-\
[ ] [ ] [ ] [p] [ ] [ ] [ ] [ ] [ ]
1 2 3 4 5 6 7 8 9
You then get returned a slip of paper saying : person lives in house number 4 and when you need to do something with person you look on your slip, go to the correct house and do stuff with person.(this sounds so wrong heh)
=|=
[|]
===
Now you enter your function. You pass your slip of paper on to the function saying "hey, person lives at number 4. do stuff with him"
/-\ /-\ /-\ /-\ /-\ /-\ /-\ /-\ /-\
[ ] [ ] [ ] [p] [ ] [ ] [ ] [ ] [ ]
1 2 3 4 5 6 7 8 9
.
=|=
[|]
===
So your function goes to house number four and does stuff with person which ends up with a new name.
But then you do
person = {}
At that moment you are actively throwing away the piece of paper. Your program totally forgets where person used to live! So, it makes a new person object and puts it in a new house and gives the piece of paper holding the address to the variable person.
/-\ /-\ /-\ /-\ /-\ /-\ /-\ /-\ /-\
[ ] [ ] [ ] [p] [ ] [p2] [ ] [ ] [ ]
1 2 3 4 5 6 7 8 9
.
=|=
[|]
===
and will continue doing things with person2 because it totally forgot person lives in house number four and has no in scope way of retrieving that knowledge because you threw away the paper.(well, maybe you could do something with the arguments array)
If you wish to clean up person totally you need to clean up all references to it. At this point there is only one reference to your main person. Person 2 will get cleaned up when your functino exists because there is no more reference to it.
But person still has a reference in the window object. The window still holds a piece of paper saying hey. person lives in house number 4.
So if you do in your function
window.person = {} it creates a new person, assigns a new house to the person object and gives the piece of paper with the address to the person variable in the window object
Then when the garbage collector comes it sees nobody has an address to the person living in house number 4 and cleans it up
/-\ /-\ /-\ /-\ /-\ /-\ /-\ /-\ /-\
[ ] [ ] [ ] [v] [ ] [p2] [ ] [ ] [ ]
1 2 3 v 5 6 7 8 9
\ v /
|_p__|-_
o o
Upvotes: 2
Reputation: 7490
Actually, it does redefine the person
object, but only in the functions scope. try this:
function changeName(person) {
person.name = "new tom";
person = {};
console.log(person.name); // gives undefined as expected
}
changeName(person);
console.log(person.name); // 'gives new Tom'
The person variable inside changeName
isnt available to code outside of the function, so person
does get set to {}
, but once we reference person
outside of the function, we are getting the original person object. (and remember we changed it's name value before setting the person variable to {}
)
This might make it more clear:
var person1 = {name: "tom"};
function changeName(person) {
person.name = "new tom";
person = {};
}
changeName(person1);
console.log(person); //ERROR
Upvotes: 0