parallelFuture

2009-10-21 Thread dsimcha
I've created an alpha release of parallelFuture, a high-level parallelization
library for D2.  Right now, it has a task pool, futures, parallel foreach, and
parallel map.

Here's the (IMHO) coolest example:

auto pool = new ThreadPool();

// Assuming we have a function isPrime(), print all
// prime numbers from 0 to uint.max, testing for primeness
// in parallel.
auto myRange = iota(0, uint.max);
foreach(num; pool.parallel(myRange)) {
if(isPrime(num)) {
synchronized writeln(num);
}
}

The interface is there and it seems to work, although it has not been
extensively stress tested yet.  Some of the implementation details could
admittedly use some cleaning up, and I would appreciate help from some
threading gurus on improving my queue (right now it's a naive synchronized
singly-linked list) and getting condition mutexes to work properly.  (Right
now, I'm using atomic polling followed by sleeping for 1 millisecond in a lot
of places.  It's a kludge, but it seems to work reasonably well in practice.)

The code is at:

http://dsource.org/projects/scrapple/browser/trunk/parallelFuture/parallelFuture.d

The docs are at:

http://cis.jhu.edu/~dsimcha/parallelFuture.html


Re: parallelFuture

2009-10-21 Thread Tim Matthews

dsimcha wrote:

I've created an alpha release of parallelFuture, a high-level parallelization
library for D2.  Right now, it has a task pool, futures, parallel foreach, and
parallel map.

Here's the (IMHO) coolest example:

auto pool = new ThreadPool();

// Assuming we have a function isPrime(), print all
// prime numbers from 0 to uint.max, testing for primeness
// in parallel.
auto myRange = iota(0, uint.max);
foreach(num; pool.parallel(myRange)) {
if(isPrime(num)) {
synchronized writeln(num);
}
}

The interface is there and it seems to work, although it has not been
extensively stress tested yet.  Some of the implementation details could
admittedly use some cleaning up, and I would appreciate help from some
threading gurus on improving my queue (right now it's a naive synchronized
singly-linked list) and getting condition mutexes to work properly.  (Right
now, I'm using atomic polling followed by sleeping for 1 millisecond in a lot
of places.  It's a kludge, but it seems to work reasonably well in practice.)

The code is at:

http://dsource.org/projects/scrapple/browser/trunk/parallelFuture/parallelFuture.d

The docs are at:

http://cis.jhu.edu/~dsimcha/parallelFuture.html


Nice. About the tasks:

In .Net a worker thread is created for each cpu core. Each worker thread 
has its own local queue of tasks which it initially retrieves from the 
global queue but if the tasks creates new tasks it adds to its local 
queue directly for less contention. When it finishes completing a task 
it takes the next from the back of its local queue to take advantage of 
cache (like a stack). The tasks at the front of the queue can be stolen 
from another worker thread if its local queue and the global queue are 
both empty to maximize cpu usage.


Also the task's wait for complete is only considered complete if all of 
the tasks it created too are complete (kinda like recursion).


What is the implementation or plans like for this.


Re: static arrays becoming value types

2009-10-21 Thread language_fan
Tue, 20 Oct 2009 16:25:05 -0400, Robert Jacques thusly wrote:

 On Tue, 20 Oct 2009 15:19:15 -0400, language_fan f...@bar.com.invalid
 wrote:
 
 Real tuple types do not have a special type tag which gets injected
 implicitly with structs. So every time you try to do something
 lightweight by emulating tuples, you need to refer to the global Tuple
 type or bang your head to the wall.
 
 Or use a templated opAssign mixin to allow two desperate types to be
 assigned to each other.

Wow, you need templates to implement == for built-in values types, nice..

 Besides, I think you're comparing apples to oranges. In the SOL example,
 you use the same declaration for all types. Shouldn't the SOL example
 be:
 
val a = (1,2) : [Int,Int]
val b = (1,2) : [Int,Int]
val c = (2,3) : MyCustomTupleType[Int,Int]
 
 which would probably generate:
   assert(a == b); // ok
   assert(a != c); // Error: incompatible types for ((a) != (b))

If you have built-in tuple literals, there is no way you can build a 
MyCustomTupleType without resorting to other language features. There are 
no apples and oranges, cause they both are seen as (Int,Int) by the 
equivalence checker. Do you understand how equivalence works in 
structural typing system (http://en.wikipedia.org/wiki/
Structural_type_system) vs nominal typing? In structural equivalence 
there are no names attached to the types (well there might be, but those 
are omitted in the comparison), only their internal structure matters.

Why would anyone want to create two incompatible tuples by default as you 
still would have 'typedef' and 'struct' for implementing just that.


Re: stack frame optimization problem

2009-10-21 Thread Vladimir Panteleev

On Wed, 21 Oct 2009 00:55:26 +0300, sprucely timber...@gmail.com wrote:

To try to be sure I had the correct syntax I tried the -S option of g++  
along with a switch for intel syntax to output the assembly. However the  
portion corresponding to the inline assembly was still in ATT syntax.


For my resulting D executable I tried using hte, but it would abort  
after mentioning something about a nonexistent htcfg file. I didn't find  
much info after a cursory search. I gave up easily because I wasn't sure  
if I would be able to make proper use of it. Maybe I should take an x86  
assembly course.


I believe DMD comes with a Linux binary of obj2asm. For Windows you can  
use the free version of IDA.


--
Best regards,
 Vladimir  mailto:thecybersha...@gmail.com


Re: Proposed D2 Feature: = for anonymous delegates

2009-10-21 Thread Pelle Månsson

Andrei Alexandrescu wrote:

Pelle Månsson wrote:

Jason House wrote:

Andrei Alexandrescu Wrote:


Jason House wrote:

Am I the only one that has trouble remembering how to write an inline
anonymous delegate when calling a function? At a minimum, both Scala
and C# use (args) = { body; } syntax. Can we please sneak it into
D2?

We have (args) { body; }

Andrei


Somehow, I missed that. What kind of type inference, if any, is 
allowed? Scala and C# allow omiting the type. Lately I'm doing a lot 
of (x) = { return x.foo(7); } in C# and it's nice to omit the 
amazingly long type for x. The IDE even knows the type of x for 
intellisense... I think scala would allow x = foo(7), or maybe even 
= _.foo(7) or even _.foo(7). I haven't written much scala, so I may 
be way off...


Recent experiments by myself indicate you cannot omit the type and you 
cannot use auto for the type, so you actually need to type your 
VeryLongClassName!(With, Templates) if you need it.


I sort of miss automatic type deduction.


Actually, full type deduction should be in vigor, but it is known that 
the feature has more than a few bugs. Feel free to report any instance 
in which type deduction does not work in bugzilla.


Andrei


int f(int delegate(int) g) {
return g(13);
}
void main() {
f((auto x) { return x+13; });
}

This does not compile in D v2.034. Am I missing something?


Re: Proposed D2 Feature: = for anonymous delegates

2009-10-21 Thread language_fan
Wed, 21 Oct 2009 12:35:41 +0200, Pelle Månsson thusly wrote:

 Andrei Alexandrescu wrote:
 Pelle Månsson wrote:
 Jason House wrote:
 Andrei Alexandrescu Wrote:

 Jason House wrote:
 Am I the only one that has trouble remembering how to write an
 inline anonymous delegate when calling a function? At a minimum,
 both Scala and C# use (args) = { body; } syntax. Can we please
 sneak it into D2?
 We have (args) { body; }

 Andrei

 Somehow, I missed that. What kind of type inference, if any, is
 allowed? Scala and C# allow omiting the type. Lately I'm doing a lot
 of (x) = { return x.foo(7); } in C# and it's nice to omit the
 amazingly long type for x. The IDE even knows the type of x for
 intellisense... I think scala would allow x = foo(7), or maybe even
 = _.foo(7) or even _.foo(7). I haven't written much scala, so I may
 be way off...

 Recent experiments by myself indicate you cannot omit the type and you
 cannot use auto for the type, so you actually need to type your
 VeryLongClassName!(With, Templates) if you need it.

 I sort of miss automatic type deduction.
 
 Actually, full type deduction should be in vigor, but it is known that
 the feature has more than a few bugs. Feel free to report any instance
 in which type deduction does not work in bugzilla.
 
 Andrei
 
 int f(int delegate(int) g) {
  return g(13);
 }
 void main() {
  f((auto x) { return x+13; });
 }
 
 This does not compile in D v2.034. Am I missing something?

No, in this context the exact type can be inferred unambiguously without 
worrying about overloading. From the error message

test.d(5): basic type expected, not auto
test.d(5): found 'auto' when expecting ')'
test.d(5): semicolon expected following function declaration
test.d(5): found 'x' when expecting ','
test.d(5): expression expected, not ')'
test.d(5): found '{' when expecting ','
test.d(5): expression expected, not 'return'
test.d(5): found 'x' when expecting ','
test.d(5): found ';' when expecting ','
test.d(5): expression expected, not '}'

I can see that the compiler does not even support this on syntactic level.


Re: Revamping associative arrays

2009-10-21 Thread Pelle Månsson

Piotrek wrote:

Bill Baxter pisze:

On Sun, Oct 18, 2009 at 1:12 PM, Piotrek star...@tlen.pl wrote:

Bill Baxter pisze:

I think the default should be to iterate over whatever 'in' looks at.

I was almost convinced, because that rule has a sense. But treating 
normal

arrays and associative array has more sense to me.


fun (SomeObject object) {
foreach (element;object.arr1){ //normal, but how do I know at first look
//just do something with element
}

foreach (element;object.arr2){ // assoc, but how do I know at first look
//just do something with element hopefully not index
}


That sounds like an argument that there should be no default, because
either way it's not clear whether you're iterating over keys or
values. 



Really?! That wasn't my intention :) In both cases I wish it were values ;)

  Just get rid of the the one-argument foreach over AAs altogether and 
force the user to be

  explicit about it.

I wouldn't do so. Would anybody do an error by thinking that foreach 
(elem,table) should iterate over keys?


Maybe I'm not thinking correctly but for me an assoc array is just an 
array with additional key (index) features thanks to which I save space 
and/or have more indexing method than only integers.



e.g.

Normal array

No.   Item
0George
1Fred
2Dany
3Lil

Index/key is infered from position (offset)


Now Assoc array:

No.Item
10Lindsey
21Romeo
1001C-Jay

Or
No.Item
firstEurope
secondSouth America
thirdAustralia

Or
Names occurrence frequency:

No. Item
Andy21
John23
Kate12

And the only difference is the need for using a hash function for value 
lookup (calculate position) which should not bother a user when he 
doesn't care.


Then when you ask somebody to iterate over the tables, what he will do 
almost for certain? If it would be me, you know... values all the time. 
Even for last example most important values are those numbers (despite 
in this case they're meaningless without keys).


Cheers
Piotrek




Put it this way:
 Is there any time you are interested in the values without the keys?
 Is there any time you are interested in the keys without the values?

If you're not interested in the keys, the real question would be why you 
are using an associative array instead of just an array.


I can think of at least one example of when you want key iteration, 
which would be when using a bool[T] as a set.


Re: Proposed D2 Feature: = for anonymous delegates

2009-10-21 Thread Andrei Alexandrescu

language_fan wrote:

Wed, 21 Oct 2009 12:35:41 +0200, Pelle Månsson thusly wrote:


Andrei Alexandrescu wrote:

Pelle Månsson wrote:

Jason House wrote:

Andrei Alexandrescu Wrote:


Jason House wrote:

Am I the only one that has trouble remembering how to write an
inline anonymous delegate when calling a function? At a minimum,
both Scala and C# use (args) = { body; } syntax. Can we please
sneak it into D2?

We have (args) { body; }

Andrei

Somehow, I missed that. What kind of type inference, if any, is
allowed? Scala and C# allow omiting the type. Lately I'm doing a lot
of (x) = { return x.foo(7); } in C# and it's nice to omit the
amazingly long type for x. The IDE even knows the type of x for
intellisense... I think scala would allow x = foo(7), or maybe even
= _.foo(7) or even _.foo(7). I haven't written much scala, so I may
be way off...

Recent experiments by myself indicate you cannot omit the type and you
cannot use auto for the type, so you actually need to type your
VeryLongClassName!(With, Templates) if you need it.

I sort of miss automatic type deduction.

Actually, full type deduction should be in vigor, but it is known that
the feature has more than a few bugs. Feel free to report any instance
in which type deduction does not work in bugzilla.

Andrei

int f(int delegate(int) g) {
 return g(13);
}
void main() {
 f((auto x) { return x+13; });
}

This does not compile in D v2.034. Am I missing something?


No, in this context the exact type can be inferred unambiguously without 
worrying about overloading.


The program should be roughly equivalent with:

int f(int delegate(int) g) {
return g(13);
}

auto __fun(T)(T x) { return x+13; }

void main() {
f(__fun);
}

which fails with

Internal error: e2ir.c 644

:o)

In brief, an untyped function literal should be considered an unbound 
template, and as long as type deduction can figure out the types (no 
Hindley-Milner, sorry) things should hold water.



Andrei


Re: Proposed D2 Feature: = for anonymous delegates

2009-10-21 Thread Pelle Månsson

Andrei Alexandrescu wrote:

Pelle Månsson wrote:

Andrei Alexandrescu wrote:

Pelle Månsson wrote:

Jason House wrote:

Andrei Alexandrescu Wrote:


Jason House wrote:
Am I the only one that has trouble remembering how to write an 
inline

anonymous delegate when calling a function? At a minimum, both Scala
and C# use (args) = { body; } syntax. Can we please sneak it into
D2?

We have (args) { body; }

Andrei


Somehow, I missed that. What kind of type inference, if any, is 
allowed? Scala and C# allow omiting the type. Lately I'm doing a 
lot of (x) = { return x.foo(7); } in C# and it's nice to omit the 
amazingly long type for x. The IDE even knows the type of x for 
intellisense... I think scala would allow x = foo(7), or maybe 
even = _.foo(7) or even _.foo(7). I haven't written much scala, so 
I may be way off...


Recent experiments by myself indicate you cannot omit the type and 
you cannot use auto for the type, so you actually need to type your 
VeryLongClassName!(With, Templates) if you need it.


I sort of miss automatic type deduction.


Actually, full type deduction should be in vigor, but it is known 
that the feature has more than a few bugs. Feel free to report any 
instance in which type deduction does not work in bugzilla.


Andrei


int f(int delegate(int) g) {
return g(13);
}
void main() {
f((auto x) { return x+13; });
}

This does not compile in D v2.034. Am I missing something?


Dropping the auto should yield a compilable program. Please report 
that to bugzilla (http://d.puremagic.com/issues/enter_bug.cgi) or let me 
know and I'll do so.


Thanks!

Andrei


I'm afraid I do not understand, simply omitting the auto does not 
compile either. Which one is the bug?


I'm putting this on the bugzilla now.


Re: Proposed D2 Feature: = for anonymous delegates

2009-10-21 Thread Andrei Alexandrescu

Pelle Månsson wrote:

Andrei Alexandrescu wrote:

Pelle Månsson wrote:

Andrei Alexandrescu wrote:

Pelle Månsson wrote:

Jason House wrote:

Andrei Alexandrescu Wrote:


Jason House wrote:
Am I the only one that has trouble remembering how to write an 
inline
anonymous delegate when calling a function? At a minimum, both 
Scala

and C# use (args) = { body; } syntax. Can we please sneak it into
D2?

We have (args) { body; }

Andrei


Somehow, I missed that. What kind of type inference, if any, is 
allowed? Scala and C# allow omiting the type. Lately I'm doing a 
lot of (x) = { return x.foo(7); } in C# and it's nice to omit the 
amazingly long type for x. The IDE even knows the type of x for 
intellisense... I think scala would allow x = foo(7), or maybe 
even = _.foo(7) or even _.foo(7). I haven't written much scala, 
so I may be way off...


Recent experiments by myself indicate you cannot omit the type and 
you cannot use auto for the type, so you actually need to type your 
VeryLongClassName!(With, Templates) if you need it.


I sort of miss automatic type deduction.


Actually, full type deduction should be in vigor, but it is known 
that the feature has more than a few bugs. Feel free to report any 
instance in which type deduction does not work in bugzilla.


Andrei


int f(int delegate(int) g) {
return g(13);
}
void main() {
f((auto x) { return x+13; });
}

This does not compile in D v2.034. Am I missing something?


Dropping the auto should yield a compilable program. Please report 
that to bugzilla (http://d.puremagic.com/issues/enter_bug.cgi) or let 
me know and I'll do so.


Thanks!

Andrei


I'm afraid I do not understand, simply omitting the auto does not 
compile either. Which one is the bug?


I'm putting this on the bugzilla now.


The version with auto shouldn't compile, the one without should. Thanks!

Andrei


Re: Proposed D2 Feature: = for anonymous delegates

2009-10-21 Thread Don

Andrei Alexandrescu wrote:

language_fan wrote:

Wed, 21 Oct 2009 12:35:41 +0200, Pelle Månsson thusly wrote:


Andrei Alexandrescu wrote:

Pelle Månsson wrote:

Jason House wrote:

Andrei Alexandrescu Wrote:


Jason House wrote:

Am I the only one that has trouble remembering how to write an
inline anonymous delegate when calling a function? At a minimum,
both Scala and C# use (args) = { body; } syntax. Can we please
sneak it into D2?

We have (args) { body; }

Andrei

Somehow, I missed that. What kind of type inference, if any, is
allowed? Scala and C# allow omiting the type. Lately I'm doing a lot
of (x) = { return x.foo(7); } in C# and it's nice to omit the
amazingly long type for x. The IDE even knows the type of x for
intellisense... I think scala would allow x = foo(7), or maybe even
= _.foo(7) or even _.foo(7). I haven't written much scala, so I may
be way off...

Recent experiments by myself indicate you cannot omit the type and you
cannot use auto for the type, so you actually need to type your
VeryLongClassName!(With, Templates) if you need it.

I sort of miss automatic type deduction.

Actually, full type deduction should be in vigor, but it is known that
the feature has more than a few bugs. Feel free to report any instance
in which type deduction does not work in bugzilla.

Andrei

int f(int delegate(int) g) {
 return g(13);
}
void main() {
 f((auto x) { return x+13; });
}

This does not compile in D v2.034. Am I missing something?


No, in this context the exact type can be inferred unambiguously 
without worrying about overloading.


The program should be roughly equivalent with:

int f(int delegate(int) g) {
return g(13);
}

auto __fun(T)(T x) { return x+13; }

void main() {
f(__fun);
}

which fails with

Internal error: e2ir.c 644

:o)


Can't reproduce that. It doesn't ICE for me. Tried on several DMD 
versions. (Doesn't compile, though).



In brief, an untyped function literal should be considered an unbound 
template, and as long as type deduction can figure out the types (no 
Hindley-Milner, sorry) things should hold water.



Andrei


Re: Proposed D2 Feature: = for anonymous delegates

2009-10-21 Thread Andrei Alexandrescu

Don wrote:

Andrei Alexandrescu wrote:

language_fan wrote:

Wed, 21 Oct 2009 12:35:41 +0200, Pelle Månsson thusly wrote:


Andrei Alexandrescu wrote:

Pelle Månsson wrote:

Jason House wrote:

Andrei Alexandrescu Wrote:


Jason House wrote:

Am I the only one that has trouble remembering how to write an
inline anonymous delegate when calling a function? At a minimum,
both Scala and C# use (args) = { body; } syntax. Can we please
sneak it into D2?

We have (args) { body; }

Andrei

Somehow, I missed that. What kind of type inference, if any, is
allowed? Scala and C# allow omiting the type. Lately I'm doing a lot
of (x) = { return x.foo(7); } in C# and it's nice to omit the
amazingly long type for x. The IDE even knows the type of x for
intellisense... I think scala would allow x = foo(7), or maybe even
= _.foo(7) or even _.foo(7). I haven't written much scala, so I may
be way off...
Recent experiments by myself indicate you cannot omit the type and 
you

cannot use auto for the type, so you actually need to type your
VeryLongClassName!(With, Templates) if you need it.

I sort of miss automatic type deduction.

Actually, full type deduction should be in vigor, but it is known that
the feature has more than a few bugs. Feel free to report any instance
in which type deduction does not work in bugzilla.

Andrei

int f(int delegate(int) g) {
 return g(13);
}
void main() {
 f((auto x) { return x+13; });
}

This does not compile in D v2.034. Am I missing something?


No, in this context the exact type can be inferred unambiguously 
without worrying about overloading.


The program should be roughly equivalent with:

int f(int delegate(int) g) {
return g(13);
}

auto __fun(T)(T x) { return x+13; }

void main() {
f(__fun);
}

which fails with

Internal error: e2ir.c 644

:o)


Can't reproduce that. It doesn't ICE for me. Tried on several DMD 
versions. (Doesn't compile, though).


Sorry, it's the emacs paste buffer being different from Thunderbird's 
that's the problem. Please try this.


int f(int delegate(int) g) {
return g(13);
}

void main() {
auto __fun(T)(T x) { return x+13; }
f(cast(int delegate(int)) __fun);
}

On my machine:

__fun(T)
Internal error: e2ir.c 644

FWIW this should work too:

int f(int delegate(int) g) {
return g(13);
}

void main() {
auto __fun(T)(T x) { return x+13; }
int delegate(int) __tmp = __fun;
f(__tmp);
}

That doesn't compile with:

./test.d(31): Error: __fun(T) is not an lvalue
./test.d(31): Error: cannot implicitly convert expression ((__fun(T))) 
of type void* to int delegate(int)



Andrei


Re: Proposed D2 Feature: = for anonymous delegates

2009-10-21 Thread Don

Andrei Alexandrescu wrote:

Don wrote:

Andrei Alexandrescu wrote:

language_fan wrote:

Wed, 21 Oct 2009 12:35:41 +0200, Pelle Månsson thusly wrote:


Andrei Alexandrescu wrote:

Pelle Månsson wrote:

Jason House wrote:

Andrei Alexandrescu Wrote:


Jason House wrote:

Am I the only one that has trouble remembering how to write an
inline anonymous delegate when calling a function? At a minimum,
both Scala and C# use (args) = { body; } syntax. Can we please
sneak it into D2?

We have (args) { body; }

Andrei

Somehow, I missed that. What kind of type inference, if any, is
allowed? Scala and C# allow omiting the type. Lately I'm doing a 
lot

of (x) = { return x.foo(7); } in C# and it's nice to omit the
amazingly long type for x. The IDE even knows the type of x for
intellisense... I think scala would allow x = foo(7), or maybe 
even
= _.foo(7) or even _.foo(7). I haven't written much scala, so I 
may

be way off...
Recent experiments by myself indicate you cannot omit the type 
and you

cannot use auto for the type, so you actually need to type your
VeryLongClassName!(With, Templates) if you need it.

I sort of miss automatic type deduction.
Actually, full type deduction should be in vigor, but it is known 
that
the feature has more than a few bugs. Feel free to report any 
instance

in which type deduction does not work in bugzilla.

Andrei

int f(int delegate(int) g) {
 return g(13);
}
void main() {
 f((auto x) { return x+13; });
}

This does not compile in D v2.034. Am I missing something?


No, in this context the exact type can be inferred unambiguously 
without worrying about overloading.


The program should be roughly equivalent with:

int f(int delegate(int) g) {
return g(13);
}

auto __fun(T)(T x) { return x+13; }

void main() {
f(__fun);
}

which fails with

Internal error: e2ir.c 644

:o)


Can't reproduce that. It doesn't ICE for me. Tried on several DMD 
versions. (Doesn't compile, though).


Sorry, it's the emacs paste buffer being different from Thunderbird's 
that's the problem. Please try this.


int f(int delegate(int) g) {
return g(13);
}

void main() {
auto __fun(T)(T x) { return x+13; }
f(cast(int delegate(int)) __fun);
}

On my machine:

__fun(T)
Internal error: e2ir.c 644


Yup. I've created bug 3432 with a reduced test case.


Re: d3 ?

2009-10-21 Thread dolive
Stewart Gordon дµ½:

 Jason House wrote:
  dolive Wrote:
  
  will appear d3 ? What are the tasks ?  it's not backward compatible 
  with D2 ? What major changes ?
  
  My understanding is that there will be a significant gap between the 
  finalization of D2 and the start of D3. Bartosz's ownership scheme may 
  be part of D3.
 snip
 
 It would be really good if this is going to happen.  It might even mean 
 that D1 is going to be finished first.
 
 What sparked this subject, anyway?
 
 Stewart.

Read the sparked of this paste: D and open development model,and Andrei 
Alexandrescu initiated the discussion of the many grammatical..

I'm Looking forward to d2 stability as soon as possible.

thank you re me !

dolive



Re: Revamped concurrency API (Don can you contact Bartosz ?)

2009-10-21 Thread Leandro Lucarella
Don, el 21 de octubre a las 09:46 me escribiste:
 Nick B wrote:
 Don wrote:
 
 
 
 Don, are you able to contact Bartosz, re the details of this test case.
 
 Nick B
 
 Bartosz has sent it to me. I can reproduce the error. It's my
 top priority, but it'll take a while -- it's nasty.
 
 Don - thanks for filing this. I did try to contact you, via
 bugzilla email (which bounced back)and via Skype,(no reply),
 without success.
 
 Nick B
 
 All my public email addresses are fake. Bugzilla is just spam bait.
 It clearly comes from a more innocent age. I once made the mistake
 of submitting a bug to gcc. Although the GCC Bugzilla hides the
 email in the submitter field, the idiots include the real email
 address in the 100% useless 'X-Ref' line. Two weeks later, my email
 address was dead. I've never made that mistake again.
 I am contactable through my dsource account.

You don't even use a real account for personal e-mails! That's odd.
I couldn't reply your private e-mail about changing the title of the
bugzilla report because the From address were fake.

-- 
Leandro Lucarella (AKA luca) http://llucax.com.ar/
--
GPG Key: 5F5A8D05 (F8CD F9A7 BF00 5431 4145  104C 949E BFB6 5F5A 8D05)
--
Hoy estuvimos en el museo de antropología, pero yo voy a volver
para estar por lo menos un día ahí adentro... es una locura, como Disney pero
de indigenas
-- Carla Lucarella (10/2008 contando de su viaje a México)


Re: static arrays becoming value types

2009-10-21 Thread Leandro Lucarella
Yigal Chripun, el 21 de octubre a las 07:18 me escribiste:
 On 21/10/2009 05:48, Robert Jacques wrote:
 On Tue, 20 Oct 2009 23:30:48 -0400, Leandro Lucarella llu...@gmail.com
 wrote:
 Robert Jacques, el 20 de octubre a las 21:06 me escribiste:
 Now, if SOL allowed tuples to do things you can't do today in D,
 like assign a tuple to a struct with the same signature, then this
 might be a point. But that wasn't the example given.
 
 Yes, that's another thing that can be done without real tuple support in
 the language. Anyway, I guess I was a little exaggerated with '*way far*
 from ideal', but I'm convinced there is plenty of room for improvements.
 =)
 
 
 Would you happen to know of a language which does tuples well already?
 
 pick any functional language.. my favorite is ML

Or Python ;)

-- 
Leandro Lucarella (AKA luca) http://llucax.com.ar/
--
GPG Key: 5F5A8D05 (F8CD F9A7 BF00 5431 4145  104C 949E BFB6 5F5A 8D05)
--
HACIA NEUQUEN: EL JUEVES SALDRA CARAVANA CON PERROS
DESDE CAPITAL EN APOYO AL CACHORRO CONDENADO A MUERTE
-- Crónica TV


d2 stability ?

2009-10-21 Thread dolive
Hope that will not be compatible with the syntax changes are put to realize d3, 
d2 as soon as possible to stabilize the full fix bugs and development of phobos 
library .

thanks to all !

dolive



Re: static arrays becoming value types

2009-10-21 Thread Robert Jacques
On Wed, 21 Oct 2009 02:23:09 -0400, language_fan f...@bar.com.invalid  
wrote:

Tue, 20 Oct 2009 16:25:05 -0400, Robert Jacques thusly wrote:


On Tue, 20 Oct 2009 15:19:15 -0400, language_fan f...@bar.com.invalid
wrote:


Real tuple types do not have a special type tag which gets injected
implicitly with structs. So every time you try to do something
lightweight by emulating tuples, you need to refer to the global Tuple
type or bang your head to the wall.


Or use a templated opAssign mixin to allow two desperate types to be
assigned to each other.


Wow, you need templates to implement == for built-in values types, nice..


Unlike C++, D templates don't require a PhD to use. And it's definitely  
better that banging your head against the wall.



Besides, I think you're comparing apples to oranges. In the SOL example,
you use the same declaration for all types. Shouldn't the SOL example
be:

   val a = (1,2) : [Int,Int]
   val b = (1,2) : [Int,Int]
   val c = (2,3) : MyCustomTupleType[Int,Int]

which would probably generate:
  assert(a == b); // ok
  assert(a != c); // Error: incompatible types for ((a) != (b))


If you have built-in tuple literals, there is no way you can build a
MyCustomTupleType without resorting to other language features. There are
no apples and oranges, cause they both are seen as (Int,Int) by the
equivalence checker. Do you understand how equivalence works in
structural typing system (http://en.wikipedia.org/wiki/
Structural_type_system) vs nominal typing? In structural equivalence
there are no names attached to the types (well there might be, but those
are omitted in the comparison), only their internal structure matters.

Why would anyone want to create two incompatible tuples by default as you
still would have 'typedef' and 'struct' for implementing just that.


My issue was that all your example _showed_ was nominal typing. Though I  
didn't mention it by name, I did mention that if SOL tuples had structural  
typing, it might would be a different story. (Well, until/if  
opImplicitCast was implemented, as it would allow for structural typing.)





Re: static arrays becoming value types

2009-10-21 Thread language_fan
Wed, 21 Oct 2009 11:07:29 -0400, Robert Jacques thusly wrote:

 On Wed, 21 Oct 2009 02:23:09 -0400, language_fan f...@bar.com.invalid
 wrote:
 Tue, 20 Oct 2009 16:25:05 -0400, Robert Jacques thusly wrote:

 On Tue, 20 Oct 2009 15:19:15 -0400, language_fan f...@bar.com.invalid
 wrote:

 Real tuple types do not have a special type tag which gets injected
 implicitly with structs. So every time you try to do something
 lightweight by emulating tuples, you need to refer to the global
 Tuple type or bang your head to the wall.

 Or use a templated opAssign mixin to allow two desperate types to be
 assigned to each other.

 Wow, you need templates to implement == for built-in values types,
 nice..
 
 Unlike C++, D templates don't require a PhD to use. And it's definitely
 better that banging your head against the wall.
 
 Besides, I think you're comparing apples to oranges. In the SOL
 example, you use the same declaration for all types. Shouldn't the SOL
 example be:

val a = (1,2) : [Int,Int]
val b = (1,2) : [Int,Int]
val c = (2,3) : MyCustomTupleType[Int,Int]

 which would probably generate:
   assert(a == b); // ok
   assert(a != c); // Error: incompatible types for ((a) != (b))

 If you have built-in tuple literals, there is no way you can build a
 MyCustomTupleType without resorting to other language features. There
 are no apples and oranges, cause they both are seen as (Int,Int) by the
 equivalence checker. Do you understand how equivalence works in
 structural typing system (http://en.wikipedia.org/wiki/
 Structural_type_system) vs nominal typing? In structural equivalence
 there are no names attached to the types (well there might be, but
 those are omitted in the comparison), only their internal structure
 matters.

 Why would anyone want to create two incompatible tuples by default as
 you still would have 'typedef' and 'struct' for implementing just that.
 
 My issue was that all your example _showed_ was nominal typing. Though I
 didn't mention it by name, I did mention that if SOL tuples had
 structural typing, it might would be a different story. (Well, until/if
 opImplicitCast was implemented, as it would allow for structural
 typing.)

Why do you insist on using nominal typing for tuples and the library 
defined literal. If I want plain old tuples without any kind of type 
name, why should I care about extra hand waving needed to make it work. I 
see opImplicitCast, introspection done with templates and all kinds of 
other voodoo to be ugly hacks. This is nothing more than one of the basic 
value types without any special semantics, for $deity's sake. If you like 
the hacky approach so much, why don't all built-in types (like static 
arrays etc.) use the same method? Implementation wise tuples are much 
simpler than D's arrays or AAs, still they are treated like some 2nd 
class citizen from some notorious 3rd world country.

Why is it so damn hard to change the 90% correctly implemented built-in 
tuples to work like in any other tuple supporting language. Do you 
somehow fancy verbose syntax for C++ compatibility reasons (ah, the good 
old std::tr1::make_tupleint, int, makes me want to wank every time..) 
Try Ruby, try python, try *ML etc. They all somehow got it right.


Re: static arrays becoming value types

2009-10-21 Thread Andrei Alexandrescu

language_fan wrote:

Wed, 21 Oct 2009 11:07:29 -0400, Robert Jacques thusly wrote:

My issue was that all your example _showed_ was nominal typing. Though I
didn't mention it by name, I did mention that if SOL tuples had
structural typing, it might would be a different story. (Well, until/if
opImplicitCast was implemented, as it would allow for structural
typing.)


Why do you insist on using nominal typing for tuples and the library 
defined literal. If I want plain old tuples without any kind of type 
name, why should I care about extra hand waving needed to make it work.


I'm late in this dialog, but I'm not seeing an impediment here. What 
does it matter to you that tuples actually have a name vs. not having a 
name at all?


I 
see opImplicitCast, introspection done with templates and all kinds of 
other voodoo to be ugly hacks. This is nothing more than one of the basic 
value types without any special semantics, for $deity's sake. If you like 
the hacky approach so much, why don't all built-in types (like static 
arrays etc.) use the same method? Implementation wise tuples are much 
simpler than D's arrays or AAs, still they are treated like some 2nd 
class citizen from some notorious 3rd world country.


How and why are they treated badly?

Why is it so damn hard to change the 90% correctly implemented built-in 
tuples to work like in any other tuple supporting language. Do you 
somehow fancy verbose syntax for C++ compatibility reasons (ah, the good 
old std::tr1::make_tupleint, int, makes me want to wank every time..) 
Try Ruby, try python, try *ML etc. They all somehow got it right.


What exactly didn't D's tuples get right?


Andrei


Re: static arrays becoming value types

2009-10-21 Thread Bill Baxter
On Wed, Oct 21, 2009 at 8:48 AM, Andrei Alexandrescu
seewebsiteforem...@erdani.org wrote:
 language_fan wrote:

 Wed, 21 Oct 2009 11:07:29 -0400, Robert Jacques thusly wrote:

 My issue was that all your example _showed_ was nominal typing. Though I
 didn't mention it by name, I did mention that if SOL tuples had
 structural typing, it might would be a different story. (Well, until/if
 opImplicitCast was implemented, as it would allow for structural
 typing.)

 Why do you insist on using nominal typing for tuples and the library
 defined literal. If I want plain old tuples without any kind of type name,
 why should I care about extra hand waving needed to make it work.

 I'm late in this dialog, but I'm not seeing an impediment here. What does it
 matter to you that tuples actually have a name vs. not having a name at all?

 I see opImplicitCast, introspection done with templates and all kinds of
 other voodoo to be ugly hacks. This is nothing more than one of the basic
 value types without any special semantics, for $deity's sake. If you like
 the hacky approach so much, why don't all built-in types (like static arrays
 etc.) use the same method? Implementation wise tuples are much simpler than
 D's arrays or AAs, still they are treated like some 2nd class citizen from
 some notorious 3rd world country.

 How and why are they treated badly?

 Why is it so damn hard to change the 90% correctly implemented built-in
 tuples to work like in any other tuple supporting language. Do you somehow
 fancy verbose syntax for C++ compatibility reasons (ah, the good old
 std::tr1::make_tupleint, int, makes me want to wank every time..) Try
 Ruby, try python, try *ML etc. They all somehow got it right.

 What exactly didn't D's tuples get right?

