Hacker News new | past | comments | ask | show | jobs | submit login

> Some newer languages that try to fill the niche are D, Nim, Rust and Go. Can't say much about Nim, it seems to be in the background.

Nim is frustrating, because to my taste it gets so many things just right while getting one particular thing so spectacularly wrong that I can't bring myself even to try it.

The one thing is its rule for when two identifiers are the same. They are compared case-insensitively, ignoring any underscores and en-dashes in either name, except that the first character must match exactly.

Consequence #1: if you have, say, something called user_sort (perhaps it's a function that sorts users) and something called use_RSort (perhaps it selects which of two sorting algorithms to use somewhere) then they will be the same identifier, with results anywhere from compilation failure to silent malfunction you don't notice until a year later.

Consequence #2: if you want to search for an identifier using some obscure tool like, say, grep or Vim or Eclipse, you're out of luck. (You can make your own tool -- call it "nimgrep", perhaps -- and extensible things like Vim and Eclipse can be given the ability to search for Nim identifiers. But their built-in facilities, like what "*" does in Vim, will do the wrong thing if you are working on Nim code.)




> Nim is frustrating

I have used Nim heavily for more than a year now, and it turned out to be the most productive language I have every used. Nim could be considered a modern Lisp with infix notation and Python like syntax with native C performance. The macro system is incredibly well designed and easy to handle.

I also tried Rust, and it turned out to be much more complicated and time consuming. I would use it for systems programming only. Redox is the only reason for me to learn Rust.

> The one thing is its rule for when two identifiers are the same.

First it looked strange to me as well. However there are actually good reasons to avoid case sensitivity.

http://blog.codinghorror.com/the-case-for-case-insensitivity...

As for the user_sort and use_rsort example, such semantic errors can easily be fixed by qualification (a.user_sort and b.use_rsort). Errors like the following one however are very hard to fix in case sensitive languages like C++ and probably even Rust:

  module A:  func smart_func (x,y) = do_this
  module B:  func smart_Func (x,y) = do_that
  module C:  func Smart_Func (x,y) = do_something_else
main:

  import A, B, C
  smart_func (a,b)  
hmm ... smart_func(a,b) doesn't work. Seems to be a typo. Which function did the author really mean?

Nim would reject such a mess in general.

The developers of Nim have implemented a lot of nice features. A really silly idea however are strong spaces. No serious developer would ever use such a dangerous "feature". It should be removed from Nim.

https://github.com/nim-lang/Nim/wiki/Whitespace-FAQ


  > Errors like the following one however are very hard to 
  > fix in case sensitive languages like C++ and probably 
  > even Rust
No, in Rust the compiler will emit a style warning if you have a function whose name includes capital letters. This can be toggled off (and also elevated into a hard error), but it's always on by default.

Furthermore, when you import a module Rust keeps it namespaced under the module's name, so you never need to worry about names accidentally colliding or being unsure as to where a symbol comes from. You have to use an explicit glob import to pull in all of a module's public items into the current namespace.

Furtherfurthermore, Rust warns when you import a symbol and then don't use it, so even if you name all of these functions differently and ignore the style warnings and glob-import the modules, then you'll get yet another warning when you fail to ever use two of the symbols.

Furtherfurtherfurthermore, Rust doesn't allow symbols with the same name to exist in the same namespace, so even if you went back and fixed all those functions to comply with the style warnings, you'd get compilation errors if you continued to glob-import any of the two of them.


> there are actually good reasons to avoid case sensitivity

My problem with Nim's identifier syntax rules are not about case-sensitivity. I have happily used case-sensitive languages and case-insensitive ones. My problem is with ignoring punctuation in identifiers.

> such semantic errors can easily be fixed by qualification

Once you notice that there's a problem. The trouble is, you might not.

> [three things with names like smart_func but different case]

Again, case-insensitivity is a red herring here as far as I'm concerned.


Case-insensitivity I get, but deleting underscores? Yikes. I don't like Nim for other reasons, but that's a huge one.


The idea is that develoers prefer different styles of coding. Some like doThisAction, others prefer do_this_action, others Do_This_Action.

Nim supports all styles. A simple reformatter can be used to transform the code of a project into a normalized form. Such an attempt would be very dangerous in C++.


So the idea is that, say, you'd have hooks in your version control system so that Alice always sees lowercase_with_underscores, Bob always sees camelCaseLikeThis, and Charlie always sees camel_Case_With_Underscores; and then each developer sees a version of the code in which everything is consistent, but it's a different consistent version for each? (And the thing in your actual repository is whatever it is -- it could be w_i_t_h___t_o_o___m_a_n_y___u_n_d_e_r_s_c_o_r_e_s for all anyone need care.)

