www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.announce - DMD 1.035 and 2.019 releases

reply Walter Bright <newshound1 digitalmars.com> writes:
Struct constructors!

http://www.digitalmars.com/d/1.0/changelog.html
http://ftp.digitalmars.com/dmd.1.035.zip

http://www.digitalmars.com/d/2.0/changelog.html
http://ftp.digitalmars.com/dmd.2.019.zip
Sep 02 2008
next sibling parent BCS <ao pathlink.com> writes:
Reply to Walter,

 Struct constructors!
 
 http://www.digitalmars.com/d/1.0/changelog.html
 http://ftp.digitalmars.com/dmd.1.035.zip
 http://www.digitalmars.com/d/2.0/changelog.html
 http://ftp.digitalmars.com/dmd.2.019.zip

bug soup!!!! :-)
Sep 02 2008
prev sibling next sibling parent reply Matti Niemenmaa <see_signature for.real.address> writes:
Walter Bright wrote:
 Struct constructors!
 
 http://www.digitalmars.com/d/1.0/changelog.html
 http://ftp.digitalmars.com/dmd.1.035.zip

Nice release, thanks! One nit: running "dmd" still says "Digital Mars D Compiler v1.034". -- E-mail address: matti.niemenmaa+news, domain is iki (DOT) fi
Sep 02 2008
parent reply Walter Bright <newshound1 digitalmars.com> writes:
Matti Niemenmaa wrote:
 Nice release, thanks! One nit: running "dmd" still says "Digital Mars D
Compiler
 v1.034".

Fixed!
Sep 02 2008
parent reply Georg Wrede <georg nospam.org> writes:
Walter Bright wrote:
 Matti Niemenmaa wrote:
 
 Nice release, thanks! One nit: running "dmd" still says "Digital Mars 
 D Compiler
 v1.034".

Fixed!

Congrats, etc., you know! :-) An idea: On www.digitalmars.com you currently replace the Current Version link with the, ehhh, Current Version, right? Now, would it be a better idea to announce here the existence of DMD X.0xx /without/ changing the default link on the web site? Point being, you'd want to get feedback for at least a week from this NG, before "publishing to the world at large" the new version. This might be handy for "real errors", because then you could have some comment next to the link about, well, caveats or whatever. Even better, you'd get rid of the most trivial, and embarrassing, erros (of the kind I make all the time, like "says v1.034") before the regular downloaders hear of them. georg PS, think about those who don't read this NG, who just happen to download the obvious choice, the current version, and then there's some embarrassing or downright dangerous thing with it, and he never gets the wiser -- because we can't mandate that everyone reads this NG. /At least 1.xx/ should do this.
Sep 04 2008
parent Walter Bright <newshound1 digitalmars.com> writes:
Georg Wrede wrote:
 /At least 1.xx/ should do this.

That's why the default download is for an older version.
Sep 05 2008
prev sibling next sibling parent "Lionello Lunesu" <lionello lunesu.remove.com> writes:
Great update once again, thanks!

 Special member functions _ctor, _dtor, etc., now have two leading _ in 
 order to not conflict with the user identifier space.

Ow, just rename this/~this to ctor/dtor and get it over with! :O L.
Sep 02 2008
prev sibling next sibling parent reply Extrawurst <spam extrawurst.org> writes:
Are opCalls deprecated now ? how do i call the ctor and how the opCall? 
a short example in the docs would have been nice.

nice release though. thanks for the bugfixing!

Walter Bright wrote:
 Struct constructors!
 
 http://www.digitalmars.com/d/1.0/changelog.html
 http://ftp.digitalmars.com/dmd.1.035.zip
 
 http://www.digitalmars.com/d/2.0/changelog.html
 http://ftp.digitalmars.com/dmd.2.019.zip

Sep 03 2008
next sibling parent reply Walter Bright <newshound1 digitalmars.com> writes:
To construct an object of struct S:

auto s = S(arguments);

Extrawurst wrote:
 Are opCalls deprecated now ? how do i call the ctor and how the opCall? 
 a short example in the docs would have been nice.

Sep 03 2008
next sibling parent reply Extrawurst <spam extrawurst.org> writes:
yeah i figured, but if i have an opCall with the exact same arguments 
its never called, isnt that ambiguous ? what happens to opcall anyway ? 
will it sooner or later fall out ?

Walter Bright wrote:
 To construct an object of struct S:
 
 auto s = S(arguments);
 
 Extrawurst wrote:
 Are opCalls deprecated now ? how do i call the ctor and how the 
 opCall? a short example in the docs would have been nice.


Sep 03 2008
next sibling parent reply Walter Bright <newshound1 digitalmars.com> writes:
Extrawurst wrote:
 yeah i figured, but if i have an opCall with the exact same arguments 
 its never called, isnt that ambiguous ? what happens to opcall anyway ? 
 will it sooner or later fall out ?
 
 Walter Bright wrote:
 To construct an object of struct S:

 auto s = S(arguments);

 Extrawurst wrote:
 Are opCalls deprecated now ? how do i call the ctor and how the 
 opCall? a short example in the docs would have been nice.



ctor's override the opCalls. The opCalls will eventually probably get deprecated.
Sep 03 2008
next sibling parent Extrawurst <spam extrawurst.org> writes:
Walter Bright wrote:
 Extrawurst wrote:
 yeah i figured, but if i have an opCall with the exact same arguments 
 its never called, isnt that ambiguous ? what happens to opcall anyway 
 ? will it sooner or later fall out ?

 Walter Bright wrote:
 To construct an object of struct S:

 auto s = S(arguments);

 Extrawurst wrote:
 Are opCalls deprecated now ? how do i call the ctor and how the 
 opCall? a short example in the docs would have been nice.



ctor's override the opCalls. The opCalls will eventually probably get deprecated.

Well the advandage of opCall is (in my intention) that you can have an empty argument list. it think its kind of inconsistend if u want to do reference counting in a generic struct template, isnt it ?
Sep 03 2008
prev sibling next sibling parent reply bobef <bobef nosmap-abv.bg> writes:
Walter Bright Wrote:

 Extrawurst wrote:
 yeah i figured, but if i have an opCall with the exact same arguments 
 its never called, isnt that ambiguous ? what happens to opcall anyway ? 
 will it sooner or later fall out ?
 
 Walter Bright wrote:
 To construct an object of struct S:

 auto s = S(arguments);

 Extrawurst wrote:
 Are opCalls deprecated now ? how do i call the ctor and how the 
 opCall? a short example in the docs would have been nice.



ctor's override the opCalls. The opCalls will eventually probably get deprecated.

opCalls are much more flexible than ctor's because their return type may vary or they may not have return type. I vote against deprecating them. Let whoever likes ctors use them and whoever likes opCalls use these. Regards
Sep 03 2008
next sibling parent reply 0ffh <frank youknow.what.todo.interNETz> writes:
bobef wrote:
 opCalls are much more flexible than ctor's because their return type may
 vary or they may not have return type. I vote against deprecating them. Let
 whoever likes ctors use them and whoever likes opCalls use these.

