Re: is there any reason UFCS can't be used with 'new'?

2014-11-10 Thread Suliman via Digitalmars-d-learn

I can't understand how to use UFCS with instance of class:

void main()
{

string name = Suliman;
userName username = new userName(name);

/// How to use UFCS here?
userName.name.sayHello();
///
}

class userName
{
string name;

this(string name)
{
this.name = name;
}

void sayHello(string name)
{
writeln(name);
}
}


Re: is there any reason UFCS can't be used with 'new'?

2014-11-10 Thread ketmar via Digitalmars-d-learn
On Mon, 10 Nov 2014 19:07:38 +
Suliman via Digitalmars-d-learn digitalmars-d-learn@puremagic.com
wrote:

 /// How to use UFCS here?
 userName.name.sayHello();
 ///
you can't.

a little explanation: UFCS substitutes only the first argument. and for
class methods first argument is hidden 'this'. so you can't do it in
this way, you have to write `userName.sayHello(name);` here.

on the very low level calling class methods looks like this:

  // what you see:
  myobj.method(arg);

  // what compiler does:
  // method(myobj, arg);

so in your example compiler sees this:

  sayHello(userName.name);

which is obviously not what you want, 'cause you need this:

  sayHello(userName, name);

or, taking it the easier way: UFCS is for *functions*, not for
*methods*. that's why it uniform *function* call syntax. it's not
expected to work with methods, as the name suggests. maybe it will be
easier to remember this way, rather than diving into compiler code
transformations. ;-)


signature.asc
Description: PGP signature


Re: is there any reason UFCS can't be used with 'new'?

2014-11-10 Thread Justin Whear via Digitalmars-d-learn
On Mon, 10 Nov 2014 19:07:38 +, Suliman wrote:

 I can't understand how to use UFCS with instance of class:
 
 void main()
 {
 
 string name = Suliman;
 userName username = new userName(name);
 
 /// How to use UFCS here?
 userName.name.sayHello();
 ///
 }
 
 class userName {
  string name;
 
  this(string name)
  {
  this.name = name;
  }
 
  void sayHello(string name)
  {
  writeln(name);
  }
 }

This has nothing to do with new--you're trying to use a virtual function 
scoped
to class userName with a string.  Rewrite it to a static module-scoped 
function:

class userName {
string name;

this(string name)
{
this.name = name;
}
}

void sayHello(string name)
{
writeln(name);
}

void main()
{

string name = Suliman;
userName username = new userName(name);

userName.name.sayHello();
}


Re: is there any reason UFCS can't be used with 'new'?

2014-11-10 Thread Ali Çehreli via Digitalmars-d-learn

On 11/10/2014 11:07 AM, Suliman wrote:

I can't understand how to use UFCS with instance of class:

void main()
{

string name = Suliman;
userName username = new userName(name);

/// How to use UFCS here?
userName.name.sayHello();
///
}

class userName
{
 string name;

 this(string name)
 {
 this.name = name;
 }

 void sayHello(string name)
 {
 writeln(name);
 }
}


UFCS is about calling a free-standing function like a member function. 
The following example makes more sense to me:


void main()
{
string name = Suliman;
userName username = new userName(name);

username.sayHello();// UFCS
}

// Does not have a sayHello() member function
class userName
{
string name;

this(string name)
{
this.name = name;
}
}

void sayHello(userName u)
{
import std.stdio;
writeln(u.name);
}

Ali



Re: is there any reason UFCS can't be used with 'new'?

2014-11-10 Thread Suliman via Digitalmars-d-learn

Thanks!

Ali Çehreli, could you add this mention and possible the example 
to your book?


Re: is there any reason UFCS can't be used with 'new'?

2014-11-10 Thread Ali Çehreli via Digitalmars-d-learn

On 11/10/2014 12:04 PM, Suliman wrote:

Thanks!

Ali Çehreli, could you add this mention and possible the example to your
book?


Of course. Perhaps I should rephrase some of the descriptions here?

  http://ddili.org/ders/d.en/ufcs.html

Please email me at acehr...@yahoo.com if you have specific suggestions.

Thank you,
Ali



Re: is there any reason UFCS can't be used with 'new'?

2014-09-30 Thread Nordlöw

On Sunday, 28 September 2014 at 20:28:11 UTC, Jay wrote:

fwiw here's what i wrote:

template New(T) if (is(T == class)) {
T New(Args...) (Args args) {
return new T(args);
}
}


