Summary of Golang Generics Discussion
docs.google.com
docs.google.com
This is disingenuous -- just to set an artificial barrier against generics.
Go doesn't solve any problem in the "best way possible":
- "Blessed" containers like Go's hash tables are not "the best way possible".
- The way it handles goroutines/channels has issues (mutability/pointer issues, not pre-emptive, etc). Again, far from "the best way possible" (that would be Erlang maybe).
- The GC was far from the "best way possible" or even "really good". Especially on the earlier versions (and crap on 32-bit).
- Losing type checks by having to use interface{} for generality, or resolving to BS textually generated code with custom string templating is not "the best way possible".
So why only Generics has to be "perfect or bust"?
And then there's this gem, about the (lack of) need for generic data structures:
>map/slice suffice for most of the cases encountered in programming.
...
Or this "con", about having generic to help with functional fold/zip/map:
>The fastest solution needs to take into account when and which order to apply those transformations, and how much data is generated at each step
So, in other cases the hit from interface{} is OK, but suddenly now those operations have to be "the fastest solution".
(Not to mention that the fastest solution, application order etc are orthogonal to Generics).
Ideology, and a push-back against outside pressure to include them.
The same goes for most of the standard library "improvements" that people make. Http middleware is necessary until you grok the power of Handlers, ORMs are prevalent until you get that it's easier to write specific CRUD routines for your structs using the standard lib.
I don't think it's austerity any more. I think it's just putting a high value on simplicity, and I really appreciate that now I understand it better.
I'm happy to let the generics argument rage and smarter people than me resolve it. I don't need generics in my coding, happy to work around the occasional time I'd use them, but I understand the "argument from make" - if the Go team needed generics to build the language, then surely they're a Good Thing and we should have them.
I'm quite happy to yield control to sane defaults, widely-accepted conventions, and obvious idioms when I'm at home. If I ever need to write some high performance application, I'll definitely consider switching back to C++ (or perhaps learning Rust), but Go is great for rapid development of decently-fast-executing programs.
$ python -c 'from __future__ import braces'
File "<string>", line 1
SyntaxError: not a chance
Whether you agree or disagree, it's not trying to bullshit you with fallacious reasoning.[1] Though one can argue that the word "best" seems inappropriate when the concern is a very subjective balancing act.
Thanks for pointing out the problems with wording. I'm slowly fixing those. I've changed that "best" to "As with any feature it should solve a set of problems, if there are better ways of solving the problems, those should be used instead."... it's better but not perfect.
"in other cases the hit from interface{}" - added that addition to the alternatives section.
Generics don't have to be perfect, but it must be actually useful and it mustn't compromise simplicity of Go.
Go has generics. For arrays, slices, channels, maps, and some "standard" library functions. Go has generic functions. "append" being the obvious example. Go has polymorphic functions : append, make, ... If you look at the compiler source, the type system has generics, to a large extent. It's simply not accessible to normal programmers, instead only allowed for golang's authors.
As if this is not bad enough. Go cheats the type system in thoroughly non-obvious ways to get more C-like behaviours that obviously do not improve safety or programmer productivity.
Go has shudder return value polymorphic functions. Range being the obvious, but not only example (range changes in meaning depending on it's parameters AND on what you assign the result to).
As for your boxing argument. As soon as you use reflect, you're boxing everything. Oh wait, if you use a package that uses reflect, of course you're also boxing everything. Surely that can't be much ... hmmm half the standard library uses reflect. Fmt, everything in encoding, text or html templates, rpc, jsonrpc ... No need for boxing, or compile-time function evaluation or generics (all present better solutions to this, for the CTFE solution see D-lang).
Golang even has functions with type parameters. Make and new being the obvious examples. Again, this is present in the type system (not just there, also in reflect, things like printf, ...). It's simply not made accessible to us lowly go programmers.
So can we please stop with the crap that generics aren't necessary ? That nobody uses advanced type system features ? Or that polymorphism isn't necessary ? It's crap, and obviously the golang authors don't actually believe that. They just think that only they can be trusted to write such functions and that their datastructures are all anyone ever needs. If you disagree with that assessment (and everybody will, soon) Go is not for you.
So Go is simply a throwback to pre-80s programming languages, and a perfect illustration of the frustrations that led to the development and extension of the C++/Java/C# programming languages. If you give people the minimal implementation of sorting an array of structs, it becomes blatantly obvious why other languages are necessary.
The more I write Go, the more I yearn for C++. There is nothing in the C++ language that I can't do for my own datastructures/functions/... That is a huge feature, and may I just say :
From my cold, dead hands !
Btw : there is a better solution to generics as well at compiler-level, that is used in things like the CLR. First, generate unboxed versions of functions where that makes sense. If specializations are possible for 1-bit, 1-byte, 2-byte, 4-byte and 8-byte primitive data types, expand those. Then for anything bigger, like structs, create a boxed implementation, because for structs there is no longer any advantage to working unboxed. Then make it possible to pass in the version to be used in a parameter, so you don't have a combinatorial explosion when many type parameters are given.
e.g. http://research.microsoft.com/pubs/64031/designandimplementa...
It has little relevance to "Generics". They are simply how Go is implemented, the question is whether "Generics" as a user implementable thing should be added.
> CLR
From my quick reasearch, it uses runtime code generation and Go must run in environments where that is disallowed.
How the generic code generation differs from the JIT approach I don't know.
Go has generic types and generic/polymorphic functions. Therefore all the focus on that such functions are not necessary/useful seems entirely beside the point, the result of misunderstanding. Can normal Go programmers please be allowed to make use of that feature ?
That sounds sensible.
I'd like to figure out a way to extend the concept of interfaces to cover use cases like generic containers, but I'm not quite sure how that would work.
Thanks for not being defensive and taking my rather harsh critique lightly!
I wasn't trying to attack your specific document either, it's just that those things have often been repeated (often verbatim) by the Go-dev camp.
Personally, I stand in the middle of the generics discussion so I pretty much can see both sides as a valid approach. And it's a WIP and I know if one person writes it, it will be biased no matter how hard you try.
PS: I find the "straight to the point" comments much more useful - they are much easier to understand. So don't worry about it :)
If this issue is so important to people, don't use Go, use C++, Java, D or Rust. Don't waste your life arguing about something you'll never use, it's not a productive use of your time! Think about how much time you could save!
Alternatively, propose a solution to the problem and try and gain some traction to get it implemented into the language, or fork Go and implement it yourself. There's evidently a hunger out there for generics in Go, but everyone keeps assuming the responsibility lies with the Go Core team who's priorities seem (right now) to be in the optimising GC/compiler area.
And exactly as you said -- for those people so offended by this: Move on. Use something different. Go isn't for you. As someone who has integrated Go very effectively into my life, I'm rather glad the Go team isn't listening to every railing fanatic and their pet issues.
And then:
>I'm rather glad the Go team isn't listening to every railing fanatic and their pet issues.
Oh, the irony.
Why people assume that only people NOT using Go are complaining, it's beyond me.
Or why people assume that if you like features X of a product, and would like it to have feature Y, you shouldn't.
Which is strange, because a post about Haskell tends to be about Haskell. A post about Go tends to be a lot of people telling everyone how Go is unlike, to its detriment, other languages. Great -- go use those languages.
Why people assume that only people NOT using Go are complaining
HN doesn't have a large community of commentators, and you get to know the common personalities. There are absolutely people building solutions in Go who might think "it would be nice to have generics", and indeed that's exactly why they've never been discounted or denied by the Go team, simply deferred. But these discussions are dominated not by those people, but instead people telling you why Go is not Rust is not Haskell is not C# is not...
What's the point? We have a lot of languages and environments to choose from, and we do. Why are people seemingly threatened by Go? It's bizarre.
Generics are nice and they're important, but there are a lot of nice and important attributes to a language, and they have bigger priorities. If generics were critical to my work, I simply wouldn't use Go (and indeed, for some subsections and components, I don't for that reason. Life goes on. Different tools serve different needs).
I don't think anyone's threatened by Go. I think some people are disappointed that Go's designers chose not to add a lot of extra type-related features, including generics, for some extra effort on the part of the language designers but very little cost (and much benefit) to the language users. If this was an unused toy language there would be no problem, but the existence of lots of code written in any language will have a small cost on other developers for social reasons, even if they don't use that language.
Yet your final sentence says exactly the opposite, indirectly. As if Go is some sort of scourge that these gallant guardians of language must fight.
Further, if you assess the simplicity of adding generics, and it is at odds with the actual people creating the language and tools (among whom are some of the most respected names in this industry), that's a point when you should stop and reassess your own, outsider-looking-in perspective.
I hope to one day experience a Go thread with no appeals to authority with regards to the language inventors/implementers.
The appeals to authority are not always used in a fallacious way (like the informal logical fallacy). But I don't personally like it, and I think it is intellectually lazy. It's better to let the product itself stand or fall on its own merit.
The appeal to authority fallacy is if I measured the acidity in a lake over a long term period, and then presented my findings and someone declares that such can't be the case because the Environment Agency says it's fine. They're undermining my objective, demonstrated efforts with a hand waving appeal to someone else. If, on the other hand, I casually and lazily said "I think that there lake is acidic, no matter what anyone tells me", it isn't an appeal to authority to point out what someone who is undoubtedly in a better position thinks and actually knows.
In this case someone offhandedly, based upon nothing but the fact that they seem to want it to be true, declared the ease with which the Go team -- you know, the actual people working on it -- could add generics. No fuss, no muss. It isn't an appeal to authority to point out that they are in absolutely no position to make such a claim.
Like I said; I didn't mean that you, or necessarily people in general, use the appeal in a fallacious way. But it was my fault for not making that clear to begin with.
This is a general note, not thinking of any post or argument in particular: I can hardly count the number of times people who advocate Go will bring up the fact that people like Rob Pike and Ken Thompson are or have been involved in the project, and how smart they are and even 'how can I even question their work, given their skill and talent'.
Most respected names in the programming industry.
Not in the language/compiler design industry.
What you write above shows that HN users don't have the same behavior with other languages indiscriminately...
So, doesn't this sound like maybe it's Go that's problematic and not HN user behavior? (see also below)
>There are absolutely people building solutions in Go who might think "it would be nice to have generics", and indeed that's exactly why they've never been discounted or denied by the Go team, simply deferred. But these discussions are dominated not by those people, but instead people telling you why Go is not Rust is not Haskell is not C# is not...
And why shouldn't they? (Well we)
Go has design problems (beside the lack of Generics) the same way PHP has or JS has.
And it's criticized in a similar manner as when JS is brought up its type coercion is mentioned, or its global by default scope, its confusing this context, etc.
Now you might agree with the above or not. But what you ask is essentially for people that perceive it that way, to not speak, and just let it go.
Isn't the whole point of HN discussion (including about languages), criticism etc? It sure is not about celebrating all languages just because they exist...
And you're right, the Go core team does not seem interested in adding generics anytime soon.
Personally, and this is my opinion, I find myself wondering if old school hackers like Thompson, Pike, and Fitzpatrick (and others) find themselves not needing generics, or that slice/maps are enough, maybe I should ponder that for a while. Ie do they know something I don't? Edit; or maybe the type of software they're creating with go is different than I as a generics user, am creating?
Or maybe their work is mostly creating Go, not using it, so they wouldn't care?
I haven't used Go at all yet, but I'm interested in hearing more about it the good and bad parts, along with other languages. Telling others to not complain at all doesn't do any favors.
Remarkably there has been close to zero promotion of Go on Hacker News. Occasionally various incremental update things appear on the front page, just as there are updates on C# 5, the next version of Java, etc, but there have been shockingly few "Why you should use Go" type posts.
People just use it. They don't advocate it. But when it comes up, inevitably it becomes an advocacy starting point for alternative languages. Somehow every single Go discussion, even about the most banal thing, ends up being about Rust, Haskell, F#, and so on.
Imagine if you were used to using power tools, but all the jobs available forced you to use hammers, screwdrivers, etc. Wouldn't this make you a little angry or at the very least disappointed?
C# does it differently to either - see here:
http://www.jprl.com/Blog/archive/development/2007/Aug-31.htm...
(The section marked ".NET Implementation")
Edit: And here's Anders Hejlsberg talking about the design:
That, at least, is correct. Generics can be erased (compile-time only) or reified (generic type instances exist at runtime).
C# uses reified generics, and Mono creates (created?) a reification for each parameter typeset, Microsoft's implementation creates the same underlying reification for all reference types as a space optimisation, but it still uses reified generics.
There is a good helping of dishonesty in using C++ as the "reified generics" example though, as C++'s templates do significantly more than just reify generics (template specialisation, code generation, etc…) and that added to the interactions between templates and other language features makes them significantly more complex than e.g. C#'s, Rust's, Ceylon's, Kotlin's, and most other instances of reified generics.
I try my best to be objective - obviously this isn't easy. This is intended to be a review of both sides of the arguments. The generics discussion comes up again and again - I made this document to stop arguments going around in circles.
I will go over all the suggestions and add any missing information. Of course, if you have some good overview of some particular generics implementation you can PM me, or simply add that as a comment.
- Eiffel
- Ada
- Modula-3
- D
- MLton
- .NET
- Rust
- Haskell
- OCaml
- Sather
- BETA
- CLU
Even if they overlap, it would be nice to see them being discussed. Not all generics are born alike.
Personally, I don't care any longer. It is still better than just plain C.
Go: still better than just plain C.
Even beats Algol 68: http://cowlark.com/2009-11-15-go/
Isn't the point of the article that Go doesn't actually beat Algol 68?
> The answer is that they're both very, very similar, with much the same level of functionality. They overlap more than they differ.
> Go has more in the way of actual features --- interfaces, channels, maps, defer , fallthough , proper closures --- but Brand X is more consistent with its features. […]
> Go, on the other hand, is full of corner cases. […]
> Most killingly of all, it's full of examples where they did not consult the literature. […]
> Brand X doesn't have any of these issues. Oh, it's got issues all of its own --- for example, the oddities in the reference type system; no varargs functions; no proper object system; the lack of little bits of syntactic sugar like keyworded composite structure literals... but it feels complete in a way that Go doesn't. I can use Brand X to implement nearly all the features of Go. I can't use Go to implement the features of Brand X.
> The only major features that Go has that Brand X doesn't are proper closures, and the interface system. And I'm afraid that's not enough.
> I would rather code in Brand X than Go.
Sort of. The point is that it's not modern at all, that it's actually comparable to Algol 68 without resorting to hyperbole.
In some ways, the article says Go beats it, in some other Algol wins.
Right, so Go does not beat Algol in the end.
And the article does conclude with preferring Algol to Go.
This seems to come up at every discussion about Go. What usually also comes up is how Rust is a much better designed language which solves real problems, while Go merely improves a little over C while leaving most of the same death-traps lying around.
Yet at the same time Go seems to have a much bigger adaptation than Rust. What's up with that? Are Googlers paid to create projects in Go, or are people genuinely happy to have anything which sucks less than C and stamped with a "final" badge of approval?
Well it has to do with Rust not even being 1.0 yet, whereas Go has been stable for 5 years...
Or with Rust changing some syntax in every point release for most of it's design cycle, so even early adopters had a difficult time.
Or maybe with Go having Google behind it, with the increased visibility it entails... (Rust, for one, never had huge Google Developer convention sessions exposing it to thousands of devs -- or any conventions for that matter).
And yet, we're already seen increased adoption for this pre-1.0 rust, major community playahs like Katz getting in the core team, more posts and libs every day, etc...
Go is about capturing dynamic languages' flow of development and put that on top of types and static compilation so you can improve early on performance and correctness (That doesn't even include inserting a "generic" way of coding concurrent processes).
Rust is much more about replacing C++ in features (from my little-knowledge POV): provide higher-level constructs to model your problem than raw C, with a heavy control over memory for maximum correctness and performance.
Rust may be better designed, yet I find it much more verbose and harder to understand than Go. While this may be a reason for the difference of adoption, a much bigger reason must be the difference in maturity.
The only features it has regarding that is GC, built-in hash-table and type inference. Hardly the gist of what makes dynamic languages flow a fast/nice one.
Plus Go was also advertised as "systems language" -- and besides, the same kind of programs Go is used for, servers, REST, network infrastructure stuff, etc, Rust will be used for too.
It's not like Rust is only (or primarily) for anything much lower level than Go.
No, the real feature is understanding that a language doesn't stop at the syntax, the tooling and the environment are extremely important:
- unless you want to build multiple binaries in one command, there is no need for any build helper.
- hack-compile-test cycles are really short, to the point you can run simplest go programs as scripts
- go has its own package manager, allowing you to manage dependencies extremely easily (not technically specific to dynamic languages, but in practice often associated with them) (Note that I'd prefer if everything was managed by my OS package manager, but we're not there yet)
The go creators (and community) has spent a lot of effort in improving the overall development environment, and this is a characteristic I have seen more developed in dynamic languages (again, I'm not saying that it's tied to a type of language, but I have seen this more developed with the pythubyerlascripts)
> It's not like Rust is only (or primarily) for anything much lower level than Go.
It's not, It's just targeted at different problems. You wouldn't use Go to build a game engine [1] (you need tight control over memory and have some realtime requirements), and I'm not sure you need the tight control that Rust gives you over memory when you build an image processing server [2] (you'll need concurrency primitives for this)
Why not?! Not all game engines need to be the next CryEngine or Unreal.
https://www.youtube.com/watch?v=cjn3twYB7xQ&list=UU7n_g2xDyS...
https://www.youtube.com/watch?v=uzQ2dnVac3Y&list=UU7n_g2xDyS...
Yet remarkably people are solving real problems with Go. Despite all of these dire predictions and pontifications on here by so many mortally offended by Go's existence, people are simply making solutions and moving on.
I don't believe I've heard of a single significant solution with Rust. I mean, I'm sure one exists somewhere, but it seems that it's caught in the advocacy trap of people talking about how great it is (overwhelmingly in Go discussions, it seems), instead of building solutions with it.
Servo is pretty much the motivating application for the Rust language. So you should keep your eye on that if you're interested.
That said, Rust doesn't have any real applications, because it's not out yet. The core team pretty much states, don't build anything significant in Rust atm.
It'll probably be out next year. Also Rust is a much more difficult language to grok, because it forces you to care about borrows.
That said, yes, before 1.0, you have to be a special kind of person to do such a risky thing. That said, Skylight can't really do it another way.
Also people do that with C, C++, Python, etc etc, so no need to invent Go at all, right?
This overall comparison might be a dead end, though. After all, we're comparing languages that effectively only have in common that they seem to have been spawned at vaguely the same time. Their philosophies are totally different.
Well, so far it looks like Rust resolves real problems in theory. In practice, I just see much more projects made in Go than in Rust. I confess that I didn't go hunting for Rust projects though.
Maybe it's the same as Mercurial vs Git. The latter is more popular, even if it's "worse", according to some.
When it comes to developing software applications, the really weak type system of Go is frankly just causing developer pain. IMHO, generics are the missing feature in this language, just try writing a generic map or reduce function in Go and the amount of code you have to duplicate is ridiculous. Interfaces and using relection is not safe and annoying and having all the XXXInt, XXXFloat, XXXMyType is crazyness too.
For what its worth, my dream language would be Julia's type system grafted onto Go.
This caught my eye because I recall you being someone who has vigorously criticized Go in every single Go discussion. A quick search and I can find lengthy critiques from you going back four years.
It very much seems like you haven't moved on.
https://groups.google.com/forum/#!msg/golang-dev/Zx2uSqvMS0Q...
If you read correctly my post, I just said I would like to see the discussion about generics take into account what other generic systems besides Java and C++ offer.
In those four years as you say, I have never seen such a document, even most discussions on gonuts went around Java, C++ and .NET implementations.
There are mentions that a prototype was made, yet the conclusions haven't been shared with the outside world.
If the designers don't want to implement generics, I can always look to Go as Active Oberon with C like syntax.
I see more value arguing about using Go for user space applications that are still made in C, just because the authors needed a compiled language than arguing about the essence of generics in Go. That boat has long left.
Edit: Just got to read Ian's opinion, quite interesting.
With Julia's type system you get a really good parametric multiple dispatch, which is a completely different (and more satisfying, to me) way to organize code than in Go. Go wouldn't be Go at all with Julia's type system.
If that's what you want, why not just program in Julia?
Although at least in Go and Java the downcast is checked and memory-safe, not so in C.
When you cast from void* to whatever type, the compiler will happily accept it and bad things will happen if the type is wrong. Maybe not right away, thus the program will bleed with corrupt memory.
With Go when you cast to the wrong type, a cast violation will occur and the program will panic right away.
But without the speed of C. D and Rust are both better than C and better than go, while still being as fast as C (ok rust isn't always as fast as C yet, but it is still faster than go).
In fact, gccgo does produce better code than the *g compilers
I remember the days when C code on home computers just sucked and most of us coded in Assembly for games, as C was a business language.
Compiler optimizations take time, even if sharing backends across languages.
No. You can clearly see that I am not doing that simply from reading my post. So, why the strawman?
Alternatives to these are just manual or semi-manual variants. For example, Go people seem to like the "empty interface" approach. Well, that is Java-style type-erasure done manually. The code generation approach is just C++-style instantiation done outside of the compiler.
See the ".Net Implementation" section here:
http://www.jprl.com/Blog/archive/development/2007/Aug-31.htm...
I am not quite sure from the interview what happens about constraint types. It seems the reference is cast into an Interface type (IComparable) and used as such. In other words, boxing.
"... C# does strong type checking when you compile the generic type. For an unconstrained type parameter, like List<T>, the only methods available on values of type T are those that are found on type Object, because those are the only methods we can generally guarantee will exist. So in C# generics, we guarantee that any operation you do on a type parameter will succeed."
Edit (more explicit quote):
"When you say K must implement IComparable, a couple of things happen. On any value of type K, you can now directly access the interface methods without a cast, because semantically in the program it's guaranteed that it will implement that interface. Whenever you try and create an instantiation of that type, the compiler will check that any type you give as the K argument implements IComparable, or else you get a compile time error."
Furthermore (related to the CLR avoiding boxing costs):
"I'm just pointing out that we do fairly aggressive code sharing where it makes sense, but we are also very conscious about not sharing where you want the performance. Typically with value types, you really do care that List<int> is int. You don't want them to be boxed as Objects. Boxing value types is one way we could share, but boy it would be an expensive way."
[1] http://www.weberc2.com/posts/2014/12/12/living-without-gener...
> someone needs to be able to do it to write the libraries he needs to use
I'm not sure what this has to do with what I wrote. As evidenced by the `container/list` package, a generic implementation can be distributed, and we can build our type-safe wrappers around that (if type-safety is really that important in your application--I haven't had much difficulty using the generic container as-is).
I do agree that the boilerplate is inconvenient (pretty much by definition). But it's fortunately also trivial by definition. People seem to think that these wrappers raise the total complexity of the program just because they contribute to the total lines of code (loc) count. Many people also think that if you don't use these type-safe wrappers that your program will be doomed to runtime errors.
I think both of these are big exaggerations, and that's why I wanted to write that post. Even in spite of Go's generics situation (I'm not entirely convinced about the degree to which it's a liability), I still find it to be the most enabling tool in my bucket.
It's one person's summary of a very long and convoluted conversation. That's all.
It's 2014. Generics are a settled deal in programming languages. It's not some syntactic sugar or something the value of which is stull undecided and its advocates might "lack an imagination".
>Use lang2 if you love it so much. Seriously.
Well, some do. That doesn't mean they don't get to complain about something they perceive broken in Go that could be better. Especially if they could use Go (to take advantage of other benefits it might have) if it weren't for those shortcomings.
In general, the statement is analogous to "if you have a problem with X in america, why don't you immigrate", which is silly. If you have a problem, you criticize, and you try to change that. You don't just dismiss everything that's also not problematic.
https://groups.google.com/d/msg/golang-nuts/smT_0BhHfBs/MWwG...
2. generics are about type-safety, not codegen. Codegen can be added on top of parametric polymorphism (e.g. C++ template specialisation), but is not required by any means (C# or Rust don't do any generic-based codegen beyond reification)
Just being able to do very light type insertion and the transparent code generation to go along with it would go a long way.
Boxing and generics are orthogonal concepts.
Also: does auto-boxing even make sense in Go? Between the fact that Go is statically compiled and that there isn't an int / java.lang.Integer dichotomy to resolve, I would assume that the compiler could just do whatever it needed to with primitives, regardless of generics.
Yes, and already happens: interfaces cause wrapping of their content[0] and go does basic escape analysis and automatically allocates things which escape a function on the heap rather than the stack[1]
I don't mean that the manually specialized version is faster than automatically specialized template. Rather that this encourages to not write abstract data-types, but rather concrete types that solve a real world problem - editor.Buffer vs. gap.Buffer. Once you have a real world problem it can optimized much better for that use case.
Now days I think that adding generics to Go will be disaster - Go lacks sound type system and piling generics on top of it will make the thinks even worse.
Once they do, you know not every "generics or bust" will be satisfied and the anti-Go hate will simply shift.
I say let the haters hate and keep generics as their focal point.
Which is the grown up, honest, thing to do.
But I'm not sure about the other thing you mention:
"Maybe but maybe the "Go needs generics" folks will just go away."
Why would they go away?
They ask for Generics because they have found some use for Go (say, because it has a OK standard library, or decent tooling and momentum compared to alternatives), but also found a need this feature.
Neither the "use of Go" they found, nor their need for generics will disappear if the language devs say "no". If anything, as stakeholders in the languge (a user is a stakeholder) they'd be even more pressed to change the language dev's mind -- down to the fork point.
the go-lang team at google is very smart. It's not that they have a huge amount of high-priority work other than generics. Why don't they address a summary of the sentiment on hacker news on generics ?
If you're a language developer, your life is made harder if you have to add generics.
And if your language gets all the people that are easily satisfied with something "static and faster to write than C" why go the extra mile?
Especially if your goal is not building a commercially succesful language, or an advanced language, or a language to solve 2014's problems, but just to hack on what you have created.
Besides, being a great programmer and a great language designer are two different skills. Would a language created by Linus be that good?
No, I don't know that.
Do you suggest they are lying and just hate go out of pure irrational emotion? (Despite some of the critics having writen thousands of lines in Go, or some like pjmlp have even had code in the standard libs).
Is there evidence to suggest that?
Does that hold true for other languages too? When people criticize a specific problem a language/technology has (e.g. Python's GIL or PHP's lack of proper language implementation with AST et al, SOAP for its verbosity, etc), is that out of "haters gonna hate" mentality?
Does that extend to that programmers cannot recognize constant pain points in a language, and those that complain about such things are irrational?
I find the idea expressed in the comment incoherent and illogical itself.
I'd myself be very happy with a hint of generics in Go, though. Something at the package level, that would be instantiated at "import" time (since the import keyword is supposed to hold some magic in itself) would have my preference.
I have been writing Go code professionally nearly every day for 6 months. Would I rather be writing C? Probably. Python? Not on a project of this scale. C++? Toss up. Java? No - doing far to much interfacing to C libs for that. Rust? Probably. Go is far from perfect, but honestly not that bad.
Either way, the example[0] I was greeted with on the homepage[1] is quite awesome. Does it have an actor implementation like Erlang? How does it handle concurrency?
0:
USING: io kernel sequences
http.client xml xml.data xml.traversal ;
"http://factorcode.org" http-get nip string>xml
"a" deep-tags-named
[ "href" attr ] map
[ print ] each
1: http://factorcode.org/Erlang has other advantages, though. 99.9999999% uptime and hot code replacement are easier with it, for instance. Their ideal niches don't completely overlap.
> do you want slow programmers, slow compilers and bloated binaries, or slow execution times?
Easy I want "slow compilers and bloated binaries".
In my experience "bloated binaries" in the real world aren't as bad as one would think, since instruction cache problems only appear when your working set is huge, not when your total binary size is huge.
Equating big binaries with slowness is simply misleading. What's next, increased download times?
> The generic structures are less useful than a concrete one.
Without generics you can't separate algorithms from data structures so everything is much less useful. If the members names are worse, sub-type then rename symbols.
> Generic structures can be less optimized than a concrete solution.
False. That "concrete solution" not only has to be written, but it will also perform identically to an instantiated template.
And type erasure is not a solution, it prevents inlining, constant folding and hoisting. Eg: In C++ std::vector<MyObject>::operator[] has 1 indirection, while using a generic C void* container would have 2. Guess which one is faster?
> Generic algorithms can be less optimized than a concrete solution.
sigh
Also wrong since generics do not prevent specialization if needed. See: static if in D, template specialization in C++.
The "bloated binaries" part is especially odd given the state of the Go compiler's optimisations (or lack thereof):
$ cat >| test.go
package main
func main() {}
^C
$ go build test.go
$ wc -c test
467008 test
$ cat >| test.go
package main
import "fmt"
func main() { fmt.Println("Hello, World!"); }
^C
$ go build test.go
$ wc -c test
1806192 testGenerics is not the only way to separate data and algorithms. I agree that it is possible to sub-type/embed and rename - although looking at generic code, I rarely see that happen.
> That "concrete solution" not only has to be written, but it will also perform identically to an instantiated template.
When you know where exactly the code will be run, it can be possible to create a better package taking into account the context where it will be run. By concrete, I mean a package in a real-world problem.
Basically, abstract things are harder to optimize for a particular case.
Do you see any way other than the 3 ones discussed in the OP article under the label "Generics"?
> When you know where exactly the code will be run, it can be possible to create a better package taking into account the context where it will be run. By concrete, I mean a package in a real-world problem. Basically, abstract things are harder to optimize for a particular case.
I could agree with that if time wasn't limited, but imho building custom data structure/algorithms for each problem will precisely leave less time to optimize for performance since reaching a working state first will be longer without reusable abstractions.
The one I mainly meant was interfaces. Of course there are also DSLs and code generation.
> I could agree with that if time wasn't limited, but imho building custom data structure/algorithms for each problem will precisely leave less time to optimize for performance since reaching a working state first will be longer without reusable abstractions.
I mentioned that in the summary. It's about tradeoffs. Even if all the cons/pros are listed people could still come to different conclusions, because people value different things. And there's nothing wrong about it.
The amount you need to reimplement depends on the amount of available third-party packages - the more good packages there are the less you need to build those custom data structures.