Re: std.conv - custom string to struct conversion ?

2013-08-01 Thread monarch_dodra

On Friday, 2 August 2013 at 05:09:14 UTC, Jonathan M Davis wrote:

On Friday, August 02, 2013 06:50:01 Douglas Petterson wrote:
Is there a way to convert a string to a struct, similarly to 
the

conversion of a struct to a custom string representation ?

The following code works fine when using format("%s",C) or
to!string(C):

 struct sCustomConv
 {
 string toString()
 {
 return "My custom representation";
 }
 }

 sCustomConv C;
 string MyBackup = to!string(C);

But I can't find which class operator must be overloaded (or 
more

simply how-to) to make this possible:

 C = to!sCustomConv(MyBackup);


http://stackoverflow.com/questions/8351245/override-tot-for-used-defined-t-in-d

- Jonathan M Davis


There was a request for enhancement to provide a "fromString" for 
arbitrary types. The idea is that once we have that, then 
functions such as parse or to!S(string) will be generic, and work 
on mostly anything. Unfortunatly, (AFAIK), nobody is working on 
this.


Here is a discussion I opened:
http://forum.dlang.org/thread/gzodptjyzpqnhxctb...@forum.dlang.org

...and I just noticed it ends with me saying "I'll try to write a 
DIP then :)" and then not doing it :/


Re: std.conv - custom string to struct conversion ?

2013-08-01 Thread Jonathan M Davis
On Friday, August 02, 2013 06:50:01 Douglas Petterson wrote:
> Is there a way to convert a string to a struct, similarly to the
> conversion of a struct to a custom string representation ?
> 
> The following code works fine when using format("%s",C) or
> to!string(C):
> 
>  struct sCustomConv
>  {
>  string toString()
>  {
>  return "My custom representation";
>  }
>  }
> 
>  sCustomConv C;
>  string MyBackup = to!string(C);
> 
> But I can't find which class operator must be overloaded (or more
> simply how-to) to make this possible:
> 
>  C = to!sCustomConv(MyBackup);

http://stackoverflow.com/questions/8351245/override-tot-for-used-defined-t-in-d

- Jonathan M Davis


std.conv - custom string to struct conversion ?

2013-08-01 Thread Douglas Petterson
Is there a way to convert a string to a struct, similarly to the 
conversion of a struct to a custom string representation ?


The following code works fine when using format("%s",C) or 
to!string(C):


struct sCustomConv
{
string toString()
{
return "My custom representation";
}
}

sCustomConv C;
string MyBackup = to!string(C);

But I can't find which class operator must be overloaded (or more 
simply how-to) to make this possible:


C = to!sCustomConv(MyBackup);

Thx.


Re: casts / wildcards for parametrized types

2013-08-01 Thread Ali Çehreli

On 08/01/2013 05:40 PM, tx wrote:

> Thanks for the reply Ali. Everything you wrote makes sense, but I
> think I may have oversimplified the problem in my original email. In
> general I don't care about what T is when working with Box (or
> ConcreteBox as it were), but I do care that Box contains a T. Consider
> this rather contrived example (I'm aware that it's a poorly written
> function, it just captures my issue.):
>
> bool truthy(Item a, Item b){
>if(cast(LongBox) a && cast(LongBox) b){
>  return (cast(LongBox) a).value && (cast(LongBox) a).value;
>} else if(cast(CharBox) a && cast(CharBox) b){
>  return (cast(CharBox) a).value && (cast(CharBox) a).value;
>} else {
>  return !(a is null || b is null);
>}
> }
>
> I would much rather write something like:
>
> bool truthy(Item a, Item b){
>if(cast(Box) a && cast(Box) b){
>  return (cast(Box) a).value && (cast(Box) a).value;
>} else {
>  return !(a is null || b is null);
>}
> }
>
> To be more explicit: By the time I'm writing these if-else/cast
> statements I already know that my objects are both instances of some
> type of Box and I also know that the operation(s) I plan to perform on
> them are valid for any T that box can contain.

Pretty complicated semantics. Something must be wrong there. ;)

Here is a solution that shares the solution between a member function 
and a non-member function. The member returns a three-value enum:


class Item{}

enum Truthy { nonzero_values, has_zero_value, mismatched_type }

class Box(T) : Item {
T value;
//  ...

this(T value)
{
this.value = value;
}

Truthy truthy_(U)(Box!U b)
{
auto rhs = cast(Box!T)b;

if (!rhs) {
return Truthy.mismatched_type;
}

return value && rhs.value
   ? Truthy.nonzero_values
   : Truthy.has_zero_value;
}
}

alias Box!(long) LongBox;
alias Box!(char) CharBox;
//etc.

bool truthy(T0, T1)(Box!T0 lhs, Box!T1 rhs)
{
if (lhs !is null) {
final switch (lhs.truthy_(rhs)) with (Truthy) {
case mismatched_type:
return rhs !is null;

case has_zero_value:
return false;

case nonzero_values:
return true;
}
}

return false;
}

unittest
{
auto l0 = new LongBox(0);
auto l1 = new LongBox(1);
LongBox ln = null;

auto c0 = new CharBox(0);
auto c1 = new CharBox('a');
CharBox cn = null;

// Same types
assert(!truthy(l0, l0));
assert(!truthy(l0, l1));
assert( truthy(l1, l1));
assert(!truthy(ln, l0));
assert(!truthy(l1, ln));
assert(!truthy(ln, ln));

assert(!truthy(c0, c0));
assert(!truthy(c0, c1));
assert( truthy(c1, c1));
assert(!truthy(cn, c0));
assert(!truthy(c1, cn));
assert(!truthy(cn, cn));

// Mixed types
assert( truthy(c0, l1));// mismatched but both are non-null
assert( truthy(l0, c1));
assert( truthy(c1, l1));
assert( truthy(l1, c1));
assert(!truthy(cn, l0));// mismatched but one is null
assert(!truthy(c1, ln));
}

void main()
{}

Ali



Re: casts / wildcards for parametrized types

2013-08-01 Thread tx
Thanks for the reply Ali. Everything you wrote makes sense, but I
think I may have oversimplified the problem in my original email. In
general I don't care about what T is when working with Box (or
ConcreteBox as it were), but I do care that Box contains a T. Consider
this rather contrived example (I'm aware that it's a poorly written
function, it just captures my issue.):

bool truthy(Item a, Item b){
  if(cast(LongBox) a && cast(LongBox) b){
return (cast(LongBox) a).value && (cast(LongBox) a).value;
  } else if(cast(CharBox) a && cast(CharBox) b){
return (cast(CharBox) a).value && (cast(CharBox) a).value;
  } else {
return !(a is null || b is null);
  }
}

I would much rather write something like:

bool truthy(Item a, Item b){
  if(cast(Box) a && cast(Box) b){
return (cast(Box) a).value && (cast(Box) a).value;
  } else {
return !(a is null || b is null);
  }
}

To be more explicit: By the time I'm writing these if-else/cast
statements I already know that my objects are both instances of some
type of Box and I also know that the operation(s) I plan to perform on
them are valid for any T that box can contain.

-tx

--
tx.lowtech-labs.org / t...@lowtech-labs.org


On Thu, Aug 1, 2013 at 5:06 PM, Ali Çehreli  wrote:
> On 08/01/2013 04:28 PM, tx wrote:
>
>> Hi All,
>> Hoping somebody can provide some help here, I have a set of classes
>> that are similar to the following
>>
>> class Item{}
>>
>> class Box(T) : Item {
>>T value;
>>//  ...
>> }
>>
>> //Along with some aliases:
>>
>> alias Box!(long) LongBox;
>> alias Box!(char) CharBox;
>> //etc.
>>
>>
>>
>> I'd like to have a function that operates on instances of Item, but I
>> want to specialize the behavior to handle instances of Box
>> differently. Is there anyway I can upcast Item to Box without
>> specifying the type parameter? In my case I don't really care about
>> what T is, just that I'm working with a Box of something. Currently I
>> have a whole if-else ladder checking to see if I'm working with an
>> instance of each of the aliases and casting appropriately, but I would
>> prefer to just write that once. I guess I'm looking for something like
>> cast(Box). Is this possible?
>>
>> To put it another way, is there a D equivalent to the Java syntax of
>> Box
>
> Inserting another layer to the hierarchy is a solution. ConcreteBox is the
> same as your Box and the new Box in a non-template intermediate class:
>
> class Item{}
>
> class Box : Item{}
>
> class ConcreteBox(T) : Box {
>   T value;
>   //  ...
> }
>
> alias ConcreteBox!(long) LongBox;
> alias ConcreteBox!(char) CharBox;
> //etc.
>
> // Explicit check
> int foo(Item item)
> {
> if (cast(Box)item) {
> return 1;
> }
>
> return 0;
> }
>
> unittest
> {
> assert(foo(new Item()) == 0);
> assert(foo(new LongBox()) == 1);
> assert(foo(new CharBox()) == 1);
> }
>
> // Automatic dispatch for compile-time binding
> class Foo
> {
> int foo(Item item)
> {
> return 0;
> }
>
> int foo(Box box)
> {
> return 1;
> }
> }
>
> unittest
> {
> auto f = new Foo();
> assert(f.foo(new Item()) == 0);
> assert(f.foo(new LongBox()) == 1);
> assert(foo(new CharBox()) == 1);
> }
>
> void main()
> {}
>
> Ali
>


