Skip to content

Commit 0248956

Browse files
committed
Add syntax sugar map + RefTuple combination.
`map` on top of ndslice composed of `RefTuples` recognises it and passes list of args instead of single tuple. Old: ``` auto c = cartesian(a, b) .map!"a.a + a.b"; ``` New: ``` auto c = cartesian(a, b) .map!"a + b"; ```
1 parent 7ecfdd6 commit 0248956

File tree

4 files changed

+29
-7
lines changed

4 files changed

+29
-7
lines changed

source/mir/functional.d

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -115,7 +115,7 @@ RefTuple!Args tuple(Args...)(auto ref Args args)
115115
}
116116

117117
/// Removes $(LREF Ref) shell.
118-
T unref(V : Ref!T, T)(V value)
118+
ref T unref(V : Ref!T, T)(V value)
119119
{
120120
return *value.__ptr;
121121
}

source/mir/ndslice/field.d

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -53,9 +53,17 @@ struct MapField(Field, alias fun)
5353
+/
5454
static alias __map(alias fun1) = MapField__map!(Field, fun, fun1);
5555

56-
auto ref opIndex(T...)(T index)
56+
auto ref opIndex(T...)(auto ref T index)
5757
{
58-
return fun(_field[index]);
58+
import mir.functional: RefTuple, unref;
59+
static if (is(typeof(_field[index]) : RefTuple!K, K...))
60+
{
61+
import mir.ndslice.field: _iotaArgs;
62+
auto t = _field[index];
63+
return mixin("fun(" ~ _iotaArgs!(K.length, "t.expand[", "].unref, ") ~ ")");
64+
}
65+
else
66+
return fun(_field[index]);
5967
}
6068

6169
auto length()() @property

source/mir/ndslice/iterator.d

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -508,8 +508,15 @@ struct MapIterator(Iterator, alias fun)
508508

509509
auto ref opUnary(string op : "*")()
510510
{
511+
import mir.functional: RefTuple, unref;
511512
static if (is(Iterator : ZipIterator!(Iterators), Iterators...))
512513
return mixin("fun(" ~ _iotaArgs!(Iterators.length, "*_iterator._iterators[", "], ") ~ ")");
514+
else
515+
static if (is(typeof(*_iterator) : RefTuple!T, T...))
516+
{
517+
auto t = *_iterator;
518+
return mixin("fun(" ~ _iotaArgs!(T.length, "t.expand[", "].unref, ") ~ ")");
519+
}
513520
else
514521
return fun(*_iterator);
515522
}
@@ -520,8 +527,15 @@ struct MapIterator(Iterator, alias fun)
520527

521528
auto ref opIndex()(ptrdiff_t index)
522529
{
530+
import mir.functional: RefTuple, unref;
523531
static if (is(Iterator : ZipIterator!(Iterators), Iterators...))
524532
return mixin("fun(" ~ _iotaArgs!(Iterators.length, "_iterator._iterators[", "][index], ") ~ ")");
533+
else
534+
static if (is(typeof(_iterator[0]) : RefTuple!T, T...))
535+
{
536+
auto t = _iterator[index];
537+
return mixin("fun(" ~ _iotaArgs!(T.length, "t.expand[", "].unref, ") ~ ")");
538+
}
525539
else
526540
return fun(_iterator[index]);
527541
}

source/mir/ndslice/topology.d

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1749,7 +1749,7 @@ unittest
17491749
[tuple(2.00, 0.00), tuple(2.00, 0.5), tuple(2.00, 1.0)],
17501750
]);
17511751

1752-
assert(s.map!"a.a * a.b" == [
1752+
assert(s.map!"a * b" == [
17531753
[0.0, 0.500, 1.00],
17541754
[0.0, 0.625, 1.25],
17551755
[0.0, 0.750, 1.50],
@@ -2564,7 +2564,7 @@ unittest
25642564
auto b = [ 1, 2, 3];
25652565

25662566
auto c = cartesian(a, b)
2567-
.map!"a.a + a.b";
2567+
.map!"a + b";
25682568

25692569
assert(c == [
25702570
[11, 12, 13],
@@ -2579,7 +2579,7 @@ unittest
25792579
auto b = iota([2, 3], 1);
25802580

25812581
auto c = cartesian(a, b)
2582-
.map!"a.a + a.b";
2582+
.map!"a + b";
25832583

25842584
assert(c.shape == [3, 2, 3]);
25852585

@@ -2606,7 +2606,7 @@ unittest
26062606
auto w = [1, 2];
26072607

26082608
auto c = cartesian(u, v, w)
2609-
.map!"a.a + a.b + a.c";
2609+
.map!"a + b + c";
26102610

26112611
assert(c.shape == [2, 3, 2]);
26122612

0 commit comments

Comments
 (0)