Thread overview
Operator precedence of "new"
Oct 15, 2010
bearophile
Oct 15, 2010
Denis Koroskin
Oct 15, 2010
Michel Fortin
Oct 15, 2010
Stanislav Blinov
Oct 15, 2010
Stanislav Blinov
Oct 15, 2010
Andrej Mitrovic
Oct 17, 2010
bearophile
Re: Accessing anonymous reference inside with block
Oct 18, 2010
Stanislav Blinov
Oct 18, 2010
Andrej Mitrovic
Oct 18, 2010
Andrej Mitrovic
October 15, 2010
Currently to call a method to a newly build object/struct you need:

(new Foo).bar();

But isn't it better to change the D operator precedence rules a bit and allow new to bind more closely than the method call, to allow a syntax like:

new Foo.bar();

Do you see bad side effects in this D2 change?

Bye and thank you,
bearophile
October 15, 2010
On Fri, 15 Oct 2010 16:12:24 +0400, bearophile <bearophileHUGS@lycos.com> wrote:

> Currently to call a method to a newly build object/struct you need:
>
> (new Foo).bar();
>
> But isn't it better to change the D operator precedence rules a bit and allow new to bind more closely than the method call, to allow a syntax like:
>
> new Foo.bar();
>
> Do you see bad side effects in this D2 change?
>
> Bye and thank you,
> bearophile

Isn't this syntax used to instantiate inner class/struct, declared in Foo?
The two are so much different there is really little point of sharing syntax for it.
October 15, 2010
On 2010-10-15 08:12:24 -0400, bearophile <bearophileHUGS@lycos.com> said:

> Currently to call a method to a newly build object/struct you need:
> 
> (new Foo).bar();
> 
> But isn't it better to change the D operator precedence rules a bit and allow new to bind more closely than the method call, to allow a syntax like:
> 
> new Foo.bar();
> 
> Do you see bad side effects in this D2 change?

But then, how does that work?

	new Foo.SubType.bar();

Could work like this:

	new (Foo.Subtype).bar();

which doesn't look too bad as long as .bar() is at the end. Remove it and you'll get this:

	new (Foo.Subtype);

Hardly interesting, and somewhat counter-intuitive. That's especially bad considering that all types are in reality enclosed module name which can be made explicit:

	new (std.stdio.File);

I much prefer that this works:

	new std.stdio.File;
	new Foo.Subtype;

Even if it means I have to do:

	(new Foo).bar();

-- 
Michel Fortin
michel.fortin@michelf.com
http://michelf.com/

October 15, 2010
 15.10.2010 16:12, bearophile пишет:
> Currently to call a method to a newly build object/struct you need:
>
> (new Foo).bar();
>
> But isn't it better to change the D operator precedence rules a bit and allow new to bind more closely than the method call, to allow a syntax like:
>
> new Foo.bar();
>
> Do you see bad side effects in this D2 change?
>
Aside from what was already mentioned about nested classes:
What if bar() is a static function of Foo? Current precedence allows the compiler to bug you if you write

new Foo.bar();

If precedence is modified in the way you propose, then you effectively get a call to static function through an instance (which in itself is valid operation), though that instance is immediately thrown away.
October 15, 2010
 15.10.2010 17:07, Stanislav Blinov пишет:
>  15.10.2010 16:12, bearophile пишет:
>> Currently to call a method to a newly build object/struct you need:
>>
>> (new Foo).bar();
>>
>> But isn't it better to change the D operator precedence rules a bit and allow new to bind more closely than the method call, to allow a syntax like:
>>
>> new Foo.bar();
>>
>> Do you see bad side effects in this D2 change?
>>
> Aside from what was already mentioned about nested classes:
> What if bar() is a static function of Foo? Current precedence allows the compiler to bug you if you write
>
> new Foo.bar();
>
> If precedence is modified in the way you propose, then you effectively get a call to static function through an instance (which in itself is valid operation), though that instance is immediately thrown away.
>

Forgot to mention the 'bad' side:
Despite you actually do throw instance away as a result of such call, in case of non-static method it is done intentionally and with keeping in mind precisely what does Foo's ctor do, while in case of static call instance construction may be unexpected and lead to subtle difficult-to-trace bugs.
October 15, 2010
Related: A nice alternative for quickly using anonymous objects is using the with statement, e.g.:

with (new Foo)
{
    foo();
    // ... more code
}

And after the with block the object doesn't exist anymore. Or you could bind it to some internal reference and keep it there, which wouldn't destroy it after exiting the with block. Many of the DFL GUI library code samples work this way, and it's quite a nice syntax imo.

