When I use the latest (1.0) release of coffee-script, a simple javascript output looks like this (by default):
(function() {
var a;
a = 1;
}).call(this);
What does .call(this) do and what would be the reason to add it?
It's a way to make sure that the compiled CoffeeScript has its own scope for variable names. This has benefits in terms of efficiency and simplicity (you know you the generated JavaScript won't stomp on variables used by other code). You can disable it with the --bare (or -b) option to the CoffeeScript compiler.
The reason for the call(this) is just to ensure that the CoffeeScript has the same this as the scope where it's placed, because functions don't normally inherit their this object from the surrounding context.
It's creating a function and then calling itself with the parent function/objects scope.
.call and .apply are different methods of invoking a function. You basically created a function that does nothing except set a=1 within its own scope.
In javascript you need to realize that every function is a object, and this is what refers to the current object/function. Using .call(this) overrides this from within the function and replaces it with the one from the calling context.
Related
When I call a function, a local scope is erected for that call. Is there any way to directly reference that scope as an object? Just like window is a reference for the global scope object.
Example:
function test(foo){
var bar=1
//Now, can I access the object containing foo, bar, arguments and anything
//else within the local scope like this:
magicIdentifier.bar
}
Alternately, does anyone have a complete list of what is in the local scope on top of custom variables?
Background: I'm trying to get down to a way of completely shifting to global scope from within a function call, the with statement is a joke, call works a little better, but it still breaks for anything declared in function scope but not in global scope, therefore I would declare these few cases in global scope, but that requires me to know what they are. The IE function execScript makes a complete shift, but that only solves the problem for IE.
Note: To anyone loading JavaScript dynamically, setTimeout(code,1) is a simple effective hack to achieve global scope, but it will not execute immediately.
No, there's no way to reference the variable object of the execution context of a function binding object of the variable environment of the execution context (that's what that thing is called [now; hence the strikethrough]; details in §10.3 of the specification). You can only access the limited view to it you get with arguments (which is very limited indeed).
Usually when I've wanted to do this, I've just put everything I wanted on an object and then used that (e.g., passed it into a function). Of course, any functions created within the context have access to everything in scope where they're created, as they "close over" the context; more: Closures are not complicated.
I know this is hugely late, and you're probably not even slightly interested any more, but I was interested in the feasibility of this too and you should be able to make a work around of some sort using:
(function(global) {
var testVar = 1;
global.scope = function(s) {
return eval(s);
}
})(this);
then running:
scope('testVar'); // 1
returns the variable from within the closure. Not particularly nice, but theoretically possible to wrap that in an object, perhaps using some validation and getters and setters if you needed?
Edit: Having re-read the question, I assume you'd want to access it without having to specify a function in the scope itself, so this probably isn't applicable. I'll leave this here anyway.
Certain versions of Netscape had a magic property in the arguments object that did what you're looking for. (I can't remember what it was called)
What about something like this?
<script type="text/javascript">
var test = {
bar : 1,
foo : function () {
alert(this.bar);
}
}
test.foo();
</script>
You don't need a keyword to reference a variable in the local scope, because it's the scope you're in.
For example I have:
var n = {
abc: function() { print("abc"); },
def: function() { print("def"); },
};
Is there a way to export abc and def as global functions, so that I can call abc() directly rather than n.abc()?
My context for this is using Rhino/Nashorn script engine, and I'd like to inject a "global" object that provides global functions.
The answers for Rhino and Nashorn would be different.
For Rhino, when you create the global object using Context.initStandardObjects, you can then add your properties on the Java side by calling ScriptableObject.defineProperty (see Rhino API) and then the properties will be added to that global scope. If you need a property of type function as your example shows, create it using the FunctionObject API.
For Nashorn, you can use the interfaces mostly based on the standard javax.script APIs, with a couple of Nashorn-specific extensions. When evaluating your script, first use ScriptEngine.createBindings() to create a Bindings object, then use Bindings.put to use eval(String/Reader,Bindings)
If you need a function property, then on the Java side call ScriptUtils.wrap to create a ScriptObjectMirror (make sure to cast it to that; return type of the method is Object), then call get([function name]) to get an executable function property, then put that in the global scope.
All of that said, it seems to me that this is more easily handled on the script side using:
var abc = function() { return n.abc.apply(n,arguments); };
That's portable across Rhino/Nashorn and is one line, which is a lot less work than what you're going to do if you want to avoid writing that one line.
If you execute that in the global scope, you don't need a qualifier; it'll be added to the top-level object as a property. If you want to be more explicit you can do something like this:
(function() {
var global = this; // inner functions called without target default to global as 'this'
this.abc = function() { return n.abc.apply(n,arguments); };
})();
... which will work unless you start doing stuff that's a lot fancier (like messing around with 'this' values when loading scripts).
Why don't you just use JavaScript's bind, call and apply methods to call the object's member functions when you need to invoke them? Making them global indicates code smell.
I was looking at adding comments to JSON and found this script that strips them out before processing making the JSON valid. I am just trying to understand how it works to make the JSON.minify() function available?
It starts with
(function(global){ ...
totally which is weird to me. I found that "global is a property of a RegExp instance, not the RegExp object" on MDN but I don't understand how it is works in this script if at all.
This snippet:
(function(global){
// your code here
// referring to the variable named "global" in this scope
// will be a reference to the default javascript global object
})(this);
is a construct for assigning the global object (whatever it might be) to an argument labeled global for all code that is inside this self-executing function.
The self executing function is used to define a separate execution scope so that any functions or variables you define inside this other scope will not interfere with or be directly accessible from outside this scope (insulating your scope from other code scopes).
In a browser, the global object is the window object, but if you intended to have code that might work in other javascript environments (like no node.js on a server) where the global object might not be window, this is a way of extracting the global value from the default this value, putting it into another variable which you can then refer to anywhere inside your code block.
For code mean to only run in a browser, there really is no point to this. You can just refer to window when you need the global object.
It's just a function parameter name. It might as well be froozboggles.
This code:
(function(foo) {
// In here, what's called "bar" in the outer scope is called "foo"
})(bar);
Defines an anonymous function taking one parameter bar and immediately calls it with the value of bar as the first parameter.
Apart from what jfriend00 mentions in his fine answer, it's also a good way of making sure that you don't leak variables and functions to the outer scope: If you declare, say, var baz = 17; in the top scope in javascript, it will be a property of window. If you wrap it in a function as in the pattern you mention, you can only export properties to window explicitly -- by assigning them to global, in the case of your example. Edit: As #josh3736 says in his comment, you can also leak to window by assigning without a previous declaration, e.g. quux = 4711;.
When I call a function, a local scope is erected for that call. Is there any way to directly reference that scope as an object? Just like window is a reference for the global scope object.
Example:
function test(foo){
var bar=1
//Now, can I access the object containing foo, bar, arguments and anything
//else within the local scope like this:
magicIdentifier.bar
}
Alternately, does anyone have a complete list of what is in the local scope on top of custom variables?
Background: I'm trying to get down to a way of completely shifting to global scope from within a function call, the with statement is a joke, call works a little better, but it still breaks for anything declared in function scope but not in global scope, therefore I would declare these few cases in global scope, but that requires me to know what they are. The IE function execScript makes a complete shift, but that only solves the problem for IE.
Note: To anyone loading JavaScript dynamically, setTimeout(code,1) is a simple effective hack to achieve global scope, but it will not execute immediately.
No, there's no way to reference the variable object of the execution context of a function binding object of the variable environment of the execution context (that's what that thing is called [now; hence the strikethrough]; details in §10.3 of the specification). You can only access the limited view to it you get with arguments (which is very limited indeed).
Usually when I've wanted to do this, I've just put everything I wanted on an object and then used that (e.g., passed it into a function). Of course, any functions created within the context have access to everything in scope where they're created, as they "close over" the context; more: Closures are not complicated.
I know this is hugely late, and you're probably not even slightly interested any more, but I was interested in the feasibility of this too and you should be able to make a work around of some sort using:
(function(global) {
var testVar = 1;
global.scope = function(s) {
return eval(s);
}
})(this);
then running:
scope('testVar'); // 1
returns the variable from within the closure. Not particularly nice, but theoretically possible to wrap that in an object, perhaps using some validation and getters and setters if you needed?
Edit: Having re-read the question, I assume you'd want to access it without having to specify a function in the scope itself, so this probably isn't applicable. I'll leave this here anyway.
Certain versions of Netscape had a magic property in the arguments object that did what you're looking for. (I can't remember what it was called)
What about something like this?
<script type="text/javascript">
var test = {
bar : 1,
foo : function () {
alert(this.bar);
}
}
test.foo();
</script>
You don't need a keyword to reference a variable in the local scope, because it's the scope you're in.
I have some third-party Javascript that has statements like this:
FOO = function() {
...functions() ...
return { hash }
}();
It is working as designed but I'm confused by it. Can anybody define what this structure is doing? Is it just a weird way to create a class?
This is a technique that uses closure. The idiom is well-known, but confusing when you first see it. FOO is defined as the object that the outermost function() returns. Notice the parenthesis at the end, which causes the function to evaluate and return { hash }.
The code is equivalent to
function bar() {
...functions() ...
return { hash }
};
FOO = bar();
So FOO is equal to { hash }. The advantage of this is that hash, whatever it is, has access to stuff defined inside the function(). Nobody else has access, so that stuff is essentially private.
Google 'Javascript closure' to learn more.
Js doesn't really have classes, per se, but "prototypes". This means that no two objects are ever of the same "type" in the normal type-safe sense, and you can dynamically add members to one instance while leaving the other unmolested. (which is what they have done).
Believe it or not, the syntax they have used is probably the most lucid, as it doesn't try to hide behind some C-style class syntax.
Doug Crockford's Javascript: The Good Parts is a quick read, and the best introduction to OOP in js that I've come across.
That's not actually a class, just an object. I'd recommend reading this: http://javascript.crockford.com/survey.html
Because JavaScript doesn't have block scope, your choice is (mostly) to have all variable reside in global or function scope. The author of your snippet wants to declare some local variables that he doesn't want to be in the global scope, so he declares an anonymous function and executes it immediately, returning the object he was trying to create. That way all the vars will be in the function's scope.
The parans at the end make this the Module Pattern, which is basically a way to have a single instance of an object(Singleton) while also using private variables and functions.
Since there's closures hash, if it's itself an object or function, will have access to all variables declared within that anonymous Singleton object.
You're missing an open parens, but it is basically a way of usually hiding information within an object i.e. a way of setting up private and privelaged methods.
For example
var foo = (function() {
/* function declarations */
return { /* expose only those functions you
want to expose in a returned object
*/
}
})();
Take a look at Papa Crockford's Private Members in JavaScript. This is basically the pattern you are seeing, but in a slightly different guise. The function declarations are wrapped in a self-invoking anonymous function - an anonymous function that is executed as soon as it's declared. Since the functions inside of it are scoped to the anonymous function, they will be unreachable after the anonymous function has executed unless they are exposed through a closure created by referencing them in the object returned from the execution of the anonymous function.
It's generally referred to as the Module Pattern.