I agree opCalls are more flexible, but unfortunately you can't have both because of syntactical ambiguity... :-( regards, 0ffh
Sep 03 2008
next sibling parent reply Walter Bright <newshound1 digitalmars.com> writes:
Jarrett Billingsley wrote:
 Speaking of syntactical ambiguity, the expression
 
 S(1, 2, 3)
 
 can, right now, have one of three meanings:
 
 1. A struct literal for struct S
 2. A call to S's static opCall
 3. An instantiation of S and a call to its ctor
 
 Even if opCall goes away, we'll still be left with the ambiguity of 
 struct literal vs. ctor.  I'd really, really like to hear Walter's view 
 on this but he has responded neither to the thread I posted on 
 digitalmars.D nor the bugzilla ticket 
 (http://d.puremagic.com/issues/show_bug.cgi?id=2170).

If there's any constructor defined for S, then S(args) is a constructor call. If there's any opCall defined for S, then S(args) is an opCall call. Otherwise, it's a struct literal.
Sep 03 2008
next sibling parent reply bearophile <bearophileHUGS lycos.com> writes:
Walter Bright:
 If there's any constructor defined for S, then S(args) is a constructor call.
 If there's any opCall defined for S, then S(args) is an opCall call.
 Otherwise, it's a struct literal.

I haven't tried that in real code, so I can't be sure, but while it may work for the compiler, it sounds a bit too much complex for the person that later reads the code. Too many alternative possibilities may make the code more complex to follow. To reduce such ambiguity (ambiguity for the person, not for the compiler) may be to change the syntax of struct literals... Bye, bearophile
Sep 03 2008
parent reply Walter Bright <newshound1 digitalmars.com> writes:
bearophile wrote:
 Walter Bright:
 If there's any constructor defined for S, then S(args) is a
 constructor call. If there's any opCall defined for S, then S(args)
 is an opCall call. Otherwise, it's a struct literal.

I haven't tried that in real code, so I can't be sure, but while it may work for the compiler, it sounds a bit too much complex for the person that later reads the code. Too many alternative possibilities may make the code more complex to follow. To reduce such ambiguity (ambiguity for the person, not for the compiler) may be to change the syntax of struct literals...

I disagree, I think just the reverse. The S(args) syntax means that it's entirely up to the struct designer to say how it should work. The user needn't know or care, and the struct designer can change the design without affecting user code.
Sep 03 2008
next sibling parent reply bobef <bobef nosmap-abv.bg> writes:
Walter Bright Wrote:

 bearophile wrote:
 Walter Bright:
 If there's any constructor defined for S, then S(args) is a
 constructor call. If there's any opCall defined for S, then S(args)
 is an opCall call. Otherwise, it's a struct literal.

I haven't tried that in real code, so I can't be sure, but while it may work for the compiler, it sounds a bit too much complex for the person that later reads the code. Too many alternative possibilities may make the code more complex to follow. To reduce such ambiguity (ambiguity for the person, not for the compiler) may be to change the syntax of struct literals...

I disagree, I think just the reverse. The S(args) syntax means that it's entirely up to the struct designer to say how it should work. The user needn't know or care, and the struct designer can change the design without affecting user code.

And why not "new S(args)" to call the constructor (which is natural so far) and "S(args)" to work as it does now?
Sep 03 2008
parent Robert Fraser <fraserofthenight gmail.com> writes:
bobef wrote:
 Walter Bright Wrote:
 
 bearophile wrote:
 Walter Bright:
 If there's any constructor defined for S, then S(args) is a
 constructor call. If there's any opCall defined for S, then S(args)
 is an opCall call. Otherwise, it's a struct literal.

may work for the compiler, it sounds a bit too much complex for the person that later reads the code. Too many alternative possibilities may make the code more complex to follow. To reduce such ambiguity (ambiguity for the person, not for the compiler) may be to change the syntax of struct literals...

entirely up to the struct designer to say how it should work. The user needn't know or care, and the struct designer can change the design without affecting user code.

And why not "new S(args)" to call the constructor (which is natural so far) and "S(args)" to work as it does now?

How would you distinguish between allocating the struct on the heap and on the stack? "new" anything does heap allocation and returns a pointer/reference, so it would be inconsistent if it did stack allocation for structs (plus, then you'd have to manually allocate the heap memory & copy the struct over... ew). class C { } struct S { } int* i = new int; // Heap allocates C c = new C; // Heap allocates S* s = new S; // Heap allocates
Sep 03 2008
prev sibling next sibling parent reply Tomas Lindquist Olsen <tomas famolsen.dk> writes:
Walter Bright wrote:
 bearophile wrote:
 Walter Bright:
 If there's any constructor defined for S, then S(args) is a
 constructor call. If there's any opCall defined for S, then S(args)
 is an opCall call. Otherwise, it's a struct literal.

I haven't tried that in real code, so I can't be sure, but while it may work for the compiler, it sounds a bit too much complex for the person that later reads the code. Too many alternative possibilities may make the code more complex to follow. To reduce such ambiguity (ambiguity for the person, not for the compiler) may be to change the syntax of struct literals...

I disagree, I think just the reverse. The S(args) syntax means that it's entirely up to the struct designer to say how it should work. The user needn't know or care, and the struct designer can change the design without affecting user code.

This is one of those things I really dislike about D :( It's really nice that we can override struct initialization, but the fact that it eliminates the possibility to override it (with a nice syntax) makes it much less appealing IMHO. The most important point to me, is that old thing about static struct initializer and struct literals have different syntaxes, and that the static variant is much more flexible. I would have loved to see the static struct initializer syntax become an expression. If the problem is ambiguity, why not just prefix the {} braces with the struct name? struct S { int a; float b; } const s = S{1, 2.0}; const t = S{b:3.14}; void foo() { auto st = S{4,5.5}; } (also not that it's currently impossible to use type inference with the current static struct initializers) This would eliminate the gripe most people have with this I think, as well as making static and non-static initializers consistent. like they are *for all other types*. I can't help feel structs (like static arrays) aren't first class citizens in D. Even with the latest additions in D2. It hurts, and is just one of those small reasons why I sometimes regret I even joined this community... My 2 cents on this, I think it's a big mistake going against the wishes of the D community. If I'm wrong, let me know. -Tomas
Sep 04 2008
next sibling parent Tomas Lindquist Olsen <tomas famolsen.dk> writes:
Jarrett Billingsley wrote:
 
 Now were you just reading off of
 http://d.puremagic.com/issues/show_bug.cgi?id=2170 or did you come to
 this conclusion independently ;)

Actually, I've never read that report before :P Seriously !! But it looks like we pretty much agree ... Glad I'm not alone here ;) -Tomas
Sep 04 2008
prev sibling next sibling parent Tomas Lindquist Olsen <tomas famolsen.dk> writes:
Denis Koroskin wrote:
 
 It may have problems with the q{}:
 
 struct q
 {
     float t;
 }
 
 auto foo = q{ t = 3.1415f };    // what's the type of foo?
 
 But then, does anybody using it?
 
 Other than that I agree, current solution is not very good.
 

A valid point, I can think of lots of other ways to provide this specific feature though. I'd also guess that struct literals are much more common than tokenized strings... So... I don't think this is a valid reason to dismiss this!
Sep 04 2008
prev sibling next sibling parent Tomas Lindquist Olsen <tomas famolsen.dk> writes:
Jarrett Billingsley wrote:
 On Thu, Sep 4, 2008 at 7:58 AM, Denis Koroskin <2korden gmail.com> wrote:
 On Thu, 04 Sep 2008 15:44:30 +0400, Tomas Lindquist Olsen
 <tomas famolsen.dk> wrote:

 Walter Bright wrote:
 bearophile wrote:
 Walter Bright:
 If there's any constructor defined for S, then S(args) is a
 constructor call. If there's any opCall defined for S, then S(args)
 is an opCall call. Otherwise, it's a struct literal.

may work for the compiler, it sounds a bit too much complex for the person that later reads the code. Too many alternative possibilities may make the code more complex to follow. To reduce such ambiguity (ambiguity for the person, not for the compiler) may be to change the syntax of struct literals...

entirely up to the struct designer to say how it should work. The user needn't know or care, and the struct designer can change the design without affecting user code.

It's really nice that we can override struct initialization, but the fact that it eliminates the possibility to override it (with a nice syntax) makes it much less appealing IMHO. The most important point to me, is that old thing about static struct initializer and struct literals have different syntaxes, and that the static variant is much more flexible. I would have loved to see the static struct initializer syntax become an expression. If the problem is ambiguity, why not just prefix the {} braces with the struct name? struct S { int a; float b; } const s = S{1, 2.0}; const t = S{b:3.14}; void foo() { auto st = S{4,5.5}; }

struct q { float t; } auto foo = q{ t = 3.1415f }; // what's the type of foo? But then, does anybody using it? Other than that I agree, current solution is not very good.

auto foo = q { t: 3.1415f}; // typeof(foo) == q q{ is treated more or less as an atomic character. Put a space between them and bam, you have a struct literal. And please don't get rid of token strings; those of us who love mixins wouldn't want to see them go ;)

