a question about jibbering.com FAQ essay on Javascript closures

L

lkrubner

I've been reading the essay here on Javascript closures:

http://jibbering.com/faq/faq_notes/closures.html


It says:

"A common use for a closure is to provide parameters for the execution
of a function prior to the execution of that function. For example,
when a function is to be provided as the first argument to the
setTimout function that is common in web browser environments.

setTimeout schedules the execution of a function (or a string of
javascript source code, but not in this context), provided as its first
argument, after an interval expressed in milliseconds (as its second
argument). If a piece of code wants to use setTimeout it calls the
setTimeout function and passes a reference to a function object as the
first argument and the millisecond interval as the second, but a
reference to a function object cannot provide parameters for the
scheduled execution of that function.

However, code could call another function that returned a reference to
an inner function object, with that inner function object being passed
by reference to the setTimeout function. The parameters to be used for
the execution of the inner function are passed with the call to the
function that returns it. setTimout executes the inner function without
passing arguments but that inner function can still access the
parameters provided by the call to the outer function that returned
it:- "


um, isn't this the same as handing settimeout an object? I don't get
the difference. Couldn't I create an object like this:

var myObject = new Object();

and then give it properties like this:

myObject.param1 = 3;
myObject.param2 = "The world is basically a good place.";
myObject.param3 = new Array("hello", "goodbye", "no way");

And then couldn't I give this to setTimeOut?

hideMenu = setTimeout(myObject, 500);

Is this different than what they suggest in the essay, with this bit of
code:


function callLater(paramA, paramB, paramC){
/* Return a reference to an anonymous inner function created
with a function expression:-
*/
return (function(){
/* This inner function is to be executed with - setTimeout
- and when it is executed it can read, and act upon, the
parameters passed to the outer function:-
*/
paramA[paramB] = paramC;
});
}

....

/* Call the function that will return a reference to the inner function
object created in its execution context. Passing the parameters that
the inner function will use when it is eventually executed as
arguments to the outer function. The returned reference to the inner
function object is assigned to a local variable:-
*/
var functRef = callLater(elStyle, "display", "none");
/* Call the setTimeout function, passing the reference to the inner
function assigned to the - functRef - variable as the first
argument:-
*/
hideMenu=setTimeout(functRef, 500);
 
T

Thomas 'PointedEars' Lahn

| However, code could call another function that returned a reference to
| an inner function object, with that inner function object being passed
| by reference to the setTimeout function. The parameters to be used for
| the execution of the inner function are passed with the call to the
| function that returns it. setTimout executes the inner function without
| passing arguments but that inner function can still access the
| parameters provided by the call to the outer function that returned
| it:- "

um, isn't this the same as handing settimeout an object?

I don't think so.
I don't get the difference. Couldn't I create an object like this:

var myObject = new Object();

and then give it properties like this:

myObject.param1 = 3;
myObject.param2 = "The world is basically a good place.";
myObject.param3 = new Array("hello", "goodbye", "no way");

And then couldn't I give this to setTimeOut?

hideMenu = setTimeout(myObject, 500);

You could, but that would probably not have a usable result. Since
setTimeout() is a host object's method and it's behavior is not clearly
specified, there are the following possibilities:

a) As `myObject' is a reference to an Object object and not to a Function
object, or as the UA's AOM does not support function references here,
the value of `myObject' (the object reference) is type-converted to
string. Unless the object defined another toString() method, this
would result in

hideMenu = setTimeout("[Object object]", 500);

and the like. Since `[Object object]' is syntactically incorrect code,
a runtime error would occur.

b) As `myObject' is neither a string nor a Function object reference,
an exception would be thrown.

c) none of the above (undefined behavior).


HTH

PointedEars
 
R

Richard Cornford

... . If a piece of code wants to use setTimeout it calls
the setTimeout function and passes a reference to a
function object as the first argument and the millisecond
interval as the second, but a reference to a function object
cannot provide parameters for the scheduled execution of
that function.
um, isn't this the same as handing settimeout an object?

In javascript functions are objects, so yes it is exactly the same as
handing setTimeout an object. Function objects are executable and
setTimeout schedules the execution of functions passed to it as
arguments so it is quite important that what is passed is executable,
and so is a function object.

Because setTimeout implementations also accept strings as their first
argument (or exclusively accept strings as their first argument)
non-function arguments will be type-converted into strings (and where
function arguments are not supported then even they will be
type-converted into strings). (There is no type-conversion mechanism
that can convert a non-function into a function; that would be
chaotic.).
I don't get
the difference. Couldn't I create an object like this:

var myObject = new Object();

Objects created with - new Object() - cannot be exeucted.
and then give it properties like this:

myObject.param1 = 3;
myObject.param2 = "The world is basically a good place.";
myObject.param3 = new Array("hello", "goodbye", "no way");

And then couldn't I give this to setTimeOut?

hideMenu = setTimeout(myObject, 500);

Is this different than what they suggest in the essay,
with this bit of code:
<snip>

Using closures to pass arguments to functions executed with setTiemout
is not the only way of achieving that goal, they are just one way of
ding so. But passing plain object references is not one of the viable
alternatives.

Richard.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,744
Messages
2,569,479
Members
44,899
Latest member
RodneyMcAu

Latest Threads

Top