Get attributes of type by string name

2013-08-01 Thread JS
how can I get the UDA's of a type that I only know by name and 
only in a CTFE.


I would like to loop over an array of names passed to a me(I 
don't know their contents beforehand) and get the attributes.


I've tried to use a mixin but I can't get the mixin to work on 
the string name...


e.g., mixin("alias a = __traits(getAttributes, "~type~");");


Re: casts / wildcards for parametrized types

2013-08-01 Thread Meta

On Friday, 2 August 2013 at 00:44:21 UTC, Meta wrote:
One more way, not necessarily a workaround but a little trick 
that doesn't require you to know the exact type of box, is to 
use typeof(box).


auto box = Box!int();
auto item = cast(Item)box;
auto box2 = cast(typeof(box));


Whoops, make that last line:

auto box2 = cast(typeof(box))item;


Re: casts / wildcards for parametrized types

2013-08-01 Thread Meta
One more way, not necessarily a workaround but a little trick 
that doesn't require you to know the exact type of box, is to use 
typeof(box).


auto box = Box!int();
auto item = cast(Item)box;
auto box2 = cast(typeof(box));



Re: are mixin string templates with functions removed?

2013-08-01 Thread Dicebot

On Thursday, 1 August 2013 at 23:15:47 UTC, Dicebot wrote:

On Thursday, 1 August 2013 at 22:59:14 UTC, Dicebot wrote:

...


To further clarify this, I have used your simplified example:


And in case someone thinks template functions are treated any 
differently, "string generator(T)(T a)" acts exactly the same.


Re: casts / wildcards for parametrized types

2013-08-01 Thread Ali Çehreli

On 08/01/2013 04:28 PM, tx wrote:

> Hi All,
> Hoping somebody can provide some help here, I have a set of classes
> that are similar to the following
>
> class Item{}
>
> class Box(T) : Item {
>T value;
>//  ...
> }
>
> //Along with some aliases:
>
> alias Box!(long) LongBox;
> alias Box!(char) CharBox;
> //etc.
>
>
>
> I'd like to have a function that operates on instances of Item, but I
> want to specialize the behavior to handle instances of Box
> differently. Is there anyway I can upcast Item to Box without
> specifying the type parameter? In my case I don't really care about
> what T is, just that I'm working with a Box of something. Currently I
> have a whole if-else ladder checking to see if I'm working with an
> instance of each of the aliases and casting appropriately, but I would
> prefer to just write that once. I guess I'm looking for something like
> cast(Box). Is this possible?
>
> To put it another way, is there a D equivalent to the Java syntax of 
Box


Inserting another layer to the hierarchy is a solution. ConcreteBox is 
the same as your Box and the new Box in a non-template intermediate class:


class Item{}

class Box : Item{}

class ConcreteBox(T) : Box {
  T value;
  //  ...
}

alias ConcreteBox!(long) LongBox;
alias ConcreteBox!(char) CharBox;
//etc.

// Explicit check
int foo(Item item)
{
if (cast(Box)item) {
return 1;
}

return 0;
}

unittest
{
assert(foo(new Item()) == 0);
assert(foo(new LongBox()) == 1);
assert(foo(new CharBox()) == 1);
}

// Automatic dispatch for compile-time binding
class Foo
{
int foo(Item item)
{
return 0;
}

int foo(Box box)
{
return 1;
}
}

unittest
{
auto f = new Foo();
assert(f.foo(new Item()) == 0);
assert(f.foo(new LongBox()) == 1);
assert(foo(new CharBox()) == 1);
}

void main()
{}

Ali



Re: Homework help, guys!

2013-08-01 Thread John Colvin

On Thursday, 1 August 2013 at 23:48:33 UTC, Timon Gehr wrote:

On 08/02/2013 01:34 AM, hunt wrote:
Hello, guys. It is weird to ask about my homework here, but I 
haven't

gotten a proper answer yet. It's about D feature...maybe..

http://dpaste.dzfl.pl/905d6ad7

Question is that "Investigate how D allows you to defend your 
definition

of Map so that it may be used only with a type of key that is
comparable, and place this defense in your solution."

Please leave your comments here. Thank you so much.





This should get you started:

http://dlang.org/concepts.html
http://dlang.org/traits.html#compiles


Also, say hello to the most esoteric expression I can think of: 
D's "is" expression


http://dlang.org/expression.html#IsExpression


Re: Homework help, guys!

2013-08-01 Thread Timon Gehr

On 08/02/2013 01:34 AM, hunt wrote:

Hello, guys. It is weird to ask about my homework here, but I haven't
gotten a proper answer yet. It's about D feature...maybe..

http://dpaste.dzfl.pl/905d6ad7

Question is that "Investigate how D allows you to defend your definition
of Map so that it may be used only with a type of key that is
comparable, and place this defense in your solution."

Please leave your comments here. Thank you so much.





This should get you started:

http://dlang.org/concepts.html
http://dlang.org/traits.html#compiles



casts / wildcards for parametrized types

2013-08-01 Thread tx
Hi All,
Hoping somebody can provide some help here, I have a set of classes
that are similar to the following

class Item{}

class Box(T) : Item {
  T value;
  //  ...
}

//Along with some aliases:

alias Box!(long) LongBox;
alias Box!(char) CharBox;
//etc.



I'd like to have a function that operates on instances of Item, but I
want to specialize the behavior to handle instances of Box
differently. Is there anyway I can upcast Item to Box without
specifying the type parameter? In my case I don't really care about
what T is, just that I'm working with a Box of something. Currently I
have a whole if-else ladder checking to see if I'm working with an
instance of each of the aliases and casting appropriately, but I would
prefer to just write that once. I guess I'm looking for something like
cast(Box). Is this possible?

To put it another way, is there a D equivalent to the Java syntax of Box


-tx

--
tx.lowtech-labs.org / t...@lowtech-labs.org


Homework help, guys!

2013-08-01 Thread hunt
Hello, guys. It is weird to ask about my homework here, but I 
haven't gotten a proper answer yet. It's about D feature...maybe..


http://dpaste.dzfl.pl/905d6ad7

Question is that "Investigate how D allows you to defend your 
definition of Map so that it may be used only with a type of key 
that is comparable, and place this defense in your solution."


Please leave your comments here. Thank you so much.





Re: are mixin string templates with functions removed?

2013-08-01 Thread Dicebot

On Thursday, 1 August 2013 at 22:59:14 UTC, Dicebot wrote:

...


To further clarify this, I have used your simplified example:

-
// test.d
string generator(int x)
{
if (x > 0)
{
asm
{
mov EAX, 0xDEAD;
}
}
return "return 42;";
}

int main()
{
mixin(generator(0));
}
-
$ dmd -release -inline -O test.d
-
$ objdump -d test | grep dead
  417705:   b8 ad de 00 00  mov$0xdead,%eax


Re: are mixin string templates with functions removed?

2013-08-01 Thread Dicebot

On Thursday, 1 August 2013 at 22:42:11 UTC, JS wrote:

I don't know why it is so damn confusing...

I didn't say templates, I SAID string mixins of templates.


Symbol emitting does not go that way. Object files are old school 
entities from C times. They have function symbol and type 
symbols. Templates, mixins - does not matter. If function is used 
- it goes to object file. If struct definition gets generated - 
same story. In the world of linker there are no things such as 
templates or anything like that.


Re: are mixin string templates with functions removed?

2013-08-01 Thread JS

On Thursday, 1 August 2013 at 22:26:06 UTC, Dicebot wrote:

On Thursday, 1 August 2013 at 22:04:57 UTC, JS wrote:
IS A GOING TO BE IN THE BINARY?!?!?! Yes, I'm yelling... just 
to get the point across about the question I'm trying to get 
answered.


HOW MANY TIMES I NEED TO ANSWER YOUR QUESTION FOR YOU TO NOTICE?

Yes.



UM, NO, BECAUSE YOU ARE NOT ANSWERING MY QUESTION!

I don't know why it is so damn confusing...

I didn't say templates, I SAID string mixins of templates.

I did a test

http://dpaste.dzfl.pl/d8e6ca2a

http://dpaste.dzfl.pl/a43b923c

What is weird, on my comp, the file sizes are exactly the same, 
searching for the string only shows up in the one with the 
template call.


So It seems the dmd does not add code for string mixins(even 
though the function is called, it is smart enough not to add it 
to the binary)... unless it is somehow encrypting the 
template(again, I would expect the file size to be smaller... 
unless it does some type of alignment/padding).




Re: are mixin string templates with functions removed?

2013-08-01 Thread JS

On Thursday, 1 August 2013 at 22:13:25 UTC, John Colvin wrote:

On Thursday, 1 August 2013 at 22:04:57 UTC, JS wrote:

IS A GOING TO BE IN THE BINARY?!?!?!


Why don't you try it and see? Disassemble the object file or 
get your linker of choice to print out some info.


I don't have any of the tools to do so at the moment. The point 
was to see if anyone actually knew this specifically or was just 
guessing on what should be... I guess I have my answer(e.g., find 
out yourself = I don't know).




Re: are mixin string templates with functions removed?

2013-08-01 Thread Dicebot

On Thursday, 1 August 2013 at 22:04:57 UTC, JS wrote:
IS A GOING TO BE IN THE BINARY?!?!?! Yes, I'm yelling... just 
to get the point across about the question I'm trying to get 
answered.


HOW MANY TIMES I NEED TO ANSWER YOUR QUESTION FOR YOU TO NOTICE?

Yes.


Re: are mixin string templates with functions removed?

2013-08-01 Thread John Colvin

On Thursday, 1 August 2013 at 22:04:57 UTC, JS wrote:

IS A GOING TO BE IN THE BINARY?!?!?!


Why don't you try it and see? Disassemble the object file or get 
your linker of choice to print out some info.


Re: are mixin string templates with functions removed?

2013-08-01 Thread JS

On Thursday, 1 August 2013 at 21:17:34 UTC, H. S. Teoh wrote:

On Thu, Aug 01, 2013 at 10:06:54PM +0200, JS wrote:
[...]

Now are you telling me that

template A()
{
void foo() { writeln("asdf"); }
}
void main()
{
A!().foo();
}

does not create a function foo in the binary? That it is 
equivalent

to just calling writeln("asdf"); directly? (exact same code)

[...]

I said that every instantiation of a template creates a copy of
everything inside. Therefore, A!().foo() will create a copy of 
A.foo()

in the binary.

The template itself has no binary representation, in the sense 
that if

you write:

template A(int x) {
void foo() { writeln(x); }
}

there is nothing in the binary corresponding with the template 
A, or the
uninstantiated function foo. But if you instantiate A with some 
value of
x, then you will get a copy of A.foo for every value of x that 
you

instantiate the template with. So if you write:

A!1.foo();
A!2.foo();
A!3.foo();

Then you will get 3 copies of foo() in your executable, one for 
each

value of x.




yes, I understand that... now use a template for a string 
mixin!


template A()
{
string A() { ... }
}

...

mixin(A());

IS A GOING TO BE IN THE BINARY?!?!?! Yes, I'm yelling... just to 
get the point across about the question I'm trying to get 
answered.


the function A is never used at runtime SO it should technically 
not be in the binary UNLESS dmd treats it as a normal template 
function then it will(but shouldn't)!


e.g.,

if the compiler smart enough to realize that A(); is different 
from mixin(A());


(one being compile time and the other not)




Re: are mixin string templates with functions removed?

2013-08-01 Thread Dicebot

On Thursday, 1 August 2013 at 21:38:15 UTC, Tofu Ninja wrote:
This scares me, it seems to me that the unused import should 
not be compiled in. And I frequently hear people talk about the 
linker removing unused code, but this proves that it doesn't or 
at least not all.


It does not. People talk about this because it seems reasonable. 
But reality differs a lot. No need to ask - just go an check.


Re: are mixin string templates with functions removed?

2013-08-01 Thread Tofu Ninja

On Thursday, 1 August 2013 at 20:06:56 UTC, JS wrote:

the binary file is is 150kB. If I add import std.stdio; It 
jumps to 300kB.


This scares me, it seems to me that the unused import should not 
be compiled in. And I frequently hear people talk about the 
linker removing unused code, but this proves that it doesn't or 
at least not all.


I wonder if this is a matter of something that is possible but 
just not implemented properly(or at all, i don't know) in the 
linker, or if their is some reason that makes this not possible.


Re: are mixin string templates with functions removed?

2013-08-01 Thread H. S. Teoh
On Thu, Aug 01, 2013 at 10:06:54PM +0200, JS wrote:
[...]
> Now are you telling me that
> 
> template A()
> {
> void foo() { writeln("asdf"); }
> }
> void main()
> {
>   A!().foo();
> }
> 
> does not create a function foo in the binary? That it is equivalent
> to just calling writeln("asdf"); directly? (exact same code)
[...]

I said that every instantiation of a template creates a copy of
everything inside. Therefore, A!().foo() will create a copy of A.foo()
in the binary.

The template itself has no binary representation, in the sense that if
you write:

template A(int x) {
void foo() { writeln(x); }
}

there is nothing in the binary corresponding with the template A, or the
uninstantiated function foo. But if you instantiate A with some value of
x, then you will get a copy of A.foo for every value of x that you
instantiate the template with. So if you write:

A!1.foo();
A!2.foo();
A!3.foo();

Then you will get 3 copies of foo() in your executable, one for each
value of x.


T

-- 
What do you get if you drop a piano down a mineshaft? A flat minor.


Re: are mixin string templates with functions removed?

2013-08-01 Thread JS

On Thursday, 1 August 2013 at 18:09:54 UTC, H. S. Teoh wrote:

On Thu, Aug 01, 2013 at 07:52:28PM +0200, JS wrote:

On Thursday, 1 August 2013 at 17:47:00 UTC, H. S. Teoh wrote:
>On Thu, Aug 01, 2013 at 07:12:51PM +0200, John Colvin wrote:
>>On Thursday, 1 August 2013 at 17:09:07 UTC, JS wrote:
>>>If I have a bunch of templates that are only used for code
>>>generation, are they removed in the binary(since they are 
>>>not

>>>needed)?
>>
>>templates don't exist in binaries.
>
>Templates are like cookie molds, you use them to generate 
>lots of
>(almost) identical cookies, but you never serve the mold to 
>the

>customer. ;-)
>
>
>T

But what about the functions that exist in them?


Like I said, cookie molds. You use the mold to press cookies, 
but only
the cookies are served, not the mold. The mold may be very 
complicated,
containing subcookies attached to bigger cookies, but whatever 
is
pressed (i.e., instantiated) is what's served on the dinner 
plate. The

mold always remains in the kitchen.



template A()
{
void A()
{
B();
}
void B() { }
}

is everything in the template removed 100% or is there junk 
that the

compiler doesn't remove?


There is nothing to remove. If you instantiated the template, 
then you
get a copy of everything in it. The number of copies equals the 
number
of distinct instantiations. The template itself is just a mold, 
an
abstract entity that doesn't exist in binary form. What it does 
is to
serve as a mold (hence, "template") to make code. So if you use 
to make
10 copies of the code, that's what you'll get in your 
executable. If
your template contains 5 functions, then each instantiation 
produces 5

copies of those functions. Simple as that.

Of course, not all code produces binary data -- enum and alias
definitions don't produce any binary code, for example -- 
they're just
logical entities that only exist at compile time. So if you 
have an enum
inside a template, it will get copied however many times you 
instantiate
the template, but none of those copies end up in the executable 
because

they're just declarations, not actual code or data.



Ok, I'm not talking about the template itself but what is 
contained in the template. It is obvious that templates can 
"insert" stuff into the binary.


a mixin template can easily do that.


Now are you telling me that

template A()
{
void foo() { writeln("asdf"); }
}
void main()
{
A!().foo();
}

does not create a function foo in the binary? That it is 
equivalent to just calling writeln("asdf"); directly? (exact same 
code)


e.g., it is the same as

void main() { A!().foo(); }

cause when I actually debug I see a function call to foo.

So, saying that templates are like cookie cutter doesn't prove 
anything.


If I have

void main() { }

the binary file is is 150kB. If I add import std.stdio; It jumps 
to 300kB.


So the linker and compiler are not removing all untouched code.




Re: What would be the best way to compile a project with GDC?

2013-08-01 Thread Dicebot

On Thursday, 1 August 2013 at 17:46:07 UTC, Gary Willoughby wrote:
There must be a simpler way to pass these files to dmd in the 
right order? rdmd does it somehow.


You do know that you can use GDC with rdmd? `rdmd 
--compiler=gdmd` afair.


Anyway, rdmd does it my checking dmd verbose output that lists 
all imports, as well as most other D build systems I am aware of.


Re: are mixin string templates with functions removed?

2013-08-01 Thread Dicebot

On Thursday, 1 August 2013 at 18:09:54 UTC, H. S. Teoh wrote:
See for yourself: run a disassembler on the result (preferably 
filtered
through ddemangle so the symbols are actually readable) and see 
what's
included and what's not. On Posix, you can use objdump or nm 
(if you use
nm, though, keep in mind that not all symbols correspond with 
actual
code/data, but they do take up a little space in the executable 
-- at

least enough to store their names).


Done it, see my previous comment here. I do have an idea how to 
fix it, but

wasn't able to get though dmd code so far :(


Re: are mixin string templates with functions removed?

2013-08-01 Thread Dicebot

On Thursday, 1 August 2013 at 17:53:38 UTC, Ali Çehreli wrote:
I think the question is whether the instantiations of such 
templates are removed. If the instance is used only to 
initialize an enum, the function shouldn't stay in the binary.


Even if the function remains, I think the linker takes care of 
removing unused functions.


Ali


Unfortunately, you are wrong. No symbol optimization is done by 
DMD is linker can't figure this out on its own, it requires 
specific object file layout to do reference counting for symbols.


It is really easy to check - make template function with some 
anchor value inside (OXDEADBEEF) and compile it with this 
template used exclusively in constraints or CTFE. Then strip and 
objdump - you'll find anchors in resulting binary for every 
instantiation.


Re: What would be the best way to compile a project with GDC?

2013-08-01 Thread Johannes Pfau
Am Thu, 01 Aug 2013 19:46:05 +0200
schrieb "Gary Willoughby" :

> I've just finished a project in D and have been using rdmd to 
> compile during testing. While this is nice, i now want to try 
> other compilers to see if i get any speed gains.
> 
> Because i use rdmd it takes care of passing everything to dmd. 
> Now i want to try GDC and i need to pass the files in the correct 
> order for compilation. I've first tried to write a bash script 
> with all the files listed correctly and passed all the necessary 
> flags to dmd but i can never get the order of the files correct.
> 
> There must be a simpler way to pass these files to dmd in the 
> right order? rdmd does it somehow.
> 
> Any ideas? How do you handle compiling projects with 50+ source 
> files?

Doesn't rdmd have a verbose flag or something to dump the executed
commands? Then you could just copy and paste it from there. You could
also try to make rdmd work with gdc but I think there was some problem
with rdmd and gdc.


Re: are mixin string templates with functions removed?

2013-08-01 Thread H. S. Teoh
On Thu, Aug 01, 2013 at 07:52:28PM +0200, JS wrote:
> On Thursday, 1 August 2013 at 17:47:00 UTC, H. S. Teoh wrote:
> >On Thu, Aug 01, 2013 at 07:12:51PM +0200, John Colvin wrote:
> >>On Thursday, 1 August 2013 at 17:09:07 UTC, JS wrote:
> >>>If I have a bunch of templates that are only used for code
> >>>generation, are they removed in the binary(since they are not
> >>>needed)?
> >>
> >>templates don't exist in binaries.
> >
> >Templates are like cookie molds, you use them to generate lots of
> >(almost) identical cookies, but you never serve the mold to the
> >customer. ;-)
> >
> >
> >T
> 
> But what about the functions that exist in them?

Like I said, cookie molds. You use the mold to press cookies, but only
the cookies are served, not the mold. The mold may be very complicated,
containing subcookies attached to bigger cookies, but whatever is
pressed (i.e., instantiated) is what's served on the dinner plate. The
mold always remains in the kitchen.


> template A()
> {
> void A()
> {
> B();
> }
> void B() { }
> }
> 
> is everything in the template removed 100% or is there junk that the
> compiler doesn't remove?

There is nothing to remove. If you instantiated the template, then you
get a copy of everything in it. The number of copies equals the number
of distinct instantiations. The template itself is just a mold, an
abstract entity that doesn't exist in binary form. What it does is to
serve as a mold (hence, "template") to make code. So if you use to make
10 copies of the code, that's what you'll get in your executable. If
your template contains 5 functions, then each instantiation produces 5
copies of those functions. Simple as that.

Of course, not all code produces binary data -- enum and alias
definitions don't produce any binary code, for example -- they're just
logical entities that only exist at compile time. So if you have an enum
inside a template, it will get copied however many times you instantiate
the template, but none of those copies end up in the executable because
they're just declarations, not actual code or data.


> Oh... and I'm not talking about theoretical... I'm talking about
> what dmd actually does.

See for yourself: run a disassembler on the result (preferably filtered
through ddemangle so the symbols are actually readable) and see what's
included and what's not. On Posix, you can use objdump or nm (if you use
nm, though, keep in mind that not all symbols correspond with actual
code/data, but they do take up a little space in the executable -- at
least enough to store their names).


T

-- 
MACINTOSH: Most Applications Crash, If Not, The Operating System Hangs


Re: are mixin string templates with functions removed?

2013-08-01 Thread John Colvin

On Thursday, 1 August 2013 at 17:57:28 UTC, JS wrote:

On Thursday, 1 August 2013 at 17:53:38 UTC, Ali Çehreli wrote:

On 08/01/2013 10:45 AM, H. S. Teoh wrote:

On Thu, Aug 01, 2013 at 07:12:51PM +0200, John Colvin wrote:

On Thursday, 1 August 2013 at 17:09:07 UTC, JS wrote:

If I have a bunch of templates that are only used for code
generation, are they removed in the binary(since they are 
not

needed)?


templates don't exist in binaries.


Templates are like cookie molds, you use them to generate 
lots of
(almost) identical cookies, but you never serve the mold to 
the

customer. ;-)


