8 ms·
I learned something: I didn't know that the difference between: function foo() { } and var foo = function() { }; Was that with the first for
by gorhill 12y ago
I learned something: I didn't know that the difference between:
function foo() {
}
and
var foo = function() {
};
Was that with the first form foo() will always be declared and available for use inside a scope, while the second form depends at which point it is declared.
But I had read somewhere (can't remember where... jshint?) a long while ago that using the latter form inside scopes was better, so I've adopted that.
I don't think I will go with the guide for this one, since not having the function defined automatically is often useful, to avoid overhead of instantiating the function for when it's not going to be used due to code flow.
- bevacqua 12y agoThat's negligible, the code is going to get compiled in C++ anyways, and the overhead is minimal
- gorhill 12y agoI don't understand why you bring up C++. With overhead, the approach I try to stick to is unless the code become more difficult to grasp, avoid overheads, however small they may be, whenever they can be avoided. Everything adds up in the end.
- warfangle 12y agoA lot of people prefer the latter form inside scope, because it disambiguates the ambiguity that hoisting introduces: define your function at the bottom of the scope, and it'll still be available at the top. By assigning it to var, you delineate "this function can be called by any line in this scope after this one, but not by any line before it." You also remove a named reference to it from the stack trace. I much prefer dealing with the "weird" "confusion" hoisting behavior than with not having a named function in my stack trace.
- couchand 12y agoFortunately they're not mutually exclusive, which is why the one true way (tm) is: var foo = function foo() { }; EDIT: The reason it's better to avoid hoisting is because global variables are almost always wrong.
- delluminatus 12y agoPretty sure hoisting is totally unrelated to global variables. If a function is defined in a scope, it'll only be hoisted to the top of the scope.
- couchand 12y agoAh, right. Should have left the original comment alone. Here's why you shouldn't rely on function hoisting: it gets weird. Weird enough that MDN has a section on it's "oddities" [0]. And since it doesn't add any expressive power, there's no compelling reason not to just treat all your code as data. [0]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Scope_Cheatsheet#function_oddities https://developer.mozilla.org/en-US/docs/Web/JavaScript/Refe...
- kevincennis 12y agoThat sounds like an argument for learning how hoisting works, not just avoiding it because it's "weird".
- warfangle 12y agoOr limiting when/where you define named functions it's pretty damn silly to declare a named function within an if block within a function call, especially if it has the same name as a function you've defined outside of it. I tend to limit them to "private" module functions. e.g., "use strict"; /*global module:true*/ function add(a, b) { return a+b; } module.exports = { sum : function(list) { return list.reduce(add, 0); } }; I don't declare named functions in a scope smaller than the module itself, so I don't really run into the 'weirdness' of hoisting. Then again, I've moved to commonjs style modules for everything - server side with node, client side with browserify (webpack does weird things with require()).
- couchand 12y agoI'd be in complete agreement if it offered any substantive benefits; however, I've yet to see an example of function-hoisting that can do something regular var-hoisting can't.
- thedufer 12y agoWhat browser are you using? As far as I can tell, all modern browsers know how to get the name of a function defined like `var foo = function(){}` for stack traces.
- spmurrayzzz 12y agoThis is referred to as "hoisting". As an aside, technically the latter's `var` declaration also gets destructured and hoisted as such... var foo; ... foo = function() { } Also another difference in the latter is that its an anonymous function, which is commonly seen in assignment expressions — but you could also name it for more informative logging. var foo = function realName(){};
- akbar501 12y agoOne gotcha about naming otherwise anonymous functions is that the function name is often removed during minification. So, if you have code or logging that assumes all functions have names, then the code may break or degrade when built and deployed in production.
- gorhill 12y ago> more informative logging. > var foo = function realName(){}; Nice trick, thanks! The "anonymous" function is especially annoying when profiling code, so that should address that annoyance. I often struggle with picking names, but another post here shows that "foo" can just be reused as the function name.
- XaspR8d 12y ago> I often struggle with picking names, but another post here shows that "foo" can just be reused as the function name. I'd be very careful about giving them the same name if you're working with IE at all. IE8 and below's JScript does some really strange stuff with function expressions, leaking and hoisting them all over the place. [1] Instead, I'd just append a character or something to differentiate the two. I've been using the format advocated for in Javascript Patterns[2][3]: var foo = function fooF(){}; [1] http://kangax.github.io/nfe/#jscript-bugs http://kangax.github.io/nfe/#jscript-bugs [2] http://shichuan.github.io/javascript-patterns/ http://shichuan.github.io/javascript-patterns/ [3] https://github.com/shichuan/javascript-patterns/blob/master/general-patterns/function-declarations.html https://github.com/shichuan/javascript-patterns/blob/master/...
- 12y ago
- donatj 12y agoI was under the assumption that we'd pretty much settled on the second syntax. I've prefer the latter as it better illustrates the way JavaScript actually works, with all methods being lambdas. The prior is just too magic.
- Flenser 12y agoThe first chapter of JavaScript Allongé explains this really really well https://leanpub.com/javascript-allonge/read https://leanpub.com/javascript-allonge/read