I'm trying to some how understand what happens inside a closure and use the variables and functions created inside of it.
My limitation is that I can add as many lines of code I want to the existing closure, but cannot edit any existing ones.
Can this be done?
<script>
var scopeClone = {};
(function(scopeClone){
//Activation Object {}
scopeClone.a = "a";
var b = "b"
//Activation Object {b:"b"}
//my custom code here
//We want to copy activation object properties to scope obj
})(scope);
//At this stage, we want to get -> scopeClone.b = "b"
</script>
Not sure it can be done:
http://interglacial.com/javascript_spec/a-10.html
10.1.6 Activation Object
The activation object is purely a specification mechanism. It is impossible for an ECMAScript program to access the activation object. It can access members of the activation object, but not the activation object itself. When the call operation is applied to a Reference value whose base object is an activation object, null is used as the this value of the call.
And from here as well:
https://www.reddit.com/r/javascript/comments/2tdwcv/are_there_any_backdoor_ways_to_access_the/
Note that Activation object is an internal mechanism and is never really accessible by program code.
Related
I was learning about constructors, and I came across the new keyword.
var obj = new myContructor();
I learnt that it created a new object, set its prototype as constructor.prototype, set its properties as according with the this keyword, and finally returns that object.
Now, I am confused as to where exactly does it create the new object, as inside memory or somewhere where it is volatile.
And what do we mean when saying it RETURNS that object, that it creates a copy of the new object at the location of the var obj, or does it reference obj to wherever it created the new object ?
inside memory or somewhere where it is volatile
Yes, of course. Just like any other piece of data in the program.
do we mean when saying it RETURNS that object
You are making a function call. Function calls have return values. The object is the return value of that function call.
it creates a copy of the new object at the location of the var obj
It creates it in the function, then it returns a reference to it (just like any other object), and that reference is stored in the variable because you used an assignment.
There are many things going in behind the scenes in Javascript; things are constantly being created in memory that you do not have access to. As far as you are concerned with this while writing Javascript code:
new creates an object and does all the prototype stuff
myConstructor() is executed, and this inside the function is set to that object
(put another way: myContructor is called with the object as context)
after myConstructor is done, the object is assigned to the variable obj as result of all this
There are a bunch of caveats regarding what myConstructor can return and how that influences the result, but we'll ignore that for simplicity. The basic chain of events is new creates object → myConstructor sees that object as this → obj "receives" this object as return value of new.
Of course, all this creating of the object and passing it around to different places is done by the Javascript engine, and requires internal storage of the object somewhere in memory.
I know that local variables dosent work when testing it, but I dont understand the concept. Why does "this" work and local variables does not? a clarification would be great on why I must use this and avoid local variables!
code:
function Person(job, married) {
var employ = job;
var status = married;
}
var ray = new Person("student", true);
console.log(ray);
You can use local variables in your constructor, but they don't automatically become instance variables of your object. Instead, the way you are using them, they are just temporal local variables, like local variables inside any function definition.
When you do this:
function Person(job, married) {
var employ = job;
var status = married;
}
var ray = new Person("student", true);
Here's what is happening:
You define a function named Person.
In that function, you define two local variables named employ and status.
Those are normal local variables within a function. They are only visible to code within that function. These may be useful for some things, but they are not available to any code outside that function. They are not available to prototyped methods of your object, they are not available to other code outside that function. In fact, without some sort of reference that creates a closure, they have a limited lifetime and are gone and garbage collected as soon as the Person function finishes executing.
So, if you intended to create the C++ equivalent of member variables of your object, this did not accomplish that. The variables are used only for the duration of the Person() function and are then disposed of and have no lasting presence.
Then, when you execute var ray = new Person("student", true);, the following things happen.
The new causes the system to create a new object, set the value of this to point to that new object and then call the Person constructor with your two arguments.
Your code then creates two local variables which you assign the two arguments to.
The Person() function then finishes executing and the two local variables are disposed of because the scope in which they were defined is done and is garbage collected.
You then assign the newly created object to the variable ray. It is indeed a new object, but it has no custom instance data because nothing was stored in a lasting way.
If you then do console.log(ray), you're just going to see an empty object with no instance data other than what the default Object instance has. Your custom data was not stored anywhere lasting so it's gone now.
If you intend for those two arguments to be saved somewhere lasting as instance data of the object, you have a couple choices. The more traditional choice is to make them publicly accessible properties of the object. You would do that like this:
function Person(job, married) {
this.employ = job;
this.status = married;
}
Since this points to the newly created object, this code assigns the job and married arguments to properties of the newly created object. These properties can be accessed either by other methods on the object or by any code outside of the constructor like this:
var ray = new Person("student", true);
console.log(ray.employ); // "student"
console.log(ray.status); // true
These properties are publicly accessible.
There are some interesting things you can do with those local variables that can allow them to persist and be used after the object is created. To do that, you have to create a closure. I think of a closure as a function scope that would normally be discarded when the function finishes executing, but because of circumstances, there are still live references within the function scope so the garbage collector does not throw away the function scope when the function finishes executing like it would in a purely stack based language like C++. Instead, it persists and can be accessed by code after the object has been created. Here's an example:
function Person(job, married) {
var employ = job;
var status = married;
this.getEmploy = function() {
return employ;
}
this.getStatus = function() {
return status;
}
}
var ray = new Person("student", true);
console.log(ray.getEmploy()); // "student"
console.log(ray.getStatus()); // true
Here's the assignment of functions within the constructor has created a closure. The private local variables employ and status are still private to within the scope of the Person function. But, because the getEmploy and getStatus properties are now publicly exposed and can be called at some time in the future and those functions reference the employ and status variables, the garbage collector realizes that it can't garbage collect the employ and status variables so they persist for the lifetime of this newly created Person object.
Using terms familiar to other object oriented languages like C++, the employ and status local variables are giving you some of the features of private instance variables. Some people call this a hack to fill the void of a feature that Javascript does not offer quite so directly. But, I don't see it as a hack. The language offers closures as an enormously useful feature that can be used in so many ways and this is just one way of using a closure to create a benefit, the benefit of private instance data.
Only the publicly assigned properties getEmploy and getStatus can be accessed by the outside world, but by calling them, we can access the private variables employ and status. If we do console.log(ray) in this new model, we still won't see employ and status there because as far as the console is concerned, they still aren't properties of the ray object. But, because of closures, they are uniquely accessible by the methods on the ray object.
Further, because a new closure is created each time we call the Person constructor, these employ and status variables are uniquely associated with each new instance of the Person object. They behave and work like private members of the object.
For more examples of this type of structure and some more explanation, see this classic discussion: http://javascript.crockford.com/private.html
Why does "this" work and local variables does not?
Unless some sort of lasting closure is created, local variables are temporal. They last only as long as the containing function is executing and they are then garbage collected. Just because they are declared inside a function that you are using as a constructor does not make them special. They are just local variables and have no magic powers beyond just being local variables.
In a class constructor why is “this required”?
a clarification would be great on why I must use this and avoid local
variables!
If you want to assign properties to your object, it is this that points to your object in the constructor so the only way to assign to a property of your object is to reference the object as this.someProperty = xxxx. That's just how the language works. All property references in Javascript require an object as the first part of the access. And, in a constructor, the reference for the newly created object is this. That's how the language was designed.
Those coming from some other object oriented languages might thing you can declare an instance variable of a class and then just use that name all by itself and the interpreter will somehow just know that it's an instance variable name, not a variable name. That might be true in some other languages. That is not true in Javascript. All property references, whether in the constructor, in some method or accessed from the outside as a property on an object must all use an object as the base of the reference. And, inside the constructor and inside a method, that base is the value of this. So, this.someProperty is how you reference that property on the current instance.
Think of it like this:
A class is basically an object, right? Well, when you declare a new instance of Person, you're saying "let's create a new object with properties x, y, and z." Using "this" allows you to access the properties for that instance later, while local variables aren't treated as properties for your object.
When a function is called as a constructor (using the new keyword), a new object is created (the instance object), prototyped on the object value of the function's prototype property, and the constructor called with its this value set to the new instance object just created.
Constructor code can set properties and methods on this (the instance object), which is the return value of the constructor call (... unless the constructor explicitly returns some other object).
If variables defined within the constructor are accessed by nested functions which persist after the contructor returns, they will not be garbage collected because they can still be accessed. If they are not accessible after the constructor returns they are essentially discarded and become available for garbage collection.
Object creation is fundamental to JavaScript behavior: Try looking up and reading about the use of constructor functions.
More about retention of variables in the scope of nested functions after an outer function exits can be found by searching for "closures in JavaScript".
I have the following code to call an function on each button in a page.
dojo.query('.btn').forEach(function(item){
Obj = new MyClass(item); // class calls the ajax request on error of each btn click I have to handle some functionality in below function showError
dojo.connect(Obj, 'showError', dojo.hitch(Obj, function(errors){
console.log(Obj + 'came');
}));
Here I tried using dojo.hitch to maintain state of each object Obj, But it is not maintaining.Only first Obj is firing.For second Button also, the first Obj is firing.Is there anything I am missing here.
Obj is declared as a global variable. Try putting a var in front of it. For example:
var Obj = new MyClass(item);
If you don't provide the var, it will create a globally accessible variable called Obj. This means that each time you loop, you refer to the same global variable. The result of this is that each one is connected to the same Obj (and that's why both buttons are connected to the same object).
Also, read this question on StackOverflow to get a more detailed view about declaring variables and the global scope.
My question is dead simple.
I just casually discovered that once you have defined a property with this. into an object, you don't need to prepend this. anymore when you want to call them.
So this. is really meant to be used ad definition time, like var?
I found it my self shortly after, i was referencing the window object with this. since i called my object without using new, so like it was a function.
One extra question, maybe for comments. Inside the main object, if i create a new object, and use this during the object definition, this this what will be referring to?
No, unless the context of this is a global object, such as window. Take the following example:
function Foo(bar) {
this.data = bar;
console.log(this.data); // OK
console.log(data); // ReferenceError
}
In this example, you'll get a ReferenceError: data is not defined on the first console.log(data), unless, data is a global variable. To access the instance's public member, you have to use this.data.
References:
Understanding JavaScript’s this keyword
The this keyword
There are all sorts of circumstances where you MUST use this in order to reference the right data.
These two implementations do very different things:
Array.prototype.truncate(newLen) {
// sets the length property on the current Array object
this.length = newLen;
}
Array.prototype.truncate(newLen) {
// sets a global variable named length
length = newLen;
}
var arr = [1,2,3,4,5,6,7];
arr.truncate(2);
You MUST use this in order to control what happens if you want to modify the current object. Your assumption that you can leave it off and it will still modify the current object's properties is not correct. If you leave it off, you are modifying global variables, not member properties.
So this. is really meant to be used ad definition time, like var?
No, the point of this is to be the current scope of execution. You can (and will) run into weird errors if you don't use this. For example, imagine you are an object with a property val and then on the prototype of that object you have
App.obj = function(){
this.val = 'initial';
}
obj.prototype.myMethod = function(val) {
// how would you assign argument val to object val?
}
also note that your reasoning breaks down with methods.
obj.prototype.meth2 = function(){
myMethod(); // fails where this.myMethod() would work.
}
See http://jsfiddle.net/BRsqH/:
function f(){
this.public='hello!';
var hidden='TOP SECRET!';
}
var instance=new f();
alert('Public data: '+instance.public+ /* gives "hello!" */
'\nHidden data: '+instance.hidden /* gives undefined */
);
Variables created with var are hidden and cannot be viewed nor modified outside the function which created them.
But variables created with this are public, so you can access them outside the function.
I think I got it.
I defined my object as function My_Object(){...} and then called it with MyObject(). This way the My_Object was treated as a function, not an object and therefore this == window.
So in the end I was attaching properties and methods to window instead of My_Object! That's way there were available without prepending .this.
The right way to initialize My_Object as an object is to call it like this new My_Object, isn't right?
Hello I'm a newcomerin JavaScript language.
I started to see some examples of JavaScript code.
and i cant understand the following code segment:
function Employee(name,salary)
{
this.name=name;
this.salary=salary;
this.paycheck=function()
{
var monthly=this.salary/12;
document.write(this.name+ ": " +monthly);
};
}
var emp= new Employee("Fred",10000);
emp.paycheck();
My question: what is the meaning of word this near the property inside class (i.e. ,this.name=name; this.salary=salary; )?
Thank you in advance!
The use of this could be explained as meaning "properties that apply to this instance". Since Employee is a constructor function (you create instances of it using the new operator), every instance has its own values for those properties:
var me = new Employee("James", 2000000); //Instance of Employee
console.log(me.name); //Prints James
var you = new Employee("Michael", 2000000); //Another instance
console.log(you.name); //Prints Michael
Note that this also means every instance of Employee has its own copy of the paycheck method. This is not particularly efficient, as a separate copy of the function has to be stored in memory for every instance of the object. You could instead declare the method on the prototype of the Employee object, which would mean the method would be shared between all instances.
In JavaScript this always refers to the “owner” of the function we're
executing, or rather, to the object that a function is a method of.
When we define our faithful function doSomething() in a page, its
owner is the page, or rather, the window object (or global object) of
JavaScript. An onclick property, though, is owned by the HTML element
it belongs to.
For further reading see these links:
http://www.quirksmode.org/js/this.html
http://justin.harmonize.fm/index.php/2009/09/an-introduction-to-javascripts-this/
http://javascriptweblog.wordpress.com/2010/08/30/understanding-javascripts-this/
this is a reference to the calling context of the function.
Its value will be different based on how a function is invoked.
In your case, because Employee is invoked using new, it's a reference to the new object being constructed.
So when you do...
this.name=name;
...what's happening is that the new object you're creating is being assigned a property name, and its value is being set to whatever was passed to the name parameter of the function.
Here's one way to demonstrate it.
Simplify your function like this...
var foo;
function Employee() {
foo = this;
}
So now all Employee does is set its this value to the outer variable foo.
Now lets create a new object
var bar = new Employee();
So bar has been assigned whatever Employee returned. If this is the new object constructed, and we assigned it to foo, then foo and bar should have the same object.
foo === bar; // true
In this case the Employee function is used a constructor. When the new Employee() syntax is used (as opposed to simply calling Employee()), this refers to an object that you are about to create, which is later assigned to emp variable.
it's a definition of properties inside the class.
You can read short information about it here http://www.phpied.com/3-ways-to-define-a-javascript-class/
this always refers to the “owner” of the function we're executing