I kinda like ""{foobar etc} as an alternative
Sep 04 2008
prev sibling next sibling parent reply Walter Bright <newshound1 digitalmars.com> writes:
Tomas Lindquist Olsen wrote:
 This is one of those things I really dislike about D :(
 It's really nice that we can override struct initialization, but the 
 fact that it eliminates the possibility to override it (with a nice 
 syntax) makes it much less appealing IMHO.
 
 The most important point to me, is that old thing about static struct 
 initializer and struct literals have different syntaxes, and that the 
 static variant is much more flexible.
 
 I would have loved to see the static struct initializer syntax become an 
 expression. If the problem is ambiguity, why not just prefix the {} 
 braces with the struct name?

The static struct initializers more or less are inherited from C. I'd eventually like to abandon them and go completely to the S(args) syntax.
Sep 04 2008
parent Leandro Lucarella <llucax gmail.com> writes:
Walter Bright, el  4 de septiembre a las 10:26 me escribiste:
 Tomas Lindquist Olsen wrote:
This is one of those things I really dislike about D :(
It's really nice that we can override struct initialization, but the fact that 
it eliminates the possibility to override it (with a nice syntax) makes it much 
less appealing IMHO.
The most important point to me, is that old thing about static struct 
initializer and struct literals have different syntaxes, and that the static 
variant is much more flexible.
I would have loved to see the static struct initializer syntax become an 
expression. If the problem is ambiguity, why not just prefix the {} braces with 
the struct name?

The static struct initializers more or less are inherited from C. I'd eventually like to abandon them and go completely to the S(args) syntax.

But they are much more flexible than constructor, it's like a constructor with named arguments! =) If you add support to named arguments, then I'll agree ;) -- Leandro Lucarella (luca) | Blog colectivo: http://www.mazziblog.com.ar/blog/ ---------------------------------------------------------------------------- GPG Key: 5F5A8D05 (F8CD F9A7 BF00 5431 4145 104C 949E BFB6 5F5A 8D05) ---------------------------------------------------------------------------- PROTESTA EN PLAZA DE MAYO: MUSICO SE COSIO LA BOCA -- Crónica TV
Sep 04 2008
prev sibling next sibling parent Russell Lewis <webmaster villagersonline.com> writes:
Jarrett Billingsley wrote:
 q{ is treated more or less as an atomic character.  Put a space
 between them and bam, you have a struct literal.

They made exactly that mistake with C++'s template syntax. It is one of the reasons that D's template syntax is better. It's an idea that sounds good when you are looking at it from an abstract, "yeah we could parse that" direction, but it makes for unreadable (and unwritable) code with strange syntax errors that are hard to find.
Sep 06 2008
prev sibling parent reply Bruno Medeiros <brunodomedeiros+spam com.gmail> writes:
Jarrett Billingsley wrote:
 
 Now were you just reading off of
 http://d.puremagic.com/issues/show_bug.cgi?id=2170 or did you come to
 this conclusion independently ;)

I was reading that, and I must say, I didn't quite understand the reasoning behind that named function parameters proposal. And what do you mean with "The issue with this is that you have to have a different named struct for every function that takes this style of parameters" ? Were you suggesting that functions who want to receive named parameters should declare an arguments struct just for that? -- Bruno Medeiros - Software Developer, MSc. in CS/E graduate http://www.prowiki.org/wiki4d/wiki.cgi?BrunoMedeiros#D
Sep 08 2008
parent reply Bruno Medeiros <brunodomedeiros+spam com.gmail> writes:
Jarrett Billingsley wrote:
 On Mon, Sep 8, 2008 at 9:39 AM, Bruno Medeiros
 <brunodomedeiros+spam com.gmail> wrote:
 Jarrett Billingsley wrote:
 Now were you just reading off of
 http://d.puremagic.com/issues/show_bug.cgi?id=2170 or did you come to
 this conclusion independently ;)

behind that named function parameters proposal.

Do you mean you don't understand the need for named function parameters, or you're not clear on the mechanism?

I meant the mechanism
 If the former, named parameters are just a clearer way of calling
 functions that take a lot of parameters or a lot of potentially
 confusing parameters.  If the latter, D currently allows you to do
 something like this:
 
 class A
 {
    this(int, int, int){}
 }
 
 void foo(A a...)
 {
    // a is a reference to a new instance of A
 }
 
 foo(1, 2, 3); // same as foo(new A(1, 2, 3));
 
 So my idea is, if struct literals allow for named members, it's not
 much of a step to go from
 
 foo(SomeStruct{x: 1, y: 2})
 
 to:
 
 foo(x: 1, y: 2)
 

Ah, I understand now what you meant, I had forgotten about that D feature that would implicitly call the constructor on a function call.
 And what do you mean with "The issue with this is that you have to have a
 different named struct for every function that takes this style of
 parameters" ?
 Were you suggesting that functions who want to receive named parameters
 should declare an arguments struct just for that?

Yes. Although without the syntactic sugar, you'd end up having to write i.e. foo(FooArgs{x: 1, y: 2}) bar(BarArgs{z: 3.4, w: "hi"}) hence having to repeat the name of the function once for the function itself and again for the named arguments. With sugar, the argument structure name and braces go away, but it still doesn't solve the problem of having to declare an argument structure for every function.

Yeah, which still makes it un-useful in my opinion.
 But, if we were to get named parameters for all functions, then both
 problems are solved: you have named parameters for free functions and
 methods, and you can initialize structs that have constructors or
 static opCalls with named members instead of having to write them in
 order:
 
 struct S
 {
     int x, y, z;
     this(int x, int y, int z) { this.x = x; this.y = y; this.z = z; }
 }
 
 S(1, 2, 3) and S(x: 1, y: 2, z: 3) are now both legal.

Now this would be a proper design for the named parameters feature. But still, to say the truth, it's not something I miss much. I understand it's use case, but I've never felt much need for it in any of the languages I've programmed. -- Bruno Medeiros - Software Developer, MSc. in CS/E graduate http://www.prowiki.org/wiki4d/wiki.cgi?BrunoMedeiros#D
Sep 12 2008
parent bearophile <bearophileHUGS lycos.com> writes:
Bruno Medeiros:
 it's not something I miss much. I understand it's use case, but
 I've never felt much need for it in any of the languages I've programmed.

If you use an IDE, it tells shows you the signature of the function/method, so such feature is less useful. But if you don't use an IDE, or you are using a dynamic language (where for the IDE is less easy to give help), they become quite useful, especially when you have several arguments, and several of them have a default value. So it's a form of documentation of the code, helps avoid some bugs, reduced the need to remember the exact signature if you don't have an IDE, etc. As most things if you overdo it, it may give you problems... Note that for delegates/closures named arguments may give some problems, because you don't know at compile time what is the order of the arguments. To solve this problem in ShedSkin I have added an extra hidden uint or ulong argument to those closures, used as a bitmask of 32 or 64 bits, to tell the closure what are the arguments actually passed... :-) If you want more details I can explain. If there are more than 64 arguments you can add a second uint or ulong, etc. Bye, bearophile
Sep 12 2008
prev sibling parent Christopher Wright <dhasenan gmail.com> writes:
Walter Bright wrote:
 bearophile wrote:
 Walter Bright:
 If there's any constructor defined for S, then S(args) is a
 constructor call. If there's any opCall defined for S, then S(args)
 is an opCall call. Otherwise, it's a struct literal.

I haven't tried that in real code, so I can't be sure, but while it may work for the compiler, it sounds a bit too much complex for the person that later reads the code. Too many alternative possibilities may make the code more complex to follow. To reduce such ambiguity (ambiguity for the person, not for the compiler) may be to change the syntax of struct literals...

I disagree, I think just the reverse. The S(args) syntax means that it's entirely up to the struct designer to say how it should work. The user needn't know or care, and the struct designer can change the design without affecting user code.

This helps a lot with future proofing your structs. I'm trying to think of a downside... It's a method call, which is a small performance hit. But it's a very small one, considering that it's a final method. It's a method call, so it could throw an exception. That's just a bug in your code, and easier to find than some random error way down the line. You might be doing something dangerous with leaving stuff on an old stack frame and still accessing it. Then you're in the realm of undefined behavior.
Sep 04 2008
prev sibling next sibling parent Walter Bright <newshound1 digitalmars.com> writes:
Jarrett Billingsley wrote:
 why don't you want to change struct literals?

See my reply to bearophile
Sep 03 2008
prev sibling next sibling parent reply Pablo Ripolles <in-call gmx.net> writes:
Sorry, but this is already somewhere else, I don't know why but I get my
responses out of thread...

