0

I have this piece of code in a module:

    for (var i = 1; i <= n; i++) {
        when = i * 1000;
        track.execute(true, when); // <-- This line calls the method below
    }

And this piece in another module:

this.execute = function(on, when){
    [...]

    var createCallback = function(w){ // <-- Here 'when' should be bound to this function when is called below
        return function(buffers){
            object.doSomething(buffers, w);
        }
    };


    [...] // None of this code modifies when or the callback 'factory'

    this.asyncObj.getBuffer(createCallback(when)); // <-- Binding ?!?
};

The problem is that the value of when is updated at each call, therefore the callback is always executed with the latest value of when, not the one that was set at the time the method was executed (which was the expected behavior).

As you can see I've already tried the hack described in this question: JavaScript closure inside loops – simple practical example but couldn't get it right.

For some reason the callback function above always gets the latest value of when.

Thanks in advance to whoever would like to help!

PS: I guess this happens because the callback is set every time and, thus, every time is set with the latest value of when. But I'm not sure.

UPDATE: here is a tinker to try it out...And it works! O.o http://tinker.io/dee10 (this code reflects the current state of my code locally. It's the same thing as above, anyway).

Community
  • 1
  • 1

1 Answers1

2

As mentioned in the accepted answer of the question you posted, there is not block scope in JS, only function scope. Your attempt doesn't work because you're only returning a new function inside the 'createCallback' function. You need to return a new one each time the 'execute' function is called.

UPDATE Hey Marco, saw your comment. I wasn't able to run the tinker you sent but I copy/pasted the code into jsfiddle and it works fine. Try it out here: http://jsfiddle.net/tKkCh/

You can see that the function is returning with the correct value of 'when' that is passed in each time. That is what you want, right? At least in the fiddle, when you call factory(i)() the code in the fiddle is being evaluated right then, b/c js is a single threaded language.

Perhaps you can try to include more of the other code to help us figure out what's going on... there is probably an issue with the way you are trying to get it to run async in the 'asyncObj'. Thanks, good luck.

TheJoe
  • 256
  • 1
  • 8
  • I know there is only function scope, that's why I'm trying to bind when to the w argument in the `createCallback`. And the created function is always a new one (as you can try here http://tinker.io/09b6b ). I don't think I understood your point. – Marco Chiappetta Aug 12 '13 at 10:37
  • thanks a lot for your help. Eventually I changed the whole approach because I couldn't figure it out. I guess there was something else under the hood I didn't consider. Anyway the fiddle and the tinker both work fine so I have no idea what to say. :) I'll take a look at it in the near future but I needed to get it to work asap. – Marco Chiappetta Aug 26 '13 at 13:44