www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.learn - templated lambda with {} cause GC

reply learnfirst1 <learnfirst1 gmail.com> writes:
import core.stdc.stdio;

struct Test {
	string name ;
}

void T(alias pred, A...)(){
	__gshared t = Test(A) ;
	 pred(t);
}

extern(C) void main(){
	T!(t => printf("test 1 name = %s\n".ptr, t.name.ptr), "test") ;  
// build OK
	T!(t => {
		printf("test 2 name = %s\n".ptr, t.name.ptr);
	}, "test") ; // build error
}

--------------

build this with betterC

Undefined symbols for architecture x86_64:
   "__d_allocmemory", referenced from:
       __D4test4mainUZ__T9__lambda2TSQBb4TestZQvFNaNbNfQtZDFNbNiZv 
in test.o
ld: symbol(s) not found for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to 
see invocation)
Error: linker exited with status 1


to use without {}, it work as expect.

Is there a way to avoid this GC with {}, because we need multi 
line here.
Aug 10 2018
next sibling parent rikki cattermole <rikki cattermole.co.nz> writes:
On 10/08/2018 9:57 PM, learnfirst1 wrote:
 
 import core.stdc.stdio;
 
 struct Test {
      string name ;
 }
 
 void T(alias pred, A...)(){
      __gshared t = Test(A) ;
       pred(t);
 }
 
 extern(C) void main(){
      T!(t => printf("test 1 name = %s\n".ptr, t.name.ptr), "test") ; // 
 build OK
      T!(t => {
          printf("test 2 name = %s\n".ptr, t.name.ptr);
      }, "test") ; // build error
 }
 
 --------------
 
 build this with betterC
 
 Undefined symbols for architecture x86_64:
    "__d_allocmemory", referenced from:
        __D4test4mainUZ__T9__lambda2TSQBb4TestZQvFNaNbNfQtZDFNbNiZv in 
 test.o
 ld: symbol(s) not found for architecture x86_64
 clang: error: linker command failed with exit code 1 (use -v to see 
 invocation)
 Error: linker exited with status 1
 
 
 to use without {}, it work as expect.
 
 Is there a way to avoid this GC with {}, because we need multi line here.
Without the brackets it is inferring to not have state and hence is a function. But with the brackets it is assuming there is state required and hence has to allocate. Without manually allocating said state (not what you want), you cannot do this.
Aug 10 2018
prev sibling next sibling parent Paul Backus <snarwin gmail.com> writes:
On Friday, 10 August 2018 at 09:57:53 UTC, learnfirst1 wrote:
 import core.stdc.stdio;

 struct Test {
 	string name ;
 }

 void T(alias pred, A...)(){
 	__gshared t = Test(A) ;
 	 pred(t);
 }

 extern(C) void main(){
 	T!(t => printf("test 1 name = %s\n".ptr, t.name.ptr), "test") 
 ;  // build OK
 	T!(t => {
 		printf("test 2 name = %s\n".ptr, t.name.ptr);
 	}, "test") ; // build error
 }

 --------------
The arrow syntax doesn't work for multi-line lambdas; you need to write them using what the spec calls "function literal" syntax [1]: T!((t) { // <- Parens around the argument, no arrow printf("test 2 name = %s\n".ptr, t.name.ptr); }, "test") ; [1] https://dlang.org/spec/expression.html#function_literals
Aug 10 2018
prev sibling parent reply Simen =?UTF-8?B?S2rDpnLDpXM=?= <simen.kjaras gmail.com> writes:
On Friday, 10 August 2018 at 09:57:53 UTC, learnfirst1 wrote:
 	T!(t => {
 		printf("test 2 name = %s\n".ptr, t.name.ptr);
 	}, "test") ; // build error
This is not doing what you think it's doing. The syntax t => { return t; } is equivalent to t => () => t. That is, it's returning a function that takes no arguments, not a value. For that very same reason, if you compile and run your code without -betterC, only the first printf() will be executed, and only one line of output will be generated. What you should do instead is: T!((t){ printf("test 2 name = %s\n".ptr, t.name.ptr); }, "test"); (note the lack of the => arrow) -- Simen
Aug 10 2018
parent reply learnfirst1 <learnfirst1 gmail.com> writes:
On Friday, 10 August 2018 at 10:38:53 UTC, Simen Kjærås wrote:
 What you should do instead is:
     T!((t){
             printf("test 2 name = %s\n".ptr, t.name.ptr);
         }, "test");

 (note the lack of the => arrow)

 --
   Simen
rikki cattermole , Paul Backus, Simen Kjærås: thanks for the explain, it work. Still, if my first example is use GC, why dmd not throw error at compile time, instead at link time report symbols is missing. Is this a bug ?
Aug 10 2018
parent Paul Backus <snarwin gmail.com> writes:
On Friday, 10 August 2018 at 11:10:55 UTC, learnfirst1 wrote:
 Still,  if my first example is use GC, why dmd not throw error 
 at compile time, instead at link time report symbols is 
 missing.   Is this a bug ?
If you make your main function nogc, you will get a compile-time error.
Aug 10 2018