The type of a string literal is a const pointer to a sentinel-terminated array of bytes, or *const [N:0]u8
. Since the length is encoded in the type, it’s not feasible to create an array of these pointer types directly unless they are all the same length. The strings in your example are all the same length, so you can create an array using the full type of the strings like so:
const array_of_fully_qualified_string_literals = [_]*const [3:0]u8{
"abc",
"def",
"ghi",
};
However, such pointers-to-arrays will coerce to a slice type, and it’s common to coerce them to []const u8
(or [:0]const u8
if you care about sentinel termination):
const str: []const u8 = "foo";
So, for an array of arbitrary strings, you can make the element type []const u8
:
const array_of_strings = [_][]const u8{ "foo", "something" };
If you take the address of that array, then it, too, will coerce to a slice, so you can also do:
const array_of_strings = [_][]const u8{ "foo", "something" };
const slice_of_strings: []const []const u8 = &array_of_strings;
The shorthand .{}
initialization can make things more convenient still, as long as the destination type is specified:
const slice_of_strings: []const []const u8 = &.{ "foo", "something" };
For completeness, note that @TypeOf(&.{ "foo", "something" })
is actually a tuple:
*const struct { comptime *const [3:0]u8 = "foo", comptime *const [9:0]u8 = "something" }
but it can be coerced to a []const []const u8