That's certainly better than having different bits of the code use different identifier styles. But it feels somehow a fragile way to do things. And I worry about encouraging bad habits in teams that don't set things up with such care.

And... can you really make a simple reformatter that will consistently do the right thing? Identifiers may make reference to things whose capitalization shouldn't be canonicalized. HTML. TeX. iPhone. DrMemory.

(Also, though this is a bit of a cheap shot: note that the three identifiers in your first paragraph are not equivalent according to Nim's rules.)


I don't see the advantage in supporting all styles. What you describe sounds like a pretty trivial benefit compared to breaking all of your ordinary text manipulation tools and violating the principle of least surprise.


When I was switching from Pascal (Delphi) to C#, I was wondering why would someone make something and Something two different things. But that what Nim does is definitely weird.


Sure, it's a misfeature, IMO, but it's certainly not a reason to write off the language.

No matter what language you use, if you have two variables named myVariable and my_variable in the same scope, you've created a huge land mine in your code, and your linter should complain. Eventually somebody's going to come along and mix the two up.

The fact that nim blows up differently than every other language just makes it more obvious that this is something you just shouldn't do.


Yup, having myVariable and my_variable is asking for trouble in any language, and what bothers me about Nim is not at all that it makes that harder.

What bothers me about Nim is that (1) it makes it easier for you to call the same variable myVariable in some places and my_variable in others because that won't make compilation fail; (2) once that happens it becomes harder to find references to that variable, because the usual searching tools will miss some of them (and you will not necessarily get any indication that you've missed any); and (3) there are -- hopefully rare, I concede -- cases where what in another language would be obviously and innocuously different identifiers collide. nOpenFiles versus no_pen_files. use_rsync versus user_sync.

And what does this buy you? What is the advantage it confers? That you have the flexibility to call the same thing myVariable in some parts of your code and my_variable in others. But that's a terrible idea and making it possible is not a feature.


> if you have two variables named myVariable and my_variable in the same scope

But that's not the situation in the example. user_sort and use_RSort are perfectly fine identifiers that no reasonable person would expect to be interpreted as the same.


Such a conflict can be resolved easily by qualification (a.user_sort and b.use_RSort). What's the problem?


This criticism usually comes from people that do not use Nim. I was very surprised as well at first - now after 1 year of using Nim I realize I never run into any trouble because of case/underscore insensitivity.

#1: those variables have to be in the same scope or be procs working on the same types to be an issue.

#2: I don't use nimgrep, I just keep a consistent style across my files. When reading somebody else's code, case-insensitive search is usually enough.


I suspect this criticism usually comes from people who don't use Nim because anyone inclined to be bothered by it will not use Nim for that reason.

I agree that "just keep a consistent style" is a good approach for single-person projects. It's harder to keep it working well as you get more people working on the code, though.


Actually Nim's attitude is more suitable for group work because every group can have its own style of coding. A simple transformer could be used to normalize the code. However it would force the developers to qualify all imported conflicting names which is a good idea anyway.

You cannot do this in C++ and Rust. There you actually have to keep a consistent style.


Is there any documentation or discussion on the justification for doing this? I'm scratching my head and asking why anyone would do this intentionally...



Way too ascii-centric. Getting case transformations right in the presence of unicode can be complicated.


Unicode in identifiers is ugly. I never use that.


Helps make code look more like the algorithm it's implementing - would rather just use α than keep spelling out "alpha" every time. Good editors and REPLs make it easy to enter unicode symbols by tab-completing the latex spelling, e.g. \alpha<tab> gets replaced by α.


I don't use nim, so I couldn't point you to the justification. But as I understand it is so an individual can choose his style preferences. myVariable or my_variable.



Thanks a lot! I had never heard of Nim before, and I'll never ever try to know more. Such a gigantic error is a triple NO.


Thirty years of C obviously has fixed the mindset of many developers so much that they don't even want to think in different ways :-(


Please don't leap so quickly to psychoanalysing the presumed intellectual failings of people who disagree with you.

