Top function Questions

List of Tags
694
Richard

I've recently started maintaining someone else's JavaScript code. I'm fixing bugs, adding features and also trying to tidy up the code and make it more consistent.

The previous developer uses two ways of declaring functions and I can't work out if there is a reason behind it or not.

The two ways are:

var functionOne = function() {
    // Some code
};
function functionTwo() {
    // Some code
}

What are the reasons for using these two different methods and what are the pros and cons of each? Is there anything that can be done with one method that can't be done with the other?

Answered By: Greg ( 629)

The difference is that functionTwo is defined at parse-time for a script block, whereas functionOne is defined at run-time. For example:

<script>
  // Error
  functionOne();

  var functionOne = function() {
  }
</script>

<script>
  // No error
  functionTwo();

  function functionTwo() {
  }
</script>
389
John Duff

What is the difference between using call and apply to invoke a function?

var func = function(){
  alert('hello!');
};

func.apply();

vs

func.call();

Are there performance differences between the two methods? When is it best to use call over apply and vice versa?

Answered By: flatline ( 443)

The main difference is that apply lets you invoke the function with arguments as an array; call requires the parameters be listed explicitly.

See here and here.

Pseudo syntax:

theFunction.apply(valueForThis, arrayOfArgs)

theFunction.call(valueForThis, arg1, arg2, ...)

Sample code:

function theFunction(name, profession) {
    alert("My name is " + name + " and I am a " + profession + ".");
}
theFunction("John", "fireman");
theFunction.apply(undefined, ["Susan", "school teacher"]);
theFunction.call(undefined, "Claude", "mathematician");

Possible Duplicate:
Is there a better way to do optional function parameters in Javascript?

I would like a JavaScript function to have optional arguments which I set a default on, which gets used if the value isn't defined. In ruby you can do it like this:

def read_file(file, delete_after = false)
  # code
end

Does this work in JavaScript?

function read_file(file, delete_after = false) {
  // Code
}
Answered By: Tom Ritter ( 434)

There are a lot of ways, but this is my preferred method - it lets you pass in anything you want, including false or null. (typeof null == "object")

 function foo(a, b)
 {
   a = typeof a !== 'undefined' ? a : 42;
   b = typeof b !== 'undefined' ? b : 'default_b';
   ...
 }
175
Sep O Sep
!function () {}();
Answered By: Neil ( 312)

OK, so back to JavaScript syntax 101. Here is a function declaration:

function foo() {}

Note that there's no semicolon: this is a statement; you need a separate invocation of foo() to actually run the function.

On the other hand, !function foo() {} is an expression, but that still doesn't invoke the function, but we can now use !function foo() {}() to do that, as () has higher precedence than !. Presumably the original example function doesn't need a self-reference so that the name then can be dropped.

So what the author is doing is saving a byte per function expression; a more readable way of writing it would be this:

(function(){})();
166
Mark Biek

I've always handled optional parameters in Javascript like this:

function myFunc(requiredArg, optionalArg){
  optionalArg = optionalArg || 'defaultValue';

  //do stuff

}

Is there a better way to do it?

Are there any cases where using || like that is going to fail?

Answered By: Paul Dixon ( 252)

Your logic fails if optionalArg is passed, but evaluates as false - try this as an alternative

optionalArg = (typeof optionalArg === "undefined") ? "defaultValue" : optionalArg;
159
user1859094

In one of my project source files, I found this C function definition:

int (foo) (int *bar)
{
    return foo (bar);
}

Note: there is no asterisk next to foo, so it's not a function pointer. Or is it? What is going on here with the recursive call?

Answered By: NPE ( 244)

In the absence of any preprocessor stuff going on, foo's signature is equivalent to

int foo (int *bar)

The only context in which I've seen people putting seemingly unnecessary parentheses around function names is when there are both a function and a function-like macro with the same name, and the programmer wants to prevent macro expansion.

This practice may seem a little odd at first, but the C library sets a precedent by providing some macros and functions with identical names.

One such function/macro pair is isdigit(). The library might define it as follows:

/* the macro */
#define isdigit(c) ...

/* the function */
int (isdigit)(int c) /* avoid the macro through the use of parentheses */
{
  return isdigit(c); /* use the macro */
}

Your function looks almost identical to the above, so I suspect this is what's going on in your code too.

Could someone explain? I understand the basic concepts behind them but I often see them used interchangeably and I get confused.

And now that we're here, how do they differ from a regular function?

Answered By: Claudiu ( 158)

A lambda is just an anonymous function - a function defined with no name. In some languages, such as Scheme, they are equivalent to named functions. In fact, function definition is re-written as binding a lambda to a variable internally. In other languages, like Python, there are some (rather needless) distinctions between them, but they behave the same way otherwise.

A closure is any function which closes over the environment in which it was defined. This means that it can access variables not in its parameter list. Examples:

def func(): return h
def anotherfunc(h):
   return func()

This will cause an error, because func does not close over the environment in anotherfunc - h is undefined. func only closes over the global environment. This will work:

def anotherfunc(h):
    def func(): return h
    return func()

Because here, func is defined in anotherfunc, and in python 2.3 and greater (or some number like this) when they almost got closures correct (mutation still doesn't work), this means that it closes over anotherfunc's environment and can access variables inside of it. In Python 3.1+, mutation works too when using the nonlocal keyword.

Another important point - func will continue to close over anotherfunc's environment even when it's no longer being evaluated in anotherfunc. This code will also work:

def anotherfunc(h):
    def func(): return h
    return func

print anotherfunc(10)()

This will print 10.

This, as you notice, has nothing to do with lambda's - they are two different (although related) concepts.

I am a long-time Applescript user and new shell scripter who wants to learn a more general scripting language like Javascript or Python for performance reasons.

I am having trouble getting my head around concepts like object orientation, classes and instantiation.

If someone could point me to a pithy explanation of methods vs. functions it might help me get over the "hump". The explanations I found using google are just barely over my head.

Thanks.

Answered By: Andrew Edgecombe ( 163)

A function is a piece of code that is called by name. It can be passed data to operate on (ie. the parameters) and can optionally return data (the return value).

All data that is passed to a function is explicitly passed.

A method is a piece of code that is called by name that is associated with an object. In most respects it is identical to a function except for two key differences.

  1. It is implicitly passed the object for which it was called
  2. It is able to operate on data that is contained within the class (remembering that an object is an instance of a class - the class is the definition, the object is an instance of that data)

(this is a simplified explanation, ignoring issues of scope etc.)