Walter Bright Wrote:

 Jarrett Billingsley wrote:
 Speaking of syntactical ambiguity, the expression
 
 S(1, 2, 3)
 
 can, right now, have one of three meanings:
 
 1. A struct literal for struct S
 2. A call to S's static opCall
 3. An instantiation of S and a call to its ctor
 
 Even if opCall goes away, we'll still be left with the ambiguity of 
 struct literal vs. ctor.  I'd really, really like to hear Walter's view 
 on this but he has responded neither to the thread I posted on 
 digitalmars.D nor the bugzilla ticket 
 (http://d.puremagic.com/issues/show_bug.cgi?id=2170).

If there's any constructor defined for S, then S(args) is a constructor call. If there's any opCall defined for S, then S(args) is an opCall call.

shouldn't this be so only for the static opCall's? shouldn't this be possible? /////////////////////////////////////////////////////// import std.stdio; struct Parabola { float a_; this(float a) { a_ = a; } float opCall(float x) { return a_ * x*x; } } void main() { Parabola f; float x, y; f = Parabola(1.0); x = 2.0; y = f(x); writefln("f(%1$s) = %2$%", x, y); } /////////////////////////////////////////////////////// Thanks!
 
 Otherwise, it's a struct literal.

Sep 04 2008
parent reply Pablo Ripolles <in-call gmx.net> writes:
little typo:
writefln("f(%1$s) = %2$%", x, y);      --->     writefln("f(%1$s) = %2$s", x,
y);

it doesn't compile anyway!

Walter, don't you think that the ctor overloading should be on "static opCall"
better than *any* opCall?


Pablo Ripolles Wrote:

 Sorry, but this is already somewhere else, I don't know why but I get my
responses out of thread...
 
 Walter Bright Wrote:
 
 Jarrett Billingsley wrote:
 Speaking of syntactical ambiguity, the expression
 
 S(1, 2, 3)
 
 can, right now, have one of three meanings:
 
 1. A struct literal for struct S
 2. A call to S's static opCall
 3. An instantiation of S and a call to its ctor
 
 Even if opCall goes away, we'll still be left with the ambiguity of 
 struct literal vs. ctor.  I'd really, really like to hear Walter's view 
 on this but he has responded neither to the thread I posted on 
 digitalmars.D nor the bugzilla ticket 
 (http://d.puremagic.com/issues/show_bug.cgi?id=2170).

If there's any constructor defined for S, then S(args) is a constructor call. If there's any opCall defined for S, then S(args) is an opCall call.

shouldn't this be so only for the static opCall's? shouldn't this be possible? /////////////////////////////////////////////////////// import std.stdio; struct Parabola { float a_; this(float a) { a_ = a; } float opCall(float x) { return a_ * x*x; } } void main() { Parabola f; float x, y; f = Parabola(1.0); x = 2.0; y = f(x); writefln("f(%1$s) = %2$%", x, y); } /////////////////////////////////////////////////////// Thanks!
 
 Otherwise, it's a struct literal.


Sep 04 2008
parent reply Walter Bright <newshound1 digitalmars.com> writes:
Pablo Ripolles wrote:
 little typo: writefln("f(%1$s) = %2$%", x, y);      --->
 writefln("f(%1$s) = %2$s", x, y);
 
 it doesn't compile anyway!
 
 Walter, don't you think that the ctor overloading should be on
 "static opCall" better than *any* opCall?

That would make opCall overload unlike anything else.
Sep 04 2008
parent reply Pablo Ripolles <in-call gmx.net> writes:
Walter Bright Wrote:

 Pablo Ripolles wrote:
 little typo: writefln("f(%1$s) = %2$%", x, y);      --->
 writefln("f(%1$s) = %2$s", x, y);
 
 it doesn't compile anyway!
 
 Walter, don't you think that the ctor overloading should be on
 "static opCall" better than *any* opCall?

That would make opCall overload unlike anything else.

Ok, sorry again, I didn't mean overloading, I did mean *override* or substitute as there is no inheritance for the structs. does it change your answer? Walter, please, correct me where I'm wrong. * ctors are somehow static operations (UML parlance), they construct the instance when the struct identifier is invoked with the corresponding arguments through the "()" operator. * static ctors, being the keyword "static" not an "Attribute" but a "StorageClass" (in D parlance), are something different. * static member functions, being the keyword "static" an "Attribute" (in D parlance), are static operations (UML parlance) as they don't need an instance to be invoked on. * opCall is the member function that is invoked when the calling-function-operator "()" is applied to an instance as if it were a function * static opCall is the static member function that is invoked when the calling-function-operator "()" is applied to a struct identifier as if it were a function. Hence, since there is a clear connection between the first point and the last point, why should the ctor substitute (or *override* as it has been used by you before) other than the static opCall mentioned in the last point? My experiments with real code and the last compiler version show that once there is present a ctor it even invalidates the possibility of accessing the *non-static* opCall to use a plain instance of that struct as if it were a function. Is that the expected behavior? I would understand if that the preference would take place between the ctor and the static opCall (both use the same syntactic expression on the struct), but I sincerely don't see the symmetry when the preference takes place between the ctor and the non-static opCall. Thanks!
Sep 04 2008
parent reply Walter Bright <newshound1 digitalmars.com> writes:
Bill Baxter wrote:
 On Fri, Sep 5, 2008 at 6:20 AM, Pablo Ripolles <in-call gmx.net> wrote:
 Walter Bright Wrote:

 Hence, since there is a clear connection between the first point and the last
point, why should the ctor substitute (or *override* as it has been used by you
before) other than the static opCall mentioned in the last point?

 My experiments with real code and the last compiler version show that once
there is present a ctor it even invalidates the possibility of accessing the
*non-static* opCall to use a plain instance of that struct as if it were a
function.  Is that the expected behavior?

If that's really the case with the latest D2 then that is odd. In C++ there isn't even a static opCall, only the non-static variety, but it works just fine in conjunction with constructors. Functor structs and structs with constructors should not be mutually exclusive. Kill off static opCall, fine, but don't kill instance opCall. That's one step forward one step back.

The non-static opCall should work fine.
Sep 04 2008
parent Max Samukha <samukha voliacable.com.removethis> writes:
On Thu, 04 Sep 2008 14:37:27 -0700, Walter Bright
<newshound1 digitalmars.com> wrote:

Bill Baxter wrote:
 On Fri, Sep 5, 2008 at 6:20 AM, Pablo Ripolles <in-call gmx.net> wrote:
 Walter Bright Wrote:

 Hence, since there is a clear connection between the first point and the last
point, why should the ctor substitute (or *override* as it has been used by you
before) other than the static opCall mentioned in the last point?

 My experiments with real code and the last compiler version show that once
there is present a ctor it even invalidates the possibility of accessing the
*non-static* opCall to use a plain instance of that struct as if it were a
function.  Is that the expected behavior?

If that's really the case with the latest D2 then that is odd. In C++ there isn't even a static opCall, only the non-static variety, but it works just fine in conjunction with constructors. Functor structs and structs with constructors should not be mutually exclusive. Kill off static opCall, fine, but don't kill instance opCall. That's one step forward one step back.

The non-static opCall should work fine.

Only the parameterless non-static opCall seem to work: struct S { this(int x) { } void opCall() { } } auto s = S(1); s(); // ok In other cases the compiler ignores the opCall and tries to use the constructor: struct S { this(int x) { } void opCall(int y) { } } auto s = S(1); s(1); // Error: * has no effect in expression Also, when opCall is a better match: struct S { this(int x) { } void opCall(int y, int z) { } } auto s = S(1); s(1, 2); // Error: this(int x) does not match parameter types
Sep 04 2008
prev sibling parent Georg Wrede <georg nospam.org> writes:
Walter Bright wrote:
 Jarrett Billingsley wrote:
 
 Speaking of syntactical ambiguity, the expression

 S(1, 2, 3)

 can, right now, have one of three meanings:

 1. A struct literal for struct S
 2. A call to S's static opCall
 3. An instantiation of S and a call to its ctor

 Even if opCall goes away, we'll still be left with the ambiguity of 
 struct literal vs. ctor.  I'd really, really like to hear Walter's 
 view on this but he has responded neither to the thread I posted on 
 digitalmars.D nor the bugzilla ticket 
 (http://d.puremagic.com/issues/show_bug.cgi?id=2170).

If there's any constructor defined for S, then S(args) is a constructor call. If there's any opCall defined for S, then S(args) is an opCall call. Otherwise, it's a struct literal.

This might be fluent for the "people in the know", but for everybody else (which is /everybody else/, until they become "people in the know") it is just distracting, ambiguous, and prone to misinterpretation. And this simply makes it take more time when debuggin the works of your team. Something ought to be done here.
Sep 04 2008
prev sibling next sibling parent "Bill Baxter" <wbaxter gmail.com> writes:
On Fri, Sep 5, 2008 at 6:37 AM, Walter Bright
<newshound1 digitalmars.com> wrote:
 Bill Baxter wrote:
 If that's really the case with the latest D2 then that is odd.  In C++
 there isn't even a static opCall, only the non-static variety, but it
 works just fine in conjunction with constructors. Functor  structs and
 structs with constructors should not be mutually exclusive.  Kill off
 static opCall, fine, but don't kill instance opCall.  That's one step
 forward one step back.

The non-static opCall should work fine.

Ok. Groovy then. --bb
Sep 04 2008
prev sibling parent "Jarrett Billingsley" <jarrett.billingsley gmail.com> writes:
On Sat, Sep 6, 2008 at 8:38 AM, Russell Lewis
<webmaster villagersonline.com> wrote:
 Jarrett Billingsley wrote:
 q{ is treated more or less as an atomic character.  Put a space
 between them and bam, you have a struct literal.

They made exactly that mistake with C++'s template syntax. It is one of the reasons that D's template syntax is better. It's an idea that sounds good when you are looking at it from an abstract, "yeah we could parse that" direction, but it makes for unreadable (and unwritable) code with strange syntax errors that are hard to find.

I'll agree with that and reiterate that if we could have named parameters I could care less about having better struct literals.
Sep 06 2008
prev sibling next sibling parent "Jarrett Billingsley" <jarrett.billingsley gmail.com> writes:
On Thu, Sep 4, 2008 at 2:09 PM, Leandro Lucarella <llucax gmail.com> wrote:
 Walter Bright, el  4 de septiembre a las 10:26 me escribiste:
 Tomas Lindquist Olsen wrote:
This is one of those things I really dislike about D :(
It's really nice that we can override struct initialization, but the fact that
it eliminates the possibility to override it (with a nice syntax) makes it much
less appealing IMHO.
The most important point to me, is that old thing about static struct
initializer and struct literals have different syntaxes, and that the static
variant is much more flexible.
I would have loved to see the static struct initializer syntax become an
expression. If the problem is ambiguity, why not just prefix the {} braces with
the struct name?

The static struct initializers more or less are inherited from C. I'd eventually like to abandon them and go completely to the S(args) syntax.

But they are much more flexible than constructor, it's like a constructor with named arguments! =) If you add support to named arguments, then I'll agree ;)

Ah, now there's a compromise I'd be more than willing to accept. If we didn't get S{} style struct literals, but were able to do S(x: 5, y: 10), that would be just as good. Named parameters are sooo easy! Please implement them!
Sep 04 2008
prev sibling next sibling parent "Jarrett Billingsley" <jarrett.billingsley gmail.com> writes:
On Mon, Sep 8, 2008 at 9:39 AM, Bruno Medeiros
<brunodomedeiros+spam com.gmail> wrote:
 Jarrett Billingsley wrote:
 Now were you just reading off of
 http://d.puremagic.com/issues/show_bug.cgi?id=2170 or did you come to
 this conclusion independently ;)

I was reading that, and I must say, I didn't quite understand the reasoning behind that named function parameters proposal.

Do you mean you don't understand the need for named function parameters, or you're not clear on the mechanism? If the former, named parameters are just a clearer way of calling functions that take a lot of parameters or a lot of potentially confusing parameters. If the latter, D currently allows you to do something like this: class A { this(int, int, int){} } void foo(A a...) { // a is a reference to a new instance of A } foo(1, 2, 3); // same as foo(new A(1, 2, 3)); So my idea is, if struct literals allow for named members, it's not much of a step to go from foo(SomeStruct{x: 1, y: 2}) to: foo(x: 1, y: 2)
 And what do you mean with "The issue with this is that you have to have a
 different named struct for every function that takes this style of
 parameters" ?
 Were you suggesting that functions who want to receive named parameters
 should declare an arguments struct just for that?

Yes. Although without the syntactic sugar, you'd end up having to write i.e. foo(FooArgs{x: 1, y: 2}) bar(BarArgs{z: 3.4, w: "hi"}) hence having to repeat the name of the function once for the function itself and again for the named arguments. With sugar, the argument structure name and braces go away, but it still doesn't solve the problem of having to declare an argument structure for every function. But, if we were to get named parameters for all functions, then both problems are solved: you have named parameters for free functions and methods, and you can initialize structs that have constructors or static opCalls with named members instead of having to write them in order: struct S { int x, y, z; this(int x, int y, int z) { this.x = x; this.y = y; this.z = z; } } S(1, 2, 3) and S(x: 1, y: 2, z: 3) are now both legal.
Sep 08 2008
prev sibling parent "Jarrett Billingsley" <jarrett.billingsley gmail.com> writes:
On Mon, Sep 8, 2008 at 9:39 AM, Bruno Medeiros
<brunodomedeiros+spam com.gmail> wrote:
 Jarrett Billingsley wrote:
 Now were you just reading off of
 http://d.puremagic.com/issues/show_bug.cgi?id=2170 or did you come to
 this conclusion independently ;)

I was reading that, and I must say, I didn't quite understand the reasoning behind that named function parameters proposal.

Do you mean you don't understand the need for named function parameters, or you're not clear on the mechanism? If the former, named parameters are just a clearer way of calling functions that take a lot of parameters or a lot of potentially confusing parameters. If the latter, D currently allows you to do something like this: class A { this(int, int, int){} } void foo(A a...) { // a is a reference to a new instance of A } foo(1, 2, 3); // same as foo(new A(1, 2, 3)); So my idea is, if struct literals allow for named members, it's not much of a step to go from foo(SomeStruct{x: 1, y: 2}) to: foo(x: 1, y: 2)
 And what do you mean with "The issue with this is that you have to have a
 different named struct for every function that takes this style of
 parameters" ?
 Were you suggesting that functions who want to receive named parameters
 should declare an arguments struct just for that?

Yes. Although without the syntactic sugar, you'd end up having to write i.e. foo(FooArgs{x: 1, y: 2}) bar(BarArgs{z: 3.4, w: "hi"}) hence having to repeat the name of the function once for the function itself and again for the named arguments. With sugar, the argument structure name and braces go away, but it still doesn't solve the problem of having to declare an argument structure for every function. But, if we were to get named parameters for all functions, then both problems are solved: you have named parameters for free functions and methods, and you can initialize structs that have constructors or static opCalls with named members instead of having to write them in order: struct S { int x, y, z; this(int x, int y, int z) { this.x = x; this.y = y; this.z = z; } } S(1, 2, 3) and S(x: 1, y: 2, z: 3) are now both legal.
Sep 08 2008
prev sibling next sibling parent "Jarrett Billingsley" <jarrett.billingsley gmail.com> writes:
On Wed, Sep 3, 2008 at 9:47 PM, Bill Baxter <wbaxter gmail.com> wrote:
 On Thu, Sep 4, 2008 at 10:38 AM, Jarrett Billingsley
 <jarrett.billingsley gmail.com> wrote:
 On Wed, Sep 3, 2008 at 8:22 PM, Moritz Warning <moritzwarning web.de> wrote:
 On Wed, 03 Sep 2008 20:04:49 -0400, Jarrett Billingsley wrote:

 On Wed, Sep 3, 2008 at 7:29 PM, Walter Bright
 <newshound1 digitalmars.com>wrote:

 Jarrett Billingsley wrote:

uh,<br><br>why don&#39;t you want to change struct literals?<br><br></div>

Hi Jarrett, do you mind not to use html markup? My news reader has no html renderer, nor my eye to brain connection. Thanks. :)

Ack, I've started using the mailing lists and gmail to interact with the newsgroups and forgot that it uses HTML by default, thanks for the heads up.

That happened to me too. I posted a suggestion to Google after that that Gmail should be smart enough not to reply to a plain text message with an HTML formatted one. Or that there should be a way to specify certain recipients don't get HTML. Maybe if you suggest it too it will push it up on their radar a bit. --bb

I think I was the one who pointed it out to you, making my transgression more than inexcusable ;) I'll let them know.
Sep 03 2008
prev sibling next sibling parent "Bill Baxter" <wbaxter gmail.com> writes:
On Thu, Sep 4, 2008 at 2:21 PM, Robert Fraser
<fraserofthenight gmail.com> wrote:
 And why not "new S(args)" to call the constructor (which is natural so
 far) and "S(args)" to work as it does now?

How would you distinguish between allocating the struct on the heap and on the stack? "new" anything does heap allocation and returns a pointer/reference, so it would be inconsistent if it did stack allocation for structs

Except for scope of course: scope foo = new Foo(); But I would guess for consistency that scope sfoo = new StructFoo(); should return a pointer to a stack-allocated struct. --bb
Sep 03 2008
prev sibling next sibling parent "Jarrett Billingsley" <jarrett.billingsley gmail.com> writes:
On Thu, Sep 4, 2008 at 7:58 AM, Denis Koroskin <2korden gmail.com> wrote:
 On Thu, 04 Sep 2008 15:44:30 +0400, Tomas Lindquist Olsen
 <tomas famolsen.dk> wrote:

 Walter Bright wrote:
 bearophile wrote:
 Walter Bright:
 If there's any constructor defined for S, then S(args) is a
 constructor call. If there's any opCall defined for S, then S(args)
 is an opCall call. Otherwise, it's a struct literal.

I haven't tried that in real code, so I can't be sure, but while it may work for the compiler, it sounds a bit too much complex for the person that later reads the code. Too many alternative possibilities may make the code more complex to follow. To reduce such ambiguity (ambiguity for the person, not for the compiler) may be to change the syntax of struct literals...

I disagree, I think just the reverse. The S(args) syntax means that it's entirely up to the struct designer to say how it should work. The user needn't know or care, and the struct designer can change the design without affecting user code.

This is one of those things I really dislike about D :( It's really nice that we can override struct initialization, but the fact that it eliminates the possibility to override it (with a nice syntax) makes it much less appealing IMHO. The most important point to me, is that old thing about static struct initializer and struct literals have different syntaxes, and that the static variant is much more flexible. I would have loved to see the static struct initializer syntax become an expression. If the problem is ambiguity, why not just prefix the {} braces with the struct name? struct S { int a; float b; } const s = S{1, 2.0}; const t = S{b:3.14}; void foo() { auto st = S{4,5.5}; }

It may have problems with the q{}: struct q { float t; } auto foo = q{ t = 3.1415f }; // what's the type of foo? But then, does anybody using it? Other than that I agree, current solution is not very good.

auto foo = q { t: 3.1415f}; // typeof(foo) == q q{ is treated more or less as an atomic character. Put a space between them and bam, you have a struct literal. And please don't get rid of token strings; those of us who love mixins wouldn't want to see them go ;)
Sep 04 2008
prev sibling parent "Bill Baxter" <wbaxter gmail.com> writes:
On Fri, Sep 5, 2008 at 6:20 AM, Pablo Ripolles <in-call gmx.net> wrote:
 Walter Bright Wrote:

 Hence, since there is a clear connection between the first point and the last
point, why should the ctor substitute (or *override* as it has been used by you
before) other than the static opCall mentioned in the last point?

 My experiments with real code and the last compiler version show that once
there is present a ctor it even invalidates the possibility of accessing the
*non-static* opCall to use a plain instance of that struct as if it were a
function.  Is that the expected behavior?

If that's really the case with the latest D2 then that is odd. In C++ there isn't even a static opCall, only the non-static variety, but it works just fine in conjunction with constructors. Functor structs and structs with constructors should not be mutually exclusive. Kill off static opCall, fine, but don't kill instance opCall. That's one step forward one step back. --bb
Sep 04 2008
prev sibling next sibling parent "Bill Baxter" <wbaxter gmail.com> writes:
On Thu, Sep 4, 2008 at 10:38 AM, Jarrett Billingsley
<jarrett.billingsley gmail.com> wrote:
 On Wed, Sep 3, 2008 at 8:22 PM, Moritz Warning <moritzwarning web.de> wrote:
 On Wed, 03 Sep 2008 20:04:49 -0400, Jarrett Billingsley wrote:

 On Wed, Sep 3, 2008 at 7:29 PM, Walter Bright
 <newshound1 digitalmars.com>wrote:

 Jarrett Billingsley wrote:

uh,<br><br>why don&#39;t you want to change struct literals?<br><br></div>

Hi Jarrett, do you mind not to use html markup? My news reader has no html renderer, nor my eye to brain connection. Thanks. :)

Ack, I've started using the mailing lists and gmail to interact with the newsgroups and forgot that it uses HTML by default, thanks for the heads up.

That happened to me too. I posted a suggestion to Google after that that Gmail should be smart enough not to reply to a plain text message with an HTML formatted one. Or that there should be a way to specify certain recipients don't get HTML. Maybe if you suggest it too it will push it up on their radar a bit. --bb
Sep 03 2008
prev sibling parent "Jarrett Billingsley" <jarrett.billingsley gmail.com> writes:
On Thu, Sep 4, 2008 at 7:44 AM, Tomas Lindquist Olsen <tomas famolsen.dk> wrote:

 The most important point to me, is that old thing about static struct
 initializer and struct literals have different syntaxes, and that the static
 variant is much more flexible.

 I would have loved to see the static struct initializer syntax become an
 expression. If the problem is ambiguity, why not just prefix the {} braces
 with the struct name?

 struct S
 {
  int a;
  float b;
 }

 const s = S{1, 2.0};
 const t = S{b:3.14};

 void foo()
 {
  auto st = S{4,5.5};
 }

 (also not that it's currently impossible to use type inference with the
 current static struct initializers)

 This would eliminate the gripe most people have with this I think, as well
 as making static and  non-static initializers consistent. like they are *for
 all other types*.

Now were you just reading off of http://d.puremagic.com/issues/show_bug.cgi?id=2170 or did you come to this conclusion independently ;)
Sep 04 2008
prev sibling next sibling parent reply Ary Borenszweig <ary esperanto.org.ar> writes:
Walter Bright a crit :
 To construct an object of struct S:
 
 auto s = S(arguments);

Please add this example to the docs. I first thought you'd create a struct like auto s = new S(arguments); (so that constructing something has a consistent syntax... so if then you decide to change your struct to a class, or viceversa, and you don't have to change a lot of bits everywhere)
 
 Extrawurst wrote:
 Are opCalls deprecated now ? how do i call the ctor and how the 
 opCall? a short example in the docs would have been nice.


Sep 03 2008
parent reply Mosfet <mosfet anonymous.org> writes:
Ary Borenszweig wrote:
 Walter Bright a crit :
 To construct an object of struct S:

 auto s = S(arguments);


keyword ? When I look at documentation I can read : The auto attribute is used when there are no other attributes and type inference is desired. In which case you want inference type ? Is it a kind o C++ RTTI ? In the sample code above, you already know that struct is of kind S. First I thought auto means automatically destruct object when out of scope.
 Please add this example to the docs. I first thought you'd create a 
 struct like
 
 auto s = new S(arguments);
 
 (so that constructing something has a consistent syntax... so if then 
 you decide to change your struct to a class, or viceversa, and you don't 
 have to change a lot of bits everywhere)
 
 Extrawurst wrote:
 Are opCalls deprecated now ? how do i call the ctor and how the 
 opCall? a short example in the docs would have been nice.



Sep 03 2008
parent Extrawurst <spam extrawurst.org> writes:
Mosfet wrote:
 When I look at documentation I can read :
 The auto attribute is used when there are no other attributes and type 
 inference is desired.
 
 In which case you want inference type ? Is it a kind o C++ RTTI ?
 In the sample code above, you already know that struct is of kind S.
 First I thought auto means automatically destruct object when out of scope.

auto just helps writing code in a more brief and readable way. The compiler infers the type which u are using by the right side of the expression, which is extremly handy when u use cascaded templates a lot. example: MyTemplateA!(MyTemplateB("foo")) variablename = new MyTemplateA!(MyTemplateB("foo"))("aParemterString"); with auto u just have to write it once: auto variablename = new MyTemplateA!(MyTemplateB("foo"))("aParemterString"); the compiler infers the type of variablename looking at the expression.
Sep 03 2008
prev sibling parent "Jarrett Billingsley" <jarrett.billingsley gmail.com> writes:
On Wed, Sep 3, 2008 at 8:22 PM, Moritz Warning <moritzwarning web.de> wrote:
 On Wed, 03 Sep 2008 20:04:49 -0400, Jarrett Billingsley wrote:

 On Wed, Sep 3, 2008 at 7:29 PM, Walter Bright
 <newshound1 digitalmars.com>wrote:

 Jarrett Billingsley wrote:

uh,<br><br>why don&#39;t you want to change struct literals?<br><br></div>

Hi Jarrett, do you mind not to use html markup? My news reader has no html renderer, nor my eye to brain connection. Thanks. :)