T



I think the question is whether the instantiations of such 
templates are removed. If the instance is used only to 
initialize an enum, the function shouldn't stay in the binary.


Even if the function remains, I think the linker takes care of 
removing unused functions.


Ali


I have a lot of code generation templates(only for code). I 
want to make sure they don't hang around in the binary(even 
strings they use) as there is no point and it is potentially 
dangerous(security issues).


The linker will get rid of anything not needed. Marking things as 
package (or more restrictive) will make sure they don't stay in 
librarys when not used.


Ultimately, if you're worried about it, get the linker to print a 
list of all functions, or check the assembly.


Re: Emulating enums

2013-08-01 Thread JS

On Thursday, 1 August 2013 at 16:36:34 UTC, Ali Çehreli wrote:

On 08/01/2013 03:29 AM, JS wrote:

> On Thursday, 1 August 2013 at 05:22:46 UTC, Ali Çehreli wrote:
>> On 07/31/2013 06:10 PM, JS wrote:
>>> http://dpaste.dzfl.pl/dbb40dbc
>>>
>>> The code was pared down from a lot of string mixin code
generation. I
>>> nest the structs because I want a nested enums. I don't
want have to
>>> have eState and eStateType but eState and eState.Type.
>>>
>>> Having the ability to nest enums would solve my problem.
>>>
>>> Regardless, I can almost achieve the effect with nested
structs but not
>>> quite.
>>>
>>> In the code, I cannot assign to the struct for some reason
even with
>>> alias this on iB, which should make State act like the int
Value.
>>>
>>> i.e.,
>>>
>>> b.State.Value = Enums.State.A;
>>>
>>> works but
>>>
>>> b.State = Enums.State.A;
>>>
>>> doesn't
>>>
>>> It maybe some stupid error on my part but I can't keep my
eyes open
>>> enough to figure it out...
>>>
>>>
>>>
>>
>> For that assignment to work, the left-hand side must be
assignable.
>> However, the property function State() returns Enums.eState
by-value.
>>
>> The following has the same issue:
>>
>> struct S
>> {
>> int i_;
>>
>> @property int i() {
>> return i_;
>> }
>>
>> alias i this;
>> }
>>
>> void main()
>> {
>> auto s = S();
>> s = 42;
>> assert(s.i == 42);
>> }
>>
>> Error: cannot implicitly convert expression (42) of type int
to S
>>
>> To compile, i() must return an lvalue:
>>
>> @property ref int i() {

Although, what I said seems more like a workaround because you 
already had a setter @property. You shouldn't need to make the 
getter return a reference as well... I guess...


I think what is at play here is the current implementation 
limitation of "a single 'alias this' per type." I think 'alias 
this' happens to pick the getter perhaps because the getter 
function is defined first in the class. I don't know...


Ali


So, a ref'ed getter is the same as a setter?

Also, it would see, I'm guessing, that using alias this on a 
property and having to ref will bypass the setter?





Re: are mixin string templates with functions removed?

2013-08-01 Thread JS

On Thursday, 1 August 2013 at 17:53:38 UTC, Ali Çehreli wrote:

On 08/01/2013 10:45 AM, H. S. Teoh wrote:

On Thu, Aug 01, 2013 at 07:12:51PM +0200, John Colvin wrote:

On Thursday, 1 August 2013 at 17:09:07 UTC, JS wrote:

If I have a bunch of templates that are only used for code
generation, are they removed in the binary(since they are not
needed)?


templates don't exist in binaries.


Templates are like cookie molds, you use them to generate lots 
of

(almost) identical cookies, but you never serve the mold to the
customer. ;-)


