6 ms·
Know what I like about Stroustrup's code? "using namespace std;". The typical convention of sticking std:: in front of std::every std::last std::bloody std::t
by chuckadams 3y ago
Know what I like about Stroustrup's code? "using namespace std;". The typical convention of sticking std:: in front of std::every std::last std::bloody std::thing drives me std::insane.
- pif 3y agoYou learned to program on Windows, didn't you?
- marcosdumay 3y agolpsiNo, spbI uiOnly lpwAdopted iThe spdwStyle usLater.
- chuckadams 3y agoI learned on C on Unix. The naming conventions in Windows are the same kind of syntactic noise I dislike: long identifiers that are just long without actually being descriptive, with extra crap ladled on top in the form of Hungarian notation (which had its uses in the Excel codebase, but doesn't belong anywhere near C++) BeOS probably had the nicest looking API. Let's hear it for is_computer_on_fire()
- HarHarVeryFunny 3y agoIt depends ... You should NEVER have "using namespace" (for any namespace) in a header file, since that is how you create name clashes, which is what the namespaces are there to avoid. I don't personally like "using namespace std;" even in implementations, since I think it makes code less readable, and the contents of std:: is so large, and growing, that I'd again prefer to just avoid the possibility of name clashes. We write code once, but read it many times, so shorter names (incl. namespaces) seems like a poor efficiency choice.
- culi 3y agoConversely, We write code once, but read it many times, so longer names seems like a poor efficiency choice.
- HarHarVeryFunny 3y agoWhat's the logic of that though? Longer more descriptive names (self-documenting code) help readability, not hinder it. Certainly time to enter code (which is increasingly going to be automated) should be the last consideration - if we're considering full software lifecycle then coding probably takes up some small single-digit percentage of the time we're interacting with the code.
- culi 3y agoShorter files allow us to have shorter names. You can read the namespace once at the top instead of 50 times. And it's not about time to enter code. It's about time to read code
- nuancebydefault 3y agoLonger names are harder to read. Think about any math formula. Does energy=mass * math::powerf(speed_of_light, 2) read more fluently? Context matters. Make sure the context is ways clear and code is written there where it belongs. Then names can be shorter while being readable.
- HarHarVeryFunny 3y agoI'm not sure that's a great example. Of course e = mc^2 is so iconic and well known that most people know it, and will probably even perceive it as a whole. Once you recognize it then no need to explain what e, m and c are. However, most code is not that obvious, and in the real world you're probably not looking at one mystery line of code who's function becomes obvious by context - you are more likely looking at entire functions or blocks of code, maybe without comments, trying to figure out what is going on. Try inheriting 10K of mostly undocumented code, and then you'd probably be a lot more grateful that the original author used descriptive names and comments, even though he knew what it all meant when he wrote it.
- chipdart 3y ago> We write code once, but read it many times, so longer names seems like a poor efficiency choice. How can you tell what's the type of an ambiguous name if you have no indication of which namespaces are within scope? I mean, think about it. If your concern is readability, doesn't this mean it's important to know what code you're looking at?
- Kranar 3y ago>We write code once, but read it many times, so shorter names (incl. namespaces) seems like a poor efficiency choice. I think it's fascinating how different people can interpret this so differently. I feel like it's precisely because we read code so much more than we write it that we should prefer using names that get to the point, instead of having so much noise and repetitive boilerplate. Reading a soup of std::this, std::that, std::foo, std::bar is so difficult to parse through. Especially if you're like me and you sound things out in your head, which I recently learned is not how everyone reads. The only justification for writing all those std::'s is because compilers can't disambiguate names from their context, but you're not going to find a human who comes across a use of vector<Foo>, or sort(...) and throw their hands up in confusion wondering what was meant. >We write code once, but read it many times, so shorter names (incl. namespaces) seems like a poor efficiency choice. This to me seems like a cargo cult justification, where you've heard the argument that descriptive names are helpful for readability, so we should name our variables in a way that conveys their intention as opposed to 1 letter names or obfuscated abbreviations, but instead of genuinely understanding the principle behind the rule, you think the rule is simply that it's better to have long names over short names. Descriptive names that can be used to disambiguate variables from one another on the basis of their purpose... yes, please do that. Writing long names just so that they are long, especially by giving everything a shared prefix like std::... no, that's a misunderstanding of the justification behind the rule. It's similar to that saying along the lines of when a principle becomes a metric, it ceases to be a useful principle.
- HarHarVeryFunny 3y ago> This to me seems like a cargo cult justification, where you've heard the argument ... Well, no, I've been a professional programmer since 1982, and a hobbyist one both before then and to this day. I might be wrong, but these are the lessons I've learnt over the decades working on a variety of projects of different size and durations ... Of course consise code is nice, and while you're in the heat of development it's easy to pretty much memorize an entire codebase, even a large one, but it's when you have to come back to it years later, and barely even recognize the code as your own, that you'll be happy it's self-documenting. Now, on a large team that "future self" may just be the new hire, or the guy who replaces you when you quit ...
- ryandrake 3y agoNot only that, but you have no idea what's going to be put into the standard tomorrow. If code I write today has a class called bubble_sorter, and then one day, the C++ standard library decides to add std::bubble_sorter, then: 1. If I had "using namespace std;" then all of my code is suddenly broken. 2. If I didn't have it, I'm fine. Also, and this is just personal preference, but I simply like to be able to clearly distinguish when my code is calling into the standard library. Typing in that short "std::" reminds me that I am calling into someone else's code.
- wakawaka28 3y ago>If I had "using namespace std;" then all of my code is suddenly broken. If this happened and if you included that specific header, you would get a simple compiler error due to ambiguous methods. Then you can simply add a namespace somewhere and move on. I know sometimes this can involve a lot of changes (if we're talking about other `using namespace ...` usage) but in general you're not gonna have problems. If you're really worried about this, you can move the statement closer to where you need it. This is very helpful for dense code that you normally want to be verbose.
- chipdart 3y ago> If this happened and if you included that specific header, you would get a simple compiler error due to ambiguous methods. Then you can simply add a namespace somewhere and move on. ...or, hear me out, you can not make the mistake of mindlessly adding using namespace directives and therefore ensure neither you nor any consumer of your code will risk.having to handle perfectly avoidabld name clashes. And by the way, name clashes will also happen if you include code from two or more dependencies which introduce ambiguous symbols. This is code outside of your control.
- wakawaka28 3y ago>...or, hear me out, you can not make the mistake of mindlessly adding using namespace directives and therefore ensure neither you nor any consumer of your code will risk.having to handle perfectly avoidabld name clashes. I'm not talking about "mindlessly" adding these namespace statements. I'm saying, use good judgement. As I pointed out, if you use a little common sense you won't have name clashes and even if you did, they usually cause compile errors. Just don't put them in headers ffs... If you really just need a lot of stuff from another namespace in a function, put the using statement in that function. >And by the way, name clashes will also happen if you include code from two or more dependencies which introduce ambiguous symbols. This is code outside of your control. The using statements are not outside your control, unless someone put them in a header. That's the only place I broadly object to them.
- winwang 3y agoYep, although I do like not having clashing names. But I mean... somehow every other language solved this.
- Jtsummers 3y ago> But I mean... somehow every other language solved this. Did they? C, Lisp, Rust, Python, Ada, Go, Java, C#, ... They all require you to qualify conflicting names if some other characteristics (for instance the number or types of arguments) don't provide enough information, or outright don't permit it (C, since it has no notion of name spaces). Can you point to the "every other language[s]" which have solved this problem?
- chuckadams 3y agoIt's certainly not every other language, but Unison has a novel approach to solving the problem of name clashes: function names are just local aliases for a content hash of the function's AST. Compiling involves replacing function names with those hashes, and putting the names back is a matter of pretty-printing. I'm sure there's an arsenal of footguns lurking in Unison's system, but for sure it opens up interesting opportunities (distributed code becomes "grab this function out of cache").
- Jtsummers 3y agoDoes that actually solve name clashes? If I have two functions compiled at the same time: def foo(n): return n + 2 def foo(n): return n * 2 foo(3) # which one is called? (I don't know Unison syntax so using Python for the example) It's still a name clash at compile time.
- chuckadams 3y agoTBH I've only dipped my toe into Unison, but I don't believe it would let you re-bind the same identifier in the same scope in the same compilation unit. It's more that `foo(3)` becomes a call to the hashed version `#e0ca5f(3)` forevermore. Once a function has been compiled, it doesn't care what the names of any functions it uses are afterward, until you explicitly recompile them to use the new names. So it really has more to do with preventing versioning conflicts ... others can explain it much better than me, sorry.
- zengid 3y agoI hear that once c++ modules lands this shouldn't be controversial anymore, right?
- Koshkin 3y agoIt’s not so much the ‘std’ thing, it’s the double colon that is an abomination. I never understood why they couldn’t simply use a single dot like some other languages have done.
- Maxatar 3y agoTo resolve ambiguities due to the fact that in C, type names live in a separate namespace from variable names so that it's possible to have a variable with the same name as a type. C++ inherits this distinction so that it is possible to write the following: struct foo { int x; }; struct bar : foo { ::foo foo; }; bar b; b.foo::x = 1; b.foo.x = 2; The b.foo::x and b.foo.x are two different x's, and the only way to disambiguate them is through the use of the . or the ::