Ack, I've started using the mailing lists and gmail to interact with the newsgroups and forgot that it uses HTML by default, thanks for the heads up.
Sep 03 2008
prev sibling next sibling parent "Jarrett Billingsley" <jarrett.billingsley gmail.com> writes:
Content-Type: text/plain; charset=ISO-8859-1
Content-Transfer-Encoding: 7bit
Content-Disposition: inline

On Wed, Sep 3, 2008 at 4:30 PM, 0ffh <frank youknow.what.todo.internetz>wrote:

 bobef wrote:

 opCalls are much more flexible than ctor's because their return type may
 vary or they may not have return type. I vote against deprecating them.
 Let
 whoever likes ctors use them and whoever likes opCalls use these.

I agree opCalls are more flexible, but unfortunately you can't have both because of syntactical ambiguity... :-( regards, 0ffh

Speaking of syntactical ambiguity, the expression S(1, 2, 3) can, right now, have one of three meanings: 1. A struct literal for struct S 2. A call to S's static opCall 3. An instantiation of S and a call to its ctor Even if opCall goes away, we'll still be left with the ambiguity of struct literal vs. ctor. I'd really, really like to hear Walter's view on this but he has responded neither to the thread I posted on digitalmars.D nor the bugzilla ticket (http://d.puremagic.com/issues/show_bug.cgi?id=2170).
Sep 03 2008
prev sibling next sibling parent "Jarrett Billingsley" <jarrett.billingsley gmail.com> writes:
Content-Type: text/plain; charset=ISO-8859-1
Content-Transfer-Encoding: 7bit
Content-Disposition: inline

On Wed, Sep 3, 2008 at 7:29 PM, Walter Bright <newshound1 digitalmars.com>wrote:

 Jarrett Billingsley wrote:

 Speaking of syntactical ambiguity, the expression

 S(1, 2, 3)

 can, right now, have one of three meanings:

 1. A struct literal for struct S
 2. A call to S's static opCall
 3. An instantiation of S and a call to its ctor

 Even if opCall goes away, we'll still be left with the ambiguity of struct
 literal vs. ctor.  I'd really, really like to hear Walter's view on this but
 he has responded neither to the thread I posted on digitalmars.D nor the
 bugzilla ticket (http://d.puremagic.com/issues/show_bug.cgi?id=2170).

If there's any constructor defined for S, then S(args) is a constructor call. If there's any opCall defined for S, then S(args) is an opCall call. Otherwise, it's a struct literal.

So uh, why don't you want to change struct literals?
Sep 03 2008
prev sibling next sibling parent Moritz Warning <moritzwarning web.de> writes:
On Wed, 03 Sep 2008 20:04:49 -0400, Jarrett Billingsley wrote:

 On Wed, Sep 3, 2008 at 7:29 PM, Walter Bright
 <newshound1 digitalmars.com>wrote:
 
 Jarrett Billingsley wrote:

uh,<br><br>why don&#39;t you want to change struct literals?<br><br></div>

Hi Jarrett, do you mind not to use html markup? My news reader has no html renderer, nor my eye to brain connection. Thanks. :)
Sep 03 2008
prev sibling parent "Denis Koroskin" <2korden gmail.com> writes:
On Thu, 04 Sep 2008 15:44:30 +0400, Tomas Lindquist Olsen  
<tomas famolsen.dk> wrote:

 Walter Bright wrote:
 bearophile wrote:
 Walter Bright:
 If there's any constructor defined for S, then S(args) is a
 constructor call. If there's any opCall defined for S, then S(args)
 is an opCall call. Otherwise, it's a struct literal.

I haven't tried that in real code, so I can't be sure, but while it may work for the compiler, it sounds a bit too much complex for the person that later reads the code. Too many alternative possibilities may make the code more complex to follow. To reduce such ambiguity (ambiguity for the person, not for the compiler) may be to change the syntax of struct literals...

it's entirely up to the struct designer to say how it should work. The user needn't know or care, and the struct designer can change the design without affecting user code.

This is one of those things I really dislike about D :( It's really nice that we can override struct initialization, but the fact that it eliminates the possibility to override it (with a nice syntax) makes it much less appealing IMHO. The most important point to me, is that old thing about static struct initializer and struct literals have different syntaxes, and that the static variant is much more flexible. I would have loved to see the static struct initializer syntax become an expression. If the problem is ambiguity, why not just prefix the {} braces with the struct name? struct S { int a; float b; } const s = S{1, 2.0}; const t = S{b:3.14}; void foo() { auto st = S{4,5.5}; }

It may have problems with the q{}: struct q { float t; } auto foo = q{ t = 3.1415f }; // what's the type of foo? But then, does anybody using it? Other than that I agree, current solution is not very good.
 (also not that it's currently impossible to use type inference with the  
 current static struct initializers)

 This would eliminate the gripe most people have with this I think, as  
 well as making static and   non-static initializers consistent. like  
 they are *for all other types*.

 I can't help feel structs (like static arrays) aren't first class  
 citizens in D. Even with the latest additions in D2. It hurts, and is  
 just one of those small reasons why I sometimes regret I even joined  
 this community...

 My 2 cents on this, I think it's a big mistake going against the wishes  
 of the D community. If I'm wrong, let me know.

 -Tomas

-- Using Opera's revolutionary e-mail client: http://www.opera.com/mail/
Sep 04 2008
prev sibling next sibling parent reply Extrawurst <spam extrawurst.org> writes:
And why is it that there is no default ctor allowed for structs ?

struct S{this(){}} //constructor main.S.this default constructor not 
allowed for structs

Walter Bright wrote:
 Struct constructors!
 
 http://www.digitalmars.com/d/1.0/changelog.html
 http://ftp.digitalmars.com/dmd.1.035.zip
 
 http://www.digitalmars.com/d/2.0/changelog.html
 http://ftp.digitalmars.com/dmd.2.019.zip

Sep 03 2008
parent Walter Bright <newshound1 digitalmars.com> writes:
Extrawurst wrote:
 And why is it that there is no default ctor allowed for structs ?

Good question. Because: 1. Having a default ctor conflicts with the concept of a .init property. 2. Using .init for default construction guarantees it can never throw, which is a useful property in many generic programming circumstances 3. It guarantees it is pure. 4. Nearly every instance of default construction I've seen would initialize it just to what .init does in D. 5. It eliminates the need for a member initializer syntax.
Sep 03 2008
prev sibling next sibling parent reply Max Samukha <samukha voliacable.com.removethis> writes:
On Tue, 02 Sep 2008 22:42:06 -0700, Walter Bright
<newshound1 digitalmars.com> wrote:

Struct constructors!

http://www.digitalmars.com/d/1.0/changelog.html
http://ftp.digitalmars.com/dmd.1.035.zip

http://www.digitalmars.com/d/2.0/changelog.html
http://ftp.digitalmars.com/dmd.2.019.zip

Thanks! Two questions about the struct constructors: 1. Why is there the limitation that the constructor list may not be empty? One problem with that rule is incorrect handling of a single parameter with a default value: struct S { this(int x = 1) { writefln("Ctor"); } } S s = S(); The constructor is not called. Is such a parameter list considered empty or non-empty? 2. How do constructiors affect static opCalls? struct S { this(int x) { } static void opCall(int x, int y) { } } S s; s(1, 2); Error: constructor Test.main.S.this (int x) does not match parameter types (int,int) dmd seems to ignore static opCalls completely, if there is a constructor. Is it intended behavior?
Sep 03 2008
parent reply Walter Bright <newshound1 digitalmars.com> writes:
Max Samukha wrote:
 On Tue, 02 Sep 2008 22:42:06 -0700, Walter Bright
 <newshound1 digitalmars.com> wrote:
 
 Struct constructors!

 http://www.digitalmars.com/d/1.0/changelog.html
 http://ftp.digitalmars.com/dmd.1.035.zip

 http://www.digitalmars.com/d/2.0/changelog.html
 http://ftp.digitalmars.com/dmd.2.019.zip

Thanks! Two questions about the struct constructors: 1. Why is there the limitation that the constructor list may not be empty? One problem with that rule is incorrect handling of a single parameter with a default value: struct S { this(int x = 1) { writefln("Ctor"); } } S s = S(); The constructor is not called. Is such a parameter list considered empty or non-empty?

Empty.
 2. How do constructiors affect static opCalls?
 
 struct S
 {
 	this(int x)
 	{
 	}
 
 	static void opCall(int x, int y)
 	{
 	}
 }
 
 S s;
 s(1, 2); 
 
 Error: constructor Test.main.S.this (int x) does not match parameter
 types (int,int)
 
 
 dmd seems to ignore static opCalls completely, if there is a
 constructor. Is it intended behavior?

Yes, that's exactly how it works.
Sep 03 2008
parent reply Max Samukha <samukha voliacable.com.removethis> writes:
On Wed, 03 Sep 2008 00:57:40 -0700, Walter Bright
<newshound1 digitalmars.com> wrote:

Max Samukha wrote:
 On Tue, 02 Sep 2008 22:42:06 -0700, Walter Bright
 <newshound1 digitalmars.com> wrote:
 
 Struct constructors!

 http://www.digitalmars.com/d/1.0/changelog.html
 http://ftp.digitalmars.com/dmd.1.035.zip

 http://www.digitalmars.com/d/2.0/changelog.html
 http://ftp.digitalmars.com/dmd.2.019.zip

Thanks! Two questions about the struct constructors: 1. Why is there the limitation that the constructor list may not be empty? One problem with that rule is incorrect handling of a single parameter with a default value: struct S { this(int x = 1) { writefln("Ctor"); } } S s = S(); The constructor is not called. Is such a parameter list considered empty or non-empty?

Empty.

Should it be a compile time error? The above is semantically equivalent to struct S { this() { this(1); } this(int x) { } } which is not allowed. Incidentally, calling other constructors from a constructor doesn't work. Is it a bug?
 2. How do constructiors affect static opCalls?
 
 struct S
 {
 	this(int x)
 	{
 	}
 
 	static void opCall(int x, int y)
 	{
 	}
 }
 
 S s;
 s(1, 2); 


Correction: should be "S(1, 2);". "S s;" is not needed.
 
 Error: constructor Test.main.S.this (int x) does not match parameter
 types (int,int)
 
 
 dmd seems to ignore static opCalls completely, if there is a
 constructor. Is it intended behavior?

Yes, that's exactly how it works.

Sep 03 2008
parent Walter Bright <newshound1 digitalmars.com> writes:
Max Samukha wrote:
 Incidentally, calling other constructors from a constructor doesn't
 work. Is it a bug? 

I'd forgotten about that. It's a bug.
Sep 03 2008
prev sibling next sibling parent Steven Schveighoffer <schveiguy yahoo.com> writes:
Walter Bright wrote:
 Struct constructors!
 
 http://www.digitalmars.com/d/1.0/changelog.html
 http://ftp.digitalmars.com/dmd.1.035.zip
 
 http://www.digitalmars.com/d/2.0/changelog.html
 http://ftp.digitalmars.com/dmd.2.019.zip

Thanks! Also, thanks for identifying all the bugs fixed now instead of later, it makes it much easier to track my issues :) -Steve
Sep 03 2008
prev sibling next sibling parent reply dsimcha <dsimcha yahoo.com> writes:
== Quote from Walter Bright (newshound1 digitalmars.com)'s article
 Struct constructors!
 http://www.digitalmars.com/d/1.0/changelog.html
 http://ftp.digitalmars.com/dmd.1.035.zip
 http://www.digitalmars.com/d/2.0/changelog.html
 http://ftp.digitalmars.com/dmd.2.019.zip

What does a struct constructor in its current form make possible/easy that was awkward/impossible with opCalls?
Sep 03 2008
parent reply Walter Bright <newshound1 digitalmars.com> writes:
dsimcha wrote:
 What does a struct constructor in its current form make possible/easy that was
 awkward/impossible with opCalls?

Aside from the logical symmetry, it enables an object to be constructed using operator new.
Sep 03 2008
parent dsimcha <dsimcha yahoo.com> writes:
== Quote from Walter Bright (newshound1 digitalmars.com)'s article
 dsimcha wrote:
 What does a struct constructor in its current form make possible/easy that was
 awkward/impossible with opCalls?

using operator new.

In that case, struct ctors are a nice addition, but please don't deprecate opCall. I personally think it's fine to just make them mutually exclusive.
Sep 03 2008
prev sibling next sibling parent reply Sean Kelly <sean invisibleduck.org> writes:
Walter Bright wrote:
 Struct constructors!

Must... have... D2. :-) By the way, no runtime changes were required to upgrade Tango to work with this release, so Tango users can drop in the new DMD without any issues. Sean
Sep 03 2008
next sibling parent reply Walter Bright <newshound1 digitalmars.com> writes:
Sean Kelly wrote:
 Walter Bright wrote:
 Struct constructors!