T



I think the question is whether the instantiations of such 
templates are removed. If the instance is used only to 
initialize an enum, the function shouldn't stay in the binary.


Even if the function remains, I think the linker takes care of 
removing unused functions.


Ali


I have a lot of code generation templates(only for code). I want 
to make sure they don't hang around in the binary(even strings 
they use) as there is no point and it is potentially 
dangerous(security issues).


Re: What would be the best way to compile a project with GDC?

2013-08-01 Thread H. S. Teoh
On Thu, Aug 01, 2013 at 07:46:05PM +0200, Gary Willoughby wrote:
> I've just finished a project in D and have been using rdmd to
> compile during testing. While this is nice, i now want to try other
> compilers to see if i get any speed gains.

Based on my experience, you will, with gdc / ldc. The optimizers in
gdc/ldc are much more mature than in dmd; I've compared the disassembly
and measured running times with gdc -O3 vs. dmd -O, and gdc consistently
produces code that performs 20-30% faster. YMMV, of course, since the
exact amount of speed gain depends on what your code does.


> Because i use rdmd it takes care of passing everything to dmd. Now i
> want to try GDC and i need to pass the files in the correct order for
> compilation. I've first tried to write a bash script with all the
> files listed correctly and passed all the necessary flags to dmd
> but i can never get the order of the files correct.

