www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.learn - Mixin on a bunch of foreach fails.

reply "Charles McAnany (dlang)" <dlang charlesmcanany.com> writes:
Content-Type: text/plain; charset=ISO-8859-1; format=flowed
Content-Transfer-Encoding: 7bit

Hi, all. So I'm trying to make some very ugly code generic. The main 
ugliness isn't in the code shape, it's in the running time. It's O(n^m) 
Eww! (don't worry, n is only about 6.)

Anyhoo, Here's what I want:

    void foo(int size)(int[] arr){
         mixin(forStart!(size));
             doStuff(pos0, pos1, pos2,...); // this line is generated by
    another mixin that works correctly.
    }

    //Generates for loop headers.
    private static string forStart( int sz)(){
         string forStrings = "";
         for(int i = 0; i < sz; i++){
             forStrings ~="foreach(pos"~text(i)~"; 0..arr.length)\n ";
         }
         return forStrings;
    }

It is my great displeasure to report:
src\hw06.d(35): found 'EOF' instead of statement
src\hw06.d(18): Error: template instance hw06.tryCombinations!(5) error 
instantiating

But here's the wacky part:
I can execute this function and print it to stdout. If I do, I get...
foreach(pos0; 0..arr.length)
foreach(pos1; 0..arr.length)
foreach(pos2; 0..arr.length)
foreach(pos3; 0..arr.length)
foreach(pos4; 0..arr.length)

and I can copy-paste this exact code into where I currently have the 
mixin, and the code behaves correctly.

Is there some subtle aspect of mixin that I'm missing here?

Cheers,
Charles.
Jan 12 2012
parent Timon Gehr <timon.gehr gmx.ch> writes:
On 01/13/2012 05:07 AM, Charles McAnany (dlang) wrote:
 Hi, all. So I'm trying to make some very ugly code generic. The main
 ugliness isn't in the code shape, it's in the running time. It's O(n^m)
 Eww! (don't worry, n is only about 6.)

 Anyhoo, Here's what I want:

     void foo(int size)(int[] arr){
     mixin(forStart!(size));
     doStuff(pos0, pos1, pos2,...); // this line is generated by another
     mixin that works correctly.
     }

     //Generates for loop headers.
     private static string forStart( int sz)(){
     string forStrings = "";
     for(int i = 0; i < sz; i++){
     forStrings ~="foreach(pos"~text(i)~"; 0..arr.length)\n ";
     }
     return forStrings;
     }

 It is my great displeasure to report:
 src\hw06.d(35): found 'EOF' instead of statement
 src\hw06.d(18): Error: template instance hw06.tryCombinations!(5) error
 instantiating

 But here's the wacky part:
 I can execute this function and print it to stdout. If I do, I get...
 foreach(pos0; 0..arr.length)
 foreach(pos1; 0..arr.length)
 foreach(pos2; 0..arr.length)
 foreach(pos3; 0..arr.length)
 foreach(pos4; 0..arr.length)

 and I can copy-paste this exact code into where I currently have the
 mixin, and the code behaves correctly.

 Is there some subtle aspect of mixin that I'm missing here?

 Cheers,
 Charles.

Yes. You can only mixin whole statements or expressions. The easiest way to fix your code is to join the two mixins into one using the concatenation operator. Eg: mixin(forStart!(size)~generateDoStuff(...)); By the way, you can make the code more clean by making 'int sz' a simple function parameter. (static string forStart(int sz){...})
Jan 12 2012