Well, auto-flattening is a colossally bad idea to be sure.

--bb


Re: static arrays becoming value types

2009-10-21 Thread Andrei Alexandrescu

Bill Baxter wrote:

Well, auto-flattening is a colossally bad idea to be sure.


Well that I agree with. I wonder if we need to fix it for D2. If we 
don't, we risk to live with it like with a chronic cough.


Andrei


this() not executing code on structs

2009-10-21 Thread Andrei Alexandrescu
Today, structs can't write their own this(). There aren't very solid 
reasons for that except that it makes language implementation more 
difficult.


I wonder how much of a problem that could be in practice. I realized 
today that the Counted example - a classic C++ primer example 
featuring a struct that counts its own instances - cannot be implemented 
in D.


In C++ the counted example looks like this:

struct Counted {
   static unsigned count;
   unsigned myCount;
   Counted() { myCount = count++; }
   Counted(const Counted rhs) { myCount = count++; }
   Counted operator=(const Counted rhs) {
  // no writing to myCount
  return *this;
   }
   ~Counted() {
  --count;
   }
}

In D there's no chance to write Counted because you can always create 
Counted objects without executing any code.


struct Counted {
   static uint count;
   uint myCount;
   this() { myCount = count++; }   // ERROR
   this(this) { myCount = count++; }
   ref Counted opAssign(Counted rhs) {
  // no writing to myCount
  return this;
   }
   ~this() {
  --count;
   }
}

