Hacker Newsnew | past | comments | ask | show | jobs | submit | ntrel's commentslogin

My understanding is that RC is relatively expensive in time (especially for atomic RC) but uses a lot less memory than state of the art fast GC. And RC doesn't handle cycles.


D doesn't store capacity in each slice. This allows a slice to fit in registers more often. Instead for GC allocated slices, the GC will store metadata before the first element of the allocation. That does make it slower to access, particularly when the slice points past the first element, but it is cached to speed up repeated accesses to the same allocation. Repeated appending can be further speeded up by using a dedicated Appender type.


Because Go designers don't like OOP and didn't want low-level system programming as core features. They also were not keen on generic programming. Basically they wanted a simpler language. (Then they realized generics are useful, ironically their constraints add complexity). Also they wanted a segmented stack and coroutines + channels as language features.


This compiles:

    ref ubyte[n*2] requires_ptr_twice_as_large_as_input(uint n)
    (
        const ref ubyte[n] input,
        ref ubyte[n*2] output,
    ) {
        output[0..n] = input[0..n];
        output[n..2*n] = input[0..n];
        return output;
    }

    void main()
    {
        ubyte[10] input = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10];
        ubyte[20] output;
        requires_ptr_twice_as_large_as_input!(10)(input, output);

        import std.stdio;
        writeln(output);
        assert(output == input ~ input);
    }


Thank you, neat to see it could be done (I had a hunch!)


Why is your proposal better than this:

  import std.sumtype;
  
  void main(){
   struct A { int a; }
   struct B { string b; }
   struct C { bool c; }
   
   alias TaggedUnion = SumType!(A, B, C);
   
   auto tgu = TaggedUnion(B("hi"));
   int i = tgu.match!(
    (A a) => a.a,
    (B b) => b.b.length,
    (C c) => c.c * 5
   );
   assert(i == 2);
  }
If you miss out a `match` handler for any of A, B, C you get a compile-time error. Or you can use a generic handler which will be instantiated for any type not explicitly handled. https://dlang.org/phobos/std_sumtype.html


I'd take a language that have built in support for tagged union over having to import a module and rely on templates

I know of sumtype, and i think it is a mistake for D to rely on this for such important language feature

I'm not a language dev, so i can't do much to help, using switch/union/enum is more natural, is cleaner, and is easier to add support for IDEs, everyone on the same page

That's in areas like this where the language falls short, and i can see people instead choosing alternatives

https://github.com/dlang/phobos/blob/master/std/sumtype.d

a mess of templates and imports to std.traits

using this will make your compile speed tank.. another reason to avoid

it's very sad that people recommend this instead of asking for built-in version, makes me sometimes reconsider my choice to use the language

if they expect language improvements to be templates, what atrocity will be added next?

this is on the same level as std::bool from C++


https://forum.dlang.org/post/bkgvdewkjwthmlfemnjm@forum.dlan...

> The good news is, I have not put a lot of effort so far into micro-optimizing the compile-time performance of match, so there is almost certainly room for improvement.

it is shame that it ended up in the standard library

once Walter will be gone, i will have no faith in the language anymore


bool is a built-in type in C++...


Class instances can go on the stack too using `scope`:

  scope obj = new Object;
  ...
  // destroyed at end of scope


Lack of generics does not ease development speed. Generic programming is about safe reusability. (Development speed includes the test, debug, fix cycle).

No generics actually harms code clarity and destroys type safety.


Missing generics -- it doesn't destroy type safety, it just forces the developer to write boilerplate variations of every method.

The official stance on that issue is: yeah, but it's better than the hassle of supporting generics (compiler effort, object code size/slowness, and excessive high-level abstraction (a bad thing in the Go world).

I have a foot on both sides: I miss generics when I'm writing one-off low-scalability code, but it's nice to have the speed of low-level Go code, and perversely fun to actually spend some of my coding time writing all those low-level sorting and array-building routines that are the meat of programmer interviews.

Now, when a candidate asks "When will I need to write a method to sort the keys of a map?", I can answer "Every time you use a map[string]T for a novel T!"

I hate novel T now. (<-- This is also a design feature of Go, the passive pressure to not use large hierarchical types, and try to do your work with just maps and slices of primitives)


Most of the time, a combination of interfaces and slices (read: souped up arrays) is enough. In practice, when your arrays don't suck like they do in C, C++, or Java, you can get a lot of work done with them.

It's actually clearer as to what's going on since slices are a language primitive. They are simple and extremely transparent. This is absolutely not the case with Java's collections library or the C++ STL.

It wouldn't be a trade-off if there weren't situations where generics are really useful. But this rings more like an armchair criticism of Go than a criticism from someone who's written some Go programs. For my part, I wish languages like Java were less hostile to arrays.


Arrays and slices really have nothing to do with generic programming. Java has poor generic support (type erasure) and C++ has poor syntax and a bad design for iterators. Languages with decent generics support have none of these problems.

If this is 'armchair criticism' why do Go's designers say they are considering adding generics support?


C's preprocessor means C code can often do interesting tricks, such as the X macro: http://www.drdobbs.com/the-new-c-x-macros/184401387

There are tons of other interesting uses for macros. Obviously I'd rather a language had safer equivalents to a C preprocessor.


> C++ has the best (imperative) language support for templates

D's template support is far superior: static if, constraints, compile-time function execution, string mixins, opDispatch. These features make templates much more practical and more powerful.


Actually it is simple: eat less meat. Meat production is vastly more wasteful than vegetable production calorie-for-calorie.


And that double-espresso fair bean organic latte is vastly more wasteful than a glass of water.

And your sharp looking clothes are far more wasteful than a peasant shirt and plain shorts.

And your smart phone is far more wasteful than a basic phone.

And a house with a yard is vastly more wasteful than a 150 sqft per person apartment.

And do you know how much wastage occurred to make that movie you watched? Or that TV show you like?

Everything can be considered wasteful by comparison. It comes down to balancing your needs/wants with energy requirements, and choosing which causes to bring up when preaching your moral superiority.


Agreed, we have a lot of things which are wasteful compared to spartan requirements. Definitely a sliding scale of luxury. So what are the real costs of meat eating? 10-50x more water for a meat diet, is that moral or practical superiority?


Nice. I saw your edit to change it from "10x" to "10-50x". Moving goalposts are of course much harder to hit.

But regardless, this is what I mean by choosing which causes to bring up when preaching your moral superiority.


None of those things cause as much greenhouse gas emissions as a high meat diet.

The level of meat consumption in rich countries is unjustifiable.


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

Search: