0
a = function (){
    var b = 10;
    var k = function(){
        console.log(b);
    }();
}();

The above code will print 10.

var k = function(){
    console.log(b);
}
var a = function (){
    var b = 10;
    k();
}();

This code will print undefined.

Is it possible to print 10 instead? Like binding the scope to k before calling it.

2
  • The direct answer to your question is "no". Variables declared inside lexical scopes that are preserved as closures are only available if some access mechanism (like, a function) has been explicitly exposed. Otherwise they're completely private to the code that has visibility into the closure contents. Commented Jun 14, 2012 at 1:40
  • I suspect the real question revolves around why you want to access a variable in that way. For function k to have access to b it needs to be part of the execution context or a function argument. Telling us why your trying to do what you're trying to do may lead to more helpful responses. Commented Jun 14, 2012 at 2:24

3 Answers 3

1

As @Derek answered, you can obviously pass an argument.

Aside from that, you can't transfer or change variable scope, but you can directly manipulate calling context.

As such, you can set b as the property of an object, and set that object as the calling context of whatever function you're calling.

var k = function(){
    console.log(this.b);
}
var a = function (){
    var obj = {b:10};
    k.call(obj);
}();

The .call() method invokes the k function, but sets the first argument you provide as the calling context of the called function.

In fact, you don't technically need to use an object. You could directly set the number as the value to use...

var k = function(){
    console.log(this);
}
var a = function (){
    var b = 10;
    k.call(b);
}();

In strict mode, you'll get the number, but in non-strict, you'll get the Number as its object wrapper.

Sign up to request clarification or add additional context in comments.

3 Comments

I found some scenarios in expressjs My app.js looks something like this var app = require('express').createServer(); app.get('/', abc.init); app.listen(3000); In abc.js I am able to access the app object. Trying to figure out how this is possible.
@user1455111: NodeJS takes your module code, concatenates it into an immediately invoked function that defines some variables, like exports, and then returns the exports object. So you need to imagine some hidden code above and below your module code. The whole code is invoked the first time your module is requested via require. The returned exports object is cached in an internal Array, so that future requests to the same module don't need to run your code again, but instead just get your exports object from the Array. If you need I can show a simplified example of what they do.
So when you do var app = require('express').createServer(), what is happening is that the require function grabs the express module code, wraps it in more code, evals it, stores the returned object, and delivers that object to you. So it's ultimately just the same as calling a function that returns an object, and putting that object in your app variable. There's no shared scope.
0

Really? What have you tried?

var k = function(b){
    console.log(b);
}
var a = function (){
    var b = 10;
    k(b);  //Done.
}();

Why does it give you undefined in your second example is because b is not defined. You have to define it first before using the variable b.

var k = function(b){ //<--There, defined. Mission accomplished.

Comments

0

Access into the scope can be granted through eval.

var a = (function() {
    var b = 10;
    return {
        eval: function(s) {
            return eval(s);
        }
    };
})();

var k = function() {
    console.log(a.eval("b"));
};

k();
​

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.