This being a toy example, I wonder whether there are much more serious 
examples that would be impossible to implement within D.



Andrei


d optimization: delegates vs. mixin

2009-10-21 Thread zoli

Can the compiler optimize the delegates (foo) to form an inline code, or the 
mixin version is prefered?

module a;

import std.stdio;

void foo2( string s )()
{

for( int i = 0 ; i  10; i++ )
{
mixin( s );
}   
}

void foo( void delegate(int) pDg )
{
for( int i = 0 ; i  10; i++ )
{
pDg( i );
}   
} 

void main()
{
foo( (int a){ writeln( a ); } );
foo2!(writeln( i );)();
}

Thank you 1


Re: static arrays becoming value types

2009-10-21 Thread language_fan
Wed, 21 Oct 2009 10:48:34 -0500, Andrei Alexandrescu thusly wrote:

 language_fan wrote:
 Wed, 21 Oct 2009 11:07:29 -0400, Robert Jacques thusly wrote:
 My issue was that all your example _showed_ was nominal typing. Though
 I didn't mention it by name, I did mention that if SOL tuples had
 structural typing, it might would be a different story. (Well,
 until/if opImplicitCast was implemented, as it would allow for
 structural typing.)
 
 Why do you insist on using nominal typing for tuples and the library
 defined literal. If I want plain old tuples without any kind of type
 name, why should I care about extra hand waving needed to make it work.
 
 I'm late in this dialog, but I'm not seeing an impediment here. What
 does it matter to you that tuples actually have a name vs. not having a
 name at all?

Using tuples in D is a major pain in the ass. In fact it has been made so 
hard that people start avoiding the feature like plague. I wrote some 
test code to reveal how inconsistent their semantics are. Note that you 
need the built-in tuples for some stuff, like assigning and mixed value/
type tuples. Stuples can only be used as values and when the auto-
flattening is not desired.

 STARTS HERE

template Tuple(T...) { alias T Tuple; }

struct STuple(T...) {
  T t;
}

void main() {
  Tuple!(int,int) a; // typeof(this) *is* the official tuple type
  STuple!(int,int) b;  // this is actually a struct

  a = Tuple!(1,1);  // ok
  // Tuple!(int,int) a2 = Tuple!(1,1); // WTF? Error: cannot implicitly 
convert expression (tuple(1,1)) of type (int, int) to int
  auto a3 = Tuple!(1,1); // ok


  b = STuple!(int,int)(1,1); // no easier way? make_tuple!(1,1) ?
  STuple!(int,int) b2 = STuple!(int,int)(1,1); // ok, but very verbose


  auto e1 = a[0];  // ok

  //auto e2 = b[0]; // nope
  auto e3 = b.t[0]; // this is how it works - you could possibly define 
opIndex but how would it work with different types then

   writefln(%s, a); // we get.. 1 !? but..
   writefln(%s, typeof(a).stringof); // (int, int)
   writefln(%s, b); // STuple!(int,int)(1, 1) - rather verbose, but 
suffices


  //auto retTest() { return STuple!(int,int)(1,1); } // no identifier for 
declarator retTest

  STuple!(int,int) retTest2() { return STuple!(int,int)(1,1); }; // ok, 
but a bit too verbose

  int d,e;
  Tuple!(d,e) = Tuple!(10,20); // ok

  // but how to discard an unnecessary value? e.g. (a, _) = (1, 2)

  // Tuple!(d,e) = STuple!(10,20); // nope, not interchangeable
  // b = STuple!(a); // same here

  a = a; // ok
  b = b; // ok
  // a = b; // Error: a is not an lvalue -- interesting!


  Tuple!(d,b) = Tuple!(1, retTest2()); // awesome, with the Tuple I can 
even assign Tuples of STuples!
  //Tuple!(d,a) = Tuple!(1, a); // but Tuples don't help when assigning 
Tuples of Tuples

//test.d(12): Error: expression _a_field_0 is not a valid template 
value argument
//test.d(12): Error: expression _a_field_1 is not a valid template 
value argument
//test.d(47): Error: template instance test.Tuple!
(1,_a_field_0,_a_field_1) error instantiating

  // LET'S MAKE ARRAYS!

   int[] a1; // ok
   int[][] a2; // ok
   auto a1b = [1,2,3]; // ok
   auto a2b = [[1],[2],[3]]; // ok

   //Tuple!(int,int)[] a4; // Error: can't have array of (int, int) -- 
WHY NOT - it's simple, try e.g. ML
   STuple!(int,int)[] a5; // ok

   auto a3b = [Tuple!(1,1)]; // works, but hey did you know this is an 
array of ints!

   auto a4b = [STuple!(int,int)(1,1)]; // ok

   // int[Tuple!(int,int)] a6; // Error: can't have associative array key 
of (int, int)
   int[STuple!(int,int)] a7; // ok

   a7[STuple!(int,int)(1,1)] = 5; // ok

   Tuple!(int,Tuple!(int,int)) a8; // this isn't a (int, (int,int)) tuple 
- it's (int,int,int) !
   STuple!(int,STuple!(int,int)) a9; // ok

   //auto a10 = [ Tuple!(1,1) : 2 ]; // Error: can't have associative 
array key of (int, int) -- Why did this work in array literal then?!

   auto a11 = [ STuple!(int,int)(1,1) : 2 ]; // ok

   alias Tuple!(int, 5) foo;
   // alias STuple!(int, 5) foo2; // parameters can only be types
}


Re: static arrays becoming value types

2009-10-21 Thread language_fan
Wed, 21 Oct 2009 16:54:22 +, language_fan thusly wrote:

 Wed, 21 Oct 2009 10:48:34 -0500, Andrei Alexandrescu thusly wrote:
 
 language_fan wrote:
 Wed, 21 Oct 2009 11:07:29 -0400, Robert Jacques thusly wrote:
 My issue was that all your example _showed_ was nominal typing.
 Though I didn't mention it by name, I did mention that if SOL tuples
 had structural typing, it might would be a different story. (Well,
 until/if opImplicitCast was implemented, as it would allow for
 structural typing.)
 
 Why do you insist on using nominal typing for tuples and the library
 defined literal. If I want plain old tuples without any kind of type
 name, why should I care about extra hand waving needed to make it
 work.
 
 I'm late in this dialog, but I'm not seeing an impediment here. What
 does it matter to you that tuples actually have a name vs. not having a
 name at all?
 
 Using tuples in D is a major pain in the ass. In fact it has been made
 so hard that people start avoiding the feature like plague. I wrote some
 test code to reveal how inconsistent their semantics are. Note that you
 need the built-in tuples for some stuff, like assigning and mixed value/
 type tuples. Stuples can only be used as values and when the auto-
 flattening is not desired.

I forgot to say that you need two kinds of tuple literals in your 
standard library in D: one with value semantics, and one that is a 
wrapper around the alias tuple since auto-flattening happens.


Re: this() not executing code on structs

2009-10-21 Thread zoli
Andrei Alexandrescu Wrote:

 Today, structs can't write their own this(). There aren't very solid 
 reasons for that except that it makes language implementation more 
 difficult.
 

If the new operator for the class is redesigned to have multiply allocation 
types 
(allocate on heap, allocate on stack, etc.?), there is no main drawback of 
using classes instead of structs for small objects( like vec2, vec3) as well.
For function parameters, use the reference for in/out and, use a copy of the 
original for value parameters ( personally I hate codes where they change the 
input parameters when they are value types - for larger codes it's hard to 
track what's going on in the function, and whether it's the original or the 
modified value...)

I don't think if there's any reason to use struct with member functions from 
that point, use class instead. And hence struct can be the good old plain data 
structures again, to give some semantics to a block of memory.

But if the scoped allocation is gone, the struct will require much more 
construction powers, and will be used more (ex vec2, vec3, etc.)



Re: static arrays becoming value types

2009-10-21 Thread Andrei Alexandrescu

language_fan wrote:

Wed, 21 Oct 2009 10:48:34 -0500, Andrei Alexandrescu thusly wrote:


language_fan wrote:

Wed, 21 Oct 2009 11:07:29 -0400, Robert Jacques thusly wrote:

My issue was that all your example _showed_ was nominal typing. Though
I didn't mention it by name, I did mention that if SOL tuples had
structural typing, it might would be a different story. (Well,
until/if opImplicitCast was implemented, as it would allow for
structural typing.)

Why do you insist on using nominal typing for tuples and the library
defined literal. If I want plain old tuples without any kind of type
name, why should I care about extra hand waving needed to make it work.

I'm late in this dialog, but I'm not seeing an impediment here. What
does it matter to you that tuples actually have a name vs. not having a
name at all?


Using tuples in D is a major pain in the ass. In fact it has been made so 
hard that people start avoiding the feature like plague.


How do you know what people do?

I wrote some 
test code to reveal how inconsistent their semantics are. Note that you 
need the built-in tuples for some stuff, like assigning and mixed value/

type tuples. Stuples can only be used as values and when the auto-
flattening is not desired.


STARTS HERE


template Tuple(T...) { alias T Tuple; }


Why do you define Tuple instead of using the standard std.typecons.tuple?


struct STuple(T...) {
  T t;
}


Why do you insist on defining another tuple type instead of using the 
one provided by the standard library?