(I do not think your analysis is anywhere near correct in my case, even though I think Nim's identifier comparison rules are very unwise.)



But this isn't about case-insensitivity.


There was a C++ developer at job mocking me for using Perl until he realized how much easier data can be parsed with it (and used my Perl code for himself). There are people who despise Lisp just for its parentheses without understanding their purpose which makes Lisp so elegant and powerful. People mock Nim for some things mentioned here without paying attention to the gain of productivity. I am always amazed how banal things can hinder smart people to advance.


Really, the view of a number of bloggers who have used Nim consider it the best among the new crop of languages around for whatever reason, variable naming not withstanding.

Your comment is the only one I have seen making such a big issue about the variable naming.



> Your comment is the only one I have seen making such a big issue about the variable naming.

It reminds of people who dislike Lisp only for its "ugly parentheses".


I tried to get into nim, but then I started reading the source for some of their stdlib and finding bugs.

I pointed it out on the boards and the response wasn't all that great, so I decided to spend my time elsewhere.

I started picking up Rust a few weeks ago, so far I'm having fun :)


I'm really sorry to hear that :(

Any chance you could give me a link to the thread/issue you posted? I really want to see where we went wrong.


I logged back into the forums to try and find it, but I didn't see a way to pull up old posts.

IIRC, the issue I posted about had to do with some of the underlying parsers. I was looking at the CSV stuff and I believe one of the types it relies on had a skipBOM function, or one of the functions would skip the BOM, or something along those lines.

But what it did was blindly increment the file pointer without checking it was looking at a BOM, or that it was at the start of the file.

To me the interface is a fairly big deal because you can't safely use the type without knowing that implementation behavior. People do stupid crap, and calling skipBOM at the wrong time will happen, even though it's obviously not intended. What I recall is recommending that it either fail noisily or turn into a noop. I'm on the side of failing noisily to help users of the class find their bugs quicker, but I can understand why someone would want it to be a noop since technically doing nothing if it's not a BOM is the right thing to do.

The response I got was the type wasn't meant to be part of the public interface for the stdlib and so wasn't an issue, and then I was pretty much ignored after that statement. I even offered to do the work myself, but pretty much got ignored.

It wasn't so much that the reaction was negative, as much as it wasn't conducive to improving the stdlib all that much. And from my perspective, one of the biggest problem nim had (at the time) is that the stdlib felt very unpolished. As if someone had written it for very specific use cases and then haven't revisited it. I guess what I'm saying is that it didn't feel like an stdlib in many places, it felt like someone who wrote some production code for very specific use cases. Which is perfectly acceptable for production code with a specific use case, but not for an stdlib (in my opinion).

The entire thing left a bad taste in my mouth and I lost a lot of trust in the quality of the stdlib and so decided to stop learning/using nim.

It's all a little fuzzy in my mind, so I may not have all the details correct but the loss of trust was definitely the result.

And who knows, perhaps I was misreading the code, I wasn't all that experienced with nim at the time. But even having someone point out it was my mistake would have felt better than simply being ignored.

It's too bad really, because I did like the language itself, which is why I had offered to try and help improve the stdlib. Nowadays I'm picking up rust for fun(putting together an NES emulator in it). I'm a little bit of a language whore :)


It seems that the thread you are referring to is this one: http://forum.nim-lang.org/t/1569 (the forum profile view really needs a listing of the person's threads/posts).

From looking at the thread, it seems that this is a simple case of your thread becoming lost in the noise of the forum. Please don't feel that you were ignored on purpose. I think that Araq simply forgot to reply to you, it's easy for threads to get lost like this.

It really sucks, but the fact is that Araq doesn't have enough time to answer everyone and in this case he is the only one who could have assisted you.

In all honesty I think this is quite common in forums. I'm not sure how we can improve it, short of getting full-time Nim devs who ensure that everyone on the forum gets a response. What do you think?


This feels like damage control to me. While your explanation is always possible, that board moved much slower than HN's front page so the idea that the post somehow got lost in the mix when he was actively involved in several other posts sitting on the front page is stretching things a bit (in my opinion).

But that isn't even the important point. The deficiencies I outlined haven't been been revisited have they?

If not, it would seem my distrust wasn't so misplaced, and that was the bigger point.

Who knows, maybe the rest of the stdlib has had more thought put into it, but that was the first bit of the stdlib I had dove into the source for and what I saw wasn't good. I didn't want to do that for the rest of the stdlib either.

If Araq has become the bottleneck, then maybe something needs to change in your process, because as you can clearly see I offered to be the one to make the changes.

And to be clear, I'm not angry about it, I just chose to spend my time elsewhere. Intentional or not, the language dev's as a whole could be doing a better job getting other people involved.


Would really appreciate some kind of link to the discussion you mentioned..


I responded to dom96.




Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact

Search: