6 ms·
How Good C# Habits can Encourage Bad JavaScript Habits
- shawndumas 14y agopart 2 [1] ----- [1]: http://enterprisejquery.com/2010/10/how-good-c-habits-can-encourage-bad-javascript-habits-part-2/ http://enterprisejquery.com/2010/10/how-good-c-habits-can-en...
- kevingadd 14y agoPart one's claim that using the 'new' keyword is somehow implicitly bad needs more to back it up than Douglas Crockford saying so. Douglas Crockford's opinions are just opinions. Is it slower in certain JS runtimes? Harder to read? Less maintainable? Anyway, re: part 2 You shouldn't encourage the use of 'value || defaultValue' without clearly, explicitly pointing out that this will prevent the use of falsy values as argument values - including 0, false, and an empty string... all values people actually want to use in some cases. It seems inexcusable to me that you would write: "Based on the false-y rules we learned earlier, if we want to check if a variable is undefined, not null, and has a value then all we need to do is check the object itself." Immediately after explaining how null and undefined are not the only falsy values in JS. Anyway, otherwise it looks like you're sharing some good advice for newbies.
- deleted 14y ago[deleted]
- k3n 14y agoYou're misinterpreting the results. > operations per second (higher is better) Using `new` is in red, while using `Object.create` is in blue, and the red bars are markedly larger than the blue in all but a few cases. Thus, using `new` is, for the most part, much faster than the Crockford way. In Chrome, it's tons faster.
- stoey 14y agoThat's not actually what the Crockford link says [1] it talks about using array and object literals in place of `new Object()` or `new Array()`. Which does indeed seem faster [2]. [1] http://yuiblog.com/blog/2006/11/13/javascript-we-hardly-new-ya/ http://yuiblog.com/blog/2006/11/13/javascript-we-hardly-new-... [2] http://jsperf.com/new-vs-object-literal http://jsperf.com/new-vs-object-literal
- k3n 14y agoThere is nothing wrong with `new` at all, and abiding to something just because some other [fallible] human says so couldn't be more wrong.
- jiggy2011 14y agoThe problem is if you forget it. x = new ConstructorFunction() vs x = ConstructorFunction() Both will work without raising an error but the second will potentially write stuff into the global object, leading to some weird bugs.
- tracker1 14y agofunction ConstructorFunction() { if (!(this instanceof ConstructorFunction)) throw new Error("new keyword required"); ... }
- k3n 14y agoYes, the Crockford argument. Just because he said it doesn't make it true, though. I don't forget it, because calling a function and creating a new object are 2 totally different things. If one can't distinguish between those, then they should probably be tutored in programming 101 because you're going to end up with a lot more serious problems than a ctor accidentally called as a normal function. Also, and I'm going out on a limb here, but I'd hazard a guess that a majority of programmers using JS will have experience with at least 1 other language (if not many) which use the very same paradigm of creating objects. I can think of a handful off the top of my head, with several of them having a virtually identical syntax (C#, Java, PHP).
- jiggy2011 14y agoNone of those languages AFAIK (I don't really know C#) will allow you to call a constructor function as anything except a constructor function and constructor functions are always constructors and therefor will always return a new object. Javascript in it's infinite wisdom will allow one to use any function as a constructor or not. So code the should be obviously wrong will not generate an error or even a warning, this is not something you want from a language. Since we can't change JS , there is merit to the argument that you should change your own code to avoid even possibly having this problem. Arguments made on the basis of "this is a mistake I am unlikely to make" fill me with skepticism.
- kbenson 14y ago> You shouldn't encourage the use of 'value || defaultValue' without clearly, explicitly pointing out that this will prevent the use of falsy values as argument values - including 0, false, and an empty string... all values people actually want to use in some cases. Perl dealt with this a few versions back, and now they have an operator for "defined-or", // [1]. It's useful. This makes it easier to correct the wrong (but common) way to supply default values for undefined/unpassed values: # Old wrong way my $foo = $bar || $baz; # $this will never be used if "falsy": 0, '', undef, '0E0' # Old right ways my $foo = defined $bar ? $bar : $baz; # Or my $foo = $bar; $foo = $baz unless defined $foo; # New way my $foo = $bar // $baz; # Uses $baz only if not defined $bar [1]: http://perldoc.perl.org/perlop.html#Logical-Defined-Or
- cmwelsh 14y agoI think the Backbone.js-style class pattern is something that helps keep your code modular and well organized. Prototype are nothing to fear. However, the article does not really touch on this. It's mostly just saying to use `{}` instead of `new Object`.
- e12e 14y agoRegarding the use of the "new" keyword, I found this stackoverflow question and answer illuminating: http://stackoverflow.com/questions/1646698/what-is-the-new-keyword-in-javascript http://stackoverflow.com/questions/1646698/what-is-the-new-k...
- saidajigumi 14y agoIs there a problem with the jsFiddle[1] linked in part 1, or am I just being an amazing jsFiddle newb? Out of the box hitting "Run" in current FF or Chrome doesn't produce console output, as I'd expect. [1] edit, added link: http://jsfiddle.net/elijahmanor/teW4J/4/ http://jsfiddle.net/elijahmanor/teW4J/4/
- fein 14y agoI didn't even realize there was an issue until you actually said something about the console not producing output. Honestly I had never noticed that pane on jsfiddle. Pop open inspector or firebug for console output, seems to work there.
- altano 14y agoYou haven't noticed it in the past because it wasn't there. That isn't a pane in jsfiddle, it's the result of the 'firebug-lite-dev.js' external script being included in the jsfiddle.
- jiggy2011 14y agoThe thing I hate about javascript "best practices" is that you have to add some many parens and squiggly brackets to your code that you may as well be writing fucking lisp.
- deleted 14y ago[deleted]
- tracker1 14y agoIf you don't like curly braces, then use coffee-script
- James_Duval 14y agoWhat's wrong with Lisp/Racket? Just the parentheses? Seems like a weird reason to have such a strong reaction to a language :/
- jiggy2011 14y agoIt makes reading the code much more difficult. "I am inside the function, the function passed into the function or the function returned from the function?"
- k3n 14y agoEh, I'd chalk this up to "C# isn't JS". Just because 2 languages share a common syntactical lineage does not mean that they behave the same way.
- revelation 14y agoIt's worse. It starts off with something that isn't even a good habit in C#, and admits as much, to go on detailing how a bunch of people have found out X can be a useful pattern, only to depict it as the way God intended and to completely disregard anything else. It is a complete and utter pretentious circle jerk building on the idea of "C# has damaged you, find enlightenment".
- yen223 14y ago"A best practice in C# is to limit the use of global variables." Limiting the use of global variables is a bad habit in C#? That's news to me.
- revelation 14y agoOops, mixed up good and bad there.
- jokoon 14y agoI hate both or those language, so I guess I'm good with this.
- Dylan16807 14y ago"you should be careful to know that Object Literals are not JSON." This rule is not only ridiculously pedantic, but the explanation page is twisted to the point of stupidity. An object literal is the source code that compiles/executes directly to an object. JSON is very much an object literal. The runtime element that isn't the same as JSON text is simply called an 'object'. On top of that, the term "JSON Object" has no predefined meaning and using it to mean an object that was created via JSON is perfectly reasonable.
- k3n 14y agoGlad that I'm not alone in this. Though I'm no stranger to pedantry, this one is just being pedantic for pedantic's sake and really has no value, unless you really don't understand what JSON is....a string representation of a data-structure. I think we'd be in a better place if instead of `JSON.parse()` and `JSON.stringify()`, we had something a little more familiar such as `JSON.serialize()` and `JSON.unserialize()` for example. In a perfect world we'd simply override `Object.toString()`, because that's really what it is -- and I've never really used `toString()` for anything else on an object, especially not now with to prevalence of robust debuggers. But I digress...
- randuser 14y agoIf you learned about JSON without really knowing Javascript first, there might be confusement about what values are acceptable in object literals but not JSON.
- ArbitraryCrow 14y agoI have very little experience with Javascript. I come from a Python background. So please excuse my ignorance, but this doesn't sound like a designed language feature at all. These look like tricks that programmers discovered they could use to provide namespace separation. Wouldn't it better if there were constructs built into the language to provide separate namespaces, in an obvious and coherent fashion?
- erik14th 14y agoIn the browser, you have the global scope in the window object o it's pretty easy to define a construct for namespaces. I thought about the namespaces thing and it sounds like a better idea than encapsulating stuff into anonymous functions so I made a little boilerplate that implement basic OOP features: http://jsfiddle.net/L4Tcw/21/ http://jsfiddle.net/L4Tcw/21/ Only thing that I think smells a bit is having to keep a reference to 'this' of the main object.
- m_mueller 14y agoIs it just me or are all the YUI theater links broken? In order to watch D. Crockford's talk I have to copy the title into google, any direct links, even on YUI itself, just lead to the front page.
- hifier 14y ago"The new keyword was added to the language partially to appease classical languages, but in reality it tends to confuse developers more than help them. Instead, there are native ways in JavaScript to declare objects and arrays and you should use those instead." Umm... what? Ever heard of constructor functions and prototypes? ...to be fair there is a small note on this at the end of the article, but this concept in javascript is far from secondary. It deserves more than a footnote. 'new' is not something to be avoided as implied here.
- duncan_bayne 14y agoThe best JavaScript habit one can have: learn Coffeescript (or ClojureScript, or BiwaScheme, etc.) ;) Seriously, I came to Javascript from a C# background and everything I saw pointed me towards treating JS as a compilation target, and choosing a language that enabled me to do the Right Thing(TM) easily and tersely. I'm not saying "don't learn JS" ... just that it seems a bit odd to be manually coding in JS when there are so many better alternatives out there.
- untog 14y agoWhile I like CoffeeScript (and code in it, day to day), I think having a base level of what's going on in the JS is still important- and will be until browsers allow you to exactly map your CS code to in-browser results.
- duncan_bayne 14y agoI strongly agree - which is why I said I'm not against learning JS. I just don't think it's terribly useful as a language as opposed to as a compilation target.