void main() {
  Tuple!(int,int) a; // typeof(this) *is* the official tuple type
  STuple!(int,int) b;  // this is actually a struct

  a = Tuple!(1,1);  // ok


That doesn't work for me at all (with std.typecons.Tuple). I think there 
is confusion about a couple of things. One is that Tuple!(int, int) is a 
type that contains two ints, whereas Tuple!(1, 1) is a type that 
contains two compile-time integral values. So if you write:


a = Tuple!(1, 1);

that is as good syntactically as:

a = int;

which I hope you agree shouldn't quite go through. Write this:

Tuple!(int,int) a;
a = tuple(1, 1);

or this:

auto a = tuple(1, 1);

  // Tuple!(int,int) a2 = Tuple!(1,1); // WTF? Error: cannot implicitly 
convert expression (tuple(1,1)) of type (int, int) to int


Yeah, WTF that doesn't work either:

int a2 = int;


  auto a3 = Tuple!(1,1); // ok


Not ok on my machine, nor it should be ok as this is also not ok:

auto a3 = int;


  b = STuple!(int,int)(1,1); // no easier way? make_tuple!(1,1) ?


Yeah try tuple(1, 1) in conjunction with std.typecons.Tuple.


  STuple!(int,int) b2 = STuple!(int,int)(1,1); // ok, but very verbose


Well write this:

auto stuple(T...)(T args) {
return STuple!(T)(args);
}


  auto e1 = a[0];  // ok


This doesn't work because of a bug in the compiler, but this does with 
std.typecons.Tuple:


auto e1 = a.field[0];

etc. etc. etc.

I'm sure you make a couple of good points, but they are difficult to 
find. I suggest you peruse std.typecons.Tuple and submit any bugs you 
find to bugzilla.



Andrei


Re: static arrays becoming value types

2009-10-21 Thread language_fan
Wed, 21 Oct 2009 16:54:22 +, language_fan thusly wrote:

 Wed, 21 Oct 2009 10:48:34 -0500, Andrei Alexandrescu thusly wrote:
 
 language_fan wrote:
 Wed, 21 Oct 2009 11:07:29 -0400, Robert Jacques thusly wrote:
 My issue was that all your example _showed_ was nominal typing.
 Though I didn't mention it by name, I did mention that if SOL tuples
 had structural typing, it might would be a different story. (Well,
 until/if opImplicitCast was implemented, as it would allow for
 structural typing.)
 
 Why do you insist on using nominal typing for tuples and the library
 defined literal. If I want plain old tuples without any kind of type
 name, why should I care about extra hand waving needed to make it
 work.
 
 I'm late in this dialog, but I'm not seeing an impediment here. What
 does it matter to you that tuples actually have a name vs. not having a
 name at all?
 
 Using tuples in D is a major pain in the ass. In fact it has been made
 so hard that people start avoiding the feature like plague. I wrote some
 test code to reveal how inconsistent their semantics are. Note that you
 need the built-in tuples for some stuff, like assigning and mixed value/
 type tuples. Stuples can only be used as values and when the auto-
 flattening is not desired.
 
 STARTS HERE

Even though not being an expert in Python (have not really used it), as 
an experiment I managed to successfully port the examples in 2 minutes 
without any kind of problems.

a = (1,1)
e1 = a[0]

print a

def retTest():
  return (1,1)

(d,e) = (10,20)

(d,_) = (10,20)

(d,b) = (1, retTest())

a3b = [ (1,1), (2,2) ]

a7 = { (1,1) : 5 }

a8 = { 5 : (1,1)}



Re: this() not executing code on structs

2009-10-21 Thread dsimcha
== Quote from zoli (z...@freemail.hu)'s article
 Andrei Alexandrescu Wrote:
  Today, structs can't write their own this(). There aren't very solid
  reasons for that except that it makes language implementation more
  difficult.
 
 If the new operator for the class is redesigned to have multiply allocation 
 types
 (allocate on heap, allocate on stack, etc.?), there is no main drawback of 
 using
classes instead of structs for small objects( like vec2, vec3) as well.

Yes there is.  How about the cost of storing vtbl and monitor?  Actually, just
last night I was in a corner case where this mattered (as well as needing fine
control over allocation), so I ended up rolling my own polymorphism with 
structs.
 This is not a complaint about the design of D classes.  They do exactly what 
they
should do:  Handle the first 99% of use cases well and make people in obscure
corner cases roll their own from lower level primitives rather than succumbing 
to
the inner platform effect.  However, I think it would be ridiculous not to allow
simple syntactic sugar like non-polymorphic member functions on structs.

 I don't think if there's any reason to use struct with member functions from
that point, use class instead. And hence struct can be the good old plain data
structures again, to give some semantics to a block of memory.

Ok, simple example that's not a corner case:  How about storing one inline in an
array?


Re: static arrays becoming value types

2009-10-21 Thread language_fan
Wed, 21 Oct 2009 12:35:35 -0500, Andrei Alexandrescu thusly wrote:

 language_fan wrote:
 void main() {
   Tuple!(int,int) a; // typeof(this) *is* the official tuple type
   STuple!(int,int) b;  // this is actually a struct
 
   a = Tuple!(1,1);  // ok
 
 That doesn't work for me at all (with std.typecons.Tuple). I think there
 is confusion about a couple of things. One is that Tuple!(int, int) is a
 type that contains two ints, whereas Tuple!(1, 1) is a type that
 contains two compile-time integral values. So if you write:
 
 a = Tuple!(1, 1);
 
 that is as good syntactically as:
 
 a = int;

It might be if we use your definition of tuple. But the mighty compiler 
dmd 2.035 himself calls my types constructed with my template

 template Tuple(T...) { alias T Tuple; }

a tuple. How do you explain that? If the resulting type is tuple 
according to dmd, why do you think it is actually not.

If it works like you say, why does this work then?

  Tuple!(int,int) a;
  a = Tuple!(12,13);

Here 'a' has a real runtime type (int,int) which is a runtime tuple 
according to dmd. And I assign a value to the tuple on runtime. I can 
even test it by printing the values a[0] and a[1] with writefln. So why 
didn't you just fix this particular tuple type and why did you come up 
with a library level hack?

Show me a better way to achieve this with your tuple system.

  int d,e;
  Tuple!(d,e) = Tuple!(10,20);

It's still not clear to me why you don't want to add full syntactic 
support for built-in tuples. Do you somehow find this kind of code 
difficult to read or maintain?

(int,int) a = (1,1);
int e1 = a[0];

writefln(a);

(int,int) retTest() { return (1,1); }

int d,e;

(d,e) = (10,20);

(d,_) = (10,20);

(int,int) b;
(d,b) = (1, retTest());

auto a3b = [ (1,1), (2,2) ];

auto a7 = [ (1,1) : 5 ];

auto a8 = [ 5 : (1,1)];

I want to know what is the rationale behind not accepting this semantics 
that is so widely used in other languages (and I very well mean the 
languages that *have* built-in tuple types).


Re: static arrays becoming value types

2009-10-21 Thread Leandro Lucarella
language_fan, el 21 de octubre a las 17:52 me escribiste:
 Wed, 21 Oct 2009 16:54:22 +, language_fan thusly wrote:
 
  Wed, 21 Oct 2009 10:48:34 -0500, Andrei Alexandrescu thusly wrote:
  
  language_fan wrote:
  Wed, 21 Oct 2009 11:07:29 -0400, Robert Jacques thusly wrote:
  My issue was that all your example _showed_ was nominal typing.
  Though I didn't mention it by name, I did mention that if SOL tuples
  had structural typing, it might would be a different story. (Well,
  until/if opImplicitCast was implemented, as it would allow for
  structural typing.)
  
  Why do you insist on using nominal typing for tuples and the library
  defined literal. If I want plain old tuples without any kind of type
  name, why should I care about extra hand waving needed to make it
  work.
  
  I'm late in this dialog, but I'm not seeing an impediment here. What
  does it matter to you that tuples actually have a name vs. not having a
  name at all?
  
  Using tuples in D is a major pain in the ass. In fact it has been made
  so hard that people start avoiding the feature like plague. I wrote some
  test code to reveal how inconsistent their semantics are. Note that you
  need the built-in tuples for some stuff, like assigning and mixed value/
  type tuples. Stuples can only be used as values and when the auto-
  flattening is not desired.
  
  STARTS HERE
 
 Even though not being an expert in Python (have not really used it), as 
 an experiment I managed to successfully port the examples in 2 minutes 
 without any kind of problems.

I think this is an important point too. Maybe tuples are not *that* broken
as stated in this thread, but they are quite more complex to understand
than tuples in other languages, and they feel somehow hackish.

 a = (1,1)
 e1 = a[0]
 
 print a
 
 def retTest():
   return (1,1)
 
 (d,e) = (10,20)
 
 (d,_) = (10,20)
 
 (d,b) = (1, retTest())
 
 a3b = [ (1,1), (2,2) ]
 
 a7 = { (1,1) : 5 }
 
 a8 = { 5 : (1,1)}

In python you can even do:

def f(a, b, c):
print a, b, c

x = (b, c)
f(a, *x) # calls to f(a, b, c)

I think this is only possible in D with type tuples, not with ... value
tuples? That's part of the complexity, having 2 type of tuples is very
confusing.

-- 
Leandro Lucarella (AKA luca) http://llucax.com.ar/
--
GPG Key: 5F5A8D05 (F8CD F9A7 BF00 5431 4145  104C 949E BFB6 5F5A 8D05)
--
You are the very reason why everything happens to you


Re: Condition Mutexes

2009-10-21 Thread Bartosz Milewski
dsimcha Wrote:


 void main() {
 condition = new Condition( new Mutex() );
 auto T = new Thread(waitThenPrint);
 T.start();
 condition.notify();  // Never wakes up and prints FOO.
 }

Your program terminates immediately after sending the notification. You need to 
stall the exit until the other thread has a chance to wake up. 


Re: static arrays becoming value types

2009-10-21 Thread Andrei Alexandrescu

language_fan wrote:

Wed, 21 Oct 2009 12:35:35 -0500, Andrei Alexandrescu thusly wrote:


language_fan wrote:

void main() {
  Tuple!(int,int) a; // typeof(this) *is* the official tuple type
  STuple!(int,int) b;  // this is actually a struct

  a = Tuple!(1,1);  // ok

That doesn't work for me at all (with std.typecons.Tuple). I think there
is confusion about a couple of things. One is that Tuple!(int, int) is a
type that contains two ints, whereas Tuple!(1, 1) is a type that
contains two compile-time integral values. So if you write:

a = Tuple!(1, 1);

that is as good syntactically as:

a = int;


It might be if we use your definition of tuple. But the mighty compiler 
dmd 2.035 himself calls my types constructed with my template



template Tuple(T...) { alias T Tuple; }


a tuple. How do you explain that? If the resulting type is tuple 
according to dmd, why do you think it is actually not.


If it works like you say, why does this work then?


 Tuple!(int,int) a;
 a = Tuple!(12,13);


Here 'a' has a real runtime type (int,int) which is a runtime tuple 
according to dmd. And I assign a value to the tuple on runtime. I can 
even test it by printing the values a[0] and a[1] with writefln. So why 
didn't you just fix this particular tuple type and why did you come up 
with a library level hack?


Show me a better way to achieve this with your tuple system.


I don't understand what you are trying to accomplish. As far as I can 
tell you want to do this:


Tuple!(int, int) a;
a = tuple(12, 13);
int x = a.field[0];

and similar things. I have no idea why you refuse to do it that way.


 int d,e;
 Tuple!(d,e) = Tuple!(10,20);


It's still not clear to me why you don't want to add full syntactic 
support for built-in tuples. Do you somehow find this kind of code 
difficult to read or maintain?


(int,int) a = (1,1);
int e1 = a[0];

writefln(a);

(int,int) retTest() { return (1,1); }

int d,e;

(d,e) = (10,20);

(d,_) = (10,20);

(int,int) b;
(d,b) = (1, retTest());

auto a3b = [ (1,1), (2,2) ];

auto a7 = [ (1,1) : 5 ];

auto a8 = [ 5 : (1,1)];

I want to know what is the rationale behind not accepting this semantics 
that is so widely used in other languages (and I very well mean the 
languages that *have* built-in tuple types).


To effect this, there'd first be a need to eliminate the current 
semantics of the comma operator. I probably find it as useless as the 
next guy, and don't take one second to buy into Walter's theory that it 
makes it easy to generate code (that may as well be his least convincing 
argument to date), but really there's two parts to your suggestion: (1) 
eliminate the comma operator, (2) make the comma operator work for 
tuples. I suspect there are some syntactical issues with (2).



Andrei


Re: this() not executing code on structs

2009-10-21 Thread zoli
  If the new operator for the class is redesigned to have multiply 
  allocation types
  (allocate on heap, allocate on stack, etc.?), there is no main drawback of 
  using
 classes instead of structs for small objects( like vec2, vec3) as well.
 
 Yes there is.  How about the cost of storing vtbl and monitor?  Actually, just

I keep forgetting those (4-8) extra bytes per instance :)
And what about the final classes (with no ancestors)? Is there a vtbl for them 
since they cannot be derived and they have no virtual parent to inherit members 
from ? Or the Object with opHash and the other operators are virtual by nature 
in all classes ? (sorry, I don't know D that much)

Well, actually it seems as struct is a much better and clear solution. In that 
case I vote for this().



Re: Condition Mutexes

2009-10-21 Thread dsimcha
== Quote from Bartosz Milewski (bartosz-nos...@relisoft.com)'s article
 dsimcha Wrote:
  void main() {
  condition = new Condition( new Mutex() );
  auto T = new Thread(waitThenPrint);
  T.start();
  condition.notify();  // Never wakes up and prints FOO.
  }
 Your program terminates immediately after sending the notification. You need 
 to
stall the exit until the other thread has a chance to wake up.

Thanks.  I've implemented this, along w/ one other suggestion from another 
poster.
 Here's the new program.  It still doesn't work.  Has anyone successfully used
core.sync.condition from druntime *on D2, not the Tango version on D1*?  If it
works, then it should be better documented so people who aren't already 
threading
gurus can figure out how to use it.  If it doesn't work, then as soon as I can
confirm that I'm not the problem, I'll go file a bug report.

Bartosz, since you're a threading guru, could you please write a simple test
program using core.sync.condition and see if it works, and if not either file a
bug report or let me know?

import core.sync.mutex, core.sync.condition, core.thread, std.stdio;

__gshared Condition condition;
__gshared Mutex mutex;

void waitThenPrint() {
mutex.lock;
condition.wait();
mutex.unlock;
writeln(FOO);
}

void main() {
mutex = new Mutex;
condition = new Condition(mutex);
auto T = new Thread(waitThenPrint);
T.start();
condition.notify();  // Never wakes up and prints FOO.
T.join;
}


Re: this() not executing code on structs

2009-10-21 Thread dsimcha
== Quote from zoli (ga...@freemail.hu)'s article
   If the new operator for the class is redesigned to have multiply
allocation types
   (allocate on heap, allocate on stack, etc.?), there is no main drawback 
   of using
  classes instead of structs for small objects( like vec2, vec3) as well.
 
  Yes there is.  How about the cost of storing vtbl and monitor?  Actually, 
  just
 I keep forgetting those (4-8) extra bytes per instance :)
 And what about the final classes (with no ancestors)?

Even final classes w/ no explicit ancestors are implicitly subclasses of Object,
which defines virtual functions.  Therefore, *all* class instances must have a
vtbl pointer.


Re: d optimization: delegates vs. mixin

2009-10-21 Thread bearophile
zoli:
 Can the compiler optimize the delegates (foo) to form an inline code, or the 
 mixin version is prefered?

Today D compilers are in general not smart enough yet (like the Scala compiler, 
for example) to inline delegates. But there's an alternative to string mixins, 
in D2 you can pass a templated function, even one where you omit the type of 
the arguments :-)
There's no shortage of tricks in D2.

Bye,
bearophile


Re: static arrays becoming value types

2009-10-21 Thread bearophile
Leandro Lucarella:

 In python you can even do:
 
 def f(a, b, c):
   print a, b, c
 
 x = (b, c)
 f(a, *x) # calls to f(a, b, c)

In Python2.x you can also do:

def foo(x, (y, (z1, z2))):
print z2
print z1
print y
print x

Z = (1, 2)
yz = [0, Z]
foo(-1, yz)

That outputs:

2
1
0
-1

Bye,
bearophile


Re: static arrays becoming value types

2009-10-21 Thread language_fan
Wed, 21 Oct 2009 13:41:50 -0500, Andrei Alexandrescu thusly wrote:

 I don't understand what you are trying to accomplish. As far as I can
 tell you want to do this:
 
 Tuple!(int, int) a;
 a = tuple(12, 13);
 int x = a.field[0];

Not only that, but also this:

  int d,e;
  Tuple!(d,e) = Tuple!(10,20);

 and similar things. I have no idea why you refuse to do it that way.

You somehow refuse to see that D has a tuple type which the compiler 
calls a tuple. Run 'strings /path/to/dmd|wc -l' and you'll see 28 
instances of the word 'tuple'. If there was no built-in support, why does 
the executable contain the word then?

Here..

 template Z(T...) { alias T Z; }
 Z!(int,int) a;
 pragma(msg,a.stringof);

I did not mention the word tuple, but guess what dmd thinks. If it is not 
a tuple, why does dmd output 'tuple(_a_field_0,_a_field_1)'? Apparently 
this does not follow the math book definition of tuple nor is the 
traditional FPL tuple, but a special D flavor of tuple.

Walter decided to build a tuple type, but something happened and he later 
started restricting its use (IIRC it *was* possible to create an array of 
these tuples, but now it is disallowed). What is left is a half-working 
mess mostly useful for compile time meta-programming. It works rather 
nicely there (except that the auto-flattening is sometimes rather 
annoying), but its operation is broken on runtime. You discarded this by 
stating that D does not have a tuple type, you just call it a 'type that 
contains two ints' in my example. DMD calls it a tuple (see .stringof, 
error messages etc.)

I can see that you try to accomplish the same things with your library 
provided version of tuple. But if that is the recommended way of using 
tuples, why there is a bug riddled version in the compiler of the same 
type. It is extremely exhausting to implement a new compiler for D 
because the reference implementation is full of bugs I mentioned in 
previous posts and you cannot really tell how it should work.

 To effect this, there'd first be a need to eliminate the current
 semantics of the comma operator. I probably find it as useless as the
 next guy, and don't take one second to buy into Walter's theory that it
 makes it easy to generate code (that may as well be his least convincing
 argument to date), but really there's two parts to your suggestion: (1)
 eliminate the comma operator, (2) make the comma operator work for
 tuples. I suspect there are some syntactical issues with (2).

I know that very well..


Re: Condition Mutexes

2009-10-21 Thread Jason House
dsimcha Wrote:

 == Quote from Bartosz Milewski (bartosz-nos...@relisoft.com)'s article
  dsimcha Wrote:
   void main() {
   condition = new Condition( new Mutex() );
   auto T = new Thread(waitThenPrint);
   T.start();
   condition.notify();  // Never wakes up and prints FOO.
   }
  Your program terminates immediately after sending the notification. You 
  need to
 stall the exit until the other thread has a chance to wake up.
 
 Thanks.  I've implemented this, along w/ one other suggestion from another 
 poster.
  Here's the new program.  It still doesn't work.  Has anyone successfully used
 core.sync.condition from druntime *on D2, not the Tango version on D1*?  If it
 works, then it should be better documented so people who aren't already 
 threading
 gurus can figure out how to use it.  If it doesn't work, then as soon as I can
 confirm that I'm not the problem, I'll go file a bug report.
 
 Bartosz, since you're a threading guru, could you please write a simple test
 program using core.sync.condition and see if it works, and if not either file 
 a
 bug report or let me know?
 
 import core.sync.mutex, core.sync.condition, core.thread, std.stdio;
 
 __gshared Condition condition;
 __gshared Mutex mutex;
 
 void waitThenPrint() {
 mutex.lock;
 condition.wait();
 mutex.unlock;
 writeln(FOO);
 }
 
 void main() {
 mutex = new Mutex;
 condition = new Condition(mutex);
 auto T = new Thread(waitThenPrint);
 T.start();
 condition.notify();  // Never wakes up and prints FOO.
 T.join;
 }

You should lock condition before calling notify. Even if you did that, you have 
a race for which thread gets the lock first. If the main thread gets it, the 
spawned thread will never receive the notify and hang forever.


Re: static arrays becoming value types

2009-10-21 Thread Denis Koroskin
On Wed, 21 Oct 2009 22:41:50 +0400, Andrei Alexandrescu  
seewebsiteforem...@erdani.org wrote:



language_fan wrote:

Wed, 21 Oct 2009 12:35:35 -0500, Andrei Alexandrescu thusly wrote:


language_fan wrote:

void main() {
  Tuple!(int,int) a; // typeof(this) *is* the official tuple type
  STuple!(int,int) b;  // this is actually a struct

  a = Tuple!(1,1);  // ok
That doesn't work for me at all (with std.typecons.Tuple). I think  
there
is confusion about a couple of things. One is that Tuple!(int, int) is  
a

type that contains two ints, whereas Tuple!(1, 1) is a type that
contains two compile-time integral values. So if you write:

a = Tuple!(1, 1);

that is as good syntactically as:

a = int;
 It might be if we use your definition of tuple. But the mighty  
compiler dmd 2.035 himself calls my types constructed with my template



template Tuple(T...) { alias T Tuple; }
 a tuple. How do you explain that? If the resulting type is tuple  
according to dmd, why do you think it is actually not.

 If it works like you say, why does this work then?


 Tuple!(int,int) a;
 a = Tuple!(12,13);
 Here 'a' has a real runtime type (int,int) which is a runtime tuple  
according to dmd. And I assign a value to the tuple on runtime. I can  
even test it by printing the values a[0] and a[1] with writefln. So why  
didn't you just fix this particular tuple type and why did you come up  
with a library level hack?

 Show me a better way to achieve this with your tuple system.


I don't understand what you are trying to accomplish. As far as I can  
tell you want to do this:


Tuple!(int, int) a;
a = tuple(12, 13);
int x = a.field[0];

and similar things. I have no idea why you refuse to do it that way.


 int d,e;
 Tuple!(d,e) = Tuple!(10,20);
 It's still not clear to me why you don't want to add full syntactic  
support for built-in tuples. Do you somehow find this kind of code  
difficult to read or maintain?

 (int,int) a = (1,1);
int e1 = a[0];
 writefln(a);
 (int,int) retTest() { return (1,1); }
 int d,e;
 (d,e) = (10,20);
 (d,_) = (10,20);
 (int,int) b;
(d,b) = (1, retTest());
 auto a3b = [ (1,1), (2,2) ];
 auto a7 = [ (1,1) : 5 ];
 auto a8 = [ 5 : (1,1)];
 I want to know what is the rationale behind not accepting this  
semantics that is so widely used in other languages (and I very well  
mean the languages that *have* built-in tuple types).


To effect this, there'd first be a need to eliminate the current  
semantics of the comma operator. I probably find it as useless as the  
next guy, and don't take one second to buy into Walter's theory that it  
makes it easy to generate code (that may as well be his least convincing  
argument to date), but really there's two parts to your suggestion: (1)  
eliminate the comma operator, (2) make the comma operator work for  
tuples. I suspect there are some syntactical issues with (2).



Andrei


Well, he could just change the symbol used to denote comma operator to  
some other character (if he uses it so heavily internally), and don't  
expose it to a user.


I don't use tuples a lot myself, but I would love to have multiple return  
types without some clumsy syntax. It's possible even now, but the syntax  
is a bit discouraging:


Tuple!(int,float) foo()
{
return tuple(42, -1.0f);
}

make_tuple(a, b) = foo();

as opposed to:

(int, float) foo()
{
return (42, -1.0f);
}

(a, b) = foo();


Re: d optimization: delegates vs. mixin

2009-10-21 Thread zoli
bearophile Wrote:

 zoli:
  Can the compiler optimize the delegates (foo) to form an inline code, or 
  the mixin version is prefered?
 
 Today D compilers are in general not smart enough yet (like the Scala 
 compiler, for example) to inline delegates. But there's an alternative to 
 string mixins, in D2 you can pass a templated function, even one where you 
 omit the type of the arguments :-)
 There's no shortage of tricks in D2.

Thank you. Could you provide a sample or a link ? 
Sorry, i know it's a d.learn topic..., 
Offtopic: Is it possible to alter the web interface of the news to change 
newsgroups during composition ? 



Re: Condition Mutexes

2009-10-21 Thread dsimcha
== Quote from Jason House (jason.james.ho...@gmail.com)'s article
 dsimcha Wrote:
  == Quote from Bartosz Milewski (bartosz-nos...@relisoft.com)'s article
   dsimcha Wrote:
void main() {
condition = new Condition( new Mutex() );
auto T = new Thread(waitThenPrint);
T.start();
condition.notify();  // Never wakes up and prints FOO.
}
   Your program terminates immediately after sending the notification. You 
   need to
  stall the exit until the other thread has a chance to wake up.
 
  Thanks.  I've implemented this, along w/ one other suggestion from another 
  poster.
   Here's the new program.  It still doesn't work.  Has anyone successfully 
  used
  core.sync.condition from druntime *on D2, not the Tango version on D1*?  If 
  it
  works, then it should be better documented so people who aren't already 
  threading
  gurus can figure out how to use it.  If it doesn't work, then as soon as I 
  can
  confirm that I'm not the problem, I'll go file a bug report.
 
  Bartosz, since you're a threading guru, could you please write a simple test
  program using core.sync.condition and see if it works, and if not either 
  file a
  bug report or let me know?
 
  import core.sync.mutex, core.sync.condition, core.thread, std.stdio;
 
  __gshared Condition condition;
  __gshared Mutex mutex;
 
  void waitThenPrint() {
  mutex.lock;
  condition.wait();
  mutex.unlock;
  writeln(FOO);
  }
 
  void main() {
  mutex = new Mutex;
  condition = new Condition(mutex);
  auto T = new Thread(waitThenPrint);
  T.start();
  condition.notify();  // Never wakes up and prints FOO.
  T.join;
  }
 You should lock condition before calling notify. Even if you did that, you 
 have
a race for which thread gets the lock first. If the main thread gets it, the
spawned thread will never receive the notify and hang forever.

Thanks, but at a more general level, where can I find documentation on how to 
use
conditions properly?  I realize that I have absolutely no fundamental
understanding of how they work or what assumptions they make, but it seems like
there is very little written material on this, either for the general case or 
for
the specific case of core.sync.  For example, for some reason I assumed that a
condition's methods would be already synchronized internally.


Re: this() not executing code on structs

2009-10-21 Thread Denis Koroskin
On Wed, 21 Oct 2009 20:15:16 +0400, Andrei Alexandrescu  
seewebsiteforem...@erdani.org wrote:


Today, structs can't write their own this(). There aren't very solid  
reasons for that except that it makes language implementation more  
difficult.


I wonder how much of a problem that could be in practice. I realized  
today that the Counted example - a classic C++ primer example  
featuring a struct that counts its own instances - cannot be implemented  
in D.


In C++ the counted example looks like this:

struct Counted {
static unsigned count;
unsigned myCount;
Counted() { myCount = count++; }
Counted(const Counted rhs) { myCount = count++; }
Counted operator=(const Counted rhs) {
   // no writing to myCount
   return *this;
}
~Counted() {
   --count;
}
}

In D there's no chance to write Counted because you can always create  
Counted objects without executing any code.


struct Counted {
static uint count;
uint myCount;
this() { myCount = count++; }   // ERROR
this(this) { myCount = count++; }
ref Counted opAssign(Counted rhs) {
   // no writing to myCount
   return this;
}
~this() {
   --count;
}
}

This being a toy example, I wonder whether there are much more serious  
examples that would be impossible to implement within D.



Andrei


I agree it's a very annoying limitation, but I believe there is a  
rationale behind it.


Imagine a class that aggregates a struct:

struct Foo { ... }

class Bar
{
   Foo foo;
   this() {}
   // ...
}

The class object construction is now consists of two steps:

1) memcpy the Bar.classinfo.init
2) call __ctor()

Unlike C++, there is no stage at which class members are being  
initialized, and it simplifies things quite a lot.


Think about the following: what happens if structs will be allowed default  
ctors? How to avoid double initialization?


You may end up with design very similar to C++ in this case (including an  
initialization list).


Some problems could be solved with an enforced explicit initialization of  
each member. That's the only way I see now that would avoid double  
initialization of a struct in presence of default and non-default ctors:


struct Scoped(T) // I like this name a lot more than InPlace, and  
especially InSitu

{
this(Args...)(Args args)
{
T obj = cast(T)data.ptr;
obj.__ctor(args);
}

ubyte[T.classinfo.init.length] data = T.classinfo.init; // I believe  
this should work at compile-time, since classinfo is immutable

}

class Foo
{
this() {}
this(int i) {}
}

class Bar
{
Scoped!(Foo) foo;
this()
{
 // foo is already constructed by now (default ctor is called)  
which is cool

 // but what if I need to initialize it with some other ctor?
 foo = Scoped!(Foo)(42); // double initialization
}

int doesntNeedToBeInitializedExplicitlyInACtor = 17;
}

Enforcing explicit initialization of each member (unless its value is set  
at the declaration, as in the example above) is gracefully solving this  
issue.


Also think about exception safety: what if an exception is thrown in a  
class ctor - should the dtors be invoked on initialized members or not? If  
yes, in what order? D doesn't enforce initialization order, so it's a bit  
tricky to determine what members are already initialized and need to be  
destroyed (with a dtor call) efficiently. C++ handles issues like this  
very well IMO. I believe D should also have a sound solution to this  
problem.


Re: Condition Mutexes

2009-10-21 Thread Jérôme M. Berger

dsimcha wrote:

== Quote from Bartosz Milewski (bartosz-nos...@relisoft.com)'s article

dsimcha Wrote:

void main() {
condition = new Condition( new Mutex() );
auto T = new Thread(waitThenPrint);
T.start();
condition.notify();  // Never wakes up and prints FOO.
}

Your program terminates immediately after sending the notification. You need to

stall the exit until the other thread has a chance to wake up.

Thanks.  I've implemented this, along w/ one other suggestion from another 
poster.
 Here's the new program.  It still doesn't work.  Has anyone successfully used
core.sync.condition from druntime *on D2, not the Tango version on D1*?  If it
works, then it should be better documented so people who aren't already 
threading
gurus can figure out how to use it.  If it doesn't work, then as soon as I can
confirm that I'm not the problem, I'll go file a bug report.

Bartosz, since you're a threading guru, could you please write a simple test
program using core.sync.condition and see if it works, and if not either file a
bug report or let me know?

import core.sync.mutex, core.sync.condition, core.thread, std.stdio;

__gshared Condition condition;
__gshared Mutex mutex;

void waitThenPrint() {
mutex.lock;
condition.wait();
mutex.unlock;
writeln(FOO);
}

void main() {
mutex = new Mutex;
condition = new Condition(mutex);
auto T = new Thread(waitThenPrint);
T.start();
condition.notify();  // Never wakes up and prints FOO.
T.join;
}
	Well, you should lock the mutex before calling condition.notify and 
release it afterwards.


	Note that there is always a chance that notify will be called 
before the thread starts waiting. In that case your program will 
deadlock (randomly).


Jerome
--
mailto:jeber...@free.fr
http://jeberger.free.fr
Jabber: jeber...@jabber.fr



signature.asc
Description: OpenPGP digital signature


Re: Revamping associative arrays

2009-10-21 Thread Piotrek

Bill Baxter pisze:


So C# avoids the ambiguity.

Unless there's some other AA type in C#.

--bb


True. Java does it too. My fault.

Cheers
Piotrek


Re: Revamping associative arrays

2009-10-21 Thread Piotrek

Pelle Månsson pisze:

Piotrek wrote:

Bill Baxter pisze:

On Sun, Oct 18, 2009 at 1:12 PM, Piotrek star...@tlen.pl wrote:

Bill Baxter pisze:

I think the default should be to iterate over whatever 'in' looks at.

I was almost convinced, because that rule has a sense. But treating 
normal

arrays and associative array has more sense to me.


fun (SomeObject object) {
foreach (element;object.arr1){ //normal, but how do I know at first 
look

//just do something with element
}

foreach (element;object.arr2){ // assoc, but how do I know at first 
look

//just do something with element hopefully not index
}


That sounds like an argument that there should be no default, because
either way it's not clear whether you're iterating over keys or
values. 



Really?! That wasn't my intention :) In both cases I wish it were 
values ;)


  Just get rid of the the one-argument foreach over AAs altogether 
and force the user to be

  explicit about it.

I wouldn't do so. Would anybody do an error by thinking that foreach 
(elem,table) should iterate over keys?


Maybe I'm not thinking correctly but for me an assoc array is just an 
array with additional key (index) features thanks to which I save 
space and/or have more indexing method than only integers.



e.g.

Normal array

No.   Item
0George
1Fred
2Dany
3Lil

Index/key is infered from position (offset)


Now Assoc array:

No.Item
10Lindsey
21Romeo
1001C-Jay

Or
No.Item
firstEurope
secondSouth America
thirdAustralia

Or
Names occurrence frequency:

No. Item
Andy21
John23
Kate12

And the only difference is the need for using a hash function for 
value lookup (calculate position) which should not bother a user when 
he doesn't care.


Then when you ask somebody to iterate over the tables, what he will do 
almost for certain? If it would be me, you know... values all the 
time. Even for last example most important values are those numbers 
(despite in this case they're meaningless without keys).


Cheers
Piotrek




Put it this way:
 Is there any time you are interested in the values without the keys?


Yes!


 Is there any time you are interested in the keys without the values?



Yes!

If you're not interested in the keys, the real question would be why you 
are using an associative array instead of just an array.




The answer is simple. I can reuse AA in many different functions. 
Sometimes I need keys other time values and even... both :) That isn't 
the issue. The problem was about what should return short version of 
foreach over AA.


I can think of at least one example of when you want key iteration, 
which would be when using a bool[T] as a set.


See above.

Cheers
Piotrek


Re: static arrays becoming value types

2009-10-21 Thread grauzone

Denis Koroskin wrote:
On Wed, 21 Oct 2009 22:41:50 +0400, Andrei Alexandrescu 
seewebsiteforem...@erdani.org wrote:



language_fan wrote:

Wed, 21 Oct 2009 12:35:35 -0500, Andrei Alexandrescu thusly wrote:


language_fan wrote:

void main() {
  Tuple!(int,int) a; // typeof(this) *is* the official tuple type
  STuple!(int,int) b;  // this is actually a struct

  a = Tuple!(1,1);  // ok
That doesn't work for me at all (with std.typecons.Tuple). I think 
there
is confusion about a couple of things. One is that Tuple!(int, int) 
is a

type that contains two ints, whereas Tuple!(1, 1) is a type that
contains two compile-time integral values. So if you write:

a = Tuple!(1, 1);

that is as good syntactically as:

a = int;
 It might be if we use your definition of tuple. But the mighty 
compiler dmd 2.035 himself calls my types constructed with my template



template Tuple(T...) { alias T Tuple; }
 a tuple. How do you explain that? If the resulting type is tuple 
according to dmd, why do you think it is actually not.

 If it works like you say, why does this work then?


 Tuple!(int,int) a;
 a = Tuple!(12,13);
 Here 'a' has a real runtime type (int,int) which is a runtime tuple 
according to dmd. And I assign a value to the tuple on runtime. I can 
even test it by printing the values a[0] and a[1] with writefln. So 
why didn't you just fix this particular tuple type and why did you 
come up with a library level hack?

 Show me a better way to achieve this with your tuple system.


I don't understand what you are trying to accomplish. As far as I can 
tell you want to do this:


Tuple!(int, int) a;
a = tuple(12, 13);
int x = a.field[0];

and similar things. I have no idea why you refuse to do it that way.


 int d,e;
 Tuple!(d,e) = Tuple!(10,20);
 It's still not clear to me why you don't want to add full syntactic 
support for built-in tuples. Do you somehow find this kind of code 
difficult to read or maintain?

 (int,int) a = (1,1);
int e1 = a[0];
 writefln(a);
 (int,int) retTest() { return (1,1); }
 int d,e;
 (d,e) = (10,20);
 (d,_) = (10,20);
 (int,int) b;
(d,b) = (1, retTest());
 auto a3b = [ (1,1), (2,2) ];
 auto a7 = [ (1,1) : 5 ];
 auto a8 = [ 5 : (1,1)];
 I want to know what is the rationale behind not accepting this 
semantics that is so widely used in other languages (and I very well 
mean the languages that *have* built-in tuple types).


To effect this, there'd first be a need to eliminate the current 
semantics of the comma operator. I probably find it as useless as the 
next guy, and don't take one second to buy into Walter's theory that 
it makes it easy to generate code (that may as well be his least 
convincing argument to date), but really there's two parts to your 
suggestion: (1) eliminate the comma operator, (2) make the comma 
operator work for tuples. I suspect there are some syntactical issues 
with (2).



Andrei


Well, he could just change the symbol used to denote comma operator to 
some other character (if he uses it so heavily internally), and don't 
expose it to a user.


I don't use tuples a lot myself, but I would love to have multiple 
return types without some clumsy syntax. It's possible even now, but the 
syntax is a bit discouraging:


Tuple!(int,float) foo()
{
return tuple(42, -1.0f);
}

make_tuple(a, b) = foo();

as opposed to:

(int, float) foo()
{
return (42, -1.0f);
}

(a, b) = foo();


Or even:

a, b = foo();

or

a, _ = foo();

Works in Python (tm)


Re: d optimization: delegates vs. mixin

2009-10-21 Thread bearophile
zoli:

 Thank you. Could you provide a sample or a link ?

Silly D2 code: 

import std.stdio: writeln;

void table(alias Mapper, T)(T[] arr) {
foreach (el; arr)
writeln(Mapper(el));
}

void main() {
table!((x){ return x * x;})([2, 3, 4]);
}

I don't like that code a lot, I'd like the D compiler to be smarter, so the 
programmer can avoid such silly tricks, and the programmer can program in a 
more functional style (where you use *functions*).


 Sorry, i know it's a d.learn topic..., 

Yep. Better to ask such things there.


 Offtopic: Is it possible to alter the web interface of the news to change 
 newsgroups during composition ?

I don't know. Probably not.

Bye,
bearophile


Re: this() not executing code on structs

2009-10-21 Thread Bartosz Milewski
Andrei Alexandrescu Wrote:

 this() { myCount = count++; }   // ERROR

It's worse than that. Try this:

struct foo {
   this(int dummy = 0) { writeln(Default constructor);}
}

foo x = foo();

Nothing gets printed. If default constructors are disallowed, so should 
constructors with all parameters defaulted.


Re: this() not executing code on structs

2009-10-21 Thread Bartosz Milewski
This means that no non-trivial invariant may be defined for a struct. In most 
cases it doesn't matter, but it might be a problem with the smart pointer 
family. 

For instance, refcounted may not assume that the shared refcount pointer has 
been allocated. Without this invariant all refcounted operations must have 
additional code that tests for null and does the right thing (which is not 
always obvious).


Re: static arrays becoming value types

2009-10-21 Thread Leandro Lucarella
grauzone, el 21 de octubre a las 22:12 me escribiste:
 Or even:
 
 a, b = foo();
 
 or
 
 a, _ = foo();
 
 Works in Python (tm)

_ is a regular symbol (variable name in this case), there is nothing
special about the second form, which is exactly the same as the first. And
BTW, the trailing ; is not needed ;)