Must... have... D2. :-)

I figured you'd be seduced sooner or later!
Sep 03 2008
parent reply "Chris R. Miller" <lordSaurontheGreat gmail.com> writes:
Content-Type: text/plain; charset=ISO-8859-1
Content-Transfer-Encoding: quoted-printable

Walter Bright wrote:
 Sean Kelly wrote:
 Walter Bright wrote:
 Struct constructors!

Must... have... D2. :-)

I figured you'd be seduced sooner or later!

So this would make structs (in effect) classes that don't exist on the he= ap?
Sep 03 2008
parent reply Walter Bright <newshound1 digitalmars.com> writes:
Chris R. Miller wrote:
 Walter Bright wrote:
 Sean Kelly wrote:
 Walter Bright wrote:
 Struct constructors!



So this would make structs (in effect) classes that don't exist on the heap?

No, structs do not inherit and do not have virtual functions.
Sep 03 2008
parent reply Ary Borenszweig <ary esperanto.org.ar> writes:
Walter Bright a crit :
 Chris R. Miller wrote:
 Walter Bright wrote:
 Sean Kelly wrote:
 Walter Bright wrote:
 Struct constructors!



So this would make structs (in effect) classes that don't exist on the heap?

No, structs do not inherit and do not have virtual functions.

So both syntax are possible? S(...) new S(...) for a struct with a constructor? Is that documented anywhere?
Sep 03 2008
parent reply Walter Bright <newshound1 digitalmars.com> writes:
Ary Borenszweig wrote:
 So both syntax are possible?
 
 S(...)