Huh? It shouldn't matter what order the files are. If it does, it sounds
like a bug!


> There must be a simpler way to pass these files to dmd in the right
> order? rdmd does it somehow.
> 
> Any ideas? How do you handle compiling projects with 50+ source
> files?

Use a real build system. ;-)  I recommend SCons (http://scons.org/) or
tup (http://gittup.org/tup/). Both require some amount of learning to
use effectively, though. If all else fails there's always makefiles, but
I rather use them only as a last resort.


T

-- 
Life is unfair. Ask too much from it, and it may decide you don't deserve what 
you have now either.


Re: are mixin string templates with functions removed?

2013-08-01 Thread JS

On Thursday, 1 August 2013 at 17:47:00 UTC, H. S. Teoh wrote:

On Thu, Aug 01, 2013 at 07:12:51PM +0200, John Colvin wrote:

On Thursday, 1 August 2013 at 17:09:07 UTC, JS wrote:
>If I have a bunch of templates that are only used for code
>generation, are they removed in the binary(since they are not
>needed)?

templates don't exist in binaries.


Templates are like cookie molds, you use them to generate lots 
of

(almost) identical cookies, but you never serve the mold to the
customer. ;-)


T


But what about the functions that exist in them?

e.g.,

template A()
{
void A()
{
B();
}
void B() { }
}

is everything in the template removed 100% or is there junk that 
the compiler doesn't remove?



Oh... and I'm not talking about theoretical... I'm talking about 
what dmd actually does.


Re: are mixin string templates with functions removed?

2013-08-01 Thread Ali Çehreli

On 08/01/2013 10:45 AM, H. S. Teoh wrote:

On Thu, Aug 01, 2013 at 07:12:51PM +0200, John Colvin wrote:

On Thursday, 1 August 2013 at 17:09:07 UTC, JS wrote:

If I have a bunch of templates that are only used for code
generation, are they removed in the binary(since they are not
needed)?


templates don't exist in binaries.


Templates are like cookie molds, you use them to generate lots of
(almost) identical cookies, but you never serve the mold to the
customer. ;-)


T



I think the question is whether the instantiations of such templates are 
removed. If the instance is used only to initialize an enum, the 
function shouldn't stay in the binary.


Even if the function remains, I think the linker takes care of removing 
unused functions.


Ali



What would be the best way to compile a project with GDC?

2013-08-01 Thread Gary Willoughby
I've just finished a project in D and have been using rdmd to 
compile during testing. While this is nice, i now want to try 
other compilers to see if i get any speed gains.


Because i use rdmd it takes care of passing everything to dmd. 
Now i want to try GDC and i need to pass the files in the correct 
order for compilation. I've first tried to write a bash script 
with all the files listed correctly and passed all the necessary 
flags to dmd but i can never get the order of the files correct.


There must be a simpler way to pass these files to dmd in the 
right order? rdmd does it somehow.


Any ideas? How do you handle compiling projects with 50+ source 
files?


Re: are mixin string templates with functions removed?

2013-08-01 Thread H. S. Teoh
On Thu, Aug 01, 2013 at 07:12:51PM +0200, John Colvin wrote:
> On Thursday, 1 August 2013 at 17:09:07 UTC, JS wrote:
> >If I have a bunch of templates that are only used for code
> >generation, are they removed in the binary(since they are not
> >needed)?
> 
> templates don't exist in binaries.

Templates are like cookie molds, you use them to generate lots of
(almost) identical cookies, but you never serve the mold to the
customer. ;-)


T

-- 
He who does not appreciate the beauty of language is not worthy to bemoan its 
flaws.


Re: are mixin string templates with functions removed?

2013-08-01 Thread John Colvin

On Thursday, 1 August 2013 at 17:09:07 UTC, JS wrote:
If I have a bunch of templates that are only used for code 
generation, are they removed in the binary(since they are not 
needed)?


templates don't exist in binaries.


are mixin string templates with functions removed?

2013-08-01 Thread JS
If I have a bunch of templates that are only used for code 
generation, are they removed in the binary(since they are not 
needed)?




Re: Emulating enums

2013-08-01 Thread JS

On Thursday, 1 August 2013 at 16:36:34 UTC, Ali Çehreli wrote:

On 08/01/2013 03:29 AM, JS wrote:

