Porting the Go compiler to Go
The Go compiler was originally written in C because 1) Go didn’t exist, 2) Go was unstable, and 3) Go was originally intended for writing network/systems code and not for compilers. But now 1) Go exists, 2) Go is stable as of Go 1.x, and 3) Go has turned out to be a nice general purpose language and the compiler won’t be an outsize influence on the language design." The hope is to have the compiler written in Go for the 1.4 release.
(Log in to post comments)
Porting the Go compiler to Go
Posted Apr 25, 2014 21:40 UTC (Fri) by fishface60 (subscriber, #88700) [Link]
Dependency loops are bloody annoying.
Porting the Go compiler to Go
Posted Apr 25, 2014 21:46 UTC (Fri) by misc (guest, #73730) [Link]
Porting the Go compiler to Go
Posted Apr 25, 2014 23:35 UTC (Fri) by HelloWorld (guest, #56129) [Link]
Porting the Go compiler to Go
Posted Apr 26, 2014 2:43 UTC (Sat) by rsidd (subscriber, #2582) [Link]
Porting the Go compiler to Go
Posted Apr 26, 2014 8:22 UTC (Sat) by torquay (guest, #92428) [Link]
The problem with Go is that it's basically a slightly saner C, with a few cherry-picked bits and pieces from other languages. Yes, it does improve upon C, but not much. C is essentially one abstraction (or syntactic sugar) level higher than assembly language, and Go doesn't really increase the abstraction much -- it's still quite low level. The language still has explicit pointers ffs!
One serious omission is the ability to overload operators. According to the Go FAQ:
- "Regarding operator overloading, it seems more a convenience than an absolute requirement. Again, things are simpler without it."
Overloading
Posted Apr 26, 2014 10:32 UTC (Sat) by tialaramex (subscriber, #21167) [Link]
Why are all these tricks such a bad idea that you might want to forbid anyone from using them (and thus, might just as well not provide them) ? Because they tend to make _reading_ programs even harder. Since reading programs is without doubt one of the trickier problems we have anything that makes it worse is undesirable.
It's pretty much certain at this point that you'll want to contradict me. Don't bother. Here's what you need to have _any_ standing in this matter. You obviously love operator overloading, so find a program you wrote ten years ago which makes significant use of operator overloading and get the present maintenance programmer for that code to follow up in this discussion explaining how they got along with your approach.
Overloading
Posted Apr 26, 2014 10:54 UTC (Sat) by rsidd (subscriber, #2582) [Link]
Not C++ but python, and libraries (numpy, sympy) that others wrote and I use (and, rarely, read and try to understand). It makes complete sense to allow arithmetic operations (+, *) to matrices and symbolic types, and python lets you define methods in the class definitions that let you do that. Of course it make no sense to define "+" to mean something totally different, like exponentiation. The language provides tools, but can't force common sense on the programmer. Properly done, operator overloading makes such code (ie code using user-defined or library-defined mathematical objects) more readable, not less.The other extreme is OCaml which has different operators for integer and floating-point arithmetic. Now that makes code harder to read, or write.
Overloading
Posted Apr 26, 2014 13:57 UTC (Sat) by aggelos (guest, #41752) [Link]
The other extreme is OCaml which has different operators for integer and floating-point arithmetic. Now that makes code harder to read, or write.Actually, I've found that to be quite helpful when writing code and I don't think +. (floating point addition operator in OCaml) is any harder to read than + (integer addition). Same for lack of automatic integer type promotions (wish I could opt out of that in some C code). I don't doubt there's programs where the extra type conversion calls would get in the way, but for most of the programs I write these days, it's nice when the type system discourages sloppy thinking about arithmetic. YMMV :-)
Overloading
Posted Apr 26, 2014 14:34 UTC (Sat) by rsidd (subscriber, #2582) [Link]
Overloading
Posted May 19, 2014 7:38 UTC (Mon) by marcH (subscriber, #57642) [Link]
"1.0 +. 2.0" is very hard to read, really?
The problem with operator overloading (and many other C++ features, or Perl,...) is giving kids matches. You CANNOT rely on programmers not to abuse them, it just does NOT work in real life. Sure, you can always find some teams of geniuses so good they don't live in real life (lucky you if you are part of one) but you also need programming languages for the masses.
Ocaml's "+." is the perfect balance. It's just as readable as a plain "+" without falling into the operator overloading trap.
Overloading
Posted May 19, 2014 14:11 UTC (Mon) by mathstuf (subscriber, #69389) [Link]
Overloading
Posted May 19, 2014 17:06 UTC (Mon) by marcH (subscriber, #57642) [Link]
Also, this discussion should probably make a clearer difference between built-in versus user defined operators.
Overloading
Posted Apr 26, 2014 13:00 UTC (Sat) by HelloWorld (guest, #56129) [Link]
Cited by whom?
> Because they tend to make _reading_ programs even harder.
Bollocks. There is no reason that an expression like a+b*c should be written a.add(b).multiply(c) just because the variables happen to be, say, arbitrary precision integers. If anything, it's crazy to use the symbols + and * for modulo-some-power-of-two arithmetic rather than proper arithmetic.
Overloading
Posted Apr 26, 2014 14:23 UTC (Sat) by ehiggs (subscriber, #90713) [Link]
There sure isn't! Maybe you meant a.add(b.multiply(c)).
Overloading
Posted Apr 26, 2014 14:38 UTC (Sat) by HelloWorld (guest, #56129) [Link]
Overloading
Posted Apr 26, 2014 14:53 UTC (Sat) by ehiggs (subscriber, #90713) [Link]
It seems like a handy language for shovelling bits here and there. It's just not a handy language for writing programs where you need to deal with mathematics. So don't use it for that.
Overloading
Posted Apr 26, 2014 17:00 UTC (Sat) by HelloWorld (guest, #56129) [Link]
http://docs.oracle.com/javafx/2/api/javafx/beans/binding/...
But the lack of operator overloading is far from the only problem in Go. Very simple abstractions like map and filter cannot be expressed in a generic and type-safe way, and I consider that a basic requirement of a modern language. I don't know what you mean by “shovelling bits”, therefore I don't see how Go makes that any easier than the bazillion languages we already have.
Overloading
Posted Apr 26, 2014 22:53 UTC (Sat) by mathstuf (subscriber, #69389) [Link]
[1]http://hackage.haskell.org/package/elerea
[2]http://hackage.haskell.org/package/elerea-examples-2.2.3/...
Overloading
Posted Apr 26, 2014 20:29 UTC (Sat) by jb.1234abcd (guest, #95827) [Link]
> Cited by whom?
This is my favorite "C++ comes from hell" site:
http://yosefk.com/c++fqa/operator.html
Btw, after "operator overloading", do not miss the opportunity to learn more
by starting from the very beginning on that site :-)
Overloading
Posted Apr 29, 2014 11:51 UTC (Tue) by simlo (guest, #10866) [Link]
I actually find STL's string + operator a bad extension of +: It works as a concatenation rather than an addition. Usually an + operation is commutable, concatenation isn't. In math * is not always commutable so it is ok to use it for matrix multiplication for instance.
In short: The operator should express only what the reader of the code expects for that symbol. The usual rules of calculus should be respected. And except for the assignment and call operators, there shall be no side effects.
Overloading
Posted Apr 29, 2014 17:08 UTC (Tue) by HelloWorld (guest, #56129) [Link]
This has nothing to do with operator overloading but with poor naming of functions, and that can be done no matter what restrictions you impose.
Overloading
Posted Apr 30, 2014 6:00 UTC (Wed) by bronson (subscriber, #4806) [Link]
If one person gets it wrong then, sure, it's a user problem. But look at how many C++ coders have screwed it up. No, you can't blame this one on a just a few poor programmers.
Overloading
Posted Apr 30, 2014 9:55 UTC (Wed) by HelloWorld (guest, #56129) [Link]
I have no idea how many screwed this up, but I have no reason to believe it's a significant problem. And besides, I have yet to see any true problem caused by the use of << for iostreams.
Overloading
Posted Apr 30, 2014 13:37 UTC (Wed) by etienne (guest, #25256) [Link]
People around me say that if you use << to put objects in an iostream, it is logical to use >> to get from an iostream. And why limit that to iostream, why not streams, queues, vectors, bags, dictionaries?
The operator priority of "<<" is not the right one if you want to use it to put to an iostream.
Overloading
Posted Apr 30, 2014 16:41 UTC (Wed) by cry_regarder (subscriber, #50545) [Link]
Overloading
Posted May 1, 2014 13:18 UTC (Thu) by Funcan (subscriber, #44209) [Link]
Much like PHP - it is so internally inconsistent and unintuitive that actually writing correct code in it requires you to keep a heroic number of things in your mind at the same time.
Overloading
Posted May 1, 2014 15:45 UTC (Thu) by jwakely (subscriber, #60262) [Link]
(We're still talking about the operator precedence of << as it relates to ostreams, right?)
Do you have an example of getting it wrong? Easily?
More importantly, do you have an example of getting it wrong that isn't caught immediately by the compiler? i.e. actually compiles, runs, but does the wrong thing.
I'll admit these days I don't have much idea of how beginners approach C++, but I seriously can't understand how someone could find writing to ostreams takes heroic effort.
Overloading
Posted May 1, 2014 23:14 UTC (Thu) by dtlin (subscriber, #36537) [Link]
I don't usually complain about iostreams, but this one's easy.cout << flags & 0xff; // (cout << flags) & 0xff cout << b ? yes : no; // (cout << b) ? yes : no
Overloading
Posted May 2, 2014 9:57 UTC (Fri) by jwakely (subscriber, #60262) [Link]
int j = i * b ? 10 : 100;
Does this mean operator* is "non-intuitive and easy to get wrong" for multiplication of integers, and "so internally inconsistent and unintuitive that actually writing correct code in it requires you to keep a heroic number of things in your mind at the same time"?
Or does it just mean you should probably use parentheses for expressions that use more than just the familiar mathematical operators we learnt at school?
Overloading
Posted May 1, 2014 16:20 UTC (Thu) by HelloWorld (guest, #56129) [Link]
Because inserting something into a collection is something *entirely different* from doing I/O. And besides, non-symbolic names like push_back are used in the STL.
Overloading
Posted Apr 30, 2014 16:40 UTC (Wed) by cry_regarder (subscriber, #50545) [Link]
The chaos that is java auto boxing and un-boxing just to get around the issues with not having operator overloads is ridiculous.
Overloading
Posted Apr 30, 2014 20:27 UTC (Wed) by mathstuf (subscriber, #69389) [Link]
I think bronson is referring to operator overloading in general, not the stream overload of the bitshift operators in particular.
Overloading
Posted Apr 29, 2014 20:53 UTC (Tue) by mathstuf (subscriber, #69389) [Link]
Overloading
Posted Apr 29, 2014 21:18 UTC (Tue) by khim (subscriber, #9252) [Link]
Matrix multiplication is most definitely not commutation. Vector multiplication can be commutative or anticommutative (and these are two different operations which immediately put C++ in the more-or-less the same bucket as Go because you can not create new operators there).
The whole story looks like such a tempest in a teapot to me that it's not even funny. What's the #1 general purpose language used by mathematicians and scientists? Right: Fortran. Does it support operator overloading? Yup. So what are we discussing here? IMNSHO it's pointless to discuss taste of oysters with the ones who are regularly consuming them.
Overloading
Posted Apr 29, 2014 22:18 UTC (Tue) by mathstuf (subscriber, #69389) [Link]
> What's the #1 general purpose language used by mathematicians and scientists? Right: Fortran. Does it support operator overloading? Yup. So what are we discussing here? IMNSHO it's pointless to discuss taste of oysters with the ones who are regularly consuming them.
And they're the only group that cares about matrix multiplication? See game developers, visualization and rendering programmers, etc.. Anyways, I think operator overloading is working from flawed principles (that operators work on concrete types rather than type classes), but since Go lacks generics, that's not even a remote possibility[1].
[1]There's interface{}, but that's only slightly better than C's void* in that you can still type match on it safely.
Overloading
Posted Apr 30, 2014 6:15 UTC (Wed) by torquay (guest, #92428) [Link]
-
What's the #1 general purpose language used by mathematicians and scientists? Right: Fortran.
Not these days. It used to be in 1970s and 80s. In the 1990s its popularity among scientists and engineers dropped quite considerably, ceding ground to Matlab, C and C++. These days Fortran is largely considered as a "legacy language", akin to Cobol. Yes, the often used LAPACK and BLAS are still written in Fortran, but that's simply due to momentum. Matlab is in effect a user-friendly wrapper for LAPACK. Similarly, C++ has many good libraries providing wrappers for LAPACK.
The grounds are shifting yet again, with many scientists, quants, etc moving to the R language and Python (using numpy etc). The point is that due to Go's inherent limitations (lack of operator overloading being one of them), it will never be seriously considered as a suitable language by mathematicians, engineers and scientists. While Go was designed by a bunch of well intentioned people, in the end they have proven to be myopic and only concerned with specific use cases.
Overloading
Posted Apr 26, 2014 13:50 UTC (Sat) by mpr22 (subscriber, #60784) [Link]
Without operator overloading you cannot implement new first-class arithmetic objects. Without the ability to implement new first-class arithmetic objects, code that relies on objects which mathematicians are quite happy to use in expressions of the form "c = a + b" (matrices and bignums are merely the obvious case) ends up being written in a profoundly unnatural and hard-to-read style.
Overloading
Posted Apr 26, 2014 14:13 UTC (Sat) by mathstuf (subscriber, #69389) [Link]
Also mat * mat. Is that element-wise or matrix multiplication? What happens if the matrices are the wrong shape? Does it return Maybe Matrix? How is that more helpful? Similar with vec * vec.
Overloading
Posted Apr 26, 2014 16:19 UTC (Sat) by rsidd (subscriber, #2582) [Link]
"Element-wise" matrix multiplication is basically never required (except for vector dot products, which are better defined as a separate operation and not as multiplication), so it has to be matrix multiplication. If they are the wrong shape, it's an error (or exception, depending).
Overloading
Posted Apr 26, 2014 16:23 UTC (Sat) by mathstuf (subscriber, #69389) [Link]
That's what the ST monad is for. You make a state structure which you setup at the start and it flows through your calculations and is dropped at the end, preserving purity. Or do you mean allowing reuse of variable names?
Overloading
Posted Apr 26, 2014 16:35 UTC (Sat) by rsidd (subscriber, #2582) [Link]
The question I'd like answered is, for someone whose work (bioinformatics/computational biology) involves numerics, data structures and algorithmics in equal measure, is Haskell worth the effort to learn? Because it is indeed a significant mental effort. Typical implementations of, eg, Needleman-Wunsch in Haskell that one finds on the net are very non-intuitive. The field is dominated these days by Python, R, and C/C++ (and to some extent Java). I'd like a not-C language that is faster than Python and more concise and expressive than C, but am still looking. Cython is not bad, but feels like a bit of a kludge (ie when one specifies enough information to get maximum performance out of it, one may as well write straight C).
To get back on-topic -- yes, there is biogo (and also biohaskell) and maybe I should check those out. There is always the tradeoff between the effort of learning a new language and the possible benefits it may bring...
Overloading
Posted Apr 26, 2014 23:50 UTC (Sat) by mathstuf (subscriber, #69389) [Link]
Also, if you're implementing some algorithm, put it in a comment in LaTeX near the implementation. This would allow folks who don't understand why the algorithm is doing what it's doing at least verify it against something and check for typos.
[1]Writing in a looser SSA style with strict const correctness (and const& in C++ to avoid copy constructors) would help with that though.
[2]http://hackage.haskell.org/package/accelerate
Overloading
Posted Apr 27, 2014 0:19 UTC (Sun) by apoelstra (subscriber, #75205) [Link]
She herself knows a bit of Haskell, as a side effect of being an xmonad user for several months, but hasn't used it for work.
I know Haskell and consider it worth learning because it forces you to think functionally — but Rust has a similar effect and has a much larger community around it, and it also forces you to think about pointer lifetimes rigorously, so it's a twofer in that sense.
Overloading
Posted Apr 27, 2014 21:32 UTC (Sun) by tjc (guest, #137) [Link]
Overloading
Posted Apr 26, 2014 20:50 UTC (Sat) by donbarry (guest, #10485) [Link]
The APL/J paradigm is that simple operators on array objects operate dyadically on corresponding elements, requiring a shape match. The sole exception is replication of a scalar to fit any array. Matrix multiplication is expressed as one case of the more general inner product, in which the ordinary matrix multiply becomes +.× -- that is, the additive reduction of the product of the row/column combinations. Used with or and and, you can iterate a state machine with a truth table.
Compare this with the ugliness and unobviousness of Python/Numpy, and one is inclined to nausea.
Overloading
Posted May 3, 2014 10:18 UTC (Sat) by paulj (subscriber, #341) [Link]
Also, having had to deal with operator overloading in code that had a mix of code operating on matrix and vector with overloaded operators, as well as regular floating point expressions, it can get quite tedious to work out what the next line of "A = B + c" is doing. It would be better to have separate operators for element-by-element and matrix. I like how Octave (and MatLab?) uses .<operator> to indicate element-by-element personally.
Speaking of Octave, I think perhaps any next generation language really ought to have matrices as the fundamental data-containing type of all variables, as it is in Octave. Vectors of and single-element data-points are trivially handled as sub-cases of matrices. This means + and * can be intrinsically defined as matrix operations (e.g. element-by-element).
Some might think that's over-kill, that not everyone needs matrices in their code. However, so many things can be expressed as operations over matrices (e.g. even routing in networks). Further, once intrinsic to the language, it allows the programmer to directly express these things as such matrix operations, making it very obvious to the compiler where things can be "parallelised".
The alternative, of not having them intrinsic, leads to bolt-on kludges, e.g. using operator-overloading, or to much more verbose and tedious to programme API level matrix libraries. It often leads to the *runtime* having to figure out where the opportunities for parallelism are - where it may be much harder to figure out.
Overloading
Posted May 3, 2014 10:20 UTC (Sat) by paulj (subscriber, #341) [Link]
Overloading
Posted Apr 26, 2014 17:38 UTC (Sat) by apoelstra (subscriber, #75205) [Link]
Overloading
Posted Apr 26, 2014 17:54 UTC (Sat) by rsidd (subscriber, #2582) [Link]
I never learned C++ and I never learned Perl, basically because I couldn't read either -- both looked like line noise to me. My main exposure to C++ concepts, sad to say, is via this old fake Stroustrup interview, which has gems like this:Take operator overloading. At the end of the project, almost every module has it, usually, because guys feel they really should do it, as it was in their training course. The same operator then means something totally different in every module. Try pulling that lot together, when you have a hundred or so modules.(and much else, which is probably vvery familiar to LWN readers)
Overloading
Posted Apr 28, 2014 18:21 UTC (Mon) by drag (guest, #31333) [Link]
You should. It's fun.
Overloading
Posted Apr 28, 2014 18:33 UTC (Mon) by HelloWorld (guest, #56129) [Link]
You should. It's fun.If you're into BDSM I guess. This prints 11:
sub a { my $x = shift; sub b { $x; } \&b; } print a(1)->(); print a(2)->();This prints 12:
sub a { my $x = shift; sub { $x; } } print a(1)->(); print a(2)->();And this leaks memory every time it's called:
sub s { my $x; $x = \$x; }Thanks, but no thanks.
Overloading
Posted Apr 28, 2014 18:44 UTC (Mon) by rsidd (subscriber, #2582) [Link]
As I remember, one stumbling block was this: the logical way to do what I wanted was via a list of lists, which in python would look like [[1,2],[3,4],[5,6]]. But perl flattens lists for you, and the syntax to get it to not flatten it was not widely known to people I talked to.
Overloading
Posted Apr 28, 2014 19:33 UTC (Mon) by madscientist (subscriber, #16861) [Link]
Feh. "The people you talked to" must have not known the first thing about Perl. Perl has its flaws (as does Python, Ruby, and just about everything else), but this is not one of them:$ perl -e 'my @foo = ([0, 1], [3, 4]); print "$foo[0][1] $foo[1][0]\n";' 1 3
Overloading
Posted Apr 28, 2014 19:36 UTC (Mon) by dtlin (subscriber, #36537) [Link]
Lists (the non-reference kind) do get flattened in list context, but the exact same syntax - [[1,2],[3,4],[5,6]] - gives you a reference to an array of array references in Perl. Nobody you talked to had read perldoc perllol?
Overloading
Posted Apr 28, 2014 21:54 UTC (Mon) by drag (guest, #31333) [Link]
Since perl has so much freedom each developer ends up their own idiosyncratic style. Since each style is so divergent it becomes very difficult to decypher what is going on. When you combine that with the fact that perl has so many little hidden variables and weird things that it does then it becomes difficult to understand what other people's code is doing.
I much rather prefer a language were there is just a small number of ways to do any single thing and one that enforces some sort of formatting rules and other things that helps make it more readable.
I am thinking that a lot of the overloading type things being discussed above for syntactic sugar type things may actually belong in the editor and not in the language. Like you can have all these language short cuts and 'jive terms' you prefer to use and have it expanded by the editor in the actual code you are working on so that it's easily read by other people that don't know your 'jive'. The editor can take care of translating back and forth for you, and if it can't figure it out then it's probably not worth doing.
Overloading
Posted Apr 28, 2014 21:32 UTC (Mon) by drag (guest, #31333) [Link]
If it hurts when you do that, don't do that.
Overloading
Posted Apr 28, 2014 22:33 UTC (Mon) by HelloWorld (guest, #56129) [Link]
Overloading
Posted Apr 28, 2014 23:22 UTC (Mon) by alankila (guest, #47141) [Link]
$ perl -we 'sub x { my $x = shift; sub y { $x } }'
Variable "$x" will not stay shared at -e line 1.
Perl's major fault is that too few of its warnings are fatal errors. I know, I know, you can opt-in to have warnings go fatal. My point is that the defaults are wrong.
Overloading
Posted Apr 28, 2014 23:45 UTC (Mon) by rgmoore (✭ supporter ✭, #75) [Link]
It's not that unreasonable. Perl makes a fairly big deal about anonymous values, and only anonymous functions can be turned into closures. If you like writing with closures, you'll learn the rules for them pretty quickly. This is the blessing and the curse of big languages like Perl. There's lots of cool features there to learn and use, but it means that different people program in different dialects that aren't as mutually comprehensible as you'd like. My take on this is that Larry Wall said he wanted Perl to be more like a human language than like a computer language, but that his idea of what human language is like is heavily influenced by being a native English speaker.
And I believe the properly snarky response to "If it hurts when you do that, don't do that." is "That's why I avoid Perl."
Overloading
Posted Apr 29, 2014 0:03 UTC (Tue) by HelloWorld (guest, #56129) [Link]
It is, it's completely nonsensical. I don't care about the excuses Larry might come up with.
Overloading
Posted Apr 29, 2014 6:21 UTC (Tue) by niner (subscriber, #26151) [Link]
Overloading
Posted May 2, 2014 12:29 UTC (Fri) by renox (guest, #23785) [Link]
I disagree with this: the more I develop in Perl, the less I like it..
Latest trap which caught me:
'do { ... } while(..)' doesn't work like 'while () { ... }', in the latter next/last work, not in the former???
Not fun!
Overloading
Posted May 2, 2014 17:51 UTC (Fri) by Wol (subscriber, #4433) [Link]
In fact, I think FORTRAN is illogical here. I can't remember much about it, but I used to program in FORTRAN IV and Fortran 77, and one of the switches available in Fortran was "always run loops at least once, like FORTRAN does". I can't remember whether that was the standard, or the Pr1me implementation, but I was well aware of it as something to be looked out for.
Cheers,
Wol
Overloading
Posted May 2, 2014 18:47 UTC (Fri) by dtlin (subscriber, #36537) [Link]
What renox means is the keywords last, next, and redo (analogous to break and continue in C) work inside while (..) { ... } but don't work inside do { ... } while (..). It's a syntactic oddity in Perl because do { ... } is an expression, not a block, and postfix while (..) turns an expression into a (looping) statement.
This is mentioned in perldoc perlsyn #Statement Modifiers, along with workarounds.
Overloading
Posted May 3, 2014 13:29 UTC (Sat) by madscientist (subscriber, #16861) [Link]
Overloading
Posted Apr 26, 2014 18:10 UTC (Sat) by mpr22 (subscriber, #60784) [Link]
Agreed. <{i,o,io}stream> should be set on fire.
Overloading
Posted Apr 27, 2014 6:56 UTC (Sun) by zorro (subscriber, #45643) [Link]
Overloading
Posted Apr 27, 2014 8:42 UTC (Sun) by khim (subscriber, #9252) [Link]
It's inefficient (by design!) and does not play well with i18n. Yes, it works fine with arbitrary data types (which is impossible to do with printf on non-GNU platforms and problematic on GNU platform), but it's hard a justification for his abomination to be presented as default way to do an I/O.
Overloading
Posted Apr 27, 2014 9:04 UTC (Sun) by mchapman (subscriber, #66589) [Link]
Can you elaborate more on these points?
From what I know about how C++ streams are implemented, I don't see how these points apply at all.
Overloading
Posted Apr 27, 2014 14:34 UTC (Sun) by khim (subscriber, #9252) [Link]
As for speed. Just compare "Hello, World" programs and note difference insys
time:
$ cat test-c.c
#include <stdio.h>
int main() {
for (int i=0;i<100000000;++i) {
printf("Hello, world\n");
}
}
$ gcc -std=c99 test-c.c -O3 -o test-c
$ time ./test-c > /dev/null
real 0m4.243s
user 0m4.172s
sys 0m0.068s
$ cat test-cpp.cc
#include <iostream>
int main() {
for (int i=0;i<100000000;++i) {
std::cout << "Hello, world" << std::endl;
}
}
$ g++ test-cpp.cc -O3 -o test-cpp
$ time ./test-cpp > /dev/null
real 0m27.249s
user 0m10.146s
sys 0m17.111s
As for i18n. Just take a look on POSIX manpage and explain how could I do something like
printf("%1$d:%2$.*3$d:%4$.*3$d\n", hour, min, precision, sec);
with C++ streams.
Overloading
Posted Apr 27, 2014 14:50 UTC (Sun) by khim (subscriber, #9252) [Link]
Just to clarify (if you don't know anything about i18n you really should, though, it's pretty important in today's connected world): gettext manual includes nice explanation which shows why it's so important to use printf and not streams.
Overloading
Posted Apr 27, 2014 15:23 UTC (Sun) by torquay (guest, #92428) [Link]
This is a bogus comparison, as it's comparing apples to oranges. The following two lines are NOT equivalent:-
printf("Hello, world\n");
std::cout << "Hello, world" << std::endl;
-
std::cout << "Hello, world\n";
Overloading
Posted Apr 27, 2014 21:17 UTC (Sun) by khim (subscriber, #9252) [Link]
It's not about “fair comparison”. It's about bad design. With printf
you can not accidentally write code which does expensive flush because each flush you insert is actually visible in code and, in most cases, it's not needed: stdout
is not buffered if it's connected to terminal and buffered when you write to file and in both cases your program does the right thing. Note: this is not something I've invented on the spot - this property is always there, because it's mandated by standard.
With streams you also can do that, but only if you know that your compiler is GCC, otherwise you must use std::endl
for stdout
and "\n"
for files. Very few know that you are supposed to do that.
If you'll do that then yes, you'll find out that printf
and streams take about the same time. Success? Not so fast:
$ cat test-c.c
#include <stdio.h>
int main(int argc, char *argv[]) {
for (int i=0;i<100000000;++i) {
printf("Hello, world %d\n", argc);
}
}
$ gcc -std=c99 -O3 -o test-c test-c.c
$ time ./test-c > /dev/null
real 0m8.733s
user 0m8.663s
sys 0m0.068s
$ cat test-cpp.cc
#include <iostream>
int main(int argc, char *argv[]) {
for (int i=0;i<100000000;++i) {
std::cout << "Hello, world" << argc << "\n";
}
}
$ g++ -O3 -o test-cpp test-cpp.cc
$ time ./test-cpp > /dev/null
real 0m10.686s
user 0m10.630s
sys 0m0.056s
This time difference is not as spectacular, but it's still there and you will not be saved by optimizing compiler: you are calling three separate functions instead of one and that's that.
Overloading
Posted Apr 27, 2014 22:30 UTC (Sun) by HelloWorld (guest, #56129) [Link]
Are you saying that std::endl is invisible in the C++ code?
> and, in most cases, it's not needed: stdout is not buffered if it's connected to terminal and buffered when you write to file
Bollocks, stdout is line-buffered when connected to a terminal (stderr is unbuffered).
> With streams you also can do that, but only if you know that your compiler is GCC, otherwise you must use std::endl for stdout and "\n" for files. Very few know that you are supposed to do that.
The C++ standard mandates that unless you call std::cout.sync_with_stdio(false), I/O must be synchronized with the stdio library. More specifically, fputc(f, c) must then be equivalent to str.rdbuf()->sputc(c) (see C++11 standard, section 27.5.3.4). It also specifies that the << operators must use calls to the sputc method to do their stuff (see C++11 standard, section 27.7.3.1). It follows that if stdout is line-buffered, so is std::cout.
IOW, what you're saying is bullshit.
Overloading
Posted Apr 27, 2014 22:36 UTC (Sun) by HelloWorld (guest, #56129) [Link]
Overloading
Posted Apr 28, 2014 7:41 UTC (Mon) by jwakely (subscriber, #60262) [Link]
Overloading
Posted Apr 28, 2014 10:01 UTC (Mon) by HelloWorld (guest, #56129) [Link]
Overloading
Posted Apr 27, 2014 19:30 UTC (Sun) by rleigh (guest, #14622) [Link]
Printing a date like this with C++ streams? There are several options, which include
- Use the time_type locale facet for localised formatting using the standard library (example: h, cpp)
- Use Boost.Format with the exact same format string
- Use a date/timestamp class with an overloaded ostream operator which does the formatting for you (and/or use Boost.DateTime which includes support for I/O; example ISO8601 timestamp h, cpp);
Regards, Roger
Overloading
Posted Apr 27, 2014 20:19 UTC (Sun) by HelloWorld (guest, #56129) [Link]
Yeah, let's look at that speed thing:$ cat test-c.c #include <stdio.h> int main() { for (int i=0;i<100000000;++i) { printf("Hello, world\n"); } } $ gcc -std=c99 test.c -O3 $ time ./a.out > /dev/null real 0m4.793s user 0m4.677s sys 0m0.114s $ cat test-without-braindead-flushes.cc #include <iostream> int main() { for (int i=0;i<100000000;++i) { std::cout << "Hello, world\n"; } } $ g++ -O3 test-without-braindead-flushes.cc $ time ./a.out > /dev/null real 0m6.582s user 0m6.518s sys 0m0.061s $ cat test-fast.c #include <malloc.h> #include <stdio.h> #include <string.h> int main() { char *c1 = malloc(100000 * strlen("Hello, world\n") + 1); char *c2 = c1; for (int i = 0; i < 100000; ++i) { strcpy(c2, "Hello, world\n"); c2 += strlen("Hello, world\n"); } for (int i = 0; i < 1000; ++i) fwrite(c1, strlen("Hello, world\n"), 100000, stdout); return 0; } $ gcc -std=c99 test-fast.c -O3 $ time ./a.out > /dev/null real 0m0.010s user 0m0.000s sys 0m0.010sI mean, please.
Overloading
Posted Apr 27, 2014 11:46 UTC (Sun) by zorro (subscriber, #45643) [Link]
I also don't see what is so inefficient about IO streams.
Overloading
Posted Apr 27, 2014 12:16 UTC (Sun) by mchapman (subscriber, #66589) [Link]
I don't agree with that... but wouldn't it just be a library issue, anyway? I'm not entirely sure what the language has to do with it, or why IO streams would even need to be concerned with it.
Overloading
Posted Apr 27, 2014 14:44 UTC (Sun) by khim (subscriber, #9252) [Link]
Strictly speaking both stdio and stream are libraries (even if both are defined in the standards for the appropriate languages), but stdio can used with l10n packages while stream can not be used like this. Thus we have this “nice” library which is
1. Useless for interprogram communications because it's inefficient.
2. Useless for human-to-program communication because it's not 18n-friendly.
So… what's left? Logging and debug-only tracing (one is advised not to use streams with in-prod tracing because if inefficiency). Do you really think such abomination must be included in language specification and presented to every beginner?
Overloading
Posted Apr 27, 2014 16:35 UTC (Sun) by HelloWorld (guest, #56129) [Link]
Overloading
Posted Apr 27, 2014 17:20 UTC (Sun) by zorro (subscriber, #45643) [Link]
Thus we have this “nice” library which is 1. Useless for interprogram communications because it's inefficient.No, it is not inefficient.
2. Useless for human-to-program communication because it's not 18n-friendly.Depends on who the human is. Many C++ programs communicate with developers and/or service engineers only (through log and configuration files). In my experience, support for a single language, typically English, is usually sufficient for these.
So… what's left? Logging and debug-only tracingYes, that's all. But that is sufficient for many applications where C++ is used for its strengths.
(one is advised not to use streams with in-prod tracing because if inefficiency).Citation needed. In my experience, C++ streams are not more or less efficient than other mechanisms. And in all C++ programs I have been involved with, trace statements are implemented with macros so they have close to zero runtime overhead when not enabled.
Overloading
Posted Apr 27, 2014 19:03 UTC (Sun) by rleigh (guest, #14622) [Link]
i18n? Use gettext to localise Boost.Format strings and stream the resulting formatted string. This has all the ease of translation and control with format specifiers you'd get with C printf strings, with the added advantage of being completely type-safe and safe at runtime if for whatever reason you pass the wrong type or number of args. Even better, it's not restricted to the small number of basic types you can use with C printf; any C++ class with an overloaded ostream operator may be used. This makes for a much more robust solution than you get with C printf. And if the translator screws up the format string, it won't crash your program.Trivial example:
std::string format_string = _("[%1% chroot] (%2%→%3%) Running login shell: ‘%4%’"); boost::format fmt(format_string); fmt % session_name() % olduser() % newuser() % shell; std::cout << fmt << std::endl;
This could of course be combined as:
std::cout << boost::format(_("[%1% chroot] (%2%→%3%) Running login shell: ‘%4%’")) % session_name() % olduser() % newuser() % shell << std::endl;
Adapted from here
Regards, Roger
Overloading
Posted Apr 27, 2014 19:06 UTC (Sun) by mpr22 (subscriber, #60784) [Link]
And yet, I still find iostream syntax to be syntactic ipecac.
Overloading
Posted Apr 27, 2014 21:25 UTC (Sun) by khim (subscriber, #9252) [Link]
Boost.Format is actually well-designed library (I don't like it's abuse ofoperator%
, but that's matter of taste), yet you can easily use it with stdio
functions, you don't need streams. Unfortunately it does not come with standard library while printf
does.
Overloading
Posted Apr 27, 2014 14:53 UTC (Sun) by apoelstra (subscriber, #75205) [Link]
I think << operator overloading is one of the best examples where operator overloading works well.It's a classic example of taking an operator which has a well-defined meaning in historical use for decades, and making it do something incomprehensibly far away from any standard use of that operator. And it doesn't help that cout et. al. are never defined in the same translation unit that they are used in.
Sane languages restrict context. Perhaps they have strong type systems; they have plenty of compiler-enforced invariants; they restrict scope and mutability; they have things like iterators which reduce the number of variables and restrict the behaviour of existing ones. In C++ on the other hand an entire translation unit is insufficient to determine anything at all about what some line of code is doing.
Overloading
Posted Apr 29, 2014 19:57 UTC (Tue) by jwakely (subscriber, #60262) [Link]
Why is that relevant? Are you saying if you see cout << str you don't know if it's an ostream insertion or a bitshift?
> In C++ on the other hand an entire translation unit is insufficient to determine anything at all about what some line of code is doing.
By definition, a translation unit must be sufficient, due to the separate compilation model used by C++. I don't think you meant "translation unit" here.
Overloading
Posted Apr 28, 2014 15:32 UTC (Mon) by rriggs (guest, #11598) [Link]
The ability to overload operators makes creating and using EDSLs in C++ a dream.
http://c2.com/cgi/wiki?EmbeddedDomainSpecificLanguage
Overloading
Posted Apr 28, 2014 17:09 UTC (Mon) by apoelstra (subscriber, #75205) [Link]
Try inventing your own English homonyms and see how well you are understood.
> Do you get equally bent out of shape about the use of "+", "-", "*" and other "mathematical operators" or array notation when dealing with regular expressions? Context #!$&ing matters.
Then context should be visible and as local as possible. There is a reason that you can't find a language where you need to read multiple files to determine whether a given character is part of a regular expression.
Overloading
Posted Apr 28, 2014 18:23 UTC (Mon) by HelloWorld (guest, #56129) [Link]
The only people who may be puzzled by this sort of code is people who don't know what the Hello World program in C++ looks like. I seriously doubt that the overloading of the shift operators for I/O ever led to a problem in any real project.
Overloading
Posted Apr 28, 2014 19:27 UTC (Mon) by mathstuf (subscriber, #69389) [Link]
The best one[1] has already been proposed.
Overloading
Posted Apr 30, 2014 22:14 UTC (Wed) by nix (subscriber, #2304) [Link]
Try inventing your own English homonyms and see how well you are understood.This happens all the time and is one of the fundamental means of lexeme creation in English.
Overloading
Posted Apr 27, 2014 15:13 UTC (Sun) by torquay (guest, #92428) [Link]
-
Why are all these tricks such a bad idea that you might want to forbid anyone from using them (and thus, might just as well not provide them) ? Because they tend to make _reading_ programs even harder. Since reading programs is without doubt one of the trickier problems we have anything that makes it worse is undesirable.
As one size does not fit all, the above statement is false overall. Yes, some people can abuse operator overloading, but that doesn't mean you should throw out the baby with the bath water. As one positive example, operator overloading is a must for matrix math (linear algebra). Otherwise any user code that doesn't use operator overloading is actually harder to read, more error prone, and harder to maintain.
-
It's pretty much certain at this point that you'll want to contradict me. Don't bother. Here's what you need to have _any_ standing in this matter. You obviously love operator overloading, so find a program you wrote ten years ago which makes significant use of operator overloading and get the present maintenance programmer for that code to follow up in this discussion explaining how they got along with your approach.
Circa 2005 I have written a medium sized (10,000+ lines) program in C++ using the old IT++ library, heavily using matrix operations. The program is still used in my division, with people adding bits and pieces (it's now around 20,000 lines). Without operator overloading it would have been a maintenance nightmare. Rewriting my old C++ program from 2005 in Go would actually make it longer and harder to read. This would not be progress, but a clear step backwards.
The original quote from the Sourcegraph site is "... Go has turned out to be a nice general purpose language ". I beg to differ. Without abstractions such as operator overloading, a whole suite of programs is not realistically doable in Go, and hence Go is not a general purpose language. Operator overloading is not limited to simply matrix operations: as an example, concatenation of two strings makes sense using the + operator.
Overloading
Posted Apr 27, 2014 16:53 UTC (Sun) by HelloWorld (guest, #56129) [Link]
Well, opinions vary on that. The meaning of + that people are familiar with is the addition of real numbers which, unlike concatenation, is commutative, has an inverse etc. In Haskell, the operation on a Monoid is called mappend, not (+), and I like it that way.
Porting the Go compiler to Go
Posted Apr 29, 2014 3:56 UTC (Tue) by PaulWay (subscriber, #45600) [Link]
If you're criticism of Go is that it's not much better than C, and you think C++ is, then really you're just blinding yourself.
Ironically (IMO), Go is at about that level precisely so that it's a familiar transition for C, C++ and Java programmers. If Go is too low level for you, write Python or whatever.
Have fun,
Paul
Porting the Go compiler to Go
Posted Apr 29, 2014 12:05 UTC (Tue) by mpr22 (subscriber, #60784) [Link]
Operator overloading and convenient type-safe generics, together, make a fairly compelling argument for me. If I pick up another statically typed compiled language any time soon, it'll most likely be Rust, which already has both.
Porting the Go compiler to Go
Posted Apr 26, 2014 17:32 UTC (Sat) by HelloWorld (guest, #56129) [Link]
Porting the Go compiler to Go
Posted Apr 26, 2014 22:31 UTC (Sat) by mathstuf (subscriber, #69389) [Link]
Porting the Go compiler to Go
Posted Apr 26, 2014 23:41 UTC (Sat) by b7j0c (subscriber, #27559) [Link]
we already know what happens when you have a "better" tool that people can't understand in a reasonable amount of time - haskell. it is better, but at twenty years old, it has far fewer developers using it than Go, which is like three years old.
Porting the Go compiler to Go
Posted May 7, 2014 20:41 UTC (Wed) by cmccabe (guest, #60281) [Link]
Porting the Go compiler to Go
Posted May 7, 2014 21:30 UTC (Wed) by Cyberax (✭ supporter ✭, #52523) [Link]
We're talking about freaking generics. Which are even available for Java.
Porting the Go compiler to Go
Posted May 7, 2014 21:51 UTC (Wed) by cmccabe (guest, #60281) [Link]
1. Java doesn't have built-in maps and slices; Go does
2. Java doesn't have an easy way to build new types by composition, or multiple inheritance. So instead of creating a type that implements interfaces A and B, it's easier to create a type which implements A and is templated on B.
One problem that keeps cropping up again and again in programming language design is that people are unable to understand the concept that more than one programming language should exist. If programming language X is a good choice for one application, shouldn't everyone use X for everything? The answer is no, because there are fundamental tradeoffs. Language features aren't free, even if you don't use them.
A language like Scala that has currying, type inference, algebraic data types, and so forth can express complex algorithms very concisely. It might be the right choice for data analysts writing machine learning algorithms. But it's going to be difficult for most programmers to pick up. The code is going to be harder to read, even for experienced programmers. And there are going to be fewer options available for squeezing out more performance.
A language like Go is easy to pick up, easy to read, and easy to optimize. The reality of programming is that N is usually small, fancy algorithms are usually not necessary, and readability is more important than ultra-concise or ultra-clever code. It makes efficient use of machine resources and doesn't require a language lawyer to figure out whether a given code snippet is legal. Go hits the sweet spot for a lot of applications.
Tradeoffs are fundamental in engineering. There is room for both languages to exist-- and possibly even other languages, like the humble shell script. Just adding one feature from Scala to Go (like generics or currying) is not going to make Go a better language, any more than adding a racing spoiler on your Honda Fit is going to make it a better car.
Porting the Go compiler to Go
Posted May 7, 2014 22:01 UTC (Wed) by Cyberax (✭ supporter ✭, #52523) [Link]
And no multimaps. So if you need to do one step away from built-in constructs - you're on your own.
> 2. Java doesn't have an easy way to build new types by composition, or multiple inheritance. So instead of creating a type that implements interfaces A and B, it's easier to create a type which implements A and is templated on B.
What? Go and Java have exactly the same inheritance system except for Go's automatic interface implementation. Generics are needed primarily for containers, so map<SomeObj>'s methods return SomeObj instead of root-of-hierarchy objects (interface{} in Go and Object in Java).
> One problem that keeps cropping up again and again in programming language design is that people are unable to understand the concept that more than one programming language should exist.
Yeah. Why not also create a Go derivative with maps which randomly removes user's files. I'm sure that somebody would like it! After all, there are very perverted people who just LOVE writing in PHP.
Sloppiness does not excuse poor language design.
Porting the Go compiler to Go
Posted May 8, 2014 2:32 UTC (Thu) by cmccabe (guest, #60281) [Link]
> built-in constructs - you're on your own.
You can just have a map from the key to a list of values to get the functionality of a multimap.
Before you start talking about other data structures, it's obvious that C++-style generics are good for containers. Nobody is disputing that. So feel free to attack that windmill all you like. Meanwhile, the real point I made, which is that most programmers don't need new and exotic containers most of the time, remains unaddressed.
> Sloppiness does not excuse poor language design.
Was anyone here arguing that sloppiness excused poor language design? Or are you just arguing against an imaginary opponent?
I am frustrated that you did not reply to my actual argument, which is that different languages fill different roles. The fact that you can't understand why people use PHP rather than your favorite programming languages (C++?) indicates that you still don't get it. There is a niche for a simple language with a short learning curve, with a lot of functionality built-in. We can all agree that PHP is not a great language (even when used for what it's good at), but the fact that it continues to exist is living proof that the stuff you care about isn't as important as you think. In the real world, different languages fill different roles. There will never be one language to rule them all, because there is not one use case to rule them all.
There are lots of languages out there with all the stuff you like. Haskell, Scala, and SML come to mind. How about using them and explaining to us why they're so great for our use-cases? That would be a nice contribution. Don't be negative about something you don't even use.
Related: http://www.yosefk.com/blog/what-worse-is-better-vs-the-ri...
Porting the Go compiler to Go
Posted May 8, 2014 3:51 UTC (Thu) by Cyberax (✭ supporter ✭, #52523) [Link]
Sure, but it's awkward. Each addition now must check that a value exists and add a new list if it doesn't. _AND_ you can't write a generic helper function to do it.
> Meanwhile, the real point I made, which is that most programmers don't need new and exotic containers most of the time, remains unaddressed.
They do. They might not _know_ it, but multimaps make a lot of code look cleaner. And the amount of interface{} casting in any Go program is just downright embarrassing.
> Was anyone here arguing that sloppiness excused poor language design? Or are you just arguing against an imaginary opponent?
Well, you seem to argue that ability to allow sloppy code now and then (well, very often in fact) excuses the poor language design. And that a convenient form (look Ma, just one binary!) trumps other considerations.
That's the argument that led to PHP. It also allowed easy-to-install environment (without those darned CLASSPATHs) and also advertised itself as a 'practical' language. After all, what programmers might want to use classes when you have this nice MySQL interface?
Porting the Go compiler to Go
Posted May 14, 2014 1:21 UTC (Wed) by HelloWorld (guest, #56129) [Link]
This “generics are only about containers“ thing is utterly stupid. Trivial abstractions like map, fold, filter, function composition etc. need generics to express them properly, and they're needed for futures, composable stream abstractions, parser combinators, on and on it goes…
Porting the Go compiler to Go
Posted Apr 27, 2014 5:20 UTC (Sun) by Cyberax (✭ supporter ✭, #52523) [Link]
Porting the Go compiler to Go
Posted Apr 26, 2014 2:58 UTC (Sat) by pabs (subscriber, #43278) [Link]
Could you explain the problems you think Go has in more detail? I haven't looked at it yet and it sounds like I shouldn't?
Porting the Go compiler to Go
Posted Apr 26, 2014 3:25 UTC (Sat) by Kit (guest, #55925) [Link]
Porting the Go compiler to Go
Posted Apr 26, 2014 13:37 UTC (Sat) by fishface60 (subscriber, #88700) [Link]
If you only have to deal with cross-compiling the C compiler you can focus all your effort on dealing with the changes involved in the new version of the C compiler, or new architecture.
The Go compiler can then work out what architecture it needs to target from what it's currently running on, which is much less manual effort, as it can detect that automatically.
Porting the Go compiler to Go
Posted May 1, 2014 23:58 UTC (Thu) by Comet (subscriber, #11646) [Link]
Go's is the cleanest cross-compilation experience I've ever had, and the nearest competition is NetBSD's setup.
Porting the Go compiler to Go
Posted Apr 26, 2014 3:44 UTC (Sat) by iabervon (subscriber, #722) [Link]
Porting the Go compiler to Go
Posted Apr 26, 2014 14:36 UTC (Sat) by HelloWorld (guest, #56129) [Link]
The problem with Go is that it isn't nearly ambitious enough. I think that the programming language should help the programmer to express invariants about the program, and the way to do that is through the type system. Go has embarassingly little to offer here. Very basic functions like map (apply a function to every element in a list and return the list of the resulting values) or filter (apply a predicate to every function in a list and return the list of those where the predicate holds) can not be expressed in a generic, type-safe way due to the lack of parametric polymorphism (aka generics). They also lack sum types (aka tagged unions), which are extremely useful for error handling among others. These concepts were understood decades ago, they're nowhere near revolutionary or controversial. Go's interface mechanism is sort of neat, but it's also not innovative, you can get that (and a lot more!) in, say, Ocaml. And there are so many other areas where significant progress was made in the last decades, like module systems (look at what ML has had for decades) or syntax (even Algol's syntax was better than Go's, Lisp has had proper macros since the 1960s). Basically, whatever part you look at, Go is several decades behind the state of the art.
What makes it actively evil is that it is nevertheless a significant improvement upon C and yet very easy to pick up for a C programmer. That sounds like a good thing at first, but it's not. It makes C programmers switch to Go because it really is less painful to program in, but they don't realize that they could get so much more out of a programming language if they were prepared to walk off the beaten paths. And that's what makes me think that it'll throw computing back by decades if it gains a significant amount of traction.
Porting the Go compiler to Go
Posted Apr 26, 2014 22:35 UTC (Sat) by mathstuf (subscriber, #69389) [Link]
[1]It's a tough tradeoff, but I think I'd go with static typing given the exclusive disjunction between the two.
Porting the Go compiler to Go
Posted Apr 27, 2014 16:41 UTC (Sun) by Nelson (subscriber, #21712) [Link]
I ignored it at first too, largely due to the specs.Give it a spin, seriously, the simplicity of it is part of what makes it fun to use. It's simple, lean, clean, easy to pick up and it is fun to use. Just enough safety.. Once you've committed to C++ or for that matter Java or a lot of other modern dynamic languages, you've had to pick up so much BS that doesn't get your problem solved faster or better, just little details and nuances. There really isn't that much nuance to Go and when you get used to it, it is a beautiful thing.
Porting the Go compiler to Go
Posted Apr 27, 2014 16:56 UTC (Sun) by mathstuf (subscriber, #69389) [Link]
Porting the Go compiler to Go
Posted May 7, 2014 21:31 UTC (Wed) by cmccabe (guest, #60281) [Link]
1. Inertia. Remember, C++ was a hot new language when Ronald Reagan was president. For all the usual reasons, big old codebases don't get rewritten very often.
2. Fear of garbage collection. Most of the C++ projects that wanted the benefits of garbage collection already jumped ship for Java back during the Java craze of the late 1990s.
Unfortunately, garbage collected, statically-typed languages have become synonymous with Java in the minds of many C++ developers. It's a shame, because Go doesn't have a lot of the limitations of Java. Java programs take a few seconds to start; Go programs start instantly. Java requires you to set up CLASSPATH; Go just requires you to run a static binary. Java requires you to write clumsy and awkward JNI shims to interface with native code; go has cgo which allows you to put C code inline inside .go files in just a line or two. Java doesn't support unsigned numbers; go does.
More fundamentally, the way the languages manage memory is different. Java fundamentally doesn't have value types, only references (*). What this means in practice is that if you have object Foo containing objects Bar and Baz, you need to allocate Bar and Baz separately, and put references to them inside Foo. This means that you have at least 8 bytes of extra overhead per-object compared to a language like Go, which just lets you put Bar and Baz inside the allocation for Foo. When you add in stuff like non-static classes, RTTI overhead, and so on, the per-object overhead in Java is actually quite high. And this matters a lot in modern architectures, where the CPU can do quite a lot in the time it takes to fetch values from main memory.
There are some projects out there that genuinely might benefit from managing memory manually. But I'm skeptical that this overlaps much with the set of projects that also need a language higher-level than C. Time will tell, I guess. The fact that people are getting angry about Go is a good sign, like when people were criticizing UNIX for being too popular and successful compared to VMS and Lisp machines.
* For the pedants out there: yes, Java supports value types for ints and other primitives. This is why you often see horrifying hacks where people create an array of ints and start passing it around and interpreting it in various ways.
Porting the Go compiler to Go
Posted Apr 28, 2014 10:51 UTC (Mon) by k3ninho (subscriber, #50375) [Link]
All of these great language features will trickle their way down to the lowest common denominator programming languages, so that in, say C72[1], there will be generics and tagged unions. The way to speed this flow up is to post videos saying "this feature is neat in $lang1, I want to port it to $lang2, here's where $lang2 fails so I can't"[2].
If you hate Go now, take a moment to consider what happens when the Go team deploy their 'fully operational battlestation' at the point in time when they include these language features in the programming API and go on to tell you to use "go fix sourcetree" to massage your old code[3] to meet the new format, allowing you to adopt the new features.
[1] 2172 or 2272, I'm not sure. And you'd think by then we'd avoid century abiguity, too.
[2] With a 5-figure number for the YouTube comments that say 'patches or it didn't happen'.
[3] Which you have entwined with integrated tests, yeah?
K3n.
Porting the Go compiler to Go
Posted Apr 26, 2014 3:46 UTC (Sat) by witheld (guest, #96686) [Link]
Porting the Go compiler to Go
Posted Apr 26, 2014 17:34 UTC (Sat) by HelloWorld (guest, #56129) [Link]
A language that doesn't allow me to implement very simply abstractions like map and filter in a type-safe, generic way is *not* suitable for writing code I'd consider sane.
Porting the Go compiler to Go
Posted Apr 27, 2014 2:26 UTC (Sun) by witheld (guest, #96686) [Link]
Porting the Go compiler to Go
Posted Apr 27, 2014 11:24 UTC (Sun) by HelloWorld (guest, #56129) [Link]
Porting the Go compiler to Go
Posted Apr 28, 2014 15:53 UTC (Mon) by dgm (subscriber, #49227) [Link]
Porting the Go compiler to Go
Posted Apr 28, 2014 16:01 UTC (Mon) by HelloWorld (guest, #56129) [Link]
Porting the Go compiler to Go
Posted Apr 26, 2014 23:46 UTC (Sat) by b7j0c (subscriber, #27559) [Link]
[]string
rather than
[]T
if in fact the general point is to operate on strings. thus negating 99% of the pointless architecture astronautics made by halfwits trying to encompass the universe of values for no benefit whatsoever. let generics come in five years when all of the Go code people actually care about has already become well known and mature
Porting the Go compiler to Go
Posted Apr 27, 2014 0:26 UTC (Sun) by mathstuf (subscriber, #69389) [Link]
Porting the Go compiler to Go
Posted Apr 27, 2014 13:42 UTC (Sun) by gilboa (guest, #23856) [Link]
As someone that spends half of my days writing kernel code in C and user-land code in C++ and Python (w/ low-level cross platform libraries written in C), I (greatly) prefer the former.
At least in my view, C code tends to be cleaner and far less complex.
YMMV, I guess.
- Gilboa
Porting the Go compiler to Go
Posted Apr 27, 2014 14:47 UTC (Sun) by HelloWorld (guest, #56129) [Link]
Porting the Go compiler to Go
Posted Apr 27, 2014 15:02 UTC (Sun) by apoelstra (subscriber, #75205) [Link]
HelloWorld said:I'm well-aware of the many unnecessary complexities and deficiencies of C++ (of which many, if not most, are actually caused by C compatibility requirements). But if your C code is cleaner than your C++ code, you're not using C++ right.It took a long time for the ideas and culture behind "using C++ right" to develop. If somebody hasn't seen C++ code since then (and is in a job position which lets them avoid learning it) I wouldn't blame them for having never learned to use it well.
Porting the Go compiler to Go
Posted Apr 28, 2014 13:57 UTC (Mon) by ndye (guest, #9947) [Link]
. . . if your C code is cleaner than your C++ code, you're not using C++ right.
[If somebody hasn't seen C++ code since] the ideas and culture behind "using C++ right" develop[ed] . . . .
What open-source project(s) constitute instructive reading of "C++ done well"?
Porting the Go compiler to Go
Posted Apr 29, 2014 1:06 UTC (Tue) by mathstuf (subscriber, #69389) [Link]
Unfortunately, it is true that I don't know of nearly as many good C++ projects (code-wise) as C (tmux, mpv, git, uzbl[2], and ffmpeg is getting better). For C++, Boost is nice if you can look past all of the gymnastics it does behind the scenes to make nice interfaces you use. LLVM isn't too bad either but that has mostly been me fixing compiler errors when various parts I build aren't in-sync. Taskwarrior is decent too (though they do "throw std::string" in there which makes me shiver).
[1]https://github.com/Kitware/sprokit
[2]Another shameless plug. Just look at the 'next' branch, not 'master' :) .
Porting the Go compiler to Go
Posted May 2, 2014 3:20 UTC (Fri) by Trelane (subscriber, #56877) [Link]
But they won't have shown up in many projects just yet.
Porting the Go compiler to Go
Posted May 2, 2014 3:58 UTC (Fri) by mathstuf (subscriber, #69389) [Link]
Porting the Go compiler to Go
Posted May 2, 2014 10:08 UTC (Fri) by jwakely (subscriber, #60262) [Link]
The hash tables have been around forever in some form but the committee couldn't agree on some details, so they didn't get included in C++98. They've been around since 2005 in namespace std::tr1, the reason it took so long to get them in namespace std is there there wasn't a new standard published that they could have been included in (it's not like there was a new C++ standard every year and the hash containers just kept being left out of it!) The reasons there wasn't a new standard for so many years have been documented elsewhere (feature creep, disagreement about standardising concepts, formalising the memory model...)
Porting the Go compiler to Go
Posted Apr 29, 2014 10:08 UTC (Tue) by yoe (guest, #25743) [Link]
Note that you can still write the compiler in its own language even if you allow for a bootstrap. All that needs is a "mini" version of the compiler which is good enough to compile the full compiler even if it doesn't support all features in the compiler. This "mini" version would either need to be written in another language, or would need to be written in an old enough version of the standard that it's a good guess that other (older) implementations of the same standard can compile it.
Porting the Go compiler to Go
Posted Apr 29, 2014 11:19 UTC (Tue) by HelloWorld (guest, #56129) [Link]
If it's so hard to cross-compile the Go compiler, that is what needs to be fixed, and not worked around by bootstrapping via C.
Bootstrapping compilers
Posted Apr 29, 2014 17:07 UTC (Tue) by david.a.wheeler (subscriber, #72896) [Link]
People who worry about malicious attackers are interested in compiler bootstrapping. The "trusting trust" attack involves creating malicious compilers. The only practical countermeasure (that I'm aware of) is described in my PhD dissertation, and that requires the ability to bootstrap. See my page on Diverse Double-Compiling (DDC) for more information. It is useful to be able to (continue to) bootstrap.
Porting the Go compiler to Go
Posted Apr 29, 2014 18:01 UTC (Tue) by riccieri (guest, #94794) [Link]
Forgive my ignorance, but is a garbage-collected, runtime-dependent language suitable for becoming "the next C"?
From my understanding, it wouldn't be possible to create libraries written in Go that are consumable by other languages (via FFI), for example.
Porting the Go compiler to Go
Posted Apr 26, 2014 3:46 UTC (Sat) by frumious (subscriber, #3892) [Link]
See https://docs.google.com/document/d/1P3BLR31VA8cvLJLfMibSu...
Boolean types
Posted Apr 26, 2014 5:54 UTC (Sat) by epa (subscriber, #39769) [Link]
Boolean types
Posted Apr 26, 2014 9:57 UTC (Sat) by nix (subscriber, #2304) [Link]
Boolean types
Posted Apr 26, 2014 12:37 UTC (Sat) by khim (subscriber, #9252) [Link]
WTF are you talking about? Is it so hard to open standard, scroll down to section 6.3.1.2 and read:
When any scalar value is converted to _Bool, the result is 0 if the value compares equal to 0; otherwise, the result is 1.
I don't see how you could misunderstand that. bools are bools in both C and C++. For the last 15 years at least. Well, if you don't use MSVC, of course, but if you do use MSVC then you deserve all the pain you'll be receiving.
Boolean types
Posted Apr 26, 2014 15:03 UTC (Sat) by nix (subscriber, #2304) [Link]
C99, which was explicitly mentioned in the parent comment, has none of that language (nor does it have a _Bool type, only bool out of <stdbool.h>, basically an alias for int).
Boolean types
Posted Apr 26, 2014 16:25 UTC (Sat) by khim (subscriber, #9252) [Link]
This is a standards-version difference.
C99, which was explicitly mentioned in the parent comment, has none of that language.
If you find yourself in a hole, stop digging. Please.
C99 (otherwise known as ISO/IEC 9899:1999) most definitely have this language. That's what I've cited. It's on page 43, to be exact. C89, yes that one does not have it, but it's ancient history by now.
Perhaps you think it's some new invention of C11? Nope, not even close. C11 does change the text slightly, but it's just a side-note NaNs do not compare equal to 0 and thus convert to 1. _Bool
, stdbool.h
, true
and false
are all defined quite explicitly by C99 standard. And bool
is specified (on page 252) is define for a macro that expands to _Bool
. Not to int
. Not to short
or char
, but only and exclusively to bool
.
As I've said: if you use non-C99-compilant compiler like MSVC then you deserve all the pain you are getting (and yes, such compilers sometimes provide stdbool.h
which maps bool
to int
), but all C99-compilant compilers must provide _Bool
type with properties outlined above.
Boolean types
Posted Apr 26, 2014 17:02 UTC (Sat) by HelloWorld (guest, #56129) [Link]
Boolean types
Posted Apr 28, 2014 7:44 UTC (Mon) by brouhaha (subscriber, #1698) [Link]
Well, actually the way C99 defines “Booleans” makes them almost completely useless in my opinion.I do a lot of C99 programming, and use stdbool all the time, and it certainly doesn't seem "almost completely useless" to me. But I suppose YMMV.
Boolean types
Posted Apr 28, 2014 10:05 UTC (Mon) by HelloWorld (guest, #56129) [Link]
Boolean types
Posted Apr 28, 2014 11:10 UTC (Mon) by epa (subscriber, #39769) [Link]
Boolean types
Posted Apr 28, 2014 12:30 UTC (Mon) by mchapman (subscriber, #66589) [Link]
Wouldn't it be simpler just documenting the behaviour for a "logically false" value (i.e. 0) and for a "logically true" value (i.e. everything else)?
I can't say I've ever felt the fact that boolean-like ints can take a range of values to be a problem. In practice you usually end up just using them in an if or while condition anyway.
Boolean types
Posted Apr 28, 2014 13:04 UTC (Mon) by HelloWorld (guest, #56129) [Link]
No, you only have two think about two cases: zero and non-zero, it's completely isomorphic. And the _Bool type is utterly half-assed as it's not strongly typed and the relational operators still evaluate to int instead of _Bool and there are no proper literals: true == 2 is false... err, I mean 0.
_Bool doesn't buy you anything relevant over typedef enum { false, true } bool;, and what's worse, it blocks any kind of true progress, because as soon as anybody wants to add *proper* booleans to the language, everybody else will point to _Bool. What the C committee has done here is just thoroughly idiotic.
Boolean types
Posted Apr 28, 2014 16:03 UTC (Mon) by epa (subscriber, #39769) [Link]
I do agree that the _Bool as defined in C99 is half-assed. It joins the signed/unsigned rules and integer overflow as one of those misfeatures of C which by some mysterious force of the universe can never be fixed.
Boolean types
Posted Apr 28, 2014 16:29 UTC (Mon) by HelloWorld (guest, #56129) [Link]
Well, use “typedef enum { False, True } Bool” then. Well, actually, don't, because boolean parameters are a code smell anyway:
http://www.nickhodges.com/post/How-Not-To-Code-2-Dont-Use...
Boolean types
Posted Apr 26, 2014 23:19 UTC (Sat) by nix (subscriber, #2304) [Link]
I clearly shouldn't be trying to look up stuff in language standards while on hefty doses of codeine, I overlook obvious stuff like the date at the top... codeine is not good for codeing, as it were...
Boolean types
Posted Apr 26, 2014 12:52 UTC (Sat) by busterb (subscriber, #560) [Link]
$ cat testbool.c
#include <stdbool.h>
#include <stdio.h>
int main()
{
bool a = 1;
bool b = 5;
bool c = (1 << 23);
bool d = true;
printf("%zu %u %u %u %u\n", sizeof(a), a, b, c, d);
}
$ ./testbool
1 1 1 1 1
Boolean types
Posted Apr 26, 2014 13:38 UTC (Sat) by alvieboy (guest, #51617) [Link]
There's a lot of overhead on most ISA to get a "boolean" 0-1 from most arithmetic functions.
Even our beloved "!!" presents often branching. Almost no ISA has a logical NOT. And I don't recall (except for X86) instructions that can propagate a flag (Carry,Zero) onto a register.
Summing it up, it works, but what's the overhead ?
Boolean types
Posted Apr 26, 2014 14:42 UTC (Sat) by ehiggs (subscriber, #90713) [Link]
Boolean types
Posted Apr 26, 2014 14:54 UTC (Sat) by PaXTeam (guest, #24616) [Link]
xorl %eax, %eax
testl %edi, %edi
setne %al
ret
on arm:
adds r0, r0, #0
movne r0, #1
bx lr
on sparc:
subcc %g0, %o0, %g0
jmp %o7+8
addx %g0, 0, %o0
Porting the Go compiler to Go
Posted Apr 26, 2014 8:21 UTC (Sat) by marcH (subscriber, #57642) [Link]
Porting the Go compiler to Go
Posted Apr 26, 2014 8:32 UTC (Sat) by marcH (subscriber, #57642) [Link]
http://en.wikipedia.org/wiki/List_of_Java_virtual_machines
Porting the Go compiler to Go
Posted Apr 26, 2014 8:39 UTC (Sat) by Cyberax (✭ supporter ✭, #52523) [Link]
Also, Java compiler (that translates Java code into bytecode) has always been written in Java.
Porting the Go compiler to Go
Posted Apr 26, 2014 23:07 UTC (Sat) by mjw (subscriber, #16740) [Link]
Jainja is a JVM (Java Virtual Machine) written in Java.
Focus is set on portability, not on performances. Currently the supported platforms are Linux, Windows, xBSD, Minix, Haiku, HelenOS, Java SE, Java ME, Android, GWT, Dart, NaCl.
Porting the Go compiler to Go
Posted Apr 29, 2014 0:22 UTC (Tue) by smoogen (subscriber, #97) [Link]
Porting the Go compiler to Go
Posted May 4, 2014 18:55 UTC (Sun) by h2 (guest, #27965) [Link]
http://golang.org/doc/go1compat
http://talks.golang.org/2012/splash.article
I got curious about what Go actually is, and why it exists, since it's struck me as interesting as an approach.
One thing after reading a lot of that fairly dense text in those 3 links I can say without much doubt, if say, HelloWorld here were applying for a job that required reading documentation and faqs as part of the job, he would be disqualified a priori based on his completely irrelevant comments about Go in this thread, which basically just boil down to: it doesn't do what I want it to do, which simply means it's a bad choice for him, nothing else.
The problem set go is working to solve requires code consistency and predictability on massively scaled projects with non stop streams of new programmers entering and leaving the work place. That's I believe why the operator overloading is not permitted, along with some other interesting decisions they took. I can relate to this more and more the older I get because I have worked with languages (that I actually like and prefer) that do not do this, and I totally understand why you want to enforce syntaxes and behaviors etc as a core part of the language.
I think most people, like me, who are interested in the question of what go is designed to do, would be much better off reading those three links at least than this lwn.net thread, which is sad in a way, often discussion here is very valuable and really exposes a lot of the different angles (the debian systemd debate comes to mind for example), but in this case it mostly seemed to ignore the actual problems go is designed to solve, ie, fast compiling, easy programming, quick pickup, enforced behaviors to eliminate hacks and non maintainable randomness, etc. But mainly it's built to run huge projects with massive scaling of programmers, and to disable the ability to do bad practices on large scales.
When one person above here suggested that Go was failing to be picked up by its target audience, C++ programmers, again, that statement makes no sense, Go is already running and replacing C++ in google, exactly as it was designed to do, and it was specifically designed to fix the realworld issues google has and had with c++ on a massively scaled level, in fact it was designed to fix those exact problems. It's also designed to resemble C closely so that young programmers can pick it up fast out of schoool, ie a true real world problem set, not some ideal or academic one.
It really pays to read their explanations in my opinion BEFORE commenting on why it does not do (favorite practice) x or y, in fact, their faqs specifically address this point.
While I doubt I will ever learn this language I certainly respect the attempt to eliminate randomness in programming, much as I am fond of and use and have lived off of various random scripting languages, and plan on continuing to do so.
Porting the Go compiler to Go
Posted May 4, 2014 22:41 UTC (Sun) by mathstuf (subscriber, #69389) [Link]
That was me, but I have a source[1], Rob Pike:
> I was asked a few weeks ago, "What was the biggest surprise you encountered rolling out Go?" I knew the answer instantly: Although we expected C++ programmers to see Go as an alternative, instead most Go programmers come from languages like Python and Ruby. Very few come from C++.
> We—Ken, Robert and myself—were C++ programmers when we designed a new language to solve the problems that we thought needed to be solved for the kind of software we wrote. It seems almost paradoxical that other C++ programmers don't seem to care.
Anyways, I agree with killing operator overloading (preferably with fire). It's just that there is no replacement (operators working on interfaces) and generics are completely ignored with "you don't need it". Sure, I don't *need* it, but I don't *need* Go either. Plus, it's not like they're anything new where you're depending on bleeding-edge research which might be obsolete or useless 5 years down the road.
The FAQ's answer of "the ability to use the empty interface to construct containers (with explicit unboxing) mean in many cases it is possible to write code that does what generics would enable, if less smoothly" means that Go is not as clean a language when I'd write in it because I love using higher-order functions like map and filter where possible.
[1]http://commandcenter.blogspot.se/2012/06/less-is-exponent...
Porting the Go compiler to Go
Posted May 5, 2014 19:43 UTC (Mon) by HelloWorld (guest, #56129) [Link]
Nonsense. The purpose of high-level programming languages is, among others, to help the programmer to avoid mistakes. Go does a poor job at that as it isn't able to express even simple abstractions in a type-safe way. This has nothing to do with “doesn't do what I want it to do”, it's about as fundamental a critique of a programming language as it gets. The fact that you didn't grok this says more about your reading comprehension than about my comment.
> It really pays to read their explanations in my opinion BEFORE commenting on why it does not do (favorite practice) x or y, in fact, their faqs specifically address this point.
I did read them and I disagree with their reasoning. It seems that that possibility never crossed your mind.