## digitalmars.D.learn - Getting the size of a type tuple

• David Zhang (16/16) Sep 21 Given the function F, where: F(Args...)(Args args) { ... }
• ag0aep6g (30/48) Sep 21 I don't have a one-liner, but here are some other solutions that might
• David Zhang (3/10) Sep 21 I think the recursive one looks best, but I agree. None of them
• H. S. Teoh (12/20) Sep 21 I'd just do:
David Zhang <straivers98 gmail.com> writes:
```Given the function F, where: F(Args...)(Args args) { ... }

How can I statically determine the size of the argument list in
bytes?

Preferably, I would like a one-liner. However, std.algorithm
doesn't seem to support tuples, or `Args.each!(T =>
T.sizeof).sum` would work.

For the moment, I've settled on using a helper function:

size_t size(Args...)()
{
size_t size;
foreach(Arg; Args)
size += Arg.sizeof;
return size;
}

But it's a bit clunky. Is there a more idiomatic way to do this?

Thanks
```
Sep 21
ag0aep6g <anonymous example.com> writes:
```On 09/21/2017 08:44 PM, David Zhang wrote:
Given the function F, where: F(Args...)(Args args) { ... }

How can I statically determine the size of the argument list in bytes?

Preferably, I would like a one-liner. However, std.algorithm doesn't
seem to support tuples, or `Args.each!(T => T.sizeof).sum` would work.

For the moment, I've settled on using a helper function:

size_t size(Args...)()
{
size_t size;
foreach(Arg; Args)
size += Arg.sizeof;
return size;
}

But it's a bit clunky. Is there a more idiomatic way to do this?

I don't have a one-liner, but here are some other solutions that might
be interesting. None of them is particularly pretty, though.

1) Recursive template:
----
template size_recur(Types ...)
{
static if (Types.length == 0) enum size_recur = 0;
else enum size_recur = Types[0].sizeof + size_recur!(Types[1 .. \$]);
}
----

2) Using the std library:
----
template size_std(Types ...)
{
import std.algorithm: sum;
import std.range: only;
import std.meta: staticMap;
enum sizeOf(T) = T.sizeof;
enum size_std = staticMap!(sizeOf, Types).only.sum;
}
----

3) Declaring a packed struct in a function literal that gets immediately
called:
----
enum size_so_very_clever(Types ...) = () {
struct S { align(1) Types fields; }
return S.sizeof;
} ();
----
```
Sep 21
David Zhang <straivers98 gmail.com> writes:
```On Thursday, 21 September 2017 at 19:49:14 UTC, ag0aep6g wrote:
I don't have a one-liner, but here are some other solutions
that might be interesting. None of them is particularly pretty,
though.

1) Recursive template: <snip>

2) Using the std library: <snip>

3) Declaring a packed struct in a function literal that gets
immediately called: <snip>

I think the recursive one looks best, but I agree. None of them
look particularly good.
```
Sep 21
"H. S. Teoh" <hsteoh quickfur.ath.cx> writes:
```On Thu, Sep 21, 2017 at 09:49:14PM +0200, ag0aep6g via Digitalmars-d-learn
wrote:
[...]
3) Declaring a packed struct in a function literal that gets
immediately called:
----
enum size_so_very_clever(Types ...) = () {
struct S { align(1) Types fields; }
return S.sizeof;
} ();
----

I'd just do:

template sizeofStruct(Types...) {
struct S { align(1) Types fields; }
enum sizeofStruct = S.sizeof;
}

Skip the CTFE implied by the function literal, the compiler already
knows the size very well.

T

--
What are you when you run out of Monet? Baroque.
```
Sep 21
ag0aep6g <anonymous example.com> writes:
```On 09/21/2017 09:59 PM, H. S. Teoh wrote:
On Thu, Sep 21, 2017 at 09:49:14PM +0200, ag0aep6g via Digitalmars-d-learn
wrote:
[...]
3) Declaring a packed struct in a function literal that gets
immediately called:
----
enum size_so_very_clever(Types ...) = () {
struct S { align(1) Types fields; }
return S.sizeof;
} ();
----

I'd just do:

template sizeofStruct(Types...) {
struct S { align(1) Types fields; }
enum sizeofStruct = S.sizeof;
}

Skip the CTFE implied by the function literal, the compiler already
knows the size very well.

Yup. That's better.
```
Sep 21