diff --git a/doc/langref.html.in b/doc/langref.html.in index 3c45d52b1b..2916033a5f 100644 --- a/doc/langref.html.in +++ b/doc/langref.html.in @@ -781,6 +781,30 @@ implementation feature, not a language semantic, so it is not guaranteed to be observable to code.
{#header_close#} + + {#header_open|Destructuring#} ++ A destructuring assignment can separate elements of indexable aggregate types + ({#link|Tuples#}, {#link|Arrays#}, {#link|Vectors#}): +
+ {#code|destructuring_to_existing.zig#} + ++ A destructuring expression may only appear within a block (i.e. not at container scope). + The left hand side of the assignment must consist of a comma separated list, + each element of which may be either an lvalue (for instance, an existing `var`) or a variable declaration: +
+ {#code|destructuring_mixed.zig#} + ++ A destructure may be prefixed with the {#syntax#}comptime{#endsyntax#} keyword, in which case the entire + destructure expression is evaluated at {#link|comptime#}. All {#syntax#}var{#endsyntax#}s declared would + be {#syntax#}comptime var{#endsyntax#}s and all expressions (both result locations and the assignee + expression) are evaluated at {#link|comptime#}. +
+ + {#see_also|Destructuring Tuples|Destructuring Arrays|Destructuring Vectors#} + {#header_close#} {#header_close#} {#header_close#} {#header_open|Zig Test#} @@ -1882,6 +1906,15 @@ or {#see_also|Sentinel-Terminated Pointers|Sentinel-Terminated Slices#} {#header_close#} + + {#header_open|Destructuring Arrays#} ++ Arrays can be destructured: +
+ {#code|destructuring_arrays.zig#} + + {#see_also|Destructuring|Destructuring Tuples|Destructuring Vectors#} + {#header_close#} {#header_close#} {#header_open|Vectors#} @@ -1929,6 +1962,14 @@ or {#see_also|@splat|@shuffle|@select|@reduce#} + {#header_open|Destructuring Vectors#} ++ Vectors can be destructured: +
+ {#code|destructuring_vectors.zig#} + {#see_also|Destructuring|Destructuring Tuples|Destructuring Arrays#} + {#header_close#} + {#header_close#} {#header_open|Pointers#} @@ -2309,6 +2350,23 @@ or {#code|test_tuples.zig#} + {#header_open|Destructuring Tuples#} ++ Tuples can be {#link|destructured|Destructuring#}. +
++ Tuple destructuring is helpful for returning multiple values from a block: +
+ {#code|destructuring_block.zig#} + ++ Tuple destructuring is helpful for dealing with functions and built-ins that return multiple values + as a tuple: +
+ {#code|destructuring_return_value.zig#} + + {#see_also|Destructuring|Destructuring Arrays|Destructuring Vectors#} + {#header_close#} {#header_close#} {#see_also|comptime|@fieldParentPtr#} {#header_close#} diff --git a/doc/langref/destructuring_arrays.zig b/doc/langref/destructuring_arrays.zig new file mode 100644 index 0000000000..e58f7b7331 --- /dev/null +++ b/doc/langref/destructuring_arrays.zig @@ -0,0 +1,18 @@ +const print = @import("std").debug.print; + +fn swizzleRgbaToBgra(rgba: [4]u8) [4]u8 { + // readable swizzling by destructuring + const r, const g, const b, const a = rgba; + return .{ b, g, r, a }; +} + +pub fn main() void { + const pos = [_]i32{ 1, 2 }; + const x, const y = pos; + print("x = {}, y = {}\n", .{x, y}); + + const orange: [4]u8 = .{ 255, 165, 0, 255 }; + print("{any}\n", .{swizzleRgbaToBgra(orange)}); +} + +// exe=succeed diff --git a/doc/langref/destructuring_block.zig b/doc/langref/destructuring_block.zig new file mode 100644 index 0000000000..7eec318796 --- /dev/null +++ b/doc/langref/destructuring_block.zig @@ -0,0 +1,22 @@ +const print = @import("std").debug.print; + +pub fn main() void { + const digits = [_]i8 { 3, 8, 9, 0, 7, 4, 1 }; + + const min, const max = blk: { + var min: i8 = 127; + var max: i8 = -128; + + for (digits) |digit| { + if (digit < min) min = digit; + if (digit > max) max = digit; + } + + break :blk .{ min, max }; + }; + + print("min = {}", .{ min }); + print("max = {}", .{ max }); +} + +// exe=succeed diff --git a/doc/langref/destructuring_mixed.zig b/doc/langref/destructuring_mixed.zig new file mode 100644 index 0000000000..d2bef4388b --- /dev/null +++ b/doc/langref/destructuring_mixed.zig @@ -0,0 +1,21 @@ +const print = @import("std").debug.print; + +pub fn main() void { + var x: u32 = undefined; + + const tuple = .{ 1, 2, 3 }; + + x, var y : u32, const z = tuple; + + print("x = {}, y = {}, z = {}\n", .{x, y, z}); + + // y is mutable + y = 100; + + // You can use _ to throw away unwanted values. + _, x, _ = tuple; + + print("x = {}", .{x}); +} + +// exe=succeed diff --git a/doc/langref/destructuring_return_value.zig b/doc/langref/destructuring_return_value.zig new file mode 100644 index 0000000000..597a1299be --- /dev/null +++ b/doc/langref/destructuring_return_value.zig @@ -0,0 +1,14 @@ +const print = @import("std").debug.print; + +fn divmod(numerator: u32, denominator: u32) struct { u32, u32 } { + return .{ numerator / denominator, numerator % denominator }; +} + +pub fn main() void { + const div, const mod = divmod(10, 3); + + print("10 / 3 = {}\n", .{div}); + print("10 % 3 = {}\n", .{mod}); +} + +// exe=succeed diff --git a/doc/langref/destructuring_to_existing.zig b/doc/langref/destructuring_to_existing.zig new file mode 100644 index 0000000000..dade79cd04 --- /dev/null +++ b/doc/langref/destructuring_to_existing.zig @@ -0,0 +1,27 @@ +const print = @import("std").debug.print; + +pub fn main() void { + var x: u32 = undefined; + var y: u32 = undefined; + var z: u32 = undefined; + + const tuple = .{ 1, 2, 3 }; + + x, y, z = tuple; + + print("tuple: x = {}, y = {}, z = {}\n", .{x, y, z}); + + const array = [_]u32{ 4, 5, 6 }; + + x, y, z = array; + + print("array: x = {}, y = {}, z = {}\n", .{x, y, z}); + + const vector: @Vector(3, u32) = .{ 7, 8, 9 }; + + x, y, z = vector; + + print("vector: x = {}, y = {}, z = {}\n", .{x, y, z}); +} + +// exe=succeed diff --git a/doc/langref/destructuring_vectors.zig b/doc/langref/destructuring_vectors.zig new file mode 100644 index 0000000000..2415827054 --- /dev/null +++ b/doc/langref/destructuring_vectors.zig @@ -0,0 +1,16 @@ +const print = @import("std").debug.print; + +// emulate punpckldq +pub fn unpack(x: @Vector(4, f32), y: @Vector(4, f32)) @Vector(4, f32) { + const a, const c, _, _ = x; + const b, const d, _, _ = y; + return .{ a, b, c, d }; +} + +pub fn main() void { + const x: @Vector(4, f32) = .{ 1.0, 2.0, 3.0, 4.0 }; + const y: @Vector(4, f32) = .{ 5.0, 6.0, 7.0, 8.0 }; + print("{}", .{unpack(x, y)}); +} + +// exe=succeed