Creates a struct instance
 new S(...)

Creates a struct instance and returns a pointer to it.
Sep 03 2008
parent reply "Steven Schveighoffer" <schveiguy yahoo.com> writes:
"Walter Bright" wrote
 Ary Borenszweig wrote:
 So both syntax are possible?

 S(...)

Creates a struct instance
 new S(...)

Creates a struct instance and returns a pointer to it.

On the heap I assume? (hope) -Steve
Sep 03 2008
parent Walter Bright <newshound1 digitalmars.com> writes:
Steven Schveighoffer wrote:
 "Walter Bright" wrote
 Ary Borenszweig wrote:
 So both syntax are possible?

 S(...)

 new S(...)


On the heap I assume? (hope)

S() creates it on the stack, new S() on the heap.
Sep 03 2008
prev sibling parent "Bill Baxter" <wbaxter gmail.com> writes:
On Thu, Sep 4, 2008 at 9:50 AM, Ary Borenszweig <ary esperanto.org.ar> wrot=
e:
 Walter Bright a =E9crit :
 Chris R. Miller wrote:
 Walter Bright wrote:
 Sean Kelly wrote:
 Walter Bright wrote:
 Struct constructors!

Must... have... D2. :-)

I figured you'd be seduced sooner or later!

So this would make structs (in effect) classes that don't exist on the heap?