My try

template New(T) if (is(T == class))
{
T New(Args...) (Args args) {
return new T(args);
}
}

unittest
{
class C { int x, y; }
auto x = New!C;
}

fails as

typecons_ex.d(60,16): Error: outer function context of 
typecons_ex.__unittestL64_4 is needed to 'new' nested class 
typecons_ex.__unittestL64_4.C
typecons_ex.d(67,14): Error: template instance 
typecons_ex.New!(C).New!() error instantiating


Re: is there any reason UFCS can't be used with 'new'?

2014-09-30 Thread Ali Çehreli via Digitalmars-d-learn

On 09/30/2014 10:35 AM, Nordlöw wrote:

 On Sunday, 28 September 2014 at 20:28:11 UTC, Jay wrote:
 fwiw here's what i wrote:

 template New(T) if (is(T == class)) {
 T New(Args...) (Args args) {
 return new T(args);
 }
 }

 My try

 template New(T) if (is(T == class))
 {
  T New(Args...) (Args args) {
  return new T(args);
  }
 }

 unittest
 {
  class C { int x, y; }
  auto x = New!C;
 }

 fails as

 typecons_ex.d(60,16): Error: outer function context of
 typecons_ex.__unittestL64_4 is needed to 'new' nested class
 typecons_ex.__unittestL64_4.C
 typecons_ex.d(67,14): Error: template instance
 typecons_ex.New!(C).New!() error instantiating

Apparently, a class definition even inside a unittest blocks are 
considered to be nested classes.


Normally, objects of nested classes are created by the 'this.new' 
syntax, 'this' meaning the object that wraps the nested class.


class Outer
{
class Inner
{}

Inner makeInner()
{
return this.new Inner();
}
}

void main()
{
Outer o = new Outer;
Outer.Inner i = o.makeInner();
}

i contains a context pointer to its creators so that it can access the 
outer object's members.


To make a nested class unnested, declare it as static, which seems to 
work in your case as well:


class C { int x, y; }
auto x = New!C();

Ali



Re: is there any reason UFCS can't be used with 'new'?

2014-09-30 Thread Ali Çehreli via Digitalmars-d-learn

On 09/30/2014 11:07 AM, Ali Çehreli wrote:

 To make a nested class unnested, declare it as static, which seems to
 work in your case as well:

  class C { int x, y; }
  auto x = New!C();