-- 
Leandro Lucarella (AKA luca) http://llucax.com.ar/
--
GPG Key: 5F5A8D05 (F8CD F9A7 BF00 5431 4145  104C 949E BFB6 5F5A 8D05)
--
Hey you, standing in the aisles
With itchy feet and fading smiles
Can you feel me?


Re: this() not executing code on structs

2009-10-21 Thread Leandro Lucarella
Bartosz Milewski, el 21 de octubre a las 16:33 me escribiste:
 Andrei Alexandrescu Wrote:
 
  this() { myCount = count++; }   // ERROR
 
 It's worse than that. Try this:
 
 struct foo {
this(int dummy = 0) { writeln(Default constructor);}
 }
 
 foo x = foo();
 
 Nothing gets printed. If default constructors are disallowed, so should
 constructors with all parameters defaulted.

Fill bug reports in bugzilla, please!

-- 
Leandro Lucarella (AKA luca) http://llucax.com.ar/
--
GPG Key: 5F5A8D05 (F8CD F9A7 BF00 5431 4145  104C 949E BFB6 5F5A 8D05)
--
Los jóvenes no son solo brazos que nos cargan... También se los puede
mandar a la guerra, que es su obligación.
-- Ricardo Vaporeso


Re: static arrays becoming value types

2009-10-21 Thread Andrei Alexandrescu

language_fan wrote:
You somehow refuse to see that D has a tuple type which the compiler 
calls a tuple.


D has tuples, it doesn't have tuple literals. Tuple attempts to supplant 
that.



Andrei


Re: Condition Mutexes

2009-10-21 Thread Steven Schveighoffer

On Wed, 21 Oct 2009 14:50:32 -0400, dsimcha dsim...@yahoo.com wrote:


== Quote from Bartosz Milewski (bartosz-nos...@relisoft.com)'s article

dsimcha Wrote:
 void main() {
 condition = new Condition( new Mutex() );
 auto T = new Thread(waitThenPrint);
 T.start();
 condition.notify();  // Never wakes up and prints FOO.
 }
Your program terminates immediately after sending the notification. You  
need to

stall the exit until the other thread has a chance to wake up.

Thanks.  I've implemented this, along w/ one other suggestion from  
another poster.

 Here's the new program.  It still doesn't work.


Here is a major flaw in your logic:

A condition is a *signal* not a *flag*.  In order to catch the signal you  
have to be listening for it.  It's not like a semaphore.


What you need in order to use a condition is a flag that is protected by  
the lock.


Generally, the model is:

thread1()
{
  lock(mutex)
  {
 set(flag);
 condition.notify();
  }
}

thread2()
{
  lock(mutex)
  {
 while(!flag)
   condition.wait();
 unset(flag); // we received the signal, clear it.
  }
}

The condition is basically a way to give control of waking up a thread to  
another thread.  But the condition is not the, um... condition you are  
waiting for :)  You still need a state variable to say hey, you should  
continue now, the state is correctly set.


Think of the flag like a mailbox flag.  You only put it up *after* you put  
mail in the mailbox, and the mailman lowers the flag when he gets the mail  
out.


There are lots of threading tutorials you can probably read to get it.   
But basically, I can break down what exactly happens, I'll do 2 scenarios:


Scenario 1:
1. thread2 locks the mutex, which protects the flag.  It sees that the  
flag is unset, so it waits on the condition.  This *atomically* unlocks  
the mutex and enters the thread into the list of threads to wake up when  
the condition is signaled.
2. thread1 now can lock the mutex, and sets the flag.  It notifies the  
condition, which wakes up thread2.
3. thread2 *remains asleep* until it can reacquire the lock.  thread1  
unlocks the mutex after leaving the scope.
4. thread2 wakes up after reacquiring the mutex, and repeats the  
while-loop, seeing that the flag is now set.

5. thread2 unsets the flag and unlocks the mutex, continuing.

Scenario 2:

1. thread1 locks the mutex.
2. thread2 sleeps because it cannot lock the mutex.
3. thread1 sets the flag, then signals the condition.  Since nobody is  
listening *this doesn't affect anything*.

4. thread1 exits the scope, releasing the mutex.
5. thread2 now acquires the lock, sees the flag is set, and doesn't even  
wait on the condition, unsets the flag, exits the scope, and unlocks the  
mutex.


You can see how the locking is important to protect the atomicity of  
setting the flag, and it is *really* important that the condition wait  
atomically unlocks the mutex and enters the thread into the condition's  
wakeup queue.  So generally speaking: rule 1, don't do anything with a  
condition unless the mutex it uses is locked.  rule 2, always have a state  
that is protected by the same lock that the condition is waiting with.


You also may wonder why there is even a while loop, I mean, why recheck  
the flag after the condition is signalled?  Well, in this case, it's not  
required, but it's very good practice.  When you have a case where the  
flag is not a flag, but a multi-state variable, and you are waiting for a  
specific state, one thread might signal every time the state changes.   
Well, you don't want to continue until you get the state that you want, so  
you need to re-check the state.  Another case is if you have several  
instances of thread2, and you only want to release one of them with the  
signal.


Hope this helps.

-Steve


Re: Condition Mutexes

2009-10-21 Thread dsimcha
== Quote from Steven Schveighoffer (schvei...@yahoo.com)'s article
 On Wed, 21 Oct 2009 14:50:32 -0400, dsimcha dsim...@yahoo.com wrote:
  == Quote from Bartosz Milewski (bartosz-nos...@relisoft.com)'s article
  dsimcha Wrote:
   void main() {
   condition = new Condition( new Mutex() );
   auto T = new Thread(waitThenPrint);
   T.start();
   condition.notify();  // Never wakes up and prints FOO.
   }
  Your program terminates immediately after sending the notification. You
  need to
  stall the exit until the other thread has a chance to wake up.
 
  Thanks.  I've implemented this, along w/ one other suggestion from
  another poster.
   Here's the new program.  It still doesn't work.
 Here is a major flaw in your logic:
 A condition is a *signal* not a *flag*.  In order to catch the signal you
 have to be listening for it.  It's not like a semaphore.
 What you need in order to use a condition is a flag that is protected by
 the lock.
 Generally, the model is:
 thread1()
 {
lock(mutex)
{
   set(flag);
   condition.notify();
}
 }
 thread2()
 {
lock(mutex)
{
   while(!flag)
 condition.wait();
   unset(flag); // we received the signal, clear it.
}
 }
 The condition is basically a way to give control of waking up a thread to
 another thread.  But the condition is not the, um... condition you are
 waiting for :)  You still need a state variable to say hey, you should
 continue now, the state is correctly set.
 Think of the flag like a mailbox flag.  You only put it up *after* you put
 mail in the mailbox, and the mailman lowers the flag when he gets the mail
 out.
 There are lots of threading tutorials you can probably read to get it.
 But basically, I can break down what exactly happens, I'll do 2 scenarios:
 Scenario 1:
 1. thread2 locks the mutex, which protects the flag.  It sees that the
 flag is unset, so it waits on the condition.  This *atomically* unlocks
 the mutex and enters the thread into the list of threads to wake up when
 the condition is signaled.
 2. thread1 now can lock the mutex, and sets the flag.  It notifies the
 condition, which wakes up thread2.
 3. thread2 *remains asleep* until it can reacquire the lock.  thread1
 unlocks the mutex after leaving the scope.
 4. thread2 wakes up after reacquiring the mutex, and repeats the
 while-loop, seeing that the flag is now set.
 5. thread2 unsets the flag and unlocks the mutex, continuing.
 Scenario 2:
 1. thread1 locks the mutex.
 2. thread2 sleeps because it cannot lock the mutex.
 3. thread1 sets the flag, then signals the condition.  Since nobody is
 listening *this doesn't affect anything*.
 4. thread1 exits the scope, releasing the mutex.
 5. thread2 now acquires the lock, sees the flag is set, and doesn't even
 wait on the condition, unsets the flag, exits the scope, and unlocks the
 mutex.
 You can see how the locking is important to protect the atomicity of
 setting the flag, and it is *really* important that the condition wait
 atomically unlocks the mutex and enters the thread into the condition's
 wakeup queue.  So generally speaking: rule 1, don't do anything with a
 condition unless the mutex it uses is locked.  rule 2, always have a state
 that is protected by the same lock that the condition is waiting with.
 You also may wonder why there is even a while loop, I mean, why recheck
 the flag after the condition is signalled?  Well, in this case, it's not
 required, but it's very good practice.  When you have a case where the
 flag is not a flag, but a multi-state variable, and you are waiting for a
 specific state, one thread might signal every time the state changes.
 Well, you don't want to continue until you get the state that you want, so
 you need to re-check the state.  Another case is if you have several
 instances of thread2, and you only want to release one of them with the
 signal.
 Hope this helps.
 -Steve

Thank you.  This was *extremely* helpful.  I'll read over it in more detail 
when I
get back to hacking my futures/parallel foreach lib.


Re: this() not executing code on structs

2009-10-21 Thread Rainer Deyke
Andrei Alexandrescu wrote:
 Today, structs can't write their own this(). There aren't very solid
 reasons for that except that it makes language implementation more
 difficult.
 
 I wonder how much of a problem that could be in practice. I realized
 today that the Counted example - a classic C++ primer example
 featuring a struct that counts its own instances - cannot be implemented
 in D.
 
 In C++ the counted example looks like this:
 
 struct Counted {
static unsigned count;
unsigned myCount;
Counted() { myCount = count++; }
Counted(const Counted rhs) { myCount = count++; }
Counted operator=(const Counted rhs) {
   // no writing to myCount
   return *this;
}
~Counted() {
   --count;
}
 }
 
 In D there's no chance to write Counted because you can always create
 Counted objects without executing any code.
 
 struct Counted {
static uint count;
uint myCount;
this() { myCount = count++; }   // ERROR
this(this) { myCount = count++; }
ref Counted opAssign(Counted rhs) {
   // no writing to myCount
   return this;
}
~this() {
   --count;
}
 }
 
 This being a toy example, I wonder whether there are much more serious
 examples that would be impossible to implement within D.

Any struct that uses dynamic memory allocation internally.

Any struct that registers its instances in some dort of global registry.

'ValueType!T', which turns reference type 'T' into a value type.

A 'ScopedLock' variant that uses a single global mutex.

RAII wrappers over global initialization/deinitialization functions.

A 'UniqueId' struct that initializes to a value that is guaranteed to be
distinct from the vale of any other 'UniqueId' used by the program.


-- 
Rainer Deyke - rain...@eldwood.com


Re: Condition Mutexes

2009-10-21 Thread Bartosz Milewski
dsimcha Wrote:

 Bartosz, since you're a threading guru, could you please write a simple test
 program using core.sync.condition and see if it works, and if not either file 
 a
 bug report or let me know?

Conditions were implemented by Sean Kelly, so he's the guru. The file 
condition.d in core.sync has unit tests, which presumably still run (although I 
don't know if anybody still runs unit tests in druntime). 

If using conditions in D is harder than in Java, than we should rethink their 
implementation. Every D object has a built-in mutex. Conditon variables should 
be able to work with this mutex and with synchronized sections out of the box. 
The most common case should be the easiest. The fact that you are having all 
those technical problems proves my point. 

As for non-technical problems, rewrite your test so that you wait on a 
condition in main and let the new thread do the signalling. That way they won't 
be able to miss each other, as they currently do.


Re: Condition Mutexes

2009-10-21 Thread dsimcha
== Quote from Bartosz Milewski (bartosz-nos...@relisoft.com)'s article
 dsimcha Wrote:
  Bartosz, since you're a threading guru, could you please write a simple test
  program using core.sync.condition and see if it works, and if not either 
  file a
  bug report or let me know?
 Conditions were implemented by Sean Kelly, so he's the guru. The file
condition.d in core.sync has unit tests, which presumably still run (although I
don't know if anybody still runs unit tests in druntime).
 If using conditions in D is harder than in Java, than we should rethink their
implementation. Every D object has a built-in mutex. Conditon variables should 
be
able to work with this mutex and with synchronized sections out of the box. The
most common case should be the easiest. The fact that you are having all those
technical problems proves my point.
 As for non-technical problems, rewrite your test so that you wait on a 
 condition
in main and let the new thread do the signalling. That way they won't be able to
miss each other, as they currently do.

I got my test program to work and understand what I did wrong.  I think the real
problem is that:

1.  core.sync isn't even in the Phobos/druntime docs yet, and is still kind of
here be dragons, so I originally thought it might legitimately just be broken.
2.  The docs for core.sync.condition assume you already know what a condition
variable is and how to use one and just provide a terse description of the
interface to the druntime implementation with zero examples.  On the other hand,
the details of this primitive are somewhat arcane and hard to find.  I'd vote 
for
improving these and will do it myself if noone else does it by the time I get 
some
higher priority hacking done.


Re: Condition Mutexes

2009-10-21 Thread Steven Schveighoffer
On Wed, 21 Oct 2009 17:13:48 -0400, Bartosz Milewski  
bartosz-nos...@relisoft.com wrote:



dsimcha Wrote:

Bartosz, since you're a threading guru, could you please write a simple  
test
program using core.sync.condition and see if it works, and if not  
either file a

bug report or let me know?


Conditions were implemented by Sean Kelly, so he's the guru. The file  
condition.d in core.sync has unit tests, which presumably still run  
(although I don't know if anybody still runs unit tests in druntime).


If using conditions in D is harder than in Java, than we should rethink  
their implementation. Every D object has a built-in mutex. Conditon  
variables should be able to work with this mutex and with synchronized  
sections out of the box. The most common case should be the easiest. The  
fact that you are having all those technical problems proves my point.


IIRC, Conditions should be able to use the in-object mutex.  However, I  
think you still need a core.sync.Mutex object.  I think the way it works  
is you initialize the Mutex with an object, and it inserts itself as the  
in-object mutex (hopefully before the on-demand mutex is created).


So indirectly, you can do:

new Condition(new Mutex(this));

Kinda odd, I agree...  This should probably be shortcutted. Sean?

-Steve


Re: static arrays becoming value types

2009-10-21 Thread grauzone

Leandro Lucarella wrote:

grauzone, el 21 de octubre a las 22:12 me escribiste:

Or even:

a, b = foo();

or

a, _ = foo();

Works in Python (tm)


_ is a regular symbol (variable name in this case), there is nothing
special about the second form, which is exactly the same as the first. And



I didn't even know this. In Python, it doesn't matter anyway, because it 
is dynamically typed, and you can assign arbitrary values to the same 
variable.


Apparently, writing foreach (index,_;something) in D isn't a special 
case either; it just declares a variable named _. Several nested loops 
using _ are not possible.


PS: let's hope Walter recognizes the need of *good* syntax for a simple, 
basic language construct like tuples. Just look at language_fan's D code 
and compare it with the corresponding Python code posted afterward. The 
D code looks so ridiculous.



BTW, the trailing ; is not needed ;)



Re: Array, AA Implementations

2009-10-21 Thread Yigal Chripun

On 19/10/2009 23:42, Andrei Alexandrescu wrote:

Yigal Chripun wrote:

here's an example of a well designed, consistent API:
http://www.gobosoft.com/eiffel/gobo/structure/index.html


This is a solid framework, unlike Java's containers which are a joke. I
disagree with some of Gobo's abstractions (e.g. I believe all containers
must be traversable and that primitives such as count() have no place in
a general container) but generally the framework seems to be very well
put together. It's a great source of inspiration for Phobos. Thanks very
much for the link.

Andrei


My understanding of this design is that they identified all the 
orthogonal properties relevant to containers and that specific 
containers are a composition of a specific set of such properties.
Eiffel has MI (different from the c++ implementation) which is helpful 
if you already have suitable default implementations for these properties.


regarding traversable property:
what if I want a container for a non-ordered type? an example would be a 
container of complex numbers, how would you traverse it?


what about hash tables?



Re: Array, AA Implementations

2009-10-21 Thread Denis Koroskin
On Thu, 22 Oct 2009 01:35:49 +0400, Yigal Chripun yigal...@gmail.com  
wrote:



On 19/10/2009 23:42, Andrei Alexandrescu wrote:

Yigal Chripun wrote:

here's an example of a well designed, consistent API:
http://www.gobosoft.com/eiffel/gobo/structure/index.html


This is a solid framework, unlike Java's containers which are a joke. I
disagree with some of Gobo's abstractions (e.g. I believe all containers
must be traversable and that primitives such as count() have no place in
a general container) but generally the framework seems to be very well
put together. It's a great source of inspiration for Phobos. Thanks very
much for the link.

