The "I understand CS code much quicker" argument is a valid one theoretically, but In my opinion, it does not hold up practically that well.
CS got one thing wrong that Python got right: There are many ways to do things.
When writing CS, I understood MY CS just fine... but it always took me longer to understand the CS of other people. Sometimes even longer than JS. This is such a huge drawback, and even if there is coffeelint, for teams, this is deadly.
A lot of devs need to read a fair amount of foreign code. Even worse a lot of coffeescript writers also need to read and understand a lot of JS code.
Understanding and reading YOUR code slightly faster gets mitigated by having longer to understand foreign code.
While some JS purists fail to see that Coffeescript has some benefits, CS people also underestimate how "quickly" you can understand JS code, if you're experienced. It's all about what your brain is trained to do.
In my opinion, with ES6, I would argue for most people (ceteris paribus) it just makes sense to read and write JS exlusively, if you want to maximize output-productivity of a full, practical project.
Shaving off a couple of seconds "understand-time" of your personal, well written CS vs well written JS will just not compensate other things that will take you longer to do with CS.
Of course you can reduce the JS verbosity with JSX instead... which again is introducing a pre-processor to the mix (one I personally am not a fan of, but w/e).
ES6 adds some sweet stuff for sure, but IMO it doesn't make JS a pleasure to work with yet (which seems to be the argument?).
I'm willing to bet it's not going to reduce the count in this list by much. https://github.com/jashkenas/coffeescript/wiki/list-of-langu...
I'm comfortable writing either as I'm sure many are, but when given the choice I opt for CoffeeScript.
P.S. Good luck telling someone using ClojureScript that they should switch back to Javascript.
My interpretation of what Retozi is saying is that CS just means that in addition to understanding JS, including ES6, you need to be familiar with all the different ways things can be done in CS.
I tend to agree, especially as JS is becoming an improving with each release.
What I'd like to see going forward is JS continuing to add selective sugar as is in CS, but also add functionality that makes going into a new fresh JS codebase and making sense of it easier. That side of things is less about CS, and more about the sorts of ideas you see in Dart and TypeScript.
http://arcturo.github.io/library/coffeescript/07_the_bad_par...
To each his own, but to me CS has been and continues to be a complete and obvious win over JS. 9 times out of 10 the benefit outweighs the annoyance of requiring a preprocessor for me.
[1] http://ceronman.com/2012/09/17/coffeescript-less-typing-bad-...
I haven't come up with a better approach than simply agreeing on a convention with your team though TBH. It's not too bad when everyone's on the same page and familiar with the gotchas (same could be said for most langs).
I put together a post comparing some of the syntax differences as it relates to building ReactJS components in case you're interested: http://rapin.com/blog/2015/02/03/reactjs-with-coffeescript/
Given that JS itself has quite a few different ways to do things though, it's kind of a wash.
I don't think this is necessarily true anymore, if it ever was. For hash-like datastructures in Python, please choose between object/dict/namedtuple/enum. In JS/CS all higher-level manipulations are dealt with through functions, whereas in Python depending on the situation you need factories, decorators, metaclasses and so on. And on a purely practical level people are moving away from the standard library (instead preferring arrow, requests, various unittest replacements etc.) but you'll still want to know the stdlib equivalents in case you encounter them in other code... and I can keep going like this.
I'm not saying this is necessarily a bad thing, sometimes one-size-fits-all just doesn't cut it, I just don't think Python can lay claim to being a simple language anymore.
Hopefully you realize that most Rubyists will strongly disagree and think that's not a "problem".
Don't forget, Python is the community that brought us "There's Only One Way To Do It".
I know this might not sound like a big deal in the grand scheme of things, but I also don't think CoffeeScript really improves on js all that much, so the annoyances of source maps are just not worth it to me personally.
It's much easier to read indentation than it is to match up pairs of brackets in your head. In other languages, if the indentation doesn't match the brackets, you'll naturally read the indentation first and get the wrong impression of what the code does. In those languages, the indentation is supposed to match the brackets anyway. Why be redundant like that?
It's much easier to read indentation than unindented/badly indented pairs of brackets, but you're setting up a strawman - it's not either or - and then you tear down the strawman yourself by pointing out we match the indentation anyway.
My code generally is properly indented and has start/end markers (though I mostly write Ruby, so rarely brackets), but what makes me stay away from significant indentation is that in the 30+ years I've been coding, I've never gone long without coming across situations where indentation has broken "in transit" e.g. with cut and paste between systems in annoying ways, or someone loading the code into an editor that butchers the indentation with tabs using "non-standard" tab settings.
When that happens, I'd rather "get the wrong impression" than have the code be broken.
That's one reason I want redundancy. My tools can trivially and automatically fix the result of breaking indentation when the indentation can be derived from the code.
Additionally, I want the visual redundancy, much like I find it far more comfortable to read syntax highlighted code even though it conveys no additional information.
The way things are in bracketed languages, humans and computers read different things, and you just have to hope that they always match up. Sometimes they don't, and the human and computer will have a misunderstanding. To make it a real linguistic redundancy, like in Spanish, the compiler should read both and issue a warning if the indentation is incorrect or misleading. As it is, you and the computer are actually speaking different languages.
Also, here's a gotcha I've run into where `a(b)` is considered different from `a (b)`
x a(b), c # => x(a(b), c);
x a (b), c # => x(a(b, c));
I encountered a non-obvious Python bug that was caused by mixed spaces-and-tabs: to my human eyes, the indentation looked fine - the same as previous line, but the interpreter saw a different level of indentation.
This is why PEP8 exists and people are supposed to follow it. Additionally, mixed spaces-and-tabs is a bug that causes poor readability - there's plenty of people who have their editors set to have tabstops as 2 or 3 spaces rather than 4, and your code will look wrong in their editors.
If you think there's any issues with mixed tabs and spaces in your codebase, Python provides a tool to find out - tabnanny. Additionally, any context-aware code editor will display a warning. (If you're using Sublime Text, the plugin to use is SublimeLinter - I assume there's similar tools for vim and emacs.) You can even set spaces and tabs to display differently in many editors!
It puts some icons in the margins, but I can't figure out how to get an explanation of those icons. I see a bunch of !s next to my import statements.
Also, computers don't deal well with it. It's a smaller problem than people don't dealing well with it (the alternative), but it's still a problem. Anyway, this is much more relevant to scripts that run inside a browser.
(nitpick: you seem to consistently use "identation" in place of "indentation".)
I'm pretty sure that plenty of proposals consistent with Python's significant indentation have been proposed; python's lambda syntax is limited due to the BDFL not being convinced of the utility of more capable lambdas over using named functions enough to want to make Python's syntax more complicated to achieve it.
> Also, computers don't deal well with it.
Computers deal fine with it.
Consequence of English not being my first language, and "indentation" being way too similar in it. I just can't spot the change.
I've seen a couple of proposals, yes they'd work, but they seem to be always ugly. But the problem is not that significant indentation makes it hard to create lambdas (Haskell's ones, for example are fine), but that it's hard to think about rules that won't create some kind of problem. On Python it's lambdas, on Haskell it's that they are often actually harder to write than explicit blocks (good thing Haskell has explicit blocks too).
And no, computers don't deal fine with it. To minimise some Python code you need almost an entire Python parser. Assembling Python code from small pieces (something that is really important for Javascript) is a frightening problem.
Sure they do.
> To minimise some Python code you need almost an entire Python parser.
I don't think source-to-source transformations requiring a parser for the source is an indication that it is problematic for computers to handle something. I mean, to execute the source code you need a parser, too, and no one says that needing a parser for execution is a sign that computers don't handle a language well.
> Assembling Python code from small pieces (something that is really important for Javascript) is a frightening problem.
Sure, assembling by cut-and-paste is a problem with significant indentation, especially when using media (like the web) which do not respect indentation well.
OTOH, using significant amount of cut-and-paste coding (rather than reuse by library code) is a sign of a problem with the language, development process, and/or execution environment, anyway, so I don't see it as a particular problem that a language structure isn't friendly to copy-paste coding.
On top of that I find it invaluable to be able to space out debugging code. Example
void SomeFunc() {
int x = doSomething1(1, 2, 3, 4);
int y = doSomething1(4, 5, 6, 8);
int z = doSomething1(5, 6, 7, 9);
printf("xyz=%d,%d,%d", x, y, z);
int a = doSomething1(0, 2, 3, 4);
int b = doSomething1(1, 5, 6, 8);
int c = doSomething1(2, 6, 7, 9);
printf("abc=%d,%d,%d", a, b, c);
int d = doSomething1(6, 2, 3, 4);
int e = doSomething1(5, 5, 6, 8);
int f = doSomething1(7, 6, 7, 9);
printf("def=%d,%d,%d", d, e, f);
return x * y * z + a * b * c + d * e * f;
}
vs void SomeFunc() {
int x = doSomething1(1, 2, 3, 4);
int y = doSomething1(4, 5, 6, 8);
int z = doSomething1(5, 6, 7, 9);
printf("xyz=%d,%d,%d", x, y, z);
int a = doSomething1(0, 2, 3, 4);
int b = doSomething1(1, 5, 6, 8);
int c = doSomething1(2, 6, 7, 9);
printf("abc=%d,%d,%d", a, b, c);
int d = doSomething1(6, 2, 3, 4);
int e = doSomething1(5, 5, 6, 8);
int f = doSomething1(7, 6, 7, 9);
printf("def=%d,%d,%d", d, e, f);
return x * y * z + a * b * c + d * e * f;
}
On a long functions I find it much easier to see/find/delete the debug print lines by indenting them separate from the real logic but I can't do that on any language that enforces code blocks by indentation.Commenting out also because an issue
void SomeFunc(int v) {
bool doit = v > 5;
if (doit)
{
DoSomething();
DoSomethingElse();
DoSomethingOther();
}
}
For testing I often want to comment out the if void SomeFunc(int v) {
bool doit = v > 5;
//if (doit)
{
DoSomething();
DoSomethingElse();
DoSomethingOther();
}
}
If I was in python I can't do that def SomeFunc(v):
doit = v > 5
#if doit
DoSomething()
DoSomethingElse()
DoSomethingOther()
Error! I have to format the whole function just to comment out a line for testing. Yes in this case I could put `if true` (then requiring two changes instead of one) but there are plenty of other cases where code blocks by indent make it really annoying to work with my code.So no, significant indentation is not a good thing.
I guess you've developed a habit where you're completely OK with having incorrect indentation a lot of the time, whereas I can't stand it. Just because it's easier to read for you doesn't make it easier for everyone, especially beginners.
And "incorrect indentation" has a very different meaning when the indentation is purely for presentation: As illustrated above, some people like to use the indentation to call out specific aspects of the code. That may be "incorrect" from Python perspective, but it is a way of visually providing additional information that is not available to you if you use a language that requires a specific indenting style.
Your last paragraph makes little sense as you should never, ever be debugging a problem on live and I think minification has caused me a problem like twice in the 8 years since it's been popular. And it was pretty obvious when it did as the is wasn't even compiling.
Until you have to
I just cannot emphasise this enough. One of my skills is debugging, everywhere I've worked I've been one of the top debuggers if not the top debugger.
Never, ever debug on live. If you can't recreate the problem locally, you don't understand the problem yet. Keep trying to replicate it until you do. I'm talking days of trying, not 10 bloody minutes.
The key to all debugging, the very fundamental skill, is consistent replication. If you can replicate a problem consistently, you can fix it.
There's a class of problems where this isn't necessarily true, especially for desktop apps, but web development problems and javascript, you can almost always replicate locally.
While I agree with your overall sentiment, in any kind of remotely complex environment you sooner or later come across problems that you have no sensible way of reproducing in dev, and which will require you to debug on a production environment without it saying anything about the quality of your development process.
I have seen production hardware or wiring be the problem once in my entire career. And I used to work for a company that ran and supported enterprise software on hundreds of different client-owned servers.
Most people these days will be running a few web servers at most.
EDIT: Worse still, we're talking about debugging javascript here, which makes what you're saying even more preposterous. Wiring, indeed.
I am guessing you have not been exposed to highly complex live environments. What you say is largely true but you state it as an absolute fact, which is a bit naive. Live environments tend to be far more complex than test or local environments and sometimes that complexity is what creates the bug. Sometimes the only solution is to debug live, but of course that is a last resort.
I'm not naive, I did actually say "almost always" and "There's a class of problems where this isn't necessarily true", but perhaps you can't read?
I feel this is statement is a tad hyperbolic.
One of my key skill sets is debugging, I'm pretty good at it. One of the things we can't do is completely replicate a production environment because we're a web hoster. Sure I can run and test stuff against our OS "gold images" but when you've added third party client code running on 300-400 sites on a single server that environment is not reproducible without a herculean effort. We also don't have the luxury of time to "Keep trying to replicate it until you do. I'm talking days of trying".
Four or five times a year I need to dig out ADPlus, point it at a customer's worker process and tell it to snapshot and dump when certain conditions/triggers occur. I then whip said dump over to my WinDbg+SOS environment to find out what the hell was happening in the process when it went bad.
Development builds should use concatenated and minified .js code. That verifies that the development build performs exactly like the production build.
You can use source maps to help with debugging.
Many people don't like that CS needs to be compiled. I don't see this as an issue since pretty much every application I work on these days is concatenated and uglified. So adding a JS compiler is already part of most JS application's build process. 6to5 is being compiled to ES5 anyway. Also, if you include in your build pipeline a source mapper, debugging is not a problem.