| |
![Menjanahary R. R.'s Gravatar profile Gravatar of Menjanahary R. R.](//www.gravatar.com/avatar/5b4c72320f0a7dfcf48c1d85a9ec81e9?d=identicon&s=32) | Posted by Menjanahary R. R. in reply to Gary Chike | Permalink Reply |
|
Menjanahary R. R. ![Menjanahary R. R.'s Gravatar profile Gravatar of Menjanahary R. R.](//www.gravatar.com/avatar/5b4c72320f0a7dfcf48c1d85a9ec81e9?d=identicon&s=80)
Posted in reply to Gary Chike
| On Wednesday, 7 February 2024 at 05:03:09 UTC, Gary Chike wrote:
> ... But overall it's an elegant way to indirectly add names to tuples in D for ergonomic access. Nice find!
Refactored it a bit to have a ready to run and easy to grasp code.
Enjoy!
import std.stdio : writefln;
import std.typecons: tuple;
// Name a Tuple's fields post hoc by copying the original's fields into a new Tuple.
template named(names...) {
auto named(T)(ref auto T t) if (names.length <= T.Types.length) =>
tuple!names(t.expand[0..names.length]);
}
// Define variables corresponding to a Tuple's fields in the current scope,
// whose identifiers are given by `names`.
mixin template Unpack(alias t, names...)
if (names.length <= t.Types.length) {
static foreach (i, n; names)
mixin("auto ", n, " = t[i];");
}
void main()
{
auto getUser() => tuple("John Doe", 32);
//
auto u = getUser().named!("name", "age");
writefln("%s (%d)", u.name, u.age); // John Doe (32)
// You could also do this.
with (getUser().named!("name", "age"))
writefln("%s (%d)", name, age); // John Doe (32)
//
mixin Unpack!(u, "name", "age");
writefln("%s (%d)", name, age); // John Doe (32)
}
|