Andrei


My understanding of this design is that they identified all the  
orthogonal properties relevant to containers and that specific  
containers are a composition of a specific set of such properties.
Eiffel has MI (different from the c++ implementation) which is helpful  
if you already have suitable default implementations for these  
properties.


regarding traversable property:
what if I want a container for a non-ordered type? an example would be a  
container of complex numbers, how would you traverse it?


what about hash tables?



What's wrong with iterating over a hash table? An order is just unreliable  
(but still deterministic).


int always 32 bits on all platforms?

2009-10-21 Thread AJ
How can/does D guarantee that int will always be 32 bits on all platforms?
Does this mean that D won't work on some platforms? Why is integer width so
ambiguous in C/C++? (I am using platform as equivalent to 
CPU+OS+compiler).






Re: this() not executing code on structs

2009-10-21 Thread grauzone

Andrei Alexandrescu wrote:
Today, structs can't write their own this(). There aren't very solid 
reasons for that except that it makes language implementation more 
difficult.


I wonder how much of a problem that could be in practice. I realized 
today that the Counted example - a classic C++ primer example 
featuring a struct that counts its own instances - cannot be implemented 
in D.


In C++ the counted example looks like this:

struct Counted {
   static unsigned count;
   unsigned myCount;
   Counted() { myCount = count++; }
   Counted(const Counted rhs) { myCount = count++; }
   Counted operator=(const Counted rhs) {
  // no writing to myCount
  return *this;
   }
   ~Counted() {
  --count;
   }
}

In D there's no chance to write Counted because you can always create 
Counted objects without executing any code.


struct Counted {
   static uint count;
   uint myCount;
   this() { myCount = count++; }   // ERROR
   this(this) { myCount = count++; }
   ref Counted opAssign(Counted rhs) {
  // no writing to myCount
  return this;
   }
   ~this() {
  --count;
   }
}

This being a toy example, I wonder whether there are much more serious 
examples that would be impossible to implement within D.


I'd really like to know why scope x = new X(); is unsafe, while 
encouraging doing exactly the same with structs seems to be a perfectly 
fine idea. Allocating structs on the stack is obviously not any safer 
than with classes. I don't remember the exact reasons why you wanted to 
turn scope into a library feature, but I think I remember something 
about discouraging it for safety reasons; please forgive me is this is 
wrong.


Why do you want to add class functionality to structs to enable RAII 
like features, when you could just use scope classes?


To refresh everyone's memory: a scope class is declared like scope 
class Foo { ... }, and references to it can only appear as a function 
local variable.


I for one don't really like the idea of having to distinguish between 
PODs and other stuff (like you had in C++) just again.


At the very least, the default constructor should always be available 
for structs. (If not, have fun figuring out what S[10] should do.)



Andrei


No header files?

2009-10-21 Thread AJ
Since D has no header files, how does one create a library that another 
developer can use without exposing the implementation? 




Re: this() not executing code on structs

2009-10-21 Thread Steven Schveighoffer

On Wed, 21 Oct 2009 17:54:08 -0400, grauzone n...@example.net wrote:

I'd really like to know why scope x = new X(); is unsafe, while  
encouraging doing exactly the same with structs seems to be a perfectly  
fine idea. Allocating structs on the stack is obviously not any safer  
than with classes. I don't remember the exact reasons why you wanted to  
turn scope into a library feature, but I think I remember something  
about discouraging it for safety reasons; please forgive me is this is  
wrong.


A class is a reference type.  If you pass the reference to the stack to a  
function that then stores it for later use, it is unsafe.  If you return  
it from the function, it's unsafe.  If you do the same with a struct (not  
a struct pointer), this is not the case.  Note that you *could* have the  
same problem with struct pointers or references, but typically, you expect  
to treat struct references like they are referencing stack data, it's not  
typical for classes.


-Steve


Re: No header files?

2009-10-21 Thread Steven Schveighoffer

On Wed, 21 Oct 2009 17:59:52 -0400, AJ a...@nospam.net wrote:


Since D has no header files, how does one create a library that another
developer can use without exposing the implementation?


try dmd -H.

.di files are D header files, basically used for the reason you specify.

-Steve


Semicolons: mostly unnecessary?

2009-10-21 Thread AJ
Why not eliminate the requirement for semicolon statement terminators 
(unless there are multiple statements per line)? Less typing is more! 




Re: No header files?

2009-10-21 Thread Yigal Chripun

On 21/10/2009 23:59, AJ wrote:

Since D has no header files, how does one create a library that another
developer can use without exposing the implementation?


D does have header files with the extension .di which can be either auto 
generated and/or manually edited. IMO this is a design mistake carried 
over from c/c++.


Re: int always 32 bits on all platforms?

2009-10-21 Thread BCS

Hello aJ,


How can/does D guarantee that int will always be 32 bits on all
platforms? Does this mean that D won't work on some platforms?



D is not built for 8 or 16 bit systems. However 32 bit math can be done on 
a 16 bit CPU, it's just slow. In the other direction, 32 bit math (and 16 
and 8 bit) can be done on a 64 bit CPU so that's not a problem. If you really 
want the machine word size (and expecting code that does that to port is 
foolish) use size_t. 


Why is
integer width so ambiguous in C/C++? (I am using platform as
equivalent to CPU+OS+compiler).



In C IIRC the rule is: native text item == char = short = int = long. 
This is a result of legacy issues from WAY back when (I think).





Re: Semicolons: mostly unnecessary?

2009-10-21 Thread Adam D. Ruppe
On Wed, Oct 21, 2009 at 05:05:04PM -0500, AJ wrote:
 Why not eliminate the requirement for semicolon statement terminators 
 (unless there are multiple statements per line)? Less typing is more! 

It looks wrong, breaks habit, opens up bizarre parsing corner cases,
and makes error messages uglier.

Next thing you know someone will propose eliminating braces and just
using whitespace to denote blocks. It's utter madness.

-- 
Adam D. Ruppe
http://arsdnet.net


Re: Semicolons: mostly unnecessary?

2009-10-21 Thread BCS

Hello aJ,


Why not eliminate the requirement for semicolon statement terminators
(unless there are multiple statements per line)? Less typing is
more!



For the same reason error correction bits are not removed from transmission 
lines; that is because the redundancy has some very nice effects when it 
comes to detecting and dealing with errors. Also, having a language that 
is whitespace aware has issues and in this cases the upside is to small.





Re: No header files?

2009-10-21 Thread AJ

Steven Schveighoffer schvei...@yahoo.com wrote in message 
news:op.u157hfkveav...@localhost.localdomain...
 On Wed, 21 Oct 2009 17:59:52 -0400, AJ a...@nospam.net wrote:

 Since D has no header files, how does one create a library that another
 developer can use without exposing the implementation?

 try dmd -H.

 .di files are D header files, basically used for the reason you specify.

OK, so header files can be generated. The thing is though, when I am 
designing at the code level, I start with the declarations (such as class 
data members and methods) and do the implementation (or one can hand it off 
to someone else) afterwards. That serves as the blue print for further 
development and remains as first level of documentation as well. Working 
with just implementation files seems to be putting the cart before the 
horse. While eliminating something unnecessary is something to strive for, I 
don't think header files are unnecessary in the development process (i.e., I 
don't think that relegating them to just the situation given with my OP is 
good, exactly for the reasons of usefullness I gave). 




Re: No header files?

2009-10-21 Thread BCS

Hello Yigal,


On 21/10/2009 23:59, AJ wrote:


Since D has no header files, how does one create a library that
another developer can use without exposing the implementation?


D does have header files with the extension .di which can be either
auto generated and/or manually edited. IMO this is a design mistake
carried over from c/c++.



What would you prefer?

Aside from a better library format you need something to give DMD the information. 
Switching to a better library format has several issues including requiring 
more tools to make them and view them as well as it doesn't solve the problem 
of linking with C libs that don't and never will use this new format. Not 
fatal issues I'll grant, but what we have works NOW.





Re: No header files?

2009-10-21 Thread digited
AJ Wrote:

 Since D has no header files, how does one create a library that another 
 developer can use without exposing the implementation? 
 
 

If you need interfaces, just do them.

your_interfaces.d: interface WhatYouWantToShow {}
your_code.d: class WhatYouDontWantToShow : somePublicInterface {}


Re: No header files?

2009-10-21 Thread BCS

Hello aJ,


Steven Schveighoffer schvei...@yahoo.com wrote in message
news:op.u157hfkveav...@localhost.localdomain...


On Wed, 21 Oct 2009 17:59:52 -0400, AJ a...@nospam.net wrote:


Since D has no header files, how does one create a library that
another developer can use without exposing the implementation?


try dmd -H.

.di files are D header files, basically used for the reason you
specify.


OK, so header files can be generated. The thing is though, when I am
designing at the code level, I start with the declarations (such as
class data members and methods) and do the implementation (or one can
hand it off to someone else) afterwards.


As it happens, .di files are just .d files that by convention only contain 
the interface. You can declare a class in a .d file and not give bodies for 
its methods and you won't get errors till link time, just like in C.



That serves as the blue
print for further development and remains as first level of
documentation as well. Working with just implementation files seems
to be putting the cart before the horse. While eliminating something
unnecessary is something to strive for, I don't think header files are
unnecessary in the development process (i.e., I don't think that
relegating them to just the situation given with my OP is good,
exactly for the reasons of usefullness I gave).


I'm not sure what use you are seeing for them. As far as documentation goes, 
In the cases where I don't care about the implementation, I'd rather see 
some kind of extracted, generated documentation rather than a header file. 
The only argument I see for a header/implementation split is if you need 
to put part of a class in one file and part in another and I think that is 
a very weak case.





Re: Semicolons: mostly unnecessary?

2009-10-21 Thread bearophile
Why not eliminate the requirement for semicolon statement terminators (unless 
there are multiple statements per line)?

Probably mostly because both some part of D language, some part of the mind of 
D developers, and some of the D programmers are old school and like to do 
things as they were in the past. I can list you twenty examples of this. 
Breaking old habits is not easy.

-

Adam D. Ruppe:

 It looks wrong,

To me semicolons everywhere look wrong, even if I've programmed enough with 
languages that require a semicolon at the ends.


 breaks habit,

It breaks a negative habit.


 opens up bizarre parsing corner cases,
 and makes error messages uglier.

I have yet to see a proof of this.


 Next thing you know someone will propose eliminating braces and just
 using whitespace to denote blocks. It's utter madness.

Even worse, someone may even implement such alternative D syntax, and the sky 
will fall on your head:
http://delight.sourceforge.net/

Bye,
bearophile


Re: int always 32 bits on all platforms?

2009-10-21 Thread AJ

BCS n...@anon.com wrote in message 
news:a6268ffbadb8cc20772570e...@news.digitalmars.com...
 Hello aJ,

 How can/does D guarantee that int will always be 32 bits on all
 platforms? Does this mean that D won't work on some platforms?


 D is not built for 8 or 16 bit systems. However 32 bit math can be done on 
 a 16 bit CPU, it's just slow. In the other direction, 32 bit math (and 16 
 and 8 bit) can be done on a 64 bit CPU so that's not a problem.

I wasn't thinking about math issues, but rather struct field 
alignment/portability, and platform alignment requirements for basic types, 
issues. I'm guessing that it is all worked out by the compiler, so that 
makes the development of a compiler more difficult, if so, but how much more 
difficult? A simple example or description of how this is done would really 
be great. (BTW, this is definitely an area where I would approve of more 
language implementation complexity for the great strides in programming 
efficiency (and fun!) it gives).





Re: No header files?

2009-10-21 Thread Jason House
AJ Wrote:

 
 Steven Schveighoffer schvei...@yahoo.com wrote in message 
 news:op.u157hfkveav...@localhost.localdomain...
  On Wed, 21 Oct 2009 17:59:52 -0400, AJ a...@nospam.net wrote:
 
  Since D has no header files, how does one create a library that another
  developer can use without exposing the implementation?
 
  try dmd -H.
 
  .di files are D header files, basically used for the reason you specify.
 
 OK, so header files can be generated. The thing is though, when I am 
 designing at the code level, I start with the declarations (such as class 
 data members and methods) and do the implementation (or one can hand it off 
 to someone else) afterwards. That serves as the blue print for further 
 development and remains as first level of documentation as well. Working 
 with just implementation files seems to be putting the cart before the 
 horse. While eliminating something unnecessary is something to strive for, I 
 don't think header files are unnecessary in the development process (i.e., I 
 don't think that relegating them to just the situation given with my OP is 
 good, exactly for the reasons of usefullness I gave). 
 
 

I think you keep a very structured development style that few share. Nothing 
stops you from writing a header-file-like .d file and then hand it off for 
someone to fill in the methods, etc... A good IDE can also make a .d file look 
like a header file. Personally, I like colocating documentation with 
implementation and using tools (such as dmd) to extract higher level 
documentation. 


Re: Semicolons: mostly unnecessary?

2009-10-21 Thread BCS

Hello bearophile,


opens up bizarre parsing corner cases,
and makes error messages uglier.

I have yet to see a proof of this.



Just off hand for parsing issues:

- it allows long code lines to be folded
- it acts as a bug check on reformat:

origonal code

MyType t; // result of -t and opSub_r(int) are lvalues
auto a = 5
-t = 3

MyType t;
auto a = 5 -t = 3   //reformat and forgot to add ';' Oops




Re: int always 32 bits on all platforms?

2009-10-21 Thread Jason House
AJ Wrote:

 
 BCS n...@anon.com wrote in message 
 news:a6268ffbadb8cc20772570e...@news.digitalmars.com...
  Hello aJ,
 
  How can/does D guarantee that int will always be 32 bits on all
  platforms? Does this mean that D won't work on some platforms?
 
 
  D is not built for 8 or 16 bit systems. However 32 bit math can be done on 
  a 16 bit CPU, it's just slow. In the other direction, 32 bit math (and 16 
  and 8 bit) can be done on a 64 bit CPU so that's not a problem.
 
 I wasn't thinking about math issues, but rather struct field 
 alignment/portability, and platform alignment requirements for basic types, 
 issues. I'm guessing that it is all worked out by the compiler, so that 
 makes the development of a compiler more difficult, if so, but how much more 
 difficult? A simple example or description of how this is done would really 
 be great. (BTW, this is definitely an area where I would approve of more 
 language implementation complexity for the great strides in programming 
 efficiency (and fun!) it gives).
 
 
 

In D, both type size and alignment have the same defaults on all platforms. If 
desired, alignment can be explicitly controlled with the align attribute. 
Similarly, use of specific types control sizes.


Re: No header files?

2009-10-21 Thread Yigal Chripun

On 22/10/2009 00:14, BCS wrote:

Hello Yigal,


On 21/10/2009 23:59, AJ wrote:


Since D has no header files, how does one create a library that
another developer can use without exposing the implementation?


D does have header files with the extension .di which can be either
auto generated and/or manually edited. IMO this is a design mistake
carried over from c/c++.



What would you prefer?

Aside from a better library format you need something to give DMD the
information. Switching to a better library format has several issues
including requiring more tools to make them and view them as well as it
doesn't solve the problem of linking with C libs that don't and never
will use this new format. Not fatal issues I'll grant, but what we have
works NOW.




As you said, what is needed is a better lib format. we already have DDL 
NOW which already has most of what you described above. D can also take 
advantage of the LLVM framework.


why do you need to choose between the two options anyway? dmd can 
support c header files combined with c libs and use a better D lib 
format for D code. Another option would be to have a simple tool to 
convert a bunch of c header files and a C lib to a D lib.


The C/C++ way of headers + lib has problems which D inherited as part of 
the same (broken) design.


Re: int always 32 bits on all platforms?

2009-10-21 Thread BCS

Hello aJ,


BCS n...@anon.com wrote in message
news:a6268ffbadb8cc20772570e...@news.digitalmars.com...


Hello aJ,


How can/does D guarantee that int will always be 32 bits on all
platforms? Does this mean that D won't work on some platforms?


D is not built for 8 or 16 bit systems. However 32 bit math can be
done on a 16 bit CPU, it's just slow. In the other direction, 32 bit
math (and 16 and 8 bit) can be done on a 64 bit CPU so that's not a
problem.


I wasn't thinking about math issues,


OK


but rather struct field
alignment/portability, and platform alignment requirements for basic
types, issues.