No, structs do not inherit and do not have virtual functions.

So both syntax are possible? S(...) new S(...) for a struct with a constructor? Is that documented anywhere?

I'm pretty sure that's: S thing =3D S(...); S* ptr =3D new S(...); So yes both syntaxes are possible, but they are not synonyms. --bb
Sep 03 2008
prev sibling parent reply =?UTF-8?B?IuOBruOBl+OBhOOBiyAobm9zaGlpa2EpIg==?= writes:
Walter Bright wrote:
 Struct constructors!

Thanks for the nice release! I have a question. The "dynamic initialization of struct" syntax seems still using opCall. Is it going to replaced by constructors? struct S { this(int x) { writeln("ctor"); } static S opCall(int x) { writeln("opCall"); return S.init; } } void main(){ S s = 1; // prints "opCall" }
Sep 03 2008
parent davidl <davidl 126.com> writes:
在 Thu, 04 Sep 2008 09:23:08 +0800,のしいか (noshiika)  
<noshiika gmail.com> 写道:

 Walter Bright wrote:
 Struct constructors!

Thanks for the nice release! I have a question. The "dynamic initialization of struct" syntax seems still using opCall. Is it going to replaced by constructors? struct S { this(int x) { writeln("ctor"); } static S opCall(int x) { writeln("opCall"); return S.init; } } void main(){ S s = 1; // prints "opCall" }

umm, another bug ? -- 使用 Opera 革命性的电子邮件客户程序: http://www.opera.com/mail/
Sep 03 2008