> On Thursday, 1 August 2013 at 05:22:46 UTC, Ali Çehreli wrote:
>> On 07/31/2013 06:10 PM, JS wrote:
>>> http://dpaste.dzfl.pl/dbb40dbc
>>>
>>> The code was pared down from a lot of string mixin code
generation. I
>>> nest the structs because I want a nested enums. I don't
want have to
>>> have eState and eStateType but eState and eState.Type.
>>>
>>> Having the ability to nest enums would solve my problem.
>>>
>>> Regardless, I can almost achieve the effect with nested
structs but not
>>> quite.
>>>
>>> In the code, I cannot assign to the struct for some reason
even with
>>> alias this on iB, which should make State act like the int
Value.
>>>
>>> i.e.,
>>>
>>> b.State.Value = Enums.State.A;
>>>
>>> works but
>>>
>>> b.State = Enums.State.A;
>>>
>>> doesn't
>>>
>>> It maybe some stupid error on my part but I can't keep my
eyes open
>>> enough to figure it out...
>>>
>>>
>>>
>>
>> For that assignment to work, the left-hand side must be
assignable.
>> However, the property function State() returns Enums.eState
by-value.
>>
>> The following has the same issue:
>>
>> struct S
>> {
>> int i_;
>>
>> @property int i() {
>> return i_;
>> }
>>
>> alias i this;
>> }
>>
>> void main()
>> {
>> auto s = S();
>> s = 42;
>> assert(s.i == 42);
>> }
>>
>> Error: cannot implicitly convert expression (42) of type int
to S
>>
>> To compile, i() must return an lvalue:
>>
>> @property ref int i() {

Although, what I said seems more like a workaround because you 
already had a setter @property. You shouldn't need to make the 
getter return a reference as well... I guess...


I think what is at play here is the current implementation 
limitation of "a single 'alias this' per type." I think 'alias 
this' happens to pick the getter perhaps because the getter 
function is defined first in the class. I don't know...


Ali



Yeah, I think I remember that being an issue before which kinda 
sucks as one doesn't want to have to necessarily return 
references.


alias this should also alias all the overloads.

In any case, how long has the multiple alias issue been going on? 
10 years?


Re: Emulating enums

2013-08-01 Thread Ali Çehreli

On 08/01/2013 03:29 AM, JS wrote:

> On Thursday, 1 August 2013 at 05:22:46 UTC, Ali Çehreli wrote:
>> On 07/31/2013 06:10 PM, JS wrote:
>>> http://dpaste.dzfl.pl/dbb40dbc
>>>
>>> The code was pared down from a lot of string mixin code generation. I
>>> nest the structs because I want a nested enums. I don't want have to
>>> have eState and eStateType but eState and eState.Type.
>>>
>>> Having the ability to nest enums would solve my problem.
>>>
>>> Regardless, I can almost achieve the effect with nested structs but not
>>> quite.
>>>
>>> In the code, I cannot assign to the struct for some reason even with
>>> alias this on iB, which should make State act like the int Value.
>>>
>>> i.e.,
>>>
>>> b.State.Value = Enums.State.A;
>>>
>>> works but
>>>
>>> b.State = Enums.State.A;
>>>
>>> doesn't
>>>
>>> It maybe some stupid error on my part but I can't keep my eyes open
>>> enough to figure it out...
>>>
>>>
>>>
>>
>> For that assignment to work, the left-hand side must be assignable.
>> However, the property function State() returns Enums.eState by-value.
>>
>> The following has the same issue:
>>
>> struct S
>> {
>> int i_;
>>
>> @property int i() {
>> return i_;
>> }
>>
>> alias i this;
>> }
>>
>> void main()
>> {
>> auto s = S();
>> s = 42;
>> assert(s.i == 42);
>> }
>>
>> Error: cannot implicitly convert expression (42) of type int to S
>>
>> To compile, i() must return an lvalue:
>>
>> @property ref int i() {

Although, what I said seems more like a workaround because you already 
had a setter @property. You shouldn't need to make the getter return a 
reference as well... I guess...


I think what is at play here is the current implementation limitation of 
"a single 'alias this' per type." I think 'alias this' happens to pick 
the getter perhaps because the getter function is defined first in the 
class. I don't know...


Ali



Re: instantiate each of a tuple of templates (Take 2)

2013-08-01 Thread John Colvin

On Thursday, 1 August 2013 at 15:06:50 UTC, Artur Skawina wrote:

On 08/01/13 14:50, John Colvin wrote:

template a(T ...)
{
void a(R r)
{
//want to get a tuple of
//the members of T, each
//instantiated with R.

//do some RT stuff
}
}

Is this possible?

Whatever I try, I keep running in to "cannot use local as 
parameter to non-global template" errors, which I understand 
is to do with context pointers
However, this is all compile-time work based entirely on 
types, there should be no need for any context pointers.




Always post real and complete (even if not working) code, as 
figuring out

what the problem is can be harder than giving the solution...


   template RealTuple(A...) { alias RealTuple = A; }
   template a(T ...)
   {
   auto a(R)(R r)
   {
   //want to get a tuple of
   //the members of T, each
   //instantiated with R.

   mixin({
  string m;
  foreach (I, _; T)
 m ~= "alias UGH"~I.stringof~" = 
T["~I.stringof~"];\n";

  m ~= "alias TupleofTsBangR = RealTuple!(";
  foreach (I, _; T)
 m ~= (I?", ":"") ~ "UGH"~I.stringof~"!R";
  return m ~ ");";
   }());

   // do some RT stuff

   TupleofTsBangR x;
   foreach (I, _; typeof(x))
   x[I] = r;

   // etc

   import std.typecons;
   return tuple(x);
   }
   }

(If this is what you were actually looking for then I hope 
somebody

 else has another solution; this approach is just too ugly...)

artur


sorry yeah I didnt think the question through before asking. I'm 
normally the one nagging for better example code when people ask 
questions!


I did consider wading through everything with string mixins etc. 
but it seemed like a lot of effort for what (on the surface) is a 
simple problem.


Anyhow, please see my response to monarch_dodra as I've revised 
my question somewhat


Re: instantiate each of a tuple of templates (Take 2)

2013-08-01 Thread John Colvin

On Thursday, 1 August 2013 at 14:57:07 UTC, monarch_dodra wrote:

On Thursday, 1 August 2013 at 12:50:42 UTC, John Colvin wrote:

template a(T ...)
{
   void a(R r)
   {
   //want to get a tuple of
   //the members of T, each
   //instantiated with R.

   //do some RT stuff
   }
}

Is this possible?

Whatever I try, I keep running in to "cannot use local as 
parameter to non-global template" errors, which I understand 
is to do with context pointers
However, this is all compile-time work based entirely on 
types, there should be no need for any context pointers.


Still not sure what you want, but you may want to look into 
adjoin and  staticMap.


Sorry, now I've thought about it some more it appears I was 
asking the wrong question completely!


Here's the situation (you might recognise the pattern from 
std.algorithm.map):


template a(funs...)
{
auto a(R)(R r)
{
alias /*something*/ nonVoidFuns;
alias /*something*/ voidFuns;

//do stuff with nonVoidFuns and voidFuns applied to r
}
}

so i need to find the return type of each fun, when called with 
something of type R (bearing in mind that fun!R may not be the 
same type as fun(r) as fun might be T fun(T)(T[] a), then filter 
funs to seperate the void functions from the non-void ones. Or 
something else to that effect.


I've tried several things with std.typetuple.Filter but nothing 
seems to work.


Re: instantiate each of a tuple of templates (Take 2)

2013-08-01 Thread Artur Skawina
On 08/01/13 14:50, John Colvin wrote:
> template a(T ...)
> {
> void a(R r)
> {
> //want to get a tuple of
> //the members of T, each
> //instantiated with R.
> 
> //do some RT stuff
> }
> }
> 
> Is this possible?
> 
> Whatever I try, I keep running in to "cannot use local as parameter to 
> non-global template" errors, which I understand is to do with context pointers
> However, this is all compile-time work based entirely on types, there should 
> be no need for any context pointers.
> 

Always post real and complete (even if not working) code, as figuring out
what the problem is can be harder than giving the solution...


   template RealTuple(A...) { alias RealTuple = A; }
   template a(T ...)
   {
   auto a(R)(R r)
   {
   //want to get a tuple of
   //the members of T, each
   //instantiated with R.

   mixin({
  string m;
  foreach (I, _; T)
 m ~= "alias UGH"~I.stringof~" = T["~I.stringof~"];\n";
  m ~= "alias TupleofTsBangR = RealTuple!(";
  foreach (I, _; T)
 m ~= (I?", ":"") ~ "UGH"~I.stringof~"!R";
  return m ~ ");";
   }());

   // do some RT stuff

   TupleofTsBangR x;
   foreach (I, _; typeof(x))
   x[I] = r;

   // etc

   import std.typecons;
   return tuple(x);
   }
   }

(If this is what you were actually looking for then I hope somebody
 else has another solution; this approach is just too ugly...)

artur


Re: instantiate each of a tuple of templates (Take 2)

2013-08-01 Thread monarch_dodra

On Thursday, 1 August 2013 at 12:50:42 UTC, John Colvin wrote:

template a(T ...)
{
void a(R r)
{
//want to get a tuple of
//the members of T, each
//instantiated with R.

//do some RT stuff
}
}

Is this possible?

Whatever I try, I keep running in to "cannot use local as 
parameter to non-global template" errors, which I understand is 
to do with context pointers
However, this is all compile-time work based entirely on types, 
there should be no need for any context pointers.


Still not sure what you want, but you may want to look into 
adjoin and  staticMap.


Re: std.container: RedBlackTree questions

2013-08-01 Thread monarch_dodra

On Thursday, 1 August 2013 at 12:27:51 UTC, Ivan Kazmenko wrote:

Hi!

The key points of this lengthy letter are:

(0) I find RedBlackTree hard to use, and below is one story of 
trying to get it to work.


(1) Perhaps I did something wrong a few times.  Please show me 
a better way to go.


(2) Perhaps the library code could be improved as well to make 
the process more intuitive.


-

I am trying to use RedBlackTree container to maintain a set of 
Elems, Elem being a non-trivial struct.  The problem is that I 
find the container hard to use.


First, I have to note that, instead of storing Elems directly 
in the RedBlackTree, I have a dynamic array of Elems and a 
RedBlackTree of integers pointing to that array to improve 
performance.  In my case, the latter proved to be a few times 
faster than the former because RedBlackTree moves the values 
around quite a bit.  Please comment if there is a common way to 
achieve a similar performance gain without decoupling.


Anyway, instead of storing say "data[a]" and "data[b]" in the 
tree, I store their indices "a" and "b" and compare these 
integers like "data[a] < data[b]".  Below is the story of my 
few steps to making this work.  I'll appreciate any comments on 
how I could improve or take a better direction on any of the 
steps.


The compiler is DMD 2.063.2, no compile options.  Struct Elem 
is replaced by an alias to long for simplicity.



1. The first try is to specify the comparison directly:
-
import std.container;
alias Elem = long;
Elem [] data;
RedBlackTree !(int, "data[a] < data[b]") tree;
void main () { }
-

This gives the following error:
rbt1.d(7): Error: template instance RedBlackTree!(int, "data[a] 
< data[b]")
does not match template declaration RedBlackTree(T, alias less 
= "a < b",
bool allowDuplicates = false) if 
(is(typeof(binaryFun!(less)(T.init, T.init


OK, that was predictable.  I never got to getting this to work 
beyond a simple "a < b" or "a + 1 > b + 1" or the like.  Is 
that even possible?



2. Let us try a lambda:
-
import std.container;
alias Elem = long;
Elem [] data;
RedBlackTree !(int, (a, b) => data[a] < data[b]) tree;
void main ()
{
	tree = redBlackTree !((a, b) => data[a] < data[b]) (new int 
[0]);

}
-

Fine with the declaration, but later, an error again:
rbt2.d(11): Error: cannot implicitly convert expression 
(redBlackTree(new
int[](0u))) of type rbt2.main.RedBlackTree!(int, 
__lambda6).RedBlackTree to

rbt2.RedBlackTree!(int, __lambda3).RedBlackTree

I see.  The compiler cannot tell that the lambdas are the same.
 Oh well.


3. An ordinary function then:
-
import std.container;
alias Elem = long;
Elem [] data;
bool less_data (int a, int b) {return data[a] < data[b];}
RedBlackTree !(int, less_data) tree;
void main ()
{
tree = redBlackTree !(less_data) (new int [0]);
}
-

Aaand:
phobos\std\container.d(6553): Error: less_data (int a, int b) 
is not callable using argument types ()
phobos\std\range.d(611): Error: static assert "Cannot put a 
char[] into a Appender!(string)"
phobos\std\format.d(1433): instantiated from here: 
put!(Appender!(string), char[])
phobos\std\format.d(1335): instantiated from here: 
formatUnsigned!(Appender!(string), char)
phobos\std\format.d(1309): instantiated from here: 
formatIntegral!(Appender!(string), ulong, char)
phobos\std\format.d(2950): ... (4 instantiations, -v to show) 
...
phobos\std\container.d(5541): instantiated from here: 
Tuple!(bool, "added", RBNode!(int)*, "n")
rbt3.d(12): instantiated from here: RedBlackTree!(int, 
less_data)


Ouch.  What?  That does not look like a user-friendly message 
at all.  Am I doing something very wrong?..



4. After a bit of guessing, I got this working by adding an 
empty template argument to the function.  Here it goes:

-
import std.container;
alias Elem = long;
Elem [] data;
bool less_data () (int a, int b) {return data[a] < data[b];}
RedBlackTree !(int, less_data) tree;
void main ()
{
tree = redBlackTree !(less_data) (new int [0]);
data = [4, 3, 5];
tree.insert (0);
tree.insert (1);
tree.insert (2);
}
-

This compiles and runs fine.  Or does it?  Adding "-unittest" 
compiler option produces another bunch of errors:

phobos\std\container.d(5672): Error: void has no value
phobos\std\container.d(5672): Error: incompatible types for 
((less_data()(int a, int b)) == ("a < b")): 'void' and 'string'

phobos\std\container.d(5946): Error: void has no value
phobos\std\container.d(5946): Error: incompatible types for 
((less_data()(int a, int b)) == ("a < b")): 'void' and 'string'

phobos\std\container.d(6021): Error: void has no value
phobos\std\container.d(6021): Error: incompatible types for 
((less_data()(int a, int b)) == ("a < b")): 'void' and 'string'

phobos\std\container.d(6067): Error: void has no value
phobos\std\container.d(6067): Error: incompatible types for 
((less_data()(int a, int b)) == ("a < b")): 'void' and 'string'

phobos\std\container

Re: instantiate each of a tuple of templates (Take 2)

2013-08-01 Thread Dicebot

On Thursday, 1 August 2013 at 12:50:42 UTC, John Colvin wrote:

...


Does this help http://dpaste.dzfl.pl/fe533f7a ?


Re: instantiate each of a tuple of templates (Take 2)

2013-08-01 Thread monarch_dodra

On Thursday, 1 August 2013 at 12:50:42 UTC, John Colvin wrote:

template a(T ...)
{
void a(R r)
{
//want to get a tuple of
//the members of T, each
//instantiated with R.

//do some RT stuff
}
}

Is this possible?

Whatever I try, I keep running in to "cannot use local as 
parameter to non-global template" errors, which I understand is 
to do with context pointers
However, this is all compile-time work based entirely on types, 
there should be no need for any context pointers.


A static foreach should do the trick. (code not actually tested)

void a(R r) //void? Not Tuple!T ?
{
Tuple!T ret
foreach(i, Type; T)
{
ret[i] = r;
}
return ret;
}

Is this what you want? This assumes that every member or T is a 
type, and not a name.


Re: std.container: RedBlackTree questions

2013-08-01 Thread Ivan Kazmenko

On Thursday, 1 August 2013 at 12:55:30 UTC, John Colvin wrote:

On Thursday, 1 August 2013 at 12:27:51 UTC, Ivan Kazmenko wrote:
On a relevant note, I find the unittests of RedBlackTree a bit 
excessive even when they compile successfully.  They seem to 
test the integrity of the whole tree every time a tree 
operation takes place, and that makes the unittests version of 
my local code run too slowly.  Is there a way to turn 
unittests on only for user code and turn them off for the 
standard library?


Ivan Kazmenko.


Unless you've compiled phobos with -unittest, the unittests in 
the standard library won't even exist in the binary, let alone 
take up time to run.


Unless... I'm mistaken and actually for some bizarre reason 
unittests get dragged in from the import files, but that seems 
very unlikely.


There is a

version(unittest) version = RBDoChecks;

line and the following

version(RBDoChecks) check();

calls in the tree implementation.
Perhaps the approach is special to RedBlackTree.

I agree that RBDoChecks can be useful occasionally, for example, 
when there is a bug in comparison function.  But I would be happy 
if the aforementioned line is removed from the library, or at 
least a way to override it is provided.


Re: Profiling graph library

2013-08-01 Thread Joseph Rushton Wakeling
On 08/01/2013 01:56 PM, bearophile wrote:
> I have not critiqued linear flow programming its, I love it and perhaps I was
> the one that has introduced it in D. In the main D newsgroup I have just said
> that in D it still causes some performance loss, even using ldc2.

That's what I meant -- your remarks on the (current) performance costs.  Wasn't
meaning to imply you'd critiqued the idea per se!


Re: std.container: RedBlackTree questions

2013-08-01 Thread John Colvin

On Thursday, 1 August 2013 at 12:27:51 UTC, Ivan Kazmenko wrote:
On a relevant note, I find the unittests of RedBlackTree a bit 
excessive even when they compile successfully.  They seem to 
test the integrity of the whole tree every time a tree 
operation takes place, and that makes the unittests version of 
my local code run too slowly.  Is there a way to turn unittests 
on only for user code and turn them off for the standard 
library?


Ivan Kazmenko.


Unless you've compiled phobos with -unittest, the unittests in 
the standard library won't even exist in the binary, let alone 
take up time to run.


Unless... I'm mistaken and actually for some bizarre reason 
unittests get dragged in from the import files, but that seems 
very unlikely.


instantiate each of a tuple of templates (Take 2)

2013-08-01 Thread John Colvin

template a(T ...)
{
void a(R r)
{
//want to get a tuple of
//the members of T, each
//instantiated with R.

//do some RT stuff
}
}

Is this possible?

Whatever I try, I keep running in to "cannot use local as 
parameter to non-global template" errors, which I understand is 
to do with context pointers
However, this is all compile-time work based entirely on types, 
there should be no need for any context pointers.


instantiate a tuple of templates

2013-08-01 Thread John Colvin

Say I have a template

template A(T ...)
{
void A
}


Re: instantiate a tuple of templates

2013-08-01 Thread John Colvin

On Thursday, 1 August 2013 at 12:43:21 UTC, John Colvin wrote:

Say I have a template

template A(T ...)
{
void A
}


woops sorry, partial post. Will finish and post again.


Re: Named UDA's

2013-08-01 Thread Dicebot

On Thursday, 1 August 2013 at 11:02:00 UTC, JS wrote:
Anyways, Just an idea I had when trying to make attributes more 
useful.


struct Name
{
string data;
}

@Name("hello")
void foo();

I favor this approach much more because of strong typing.


std.container: RedBlackTree questions

2013-08-01 Thread Ivan Kazmenko

Hi!

The key points of this lengthy letter are:

(0) I find RedBlackTree hard to use, and below is one story of 
trying to get it to work.


(1) Perhaps I did something wrong a few times.  Please show me a 
better way to go.


(2) Perhaps the library code could be improved as well to make 
the process more intuitive.


-

I am trying to use RedBlackTree container to maintain a set of 
Elems, Elem being a non-trivial struct.  The problem is that I 
find the container hard to use.


First, I have to note that, instead of storing Elems directly in 
the RedBlackTree, I have a dynamic array of Elems and a 
RedBlackTree of integers pointing to that array to improve 
performance.  In my case, the latter proved to be a few times 
faster than the former because RedBlackTree moves the values 
around quite a bit.  Please comment if there is a common way to 
achieve a similar performance gain without decoupling.


Anyway, instead of storing say "data[a]" and "data[b]" in the 
tree, I store their indices "a" and "b" and compare these 
integers like "data[a] < data[b]".  Below is the story of my few 
steps to making this work.  I'll appreciate any comments on how I 
could improve or take a better direction on any of the steps.


The compiler is DMD 2.063.2, no compile options.  Struct Elem is 
replaced by an alias to long for simplicity.



1. The first try is to specify the comparison directly:
-
import std.container;
alias Elem = long;
Elem [] data;
RedBlackTree !(int, "data[a] < data[b]") tree;
void main () { }
-

This gives the following error:
rbt1.d(7): Error: template instance RedBlackTree!(int, "data[a] < 
data[b]")
does not match template declaration RedBlackTree(T, alias less = 
"a < b",
bool allowDuplicates = false) if 
(is(typeof(binaryFun!(less)(T.init, T.init


OK, that was predictable.  I never got to getting this to work 
beyond a simple "a < b" or "a + 1 > b + 1" or the like.  Is that 
even possible?



2. Let us try a lambda:
-
import std.container;
alias Elem = long;
Elem [] data;
RedBlackTree !(int, (a, b) => data[a] < data[b]) tree;
void main ()
{
tree = redBlackTree !((a, b) => data[a] < data[b]) (new int [0]);
}
-

Fine with the declaration, but later, an error again:
rbt2.d(11): Error: cannot implicitly convert expression 
(redBlackTree(new
int[](0u))) of type rbt2.main.RedBlackTree!(int, 
__lambda6).RedBlackTree to

rbt2.RedBlackTree!(int, __lambda3).RedBlackTree

I see.  The compiler cannot tell that the lambdas are the same.  
Oh well.



3. An ordinary function then:
-
import std.container;
alias Elem = long;
Elem [] data;
bool less_data (int a, int b) {return data[a] < data[b];}
RedBlackTree !(int, less_data) tree;
void main ()
{
tree = redBlackTree !(less_data) (new int [0]);
}
-

Aaand:
phobos\std\container.d(6553): Error: less_data (int a, int b) is 
not callable using argument types ()
phobos\std\range.d(611): Error: static assert "Cannot put a 
char[] into a Appender!(string)"
phobos\std\format.d(1433): instantiated from here: 
put!(Appender!(string), char[])
phobos\std\format.d(1335): instantiated from here: 
formatUnsigned!(Appender!(string), char)
phobos\std\format.d(1309): instantiated from here: 
formatIntegral!(Appender!(string), ulong, char)

phobos\std\format.d(2950): ... (4 instantiations, -v to show) ...
phobos\std\container.d(5541): instantiated from here: 
Tuple!(bool, "added", RBNode!(int)*, "n")

rbt3.d(12): instantiated from here: RedBlackTree!(int, less_data)

Ouch.  What?  That does not look like a user-friendly message at 
all.  Am I doing something very wrong?..



4. After a bit of guessing, I got this working by adding an empty 
template argument to the function.  Here it goes:

-
import std.container;
alias Elem = long;
Elem [] data;
bool less_data () (int a, int b) {return data[a] < data[b];}
RedBlackTree !(int, less_data) tree;
void main ()
{
tree = redBlackTree !(less_data) (new int [0]);
data = [4, 3, 5];
tree.insert (0);
tree.insert (1);
tree.insert (2);
}
-

This compiles and runs fine.  Or does it?  Adding "-unittest" 
compiler option produces another bunch of errors:

phobos\std\container.d(5672): Error: void has no value
phobos\std\container.d(5672): Error: incompatible types for 
((less_data()(int a, int b)) == ("a < b")): 'void' and 'string'

phobos\std\container.d(5946): Error: void has no value
phobos\std\container.d(5946): Error: incompatible types for 
((less_data()(int a, int b)) == ("a < b")): 'void' and 'string'

phobos\std\container.d(6021): Error: void has no value
phobos\std\container.d(6021): Error: incompatible types for 
((less_data()(int a, int b)) == ("a < b")): 'void' and 'string'

phobos\std\container.d(6067): Error: void has no value
phobos\std\container.d(6067): Error: incompatible types for 
((less_data()(int a, int b)) == ("a < b")): 'void' and 'string'

phobos\std\container.d(6108): Error: void has no value
phobos\std\container.d(610

Re: Profiling graph library

2013-08-01 Thread bearophile

Joseph Rushton Wakeling:


So, your critiques of component programming certainly
have merit on the performance side.


I have not critiqued linear flow programming its, I love it and 
perhaps I was the one that has introduced it in D. In the main D 
newsgroup I have just said that in D it still causes some 
performance loss, even using ldc2.


Bye,
bearophile


Named UDA's

2013-08-01 Thread JS

I guess D doesn't support named UDA's directly?

e.g.,

@(Name = "My Name", Other = .34)

It would be nice to have the ability to have an "attribute" 
hierarchy where looking up attributes on objects could easily be 
done.


e.g.,

@(Name = "s", Other = 2) struct s
{
@(Name = "q", Default_Value = 4) int q = 4;
}

which would form a hierarchy

Attributes[]...[]

Which @[s].Attributes = {"Name" = "s", "Other" = 2} (Key/Value 
pairs)


@[s][q].Attributes = {"Name" = "q", "Other" = 2, "Default_Value" 
= 4 }


(attributes are inherited

Querying at runtime would be a binary search or O(1) if the 
object type is known.


Anyways, Just an idea I had when trying to make attributes more 
useful.


Re: Profiling graph library

2013-08-01 Thread Joseph Rushton Wakeling
On 07/31/2013 02:31 PM, bearophile wrote:
> If this resulting array is used only for a short period of time:
> 
> return sequence.map!(x => x.func).array;

Just to compare, I tried rewriting the cacheing version of the neighbours()
function to use this kind of sequence.  Here's the original code:
https://github.com/WebDrake/Dgraph/blob/cache/dgraph/graph.d#L358-L379

... and here's the rewritten version:

auto neighbours(immutable size_t v)
{
if (!_cacheNeighbours[v])
{
iota(_sumTail[v], _sumTail[v + 1])
.map!(a => _head[_indexTail[a]])
.copy(_neighbours[_sumTail[v] + _sumHead[v] .. _sumHead[v] +
_sumTail[v + 1]]);
iota(_sumHead[v], _sumHead[v + 1])
.map!(a => _tail[_indexHead[a]])
.copy(_neighbours[_sumHead[v] + _sumTail[v + 1] .. _sumTail[v +
1] + _sumHead[v + 1]]);
_cacheNeighbours[v] = true;
}
return _neighbours[_sumTail[v] + _sumHead[v] .. _sumTail[v + 1] +
_sumHead[v + 1]];
}

Although it's faster than the non-cached map-based version, there's still a
substantial performance hit from a large number of small allocations.  So, your
critiques of component programming certainly have merit on the performance side.

What's weird is that even though the graph is always passed around by ref,
meaning that the neighbours are calculated only once, according to callgrind the
number of calls to _d_allocmemory still amounts to no. of vertices * no. of
trial runs.

And yes, I put in some checks to make sure that the loop was only being called
the correct number of times.


Re: Emulating enums

2013-08-01 Thread JS

On Thursday, 1 August 2013 at 05:22:46 UTC, Ali Çehreli wrote:

On 07/31/2013 06:10 PM, JS wrote:

http://dpaste.dzfl.pl/dbb40dbc

The code was pared down from a lot of string mixin code 
generation. I
nest the structs because I want a nested enums. I don't want 
have to

have eState and eStateType but eState and eState.Type.

Having the ability to nest enums would solve my problem.

Regardless, I can almost achieve the effect with nested 
structs but not

quite.

In the code, I cannot assign to the struct for some reason 
even with
alias this on iB, which should make State act like the int 
Value.


i.e.,

b.State.Value = Enums.State.A;

works but

b.State = Enums.State.A;

doesn't

It maybe some stupid error on my part but I can't keep my eyes 
open

enough to figure it out...





For that assignment to work, the left-hand side must be 
assignable. However, the property function State() returns 
Enums.eState by-value.


The following has the same issue:

struct S
{
int i_;

@property int i() {
return i_;
}

alias i this;
}

void main()
{
auto s = S();
s = 42;
assert(s.i == 42);
}

Error: cannot implicitly convert expression (42) of type int to 
S


To compile, i() must return an lvalue:

@property ref int i() {

Ali


Thanks...


Re: Mysql - Sql things ?

2013-08-01 Thread Larry

On Wednesday, 31 July 2013 at 12:09:02 UTC, David wrote:

https://github.com/rejectedsoftware/mysql-native


Waw ! Many thanks,

Completely missed it :)

See you