Copy+paste cannot read my mind. :( Of course there should be 'static' 
keyword there. :p


static class C { int x, y; }

Ali

P.S. Shame! There is no mention of nested classes in my book. I put it 
in my short to-do list.




Re: is there any reason UFCS can't be used with 'new'?

2014-09-30 Thread Steven Schveighoffer via Digitalmars-d-learn

On 9/30/14 2:07 PM, Ali Çehreli wrote:



Apparently, a class definition even inside a unittest blocks are
considered to be nested classes.

Normally, objects of nested classes are created by the 'this.new'
syntax, 'this' meaning the object that wraps the nested class.


I think unit test blocks are actually functions disguised as attributes.

So it makes sense.

void foo()
{
   class C {}
   auto c = New!C; // same error
}

-Steve


Re: is there any reason UFCS can't be used with 'new'?

2014-09-29 Thread Jay via Digitalmars-d-learn

On Sunday, 28 September 2014 at 22:17:03 UTC, Meta wrote:
I'm not sure. Maybe it's on the same level as the Lambda 
Abstraction (14.5), but you'll probably have to do some testing 
to figure it out exactly.


precedence levels seem to be defined in `src/parse.h` (the `PREC` 
enum) and assigned to operators in `src/parse.c` 
(`initPrecedence()`).


Re: is there any reason UFCS can't be used with 'new'?

2014-09-28 Thread Foo via Digitalmars-d-learn

On Sunday, 28 September 2014 at 19:11:23 UTC, Jay wrote:
i want to chain 'new' with method calls on the created object. 
i found this on the internet:


window.mainWidget = (new Button()).text(Hello 
worldd).textColor(0xFF);


it would look much nicer with UFCS:

window.mainWidget = Button.new().text(Hello 
worldd).textColor(0xFF);


well, it's not *exactly* UFCS but you get what i mean.


mixin template New(T) if (is(T == class)) {
static T New(Args...)(Args args) {
return new T(args);
}
}

class Bar {
string txt;

this() {
txt = Foo;
}

this(string t) {
txt = t;
}

mixin New!Bar;
}

void main() {
import std.stdio;

writeln(Bar.New().txt);
writeln(Bar.New(Bar).txt);
}


Re: is there any reason UFCS can't be used with 'new'?

2014-09-28 Thread Jay via Digitalmars-d-learn
thanks! but i'm still interested *why* you can't have this with 
'new'. if there's no good reason i will file a bug report.


On Sunday, 28 September 2014 at 19:19:56 UTC, Foo wrote:

mixin template New(T) if (is(T == class)) {
static T New(Args...)(Args args) {
return new T(args);
}
}

class Bar {
string txt;

this() {
txt = Foo;
}

this(string t) {
txt = t;
}

mixin New!Bar;
}

void main() {
import std.stdio;

writeln(Bar.New().txt);
writeln(Bar.New(Bar).txt);
}




Re: is there any reason UFCS can't be used with 'new'?

2014-09-28 Thread Idan Arye via Digitalmars-d-learn

On Sunday, 28 September 2014 at 19:32:11 UTC, Jay wrote:
thanks! but i'm still interested *why* you can't have this with 
'new'. if there's no good reason i will file a bug report.


Because `new` is not a function - it's an operator.


Re: is there any reason UFCS can't be used with 'new'?

2014-09-28 Thread Jay via Digitalmars-d-learn

On Sunday, 28 September 2014 at 19:41:29 UTC, Idan Arye wrote:

Because `new` is not a function - it's an operator.


do you think the function call syntax has any chance to be 
implemented? is it just me who needs it?


Re: is there any reason UFCS can't be used with 'new'?

2014-09-28 Thread Jay via Digitalmars-d-learn

On Sunday, 28 September 2014 at 19:19:56 UTC, Foo wrote:

mixin template New(T) if (is(T == class)) {
static T New(Args...)(Args args) {
return new T(args);
}
}


fwiw here's what i wrote:

template New(T) if (is(T == class)) {
T New(Args...) (Args args) {
return new T(args);
}
}

...

New!Bar(hi).txt.writeln;

not as neat as your version but still improves on the ugly (new 
Class()).method syntax and doesn't need to be mixed into the 
class definition.


Re: is there any reason UFCS can't be used with 'new'?

2014-09-28 Thread Meta via Digitalmars-d-learn

On Sunday, 28 September 2014 at 19:11:23 UTC, Jay wrote:
i want to chain 'new' with method calls on the created object. 
i found this on the internet:


window.mainWidget = (new Button()).text(Hello 
worldd).textColor(0xFF);


it would look much nicer with UFCS:

window.mainWidget = Button.new().text(Hello 
worldd).textColor(0xFF);


well, it's not *exactly* UFCS but you get what i mean.


The following code works perfectly fine. The precedence of the 
`new` operator was changed in a release a year or two ago.


class Button
{
typeof(this) text(string t)
{
return this;
}

typeof(this) textColour(int c)
{
return this;
}
}

void main()
{
auto b = new Button()
.text(Hello, world!)
.textColour(0xFF00);
}


Re: is there any reason UFCS can't be used with 'new'?

2014-09-28 Thread Jay via Digitalmars-d-learn

On Sunday, 28 September 2014 at 20:30:42 UTC, Meta wrote:

class Button
{
typeof(this) text(string t)
{
return this;
}

typeof(this) textColour(int c)
{
return this;
}
}

void main()
{
auto b = new Button()
.text(Hello, world!)
.textColour(0xFF00);
}


thanks! where should i put it in this table: 
http://wiki.dlang.org/Operator_precedence ?


Re: is there any reason UFCS can't be used with 'new'?

2014-09-28 Thread Meta via Digitalmars-d-learn

On Sunday, 28 September 2014 at 20:50:07 UTC, Jay wrote:

On Sunday, 28 September 2014 at 20:30:42 UTC, Meta wrote:

class Button
{
typeof(this) text(string t)
{
return this;
}

typeof(this) textColour(int c)
{
return this;
}
}

void main()
{
auto b = new Button()
   .text(Hello, world!)
   .textColour(0xFF00);
}


thanks! where should i put it in this table: 
http://wiki.dlang.org/Operator_precedence ?


I'm not sure. Maybe it's on the same level as the Lambda 
Abstraction (14.5), but you'll probably have to do some testing 
to figure it out exactly.