Thread overview | ||||||||||||||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|
May 02, 2016 inferred size for static array initialization | ||||
---|---|---|---|---|
| ||||
Is there a way to initialize a static array and have it's size inferred (and that works for arrays of structs using braced literals)? This would make it easier to maintain longer static array definitions. The code below doesn't work when removing the array size even though the array is declared as static immutable. import std.traits; static immutable int[] a = [1,2,3]; static assert(isStaticArray!(typeof(a))); // fails |
May 02, 2016 Re: inferred size for static array initialization | ||||
---|---|---|---|---|
| ||||
Posted in reply to Erik Smith | On Monday, 2 May 2016 at 13:00:27 UTC, Erik Smith wrote: > Is there a way to initialize a static array and have it's size inferred (and that works for arrays of structs using braced literals)? This would make it easier to maintain longer static array definitions. The code below doesn't work when removing the array size even though the array is declared as static immutable. > > import std.traits; > static immutable int[] a = [1,2,3]; > static assert(isStaticArray!(typeof(a))); // fails Help yourself with a template: ---- import std.traits; auto toStaticArray(alias array)() if (isArray!(typeof(array))) { enum size = array.length; alias T = typeof(array.init[0])[size]; T result = array[0..size]; return result; } enum a = toStaticArray!([1,2,3]); static assert(isStaticArray!(typeof(a))); // success ---- Does it fit ? |
May 02, 2016 Re: inferred size for static array initialization | ||||
---|---|---|---|---|
| ||||
Posted in reply to Basile B | On Monday, 2 May 2016 at 13:22:01 UTC, Basile B wrote: > On Monday, 2 May 2016 at 13:00:27 UTC, Erik Smith wrote: >> Is there a way to initialize a static array and have it's size inferred (and that works for arrays of structs using braced literals)? This would make it easier to maintain longer static array definitions. The code below doesn't work when removing the array size even though the array is declared as static immutable. >> >> import std.traits; >> static immutable int[] a = [1,2,3]; >> static assert(isStaticArray!(typeof(a))); // fails > > Help yourself with a template: > > ---- > import std.traits; > > auto toStaticArray(alias array)() > if (isArray!(typeof(array))) > { > enum size = array.length; > alias T = typeof(array.init[0])[size]; > T result = array[0..size]; > return result; > } > > enum a = toStaticArray!([1,2,3]); > static assert(isStaticArray!(typeof(a))); // success > ---- > > Does it fit ? Using an enum is probably a bit better ---- auto toStaticArray(alias array)() if (isDynamicArray!(typeof(array)) && array.length) { alias T = typeof(array[0])[array.length]; enum T result = array[0..array.length]; return result; } |
May 02, 2016 Re: inferred size for static array initialization | ||||
---|---|---|---|---|
| ||||
Posted in reply to Erik Smith | Am Mon, 02 May 2016 13:00:27 +0000 schrieb Erik Smith <erik@cruiserhouse.com>: > Is there a way to initialize a static array and have it's size inferred (and that works for arrays of structs using braced literals)? This would make it easier to maintain longer static array definitions. The code below doesn't work when removing the array size even though the array is declared as static immutable. > > import std.traits; > static immutable int[] a = [1,2,3]; > static assert(isStaticArray!(typeof(a))); // fails > Sure, struct S { int a, b; } immutable tab = { static enum S[] s = [ {1,2}, {3,4}, ]; return cast(typeof(s[0])[s.length])s; }(); static assert(isStaticArray!(typeof(tab))); // succeeds -- Marco |
May 02, 2016 Re: inferred size for static array initialization | ||||
---|---|---|---|---|
| ||||
Posted in reply to Marco Leise | On 02.05.2016 15:53, Marco Leise wrote:
> immutable tab = { static enum S[] s = [
`static enum`? What kind of black magic is this?
|
May 02, 2016 Re: inferred size for static array initialization | ||||
---|---|---|---|---|
| ||||
Posted in reply to ag0aep6g | Am Mon, 2 May 2016 18:52:11 +0200 schrieb ag0aep6g <anonymous@example.com>: > On 02.05.2016 15:53, Marco Leise wrote: > > immutable tab = { static enum S[] s = [ > > `static enum`? What kind of black magic is this? I don't know, but it works, haha. -- Marco |
May 02, 2016 Re: inferred size for static array initialization | ||||
---|---|---|---|---|
| ||||
Posted in reply to Marco Leise | I tried to combine the two solutions (Basile with the wrapper, Marco with the struct initializer support) but it didn't work. The struct initializer is not a array literal (seems obvious now). I might go with the 2nd but it's pretty heavy just to get the size. Thanks. struct S { int a, b; } auto toStaticArray(alias array)() { struct S { int a, b; } immutable tab = { static enum S[] s = array; return cast(typeof(s[0])[s.length])s; }(); return tab; } enum a = toStaticArray!([{1,2},{3,4}]); // error |
May 02, 2016 Re: inferred size for static array initialization | ||||
---|---|---|---|---|
| ||||
Posted in reply to Erik Smith | On Monday, 2 May 2016 at 13:00:27 UTC, Erik Smith wrote: > Is there a way to initialize a static array and have it's size inferred (and that works for arrays of structs using braced literals)? This would make it easier to maintain longer static array definitions. The code below doesn't work when removing the array size even though the array is declared as static immutable. > > import std.traits; > static immutable int[] a = [1,2,3]; > static assert(isStaticArray!(typeof(a))); // fails I still like ---- auto s(T, size_t n)(T[n] arr) { return arr; } auto arr = [1, 2, 3].s; ---- But of course this won't work: ---- int[] a = [1,2,3].s; static assert(isStaticArray!(typeof(a))); // fails ---- Since 'a' is just a slice. But this will work: ---- immutable auto a = [1,2,3].s; ---- |
May 02, 2016 Re: inferred size for static array initialization | ||||
---|---|---|---|---|
| ||||
Posted in reply to Namespace | On 5/2/16 1:43 PM, Namespace wrote: > On Monday, 2 May 2016 at 13:00:27 UTC, Erik Smith wrote: >> Is there a way to initialize a static array and have it's size >> inferred (and that works for arrays of structs using braced >> literals)? This would make it easier to maintain longer static array >> definitions. The code below doesn't work when removing the array size >> even though the array is declared as static immutable. >> >> import std.traits; >> static immutable int[] a = [1,2,3]; >> static assert(isStaticArray!(typeof(a))); // fails > > I still like > ---- > auto s(T, size_t n)(T[n] arr) { > return arr; > } Interesting. But there is a major problem here... > > auto arr = [1, 2, 3].s; > ---- > > But of course this won't work: > ---- > int[] a = [1,2,3].s; > static assert(isStaticArray!(typeof(a))); // fails > ---- And this is the problem. > Since 'a' is just a slice. A slice of a no-longer-existing temporary! Admittedly, this is not an issue with your code, but a deeper issue of allowing slicing of rvalues. > > But this will work: > ---- > immutable auto a = [1,2,3].s; > ---- You can drop auto. It's just a placeholder for the storage class in the case where a storage class isn't specified. -Steve |
May 02, 2016 Re: inferred size for static array initialization | ||||
---|---|---|---|---|
| ||||
Posted in reply to Steven Schveighoffer | > A slice of a no-longer-existing temporary! Admittedly, this is not an issue with your code, but a deeper issue of allowing slicing of rvalues. This works: ---- int[] as = [1, 2, 3].s; writeln(as[2]); ---- Bug or feature? Or did I may misunderstood you? > You can drop auto. It's just a placeholder for the storage class in the case where a storage class isn't specified. Right, I forgot, it's a bit since I wrote something in D. |
Copyright © 1999-2021 by the D Language Foundation