On Sunday, 11 December 2016 at 23:07:16 UTC, Era Scarecrow wrote:
On Sunday, 11 December 2016 at 18:05:19 UTC, Era Scarecrow wrote:
On Sunday, 11 December 2016 at 16:34:38 UTC, Orut wrote:
I need to be able to vary the number of ranges to feed into cartesianProduct() at run time.

Hmmm... what kind of ranges? Are they going to be arrays? Or something else?


Well, with the assumption of using arrays (since you kinda need a length for it to work) I've thrown together a quick struct that does the job. Not fully tested, but will do the same thing with a varying number of inputs.

[code]
struct MultiCart(T) {
    T[][] data;
    int iteration;
    int max;

    this(T[][] _d, int iter=0) {
        data = _d;
        iteration = iter;

        max = 1;
        foreach(a; _d) {
            if (a.length)
                max *= a.length;
        }
    }

    T[] front() {
        int i = iteration;
        T[] val;

        foreach(d; data) {
            if (d.length) {
                val ~= d[i % d.length];
                i /= d.length;
            }
        }

        return val;
    }

    void popFront() {
        iteration++;
    }

    bool empty() {
        return iteration >= max;
    }
}

unittest {
    import std.stdio;
    alias CartInt = MultiCart!int;

    int[] a=[1,2,3],b=[4,5],c=[6,7];
    foreach(x; CartInt([a,b,c]))
        writeln(x);

    foreach(x; CartInt([a,b]))
        writeln(x);
}
[/code]

The code works beautifully! Thank you very much. Will certainly acknowledge you as source of this code if this becomes of part of a bigger project. I hope others searching this forum would also discover this code.

Reply via email to