digitalmars.dip.ideas - Explicit pack expansion and the Expansion Operator
- Quirin Schroll (30/30) Aug 07 In D, unlike C++, compile-time sequences (a.k.a. packs, tuples,
- user1234 (5/27) Aug 07 About the syntax I think that using the system of type properties
In D, unlike C++, compile-time sequences (a.k.a. packs, tuples, alias sequences, and many more) auto-expand. This is usually desirable, but sometimes, it requires programmers to write auxiliary constructs to get C++-like pattern expansion. For example, if `pack` is a parameter pack, in D, `f(pack)` calls `f` with the pack’s components as parameters. In C++, `f(pack)` is, generally speaking, invalid, but requires either `f(pack...)` to expand the pack as parameters for `f` or `f(pack)...` to create as many invocations of `f` as there are pack members, each invocation with 1 argument each. And if `fs` is a pack as well, `fs(pack)...` creates lockstepped invocations: `fs[0](pack[0])` … `fs[$-1](pack[$-1])`, and the packs involved must be of equal length. Essentially, the `...` postfix operator expands packs in lockstep (and repeats non-packs) into a compile-time sequence. While C++ requires packs to be expanded (except for some constructs that handle packs specifically, such as `sizeof...`), D never did that. The semantics with `...` are simply that if a declaration or statement is complete and unexpanded packs remain, those are expanded at the innermost possible place. Also add the Expansion Operator `opExpand`. When a sub-expression `e` (possibly a type) is part of a pattern that is to be expanded and it defines `opExpand`, the sub-expression is considered a pack and its expansion is considered to be `e.opExpand`. In the expansion, it is not necessarily indexed, i.e. `opExpand` may be a sequence, in which case it is indexed, but it may also be a value, in which case it is repeated. In both cases, though, `opExpand` keeps expansion from considering sub-expressions. If `opExpand` is a template, it is passed the length of the expansion as a `size_t` value argument.
Aug 07
On Wednesday, 7 August 2024 at 09:57:22 UTC, Quirin Schroll wrote:In D, unlike C++, compile-time sequences (a.k.a. packs, tuples, alias sequences, and many more) auto-expand. This is usually desirable, but sometimes, it requires programmers to write auxiliary constructs to get C++-like pattern expansion. For example, if `pack` is a parameter pack, in D, `f(pack)` calls `f` with the pack’s components as parameters. In C++, `f(pack)` is, generally speaking, invalid, but requires either `f(pack...)` to expand the pack as parameters for `f` or `f(pack)...` to create as many invocations of `f` as there are pack members, each invocation with 1 argument each. And if `fs` is a pack as well, `fs(pack)...` creates lockstepped invocations: `fs[0](pack[0])` … `fs[$-1](pack[$-1])`, and the packs involved must be of equal length. Essentially, the `...` postfix operator expands packs in lockstep (and repeats non-packs) into a compile-time sequence. While C++ requires packs to be expanded (except for some constructs that handle packs specifically, such as `sizeof...`), D never did that. The semantics with `...` are simply that if a declaration or statement is complete and unexpanded packs remain, those are expanded at the innermost possible place. [...]About the syntax I think that using the system of type properties (to be perfectly clear I speak about things like `.stringof`) would be more judicious than a new operator. Properties dont require parser modifications. So `.expand`.
Aug 07