On 10/15/10, Stanislav Blinov <blinov@loniir.ru> wrote:
>   15.10.2010 17:07, Stanislav Blinov пишет:
>>  15.10.2010 16:12, bearophile пишет:
>>> Currently to call a method to a newly build object/struct you need:
>>>
>>> (new Foo).bar();
>>>
>>> But isn't it better to change the D operator precedence rules a bit and allow new to bind more closely than the method call, to allow a syntax like:
>>>
>>> new Foo.bar();
>>>
>>> Do you see bad side effects in this D2 change?
>>>
>> Aside from what was already mentioned about nested classes:
>> What if bar() is a static function of Foo? Current precedence allows
>> the compiler to bug you if you write
>>
>> new Foo.bar();
>>
>> If precedence is modified in the way you propose, then you effectively get a call to static function through an instance (which in itself is valid operation), though that instance is immediately thrown away.
>>
>
> Forgot to mention the 'bad' side:
> Despite you actually do throw instance away as a result of such call, in
> case of non-static method it is done intentionally and with keeping in
> mind precisely what does Foo's ctor do, while in case of static call
> instance construction may be unexpected and lead to subtle
> difficult-to-trace bugs.
>
October 17, 2010
I was busy, I am back.
Indeed it wasn't a good idea.
Thank you for all the answers.

Bye,
bearophile
October 18, 2010
 15.10.2010 19:43, Andrej Mitrovic wrote:
> Related: A nice alternative for quickly using anonymous objects is
> using the with statement, e.g.:
>
> with (new Foo)
> {
>      foo();
>      // ... more code
> }
>
> And after the with block the object doesn't exist anymore.
> Or you could bind it to some internal reference and keep it there,

I must ask, how can this binding be achieved?

> which wouldn't destroy it after exiting the with block. Many of the DFL GUI
> library code samples work this way, and it's quite a nice syntax imo.

October 18, 2010
Here's an example from DFL where I'm using an anonymous Scintilla object which is a subclass of a text editing widget in DFL (just another window subclass), but behind the scenes it actually loads the Scintilla DLL and behaves like a normal DFL text editing widget:

http://pastebin.com/YAduPRtF

What really happens in DFL is that assiging the "parent" variable of a window class object (lets call it client) to another window class object (call it host) means that the host now holds a reference to the client. So the client will not be destroyed unless any of it's destroy methods are explicitly called, or if the host window is destroyed then the client window is destroyed as well (this is how DFL works).

I think that's how it works. If I'm wrong someone can correct me, though. :)

On 10/18/10, Stanislav Blinov <blinov@loniir.ru> wrote:
>   15.10.2010 19:43, Andrej Mitrovic wrote:
>> Related: A nice alternative for quickly using anonymous objects is using the with statement, e.g.:
>>
>> with (new Foo)
>> {
>>      foo();
>>      // ... more code
>> }
>>
>> And after the with block the object doesn't exist anymore.
>> Or you could bind it to some internal reference and keep it there,
>
> I must ask, how can this binding be achieved?
>
>> which wouldn't destroy it after exiting the with block. Many of the DFL
>> GUI
>> library code samples work this way, and it's quite a nice syntax imo.
>
>
October 18, 2010
Oops, the code came out a little fuzzy, here's the fixed one:

http://pastebin.com/kiXPeQLB

On 10/18/10, Andrej Mitrovic <andrej.mitrovich@gmail.com> wrote:
> Here's an example from DFL where I'm using an anonymous Scintilla object which is a subclass of a text editing widget in DFL (just another window subclass), but behind the scenes it actually loads the Scintilla DLL and behaves like a normal DFL text editing widget:
>
> http://pastebin.com/YAduPRtF
>
> What really happens in DFL is that assiging the "parent" variable of a window class object (lets call it client) to another window class object (call it host) means that the host now holds a reference to the client. So the client will not be destroyed unless any of it's destroy methods are explicitly called, or if the host window is destroyed then the client window is destroyed as well (this is how DFL works).
>
> I think that's how it works. If I'm wrong someone can correct me, though. :)
>
> On 10/18/10, Stanislav Blinov <blinov@loniir.ru> wrote:
>>   15.10.2010 19:43, Andrej Mitrovic wrote:
>>> Related: A nice alternative for quickly using anonymous objects is using the with statement, e.g.:
>>>
>>> with (new Foo)
>>> {
>>>      foo();
>>>      // ... more code
>>> }
>>>
>>> And after the with block the object doesn't exist anymore.
>>> Or you could bind it to some internal reference and keep it there,
>>
>> I must ask, how can this binding be achieved?
>>
>>> which wouldn't destroy it after exiting the with block. Many of the DFL
>>> GUI
>>> library code samples work this way, and it's quite a nice syntax imo.
>>
>>
>