Unless you say otherwise, the compiler is free to align struct however it 
wants (this is true in C but there are conventions) and in general you can't 
expect it to do the same for different system (again, ditto re C)


OTOH I'm not sure how that links into int being the same size all over. If 
anything that should make these issue less of a problem.



I'm guessing that it is all worked out by the compiler,
so that makes the development of a compiler more difficult, if so, but
how much more difficult? A simple example or description of how this
is done would really be great. (BTW, this is definitely an area where
I would approve of more language implementation complexity for the
great strides in programming efficiency (and fun!) it gives).





Re: Semicolons: mostly unnecessary?

2009-10-21 Thread AJ

Adam D. Ruppe destructiona...@gmail.com wrote in message 
news:mailman.222.1256163114.20261.digitalmar...@puremagic.com...
 On Wed, Oct 21, 2009 at 05:05:04PM -0500, AJ wrote:
 Why not eliminate the requirement for semicolon statement terminators
 (unless there are multiple statements per line)? Less typing is more!

 It looks wrong, breaks habit, opens up bizarre parsing corner cases,
 and makes error messages uglier.

 Next thing you know someone will propose eliminating braces and just
 using whitespace to denote blocks. It's utter madness.

Not whitespace aware, but rather newline aware. Newlines are already 
at the end of a line, so a semicolon is redundant. IOW, the default 
statement terminator can be the newline.

struct something
{
int x1
long x2
}

vs.

struct something
{
int x1;
long x2;
};

First one is definitely cleaner. The less the eye has to bring in to be 
deciphered by the brain, the better.

void somefunc()

Is the above a declaration or start of a definition? Still though, only 1 
char of lookahead needed to determine.

Maybe one can't fully appreciate semicolon terminators until one tries to 
implement a language without them. (Because apparently no one has written 
that article or paper (?)). 




Re: Semicolons: mostly unnecessary?

2009-10-21 Thread language_fan
Wed, 21 Oct 2009 18:29:37 -0400, bearophile thusly wrote:

Why not eliminate the requirement for semicolon statement terminators
(unless there are multiple statements per line)?
 
 Probably mostly because both some part of D language, some part of the
 mind of D developers, and some of the D programmers are old school and
 like to do things as they were in the past. I can list you twenty
 examples of this. Breaking old habits is not easy.
 
 -
 
 Adam D. Ruppe:
 
 It looks wrong,
 
 To me semicolons everywhere look wrong, even if I've programmed enough
 with languages that require a semicolon at the ends.
 
 
 breaks habit,
 
 It breaks a negative habit.
 
 
 opens up bizarre parsing corner cases, and makes error messages uglier.
 
 I have yet to see a proof of this.
 
 
 Next thing you know someone will propose eliminating braces and just
 using whitespace to denote blocks. It's utter madness.
 
 Even worse, someone may even implement such alternative D syntax, and
 the sky will fall on your head: http://delight.sourceforge.net/

Relax, bearophile. It seems there are some things you cannot change in 
this world. It will not suffice that you prove them wrong. I think I'll 
just give up on D. The development model is too stagnant. The author 
refuses to learn from new languages like Python or C#, or old languages 
(SML) unless someone is kind enough to spend whole day explaining the 
features to him. That's a sick basis for developing new languages. Large 
part of the community shares this mindset. The more I think about it, the 
more I realize this language is not for me. I apologize my arrogance. Bye.


Re: Semicolons: mostly unnecessary?

2009-10-21 Thread Steven Schveighoffer

On Wed, 21 Oct 2009 18:05:04 -0400, AJ a...@nospam.net wrote:


Why not eliminate the requirement for semicolon statement terminators
(unless there are multiple statements per line)? Less typing is more!


It has been said in the past that having semicolons makes parsing easier.   
I don't know how true this is, but Walter said it, so it probably is  
pretty important.


You also forget about statements that span multiple lines, functions with  
15 args are much easier to read when they are separated into multiple  
lines IMO.


To all those guys who want no semicolons: get over it.  Use another  
language if you don't want semicolons.  There are some out there.  D isn't  
going to to change one of it's most fundamental constructs because it's  
less typing.


-Steve


Re: Semicolons: mostly unnecessary?

2009-10-21 Thread Ary Borenszweig

Adam D. Ruppe wrote:

On Wed, Oct 21, 2009 at 05:05:04PM -0500, AJ wrote:
Why not eliminate the requirement for semicolon statement terminators 
(unless there are multiple statements per line)? Less typing is more! 


It looks wrong, breaks habit, opens up bizarre parsing corner cases,
and makes error messages uglier.

Next thing you know someone will propose eliminating braces and just
using whitespace to denote blocks. It's utter madness.


Yay, Ruby! (almost)

I started to use it some days ago and I feel in love with it.


Re: int always 32 bits on all platforms?

2009-10-21 Thread Sean Kelly
AJ Wrote:

 How can/does D guarantee that int will always be 32 bits on all platforms?
 Does this mean that D won't work on some platforms? Why is integer width so
 ambiguous in C/C++? (I am using platform as equivalent to 
 CPU+OS+compiler).

int can be any width D wants it to be and everything works great so long as 
you're only calling D functions.  The conflict comes when calling C functions, 
and there's nothing in the language for addressing this.  Instead, it's a 
library issue.  For example, Druntime's core.stdc.config defines c_long and 
c_ulong types for interfacing with C, since these types change width across 
32 and 64-bit platforms.  There's been no attempt to deal with odd-sized int or 
other types though.  That just isn't an issue on common platforms.


Re: No header files?

2009-10-21 Thread Steven Schveighoffer

On Wed, 21 Oct 2009 18:16:48 -0400, AJ a...@nospam.net wrote:



Steven Schveighoffer schvei...@yahoo.com wrote in message
news:op.u157hfkveav...@localhost.localdomain...

On Wed, 21 Oct 2009 17:59:52 -0400, AJ a...@nospam.net wrote:

Since D has no header files, how does one create a library that  
another

developer can use without exposing the implementation?


try dmd -H.

.di files are D header files, basically used for the reason you specify.


OK, so header files can be generated. The thing is though, when I am
designing at the code level, I start with the declarations (such as class
data members and methods) and do the implementation (or one can hand it  
off

to someone else) afterwards. That serves as the blue print for further
development and remains as first level of documentation as well. Working
with just implementation files seems to be putting the cart before the
horse. While eliminating something unnecessary is something to strive  
for, I
don't think header files are unnecessary in the development process  
(i.e., I
don't think that relegating them to just the situation given with my OP  
is

good, exactly for the reasons of usefullness I gave).


Separating interface from implementation is good -- but not if you have to  
repeat the interface (as you do with C++ or C).  What happens (and being a  
long-time C++ developer, I've had my fair share of experience with it) is  
that the interface gets out of sync with the implementation, so weird shit  
happens.


I even think d's editable interface files are suspect.  They can be out  
of sync with the object files, and then you have the same problem.  The  
best model by far is Java and C# where the object files *are* the  
interface files.  Then you only have to worry about documentation being  
out of sync.  But at least your programs don't crash randomly for no  
reason because the docs are invalid.


What I would suggest is creating stub functions via {} and then when you  
go back to fill in the interface, fill in the {} area.  You get the same  
effect.


-Steve


Re: Semicolons: mostly unnecessary?

2009-10-21 Thread bearophile
BCS:

 - it allows long code lines to be folded

This is not a problem, when you have optional semicolons, you add some syntax 
to fold long lines. Python uses \ Mathematica uses \\ and so on. Languages like 
Scala, Boo, Genie, etc seem able to survive.


 - it acts as a bug check on reformat:
 
 origonal code
 
 MyType t; // result of -t and opSub_r(int) are lvalues
 auto a = 5
 -t = 3
 
 MyType t;
 auto a = 5 -t = 3   //reformat and forgot to add ';' Oops

I've written enough Python code to fill few books, and this doesn't happen 
often, something like few times in a year.
I think this is one of those things that you have to try for real for few hours 
in a row to be able to judge them a little.

Bye,
bearophile


Re: No header files?

2009-10-21 Thread BCS

Hello Yigal,


On 22/10/2009 00:14, BCS wrote:


Hello Yigal,


On 21/10/2009 23:59, AJ wrote:


Since D has no header files, how does one create a library that
another developer can use without exposing the implementation?


D does have header files with the extension .di which can be either
auto generated and/or manually edited. IMO this is a design mistake
carried over from c/c++.


What would you prefer?

Aside from a better library format you need something to give DMD the
information. Switching to a better library format has several issues
including requiring more tools to make them and view them as well as
it doesn't solve the problem of linking with C libs that don't and
never will use this new format. Not fatal issues I'll grant, but what
we have works NOW.


As you said, what is needed is a better lib format. we already have
DDL NOW which already has most of what you described above. D can also
take advantage of the LLVM framework.


Does DDL or LLVM work to generate monolithic executable that use all of D's 
features and do so for both Win32 and *nux?


Also, can I use notepad to view either of those file types?



why do you need to choose between the two options anyway? dmd can
support c header files combined with c libs and use a better D lib
format for D code. Another option would be to have a simple tool to
convert a bunch of c header files and a C lib to a D lib.


Option 1 is a no starter (Walter has said NO the that exact option based 
on it needing in effect a full C frontend to work) Option 2 in interesting 
but, it runs flat into to needs more tools issue.



The C/C++ way of headers + lib has problems which D inherited as part
of the same (broken) design.





Re: static arrays becoming value types

2009-10-21 Thread Leandro Lucarella
grauzone, el 21 de octubre a las 23:32 me escribiste:
 Leandro Lucarella wrote:
 grauzone, el 21 de octubre a las 22:12 me escribiste:
 Or even:
 
 a, b = foo();
 
 or
 
 a, _ = foo();
 
 Works in Python (tm)
 
 _ is a regular symbol (variable name in this case), there is nothing
 special about the second form, which is exactly the same as the first. And
 
 
 I didn't even know this. In Python, it doesn't matter anyway,
 because it is dynamically typed, and you can assign arbitrary values
 to the same variable.
 
 Apparently, writing foreach (index,_;something) in D isn't a special
 case either; it just declares a variable named _. Several nested
 loops using _ are not possible.

Using _ is a bad idea if you use gettext though ;)

-- 
Leandro Lucarella (AKA luca) http://llucax.com.ar/
--
GPG Key: 5F5A8D05 (F8CD F9A7 BF00 5431 4145  104C 949E BFB6 5F5A 8D05)
--
El techo de mi cuarto lleno de estrellas


Re: Semicolons: mostly unnecessary?

2009-10-21 Thread Ary Borenszweig

BCS wrote:

Hello bearophile,


opens up bizarre parsing corner cases,
and makes error messages uglier.

I have yet to see a proof of this.



Just off hand for parsing issues:

- it allows long code lines to be folded


If you don't have semicolons this is also true, for example

a = somefunc( first_param,
   second_param)
b = something_else

I can insert a line break there without confusing the parser because the 
parser is expecting the function call to end



- it acts as a bug check on reformat:

origonal code

MyType t; // result of -t and opSub_r(int) are lvalues
auto a = 5
-t = 3

MyType t;
auto a = 5 -t = 3   //reformat and forgot to add ';' Oops


Why would the formatter do that? The line break is acting as a 
semicolon, it won't remove it.


Re: int always 32 bits on all platforms?

2009-10-21 Thread BCS

Hello Jason,


In D, both type size and alignment have the same defaults on all
platforms. If desired, alignment can be explicitly controlled with the
align attribute. Similarly, use of specific types control sizes.



Ummm? IIRC, struct alignment follows the lead of the native compiler for 
the given system. That is, type size issues aside, structs without align 
directive can be passed from C to D by default.





Re: Semicolons: mostly unnecessary?

2009-10-21 Thread bearophile
language_fan:

 It will not suffice that you prove them wrong.

Usually I am not able to prove things, I mostly just give suggestions.


The development model is too stagnant.

D is now quite alive, Andrei seems interested in changing something basic of D 
every day :-)

Bye,
bearophile


Re: No header files?

2009-10-21 Thread AJ

BCS n...@anon.com wrote in message 
news:a6268ffbae78cc207990f9b...@news.digitalmars.com...
 Hello aJ,

 Steven Schveighoffer schvei...@yahoo.com wrote in message
 news:op.u157hfkveav...@localhost.localdomain...

 On Wed, 21 Oct 2009 17:59:52 -0400, AJ a...@nospam.net wrote:

 Since D has no header files, how does one create a library that
 another developer can use without exposing the implementation?

 try dmd -H.

 .di files are D header files, basically used for the reason you
 specify.

 OK, so header files can be generated. The thing is though, when I am
 designing at the code level, I start with the declarations (such as
 class data members and methods) and do the implementation (or one can
 hand it off to someone else) afterwards.

 As it happens, .di files are just .d files that by convention only contain 
 the interface. You can declare a class in a .d file and not give bodies 
 for its methods and you won't get errors till link time, just like in C.

 That serves as the blue
 print for further development and remains as first level of
 documentation as well. Working with just implementation files seems
 to be putting the cart before the horse. While eliminating something
 unnecessary is something to strive for, I don't think header files are
 unnecessary in the development process (i.e., I don't think that
 relegating them to just the situation given with my OP is good,
 exactly for the reasons of usefullness I gave).

 I'm not sure what use you are seeing for them.

The 2 that I gave were:

   1. Serves as a blueprint (or skeleton) for further development.
   2. Serves as documentation for usage or for evaluation-for-purpose 
(suitability).

(1) is working at a higher level (designing vs. implenting) and perhaps 
even separating much of the design work from the implementation work (i.e., 
separate individuals or teams working on one or the other). (2) eliminates 
the need for secondary documentation (for well-designed code). I think of 
secondary documentation as the detailed description of how something works. 
Prior to consulting such, I'd want to know what something is, and 
something like a class declaration gives me that information immediately, 
without reading paragraphs of text. For example, you can describe car to 
me, but it would be much easier to just show me one.

 As far as documentation goes, In the cases where I don't care about the 
 implementation, I'd rather see some kind of extracted, generated 
 documentation rather than a header file.

Class Shape
{
void Draw();
}

What more do you need to know usually?

 The only argument I see for a header/implementation split is if you need 
 to put part of a class in one file and part in another and I think that is 
 a very weak case.




Re: int always 32 bits on all platforms?

2009-10-21 Thread AJ

BCS n...@anon.com wrote in message 
news:a6268ffbaf38cc207c67388...@news.digitalmars.com...
 Hello aJ,

 BCS n...@anon.com wrote in message
 news:a6268ffbadb8cc20772570e...@news.digitalmars.com...

 Hello aJ,

 How can/does D guarantee that int will always be 32 bits on all
 platforms? Does this mean that D won't work on some platforms?

 D is not built for 8 or 16 bit systems. However 32 bit math can be
 done on a 16 bit CPU, it's just slow. In the other direction, 32 bit
 math (and 16 and 8 bit) can be done on a 64 bit CPU so that's not a
 problem.

 I wasn't thinking about math issues,

 OK

 but rather struct field
 alignment/portability, and platform alignment requirements for basic
 types, issues.

 Unless you say otherwise, the compiler is free to align struct however it 
 wants (this is true in C but there are conventions) and in general you 
 can't expect it to do the same for different system (again, ditto re C)

 OTOH I'm not sure how that links into int being the same size all over. If 
 anything that should make these issue less of a problem.

I would think so. Anyway, what I find compelling about guaranteed widths is 
the potential to eliminate alignment and padding issues (that is, be able to 
control it with confidence across platforms as one already can on a single 
platform via compiler pragmas or cmdline switches).


 I'm guessing that it is all worked out by the compiler,
 so that makes the development of a compiler more difficult, if so, but
 how much more difficult? A simple example or description of how this
 is done would really be great. (BTW, this is definitely an area where
 I would approve of more language implementation complexity for the
 great strides in programming efficiency (and fun!) it gives).

 




Re: Semicolons: mostly unnecessary?

2009-10-21 Thread BCS

Hello bearophile,


BCS:


- it allows long code lines to be folded


This is not a problem, when you have optional semicolons, you add some
syntax to fold long lines. Python uses \ Mathematica uses \\ and so
on. Languages like Scala, Boo, Genie, etc seem able to survive.


The only one of those in common use is Python and its not a good date point 
because of all the other whitespace stuff it does (it's in a category all 
its own).


Also line continuation Is just ugly. (And before you ask, no, I don't think 
semicolons are ugly)



- it acts as a bug check on reformat:

origonal code

MyType t; // result of -t and opSub_r(int) are lvalues
auto a = 5
-t = 3
MyType t;
auto a = 5 -t = 3   //reformat and forgot to add ';' Oops


I've written enough Python code to fill few books, and this doesn't
happen often, something like few times in a year.

I think this is one of those things that you have to try for real for
few hours in a row to be able to judge them a little.


I'll grant the only white space aware languages I've used much are basic 
(a long time ago) and the C preprocessor. As for CPP the whitespace issues 
are the #1 thing I dislike about it (and there are a few other things I don't 
like one bit)





  1   2   >