imports and a data structure (any critique welcome)

bearophile bearophileHUGS at lycos.com
Fri Dec 27 04:55:24 PST 2013


Jonathan:

> Thank you.  In reply to [1]: that is an interesting issue that 
> I don't really understand right now.  Can you explain exactly 
> where I invoke undefined behavior?

It can be shown with this function:

int*[] foo() {
     int x;
     int*[] arr = [&x];
     return arr;
}


Here the value 'x' is allocated on the stack, in the stack frame 
of the function foo(). arr is a heap-allocated array, so you can 
return it safely from foo. But arr contains a pointer to x, that 
points still to the stack frame of foo(). When foo() ends, the 
stack space used by the stack frame of foo gets reused for other 
purposes, so now the pointer inside the array arr points to data 
unrelated to the original x, essentially garbage.


> It was my understanding that structs are passed and returned by 
> value, and the assignment
>   x = some struct
> makes a copy of some struct and stores it in x.

This is right. Bit the problem is different.


> Does auto do a simple type inference to find out that Term* 
> should be there?

Right.


> Is there an advantage to using auto?

It makes writing the code faster, the code less cluttered, and 
sometimes the type is "obvious" for the person that reads the 
code. Just don't abuse it.


> I can't seem to put @safe: at the top of the file -- is it the 
> same as compiling with -safe.  Is there a way to add this as a 
> source annotation?

There is a writeln in the main, so you have to use:

void main(string[] args) @system {

But still the code doesn't compile:

temp.d(30): Error: field TermBody.terms cannot be accessed in 
@safe code because it overlaps with a pointer
...

So @safe can't be used here.


> Is ! an operator in e.g. ADT!q ...

! is the "not" operator, but there it's used to instantiate a 
template.


> What is the mixin bit doing?

It probably mixes-in (statically) some code generated at 
compile-time.


> Can you point me towards any tutorials, or should I buy the 
> book?

The book is useful if you want to get serious about learning D. 
Otherwise the online docs, Rosettacode and the book by a person 
that posts often in D.learn could suffice.


> That is odd; I find that D shares a philosophy closer to 
> Haskell than many of the "lower level" languages like C.

In D you can write functional-style code, look at Rosettacode D 
entries for many examples. (Also regarding your first post, D1 
language used to have literary programming built-in, as 
GHC-Haskell, but this feature was dropped in D2).


> However, this is really *not* an algebraic type since sharing
> is not algebraic,

If you share something that is immutable, and you assure there 
are no null pointers, then the fact that is shared is 
transparent, so why is it not algebraic?


>  The only reason I didn't use an object oriented approach off 
> the bat is that I don't think I completely understand when to 
> use a struct versus an object.  Using structs seem to fit the 
> story better, because the structure isn't really emitting any 
> functionality, I just want to perform some functions to it.  So 
> using structs feel like a better fit.  Feel free to correct me 
> here.  What are some of the drawbacks to using object.  How 
> much more time overhead is there once the object is created?

Class instances have some overhead, +2 words of memory, plus a 
bit of time to initialize those fields. Class instances allocated 
on the heap are a bit simpler to use compared to structs handled 
by pointers.


> You are right, I probably look like an idiomless noob!  I 
> totally am!

Don't worry, you are going to learn.


> (there is quite a lot of syntax in D).

D is a system language designed to be simpler to use, and it 
tries to be safer, and it tries to have many of the most useful 
tools. All this leads to a complex language. And the syntax 
reflects the varied semantics of all the things it contains. It's 
not just syntax sugar of the same bits of lambda calculus.


> For now, can you tell me what I could do better about the 
> switch statement

That switch can become an array. Or you can use enumerations with 
"final switch", and so on.


> and what is wrong with (*term).node?

D is a bit smarter than C, so "term.node" suffices.

Bye,
bearophile


More information about the Digitalmars-d-learn mailing list