enigmare/v2-crawler
1904
1{"id":"stack-73019693","source":"stackoverflow","questionId":73019693,"title":"Looping over an integer range in Zig","tags":["zig"],"text":"Title: Looping over an integer range in Zig\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nIs a while-loop like this the idiomatic way to loop over an integer range in Zig?\n\n```\nvar i: i32 = 5;\nwhile (iI first tried the python-like\n\n```\nfor (5..10) |i| {\n // ....\n```\n\nbut that doesn't work.\n\n========================================\n\nTop Answer:\nThe way you suggested is valid since 0.11.0 (next release). In the meantime I used to do a version of Ali's answer.\n\n```\nfor ([_]u32{0} ** 6) |_, i| {\n std.debug.print(\"{}\\n\", .{i});\n}\n```\n\n========================================\n\nCode:\n```text\nvar i: i32 = 5;\nwhile (i<10): (i+=1) {\n std.debug.print(\"{}\\n\", .{i});\n}\n```\n\n```text\nfor (5..10) |i| {\n // ....\n```\n\n```rs\nconst std = @import(\"std\");\n\nfn range(len: usize) []const void {\n return @as([*]void, undefined)[0..len];\n}\n\nfor (range(10)) |_, i| {\n std.debug.print(\"{d}\\n\", .{i});\n}\n```\n\n```text\n[]void\n```\n\n```text\nfor\n```\n\n```text\nfor ([_]u32{0} ** 6) |_, i| {\n std.debug.print(\"{}\\n\", .{i});\n}\n```\n\n```text\nfor (5..10) |i| {\n std.debug.print(\"{d}\\n\", .{i});\n }\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.840Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":7,"totalLines":75,"estimatedTokens":273}}2{"id":"stack-71186556","source":"stackoverflow","questionId":71186556,"title":"How do I include one .zig file from another .zig file","tags":["zig"],"text":"Title: How do I include one .zig file from another .zig file\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nJust exploring Zig... I have one .zig file with a bunch of comptime functions and constants, and I want to use those in other .zig programs. Equivalent to `#include \"my.h\"` in C.\n\n========================================\n\nTop Answer:\nYou actually can use:\n\n```\nconst bar = struct {\n usingnamespace @import(\"foo.zig\");\n};\n```\n\nto import a complete namespace into a struct, but not at the top level.\n\n========================================\n\nCode:\n```text\n#include \"my.h\"\n```\n\n```text\nconst a = 1;\npub const b = 2;\npub const c = 3;\n```\n\n```text\nconst stdout = @import(\"std\").io.getStdOut().writer();\nconst foo = @import(\"foo.zig\");\nconst c = foo.c;\nconst a = foo.a;\ntest \"@import\" {\n// try stdout.print(\"a={}\\n\",.{foo.a});\n// try stdout.print(\"a={}\\n\",.{a});\n try stdout.print(\"b={}\\n\",.{foo.b});\n try stdout.print(\"c={}\\n\",.{c});\n}\n```\n\n```text\n@import(\"foo.zig\")\n```\n\n```text\npub\n```\n\n```text\nconst a=foo.a\n```\n\n```text\na\n```\n\n```text\nconst\n```\n\n```text\nconst bar = struct {\n usingnamespace @import(\"foo.zig\");\n};\n```\n\n```text\npub const foo = @import(\"foo.zig\").foo;\n```\n\n```text\npub const foo = @import(\"foo.zig\");\n```\n\n```text\n.zig\n```\n\n========================================\n\nComments:\n- Is the extension mandatory or good practice? Without extension, it would feel more \"package-style\" than file.\n- That's the same as `const bar = @import(\"foo.zig\");`, is it not?\n- FYI, `usingnamespace` is gone, it was taken away in 0.15.1","metadata":{"transformedAt":"2026-08-18T18:33:48.840Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":12,"totalLines":90,"estimatedTokens":387}}3{"id":"stack-62554187","source":"stackoverflow","questionId":62554187,"title":"struct definition with var instead of const in zig language","tags":["zig"],"text":"Title: struct definition with var instead of const in zig language\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI am now learning `zig` language. I have seen definitions of structs with `const` keyword like\n\n```\nconst X = struct {\n n: i32,\n};\n```\n\nMy understanding is that `const` is a kind of complementary to `var`, the latter allows change, the former does not. But what would mean defining struct with `var`?\n\n```\nvar Y = struct {\n n: i32,\n};\n```\n\nIs this legal? I compiles, so yes, it is. But what is the meaning and use of this?\n\n========================================\n\nCode:\n```text\nconst X = struct {\n n: i32,\n};\n```\n\n```text\nvar Y = struct {\n n: i32,\n};\n```\n\n```text\nzig\n```\n\n```text\nconst\n```\n\n```text\nconst\n```\n\n```text\nvar\n```\n\n```text\nvar\n```\n\n```js\nvar Y = struct {\n n: i32,\n};\n\ncomptime {\n @compileLog(Y);\n}\n```\n\n```text\nerror: variable of type 'type' must be constant\n var Y = struct {\n ^\n```\n\n```js\nvar Y = struct {\n n: i32,\n};\n```\n\n```js\ncomptime {\n var Y = struct {\n n: i32,\n };\n\n Y = struct {\n count: u32,\n };\n\n const concrete = Y { .count = 10 };\n\n @compileLog(concrete.count);\n}\n```\n\n```text\n| 10\n```\n\n```js\nconst std = @import(\"std\");\n\nfn compilerKnown(arg: []const u8) type {\n return u64;\n}\n\npub fn main() !void {\n var runtimeValue = \"hello world\";\n\n std.debug.print(\"{}\\n\", .{ compilerKnown(runtimeValue) });\n}\n```\n\n```text\nerror: unable to evaluate constant expression\n std.debug.print(\"{}\\n\", .{ compilerKnown(runtimeValue) });\n ^\n```\n\n```text\nY\n```\n\n```text\nvar\n```\n\n```text\nvar\n```\n\n```text\nY\n```\n\n```text\nY\n```\n\n```text\ntype\n```\n\n```text\ntype\n```\n\n```text\nY\n```\n\n```text\nY\n```\n\n```text\ncompilerKnown\n```\n\n```text\ntype\n```\n\n```text\nreturn u64\n```\n\n========================================\n\nComments:\n- Wow, that is a perfect explanation. It seems I will have to unlearn C/C++ a bit before learning zig. :)\n- I have yet another question, maybe I am still missing some understanding... what is the reason that `struct`s are defined with `const` while functions are defined with very different syntax like `pub fn x(bool) void`? In my view these are both types and their definitions should the same syntax. Why is not function defined e.g. `const x = fn(bool) -> void` (like structs) or structs defined `pub struct x { ... }` (like functions). Is there any reason behind this syntax design decision, i.e. does it allow some language features? Or was this more or less just an arbitrary decision?\n- Yes, there is a proposal for that: github.com/ziglang/zig/issues/1717 Is something that is wanted. The problem is that functions pointers has similar syntax, is more difficult to declare the function exportable, inline, etc. So, for the moment, this make the language more complex and is in contrapose to the philosophy of zig (Zen).\n- Thank you for the explanation. I really like the language, it has lots of amazing features. But the syntax still needs a little polishing. It seems that in version 0.7.0 the syntax will settle down.","metadata":{"transformedAt":"2026-08-18T18:33:48.840Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":26,"totalLines":175,"estimatedTokens":767}}4{"id":"stack-61134368","source":"stackoverflow","questionId":61134368,"title":"Mutating a value in an array list in Zig","tags":["arraylist","zig"],"text":"Title: Mutating a value in an array list in Zig\nTags: arraylist, zig\nSource: Stack Overflow\n\nQuestion:\nNoob question:\n\nI want to mutate a value that exists in an array list. I initially tried to just grab the indexed item and directly change its field value. \n\n```\nconst Foo = struct {\n const Self = @This();\n\n foo: u8,\n};\n\npub fn main() anyerror!void {\n const foo = Foo {\n .foo = 1,\n };\n\n const allocator = std.heap.page_allocator;\n\n var arr = ArrayList(Foo).init(allocator);\n\n arr.append(foo) catch unreachable;\n\n var a = arr.items[0];\n\n std.debug.warn(\"a: {}\", .{a});\n\n a.foo = 2;\n\n std.debug.warn(\"a: {}\", .{a}); \n std.debug.warn(\"arr.items[0]: {}\", .{arr.items[0]});\n\n //In order to update the memory in [0] I have to reassign it to a.\n //arr.items[0] = a;\n}\n```\n\nHowever, the result is unexpected to me:\n\n```\na: Foo{ .foo = 1 }\na: Foo{ .foo = 2 }\narr.items[0]: Foo{ .foo = 1 }\n```\n\nI would have thought that `arr.items[0]` would now equal `Foo{ .foo = 2 }`.\n\nThis is probably because I misunderstand slices. \n\nDoes `a` not point to the same memory as `arr.items[0]`?\n\nDoes `arr.items[0]` return a pointer to a copied item?\n\n========================================\n\nCode:\n```text\nconst Foo = struct {\n const Self = @This();\n\n foo: u8,\n};\n\npub fn main() anyerror!void {\n const foo = Foo {\n .foo = 1,\n };\n\n const allocator = std.heap.page_allocator;\n\n var arr = ArrayList(Foo).init(allocator);\n\n arr.append(foo) catch unreachable;\n\n var a = arr.items[0];\n\n std.debug.warn(\"a: {}\", .{a});\n\n a.foo = 2;\n\n std.debug.warn(\"a: {}\", .{a}); \n std.debug.warn(\"arr.items[0]: {}\", .{arr.items[0]});\n\n //In order to update the memory in [0] I have to reassign it to a.\n //arr.items[0] = a;\n}\n```\n\n```text\na: Foo{ .foo = 1 }\na: Foo{ .foo = 2 }\narr.items[0]: Foo{ .foo = 1 }\n```\n\n```text\narr.items[0]\n```\n\n```text\nFoo{ .foo = 2 }\n```\n\n```text\na\n```\n\n```text\narr.items[0]\n```\n\n```text\narr.items[0]\n```\n\n```text\nvar a = arr.items[0];\n```\n\n```text\narr.items[0]\n```\n\n```text\nvar a = &arr.items[0];\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.840Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":10,"totalLines":129,"estimatedTokens":579}}5{"id":"stack-73467232","source":"stackoverflow","questionId":73467232,"title":"How to incorporate the C++ standard library into a Zig program?","tags":["zig"],"text":"Title: How to incorporate the C++ standard library into a Zig program?\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nIn reading the documentation for zig, I was under the impression that zig could compile both C and C++ code. Consequently, I thought you could import a C++ file's header via `@cImport` and have `zig build` succeed. However, I can't seem to get this to work for a C++ library integration.\n\nI first create my project, `zig init-lib` and then add my import to `src/main.zig` via the `@cImport` directive. Specifically, I `@cInclude(\"hooks/hooks.h\")` the C++ header file of this library. If I attempt to `zig build` at this point, the build fails, unable to find the header. I fix this by modifying `build.zig` to `lib.addIncludeDir(\"/usr/include/library\")`.\n\nSince this C++ library is now being parsed and uses the C++ standard library, the next error I get when I `zig build` is that the `stdexcept` header is not found. To fix this, I modify `build.zig` to `lib.linkSystemLibrary(\"c++\")`.\n\nLastly, and the error I'm stuck on now, is an assortment of errors in `/path/to/zig-linux-x86_64-0.9.1/lib/libcxx/include/`. I get stuff like `unknown type name '__LIBCPP_PUSH_MACROS`, `unknown type name 'namespace'`, or `unknown type name 'template'`.\nGoogling this, the only thing of partial relevance that I could find was that this is due to clang's default interpretation of .h files is as C files which obviously don't have `namespace` or `template` keywords, but I don't know what to do with that knowledge. LLVM on MacOs - unknown type name 'template' in standard file iosfwd\n\nDoes anyone have any insight as to how to actually integrate with a C++ (not pure C) library through zig?\n\n========================================\n\nCode:\n```text\n@cImport\n```\n\n```text\nzig build\n```\n\n```text\nzig init-lib\n```\n\n```text\nsrc/main.zig\n```\n\n```text\n@cImport\n```\n\n```text\n@cInclude(\"hooks/hooks.h\")\n```\n\n```text\nzig build\n```\n\n```text\nbuild.zig\n```\n\n```text\nlib.addIncludeDir(\"/usr/include/library\")\n```\n\n```text\nzig build\n```\n\n```text\nstdexcept\n```\n\n```text\nbuild.zig\n```\n\n```text\nlib.linkSystemLibrary(\"c++\")\n```\n\n```text\n/path/to/zig-linux-x86_64-0.9.1/lib/libcxx/include/<files>\n```\n\n```text\nunknown type name '__LIBCPP_PUSH_MACROS\n```\n\n```text\nunknown type name 'namespace'\n```\n\n```text\nunknown type name 'template'\n```\n\n```text\nnamespace\n```\n\n```text\ntemplate\n```\n\n```cpp\n// src/bindings.cpp\n#include <iostream>\n\nextern \"C\" void doSomeCppThing(void) {\n std::cout << \"Hello, World!\\n\";\n}\n```\n\n```c\n// src/bindings.h\nvoid doSomeCppThing(void);\n```\n\n```text\n// build.zig\nconst std = @import(\"std\");\n\npub fn build(b: *std.build.Builder) void {\n const target = b.standardTargetOptions(.{});\n\n const optimize = b.standardOptimizeOption(.{});\n\n const exe = b.addExecutable(.{\n .name = \"tmp\",\n .root_source_file = .{ .path = \"src/main.zig\" },\n .target = target,\n .optimize = optimize,\n });\n\n exe.linkLibC();\n exe.linkLibCpp(); \n exe.addIncludePath(\"src\");\n exe.addCSourceFile(\"src/bindings.cpp\", &.{});\n\n b.installArtifact(exe);\n}\n```\n\n```text\n// src/main.zig\nconst c = @cImport({\n @cInclude(\"bindings.h\");\n});\n\npub fn main() !void {\n c.doSomeCppThing();\n}\n```\n\n```text\n@cImport()\n```\n\n```text\n@cImport()\n```\n\n========================================\n\nComments:\n- For context, I'm attempting to use the kea hooks/hooks.h headers to implement a handler. In your example, it seems the point is for the interface to be pure C, irrespective of whether the implementation is pure C or includes C++. In which case, I'm still a little confused. Even with a C interface, if your C++ code includes , and subsequently libcxx/include/cstddef, won't you still have the parsing error I'm having where zig doesn't recognize `template` or `namespace`?\n- @AmbiguousIllumination if the header file is designed to be compatible with C, the header won't include stdexcept, instead the implementation will include it. Looking at `hooks.h`, it seems like it is designed to be included by C++ code because it has namespaces and uses C++ features: github.com/isc-projects/kea/blob/master/src/lib/hooks/hooks.‌​h\n- > With a C interface, if your C++ code includes won't you still have the parsing error < No. The C++ code is compiled in the build.zig file with `addCSourceCode()`. This is capable of handling C++. The C header file is parsed by `@cImport`, which cannot handle C++.\n- OK, I'm going to mark this as the answer for now. I'll try and experiment to see if I can properly create the pure C interface for the few C++ functionalities I'd need, assuming it's not beyond my skill.","metadata":{"transformedAt":"2026-08-18T18:33:48.840Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":25,"totalLines":160,"estimatedTokens":1160}}6{"id":"stack-62018241","source":"stackoverflow","questionId":62018241,"title":"Current Way to Get User Input","tags":["zig"],"text":"Title: Current Way to Get User Input\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI'm following this blog post on 'comptime' in Zig.\n\nThe following line no longer compiles in Zig `0.6.0`.\n\n```\nconst user_input = try io.readLineSlice(buf[0..]);\n```\n\nBelow is the full function:\n\n```\nfn ask_user() !i64 {\n var buf: [10]u8 = undefined;\n std.debug.warn(\"A number please: \");\n const user_input = try io.readLineSlice(buf[0..]);\n return fmt.parseInt(i64, user_input, 10);\n}\n```\n\nWhat is the equivalent in the current version (of getting user input)?\n\n========================================\n\nTop Answer:\nEven though Cristobal Montecino's answer might work, because windows uses CR/LF line endings, you might also need to trim the end of the string:\n\n```\n// We can read any arbitrary number type with number_type\nfn get_number(comptime number_type: type) !number_type {\n const stdin = std.io.getStdIn().reader();\n\n // Adjust the buffer size depending on what length the input\n // will be or use \"readUntilDelimiterOrEofAlloc\"\n var buffer: [8]u8 = undefined;\n\n // Read until the '\\n' char and capture the value if there's no error\n if (try stdin.readUntilDelimiterOrEof(buffer[0..], '\\n')) |value| {\n // We trim the line's contents to remove any trailing '\\r' chars \n const line = std.mem.trimRight(u8, value[0..value.len - 1], \"\\r\");\n return try std.fmt.parseInt(number_type, line, 10);\n } else {\n return @as(number_type, 0);\n }\n}\n```\n\n========================================\n\nCode:\n```text\nconst user_input = try io.readLineSlice(buf[0..]);\n```\n\n```text\nfn ask_user() !i64 {\n var buf: [10]u8 = undefined;\n std.debug.warn(\"A number please: \");\n const user_input = try io.readLineSlice(buf[0..]);\n return fmt.parseInt(i64, user_input, 10);\n}\n```\n\n```text\n0.6.0\n```\n\n```rust\n// On the top of your file\nconst std = @import(\"std\");\n\n// Inside your function\n\n// Initialize the stdin\n// There is no global variables, so you need to do it \nvar stdin_buffer: [1024]u8 = undefined;\nvar stdin = std.fs.File.stdin().reader(&stdin_buffer);\n\n// A fix size is fine:\n// you don't always want the user to exhaust all the system memory\nvar line_buffer: [1024]u8 = undefined;\nvar w: std.io.Writer = .fixed(&line_buffer);\n\n// Read an input until \"\\n\" or end of file, and write it to the buffer\nconst line_length = try stdin.interface.streamDelimiterLimit(&w, \"\\n\", .unlimited);\n\n// Your input line:\nconst input_line = line_buffer[0..line_length];\n```\n\n```rust\nconst std = @import(\"std\");\nconst builtin = @import(\"builtin\");\n\nfn read_line(line_buffer: []u8, input: *std.io.Reader) ![]u8 { \n var w: std.Io.Writer = .fixed(line_buffer);\n\n var line_length = try input.streamDelimiterLimit(&w, '\\n', .unlimited);\n std.debug.assert(line_length <= line_buffer.len);\n\n // Consume the '\\n' with takeByte and throw it away\n var next_byte: ?u8 = null;\n if (input.takeByte()) |value| {\n next_byte = value;\n } else |err| switch (err) {\n error.EndOfStream => {\n std.debug.assert(next_byte == null);\n },\n else => return err,\n }\n std.debug.assert(next_byte == '\\n' or next_byte == null);\n\n // Trim \\r on windows\n // @see @Sawcce's answer: https://stackoverflow.com/a/75912768/9959510\n // @see https://en.wikipedia.org/wiki/Newline#Representation\n if (builtin.os.tag == .windows) {\n if (line_length > 0) {\n if (next_byte == '\\n' and line_buffer[line_length - 1] == '\\r') {\n line_length -= 1;\n }\n }\n }\n\n return line_buffer[0..line_length];\n}\n```\n\n```rust\nfn ask_number(line_buffer: []u8, input: *std.io.Reader, output: *std.io.Writer) !i64 {\n try output.writeAll(\"A number please: \");\n // Flush to write all the message before read the line\n try output.flush();\n\n const input_line = try read_line(line_buffer, input);\n\n // Attempt to parse the line into an i64 in base 10.\n // If parsing fails (not a valid number or overflow),\n // propagates the parsing error.\n return std.fmt.parseInt(i64, input_line, 10);\n}\n\npub fn main() !void {\n var stdin_buffer: [1024]u8 = undefined;\n var stdout_buffer: [1024]u8 = undefined;\n var stdin = std.fs.File.stdin().reader(&stdin_buffer);\n var stdout = std.fs.File.stdout().writer(&stdout_buffer);\n\n // A capacity to hold any i64 + '\\r'\n var line_buffer: [1024]u8 = undefined;\n\n const num = try ask_number(line_buffer[0..], &stdin.interface, &stdout.interface);\n\n try stdout.interface.print(\"Your number: {}.\", .{num});\n\n // Flush only in success path, no defer\n try stdout.interface.flush();\n}\n```\n\n```text\nstdin.reader(buf)\n```\n\n```text\n.interface\n```\n\n```rust\n// We can read any arbitrary number type with number_type\nfn get_number(comptime number_type: type) !number_type {\n const stdin = std.io.getStdIn().reader();\n\n // Adjust the buffer size depending on what length the input\n // will be or use \"readUntilDelimiterOrEofAlloc\"\n var buffer: [8]u8 = undefined;\n\n // Read until the '\\n' char and capture the value if there's no error\n if (try stdin.readUntilDelimiterOrEof(buffer[0..], '\\n')) |value| {\n // We trim the line's contents to remove any trailing '\\r' chars \n const line = std.mem.trimRight(u8, value[0..value.len - 1], \"\\r\");\n return try std.fmt.parseInt(number_type, line, 10);\n } else {\n return @as(number_type, 0);\n }\n}\n```\n\n```rust\nconst std = @import(\"std\");\n\nvar input_buf: [1024]u8 = undefined;\nvar stdin_reader = std.fs.File.stdin().reader(&input_buf);\n\n// This is what you pass around to functions that take a std.Io.Reader\nconst stdin = &stdin_reader.interface;\n\n// Same goes for stdout\nvar output_buf: [1024]u8 = undefined;\nvar stdout_writer = std.fs.File.stdout().writer(&output_buf);\nconst stdout = &stdout_writer.interface;\n\nfn ask_user(reader: *std.Io.Reader, writer: *std.Io.Writer) !i64 {\n try writer.print(\"A number please: \", .{});\n // Use flush to ensure output is written immediately\n // Otherwise, output is only written if output_buf is full.\n try writer.flush();\n\n // Reads data into input_buf and returns a slice to it\n // This slice is only valid until the next \"peek\" operation (take does a peek)\n const line = try reader.takeDelimiterExclusive('\\n');\n return std.fmt.parseInt(i64, line, 10);\n}\n\npub fn main() !void {\n const value = try ask_user(stdin, stdout);\n\n try stdout.print(\"You wrote: {d}\\n\", .{value});\n // don't forget to flush\n try stdout.flush();\n}\n```\n\n```text\nerror.StreamTooLong\n```\n\n```text\nstdin_buf\n```\n\n```text\n1024\n```\n\n========================================\n\nComments:\n- this is really complicated for a simple use such as reading console input. Is there a better way of doing this keeping in mind Zig is a drop in replacement for C which has Scanf?\n- There's no `scanf` at the moment, see issue 12161. I would also recommend taking a look at Q: Disadvantages of scanf.\n- Does 'parseInt' consumes the buffer (user_input in that case)?\n- Since the latest version 0.15.0, this getStdIn is removed from zig, so once again, what is the new way to read a user input?\n- the code crashed when i try to read in a second line. i'm not smart enough to know if this is the right thing to do but i added `input.tossBuffered();` to the end of the read line function in an attempt to clear out whatever is still there and that works 🤷.\n- @AndrewTreadwell You're right, read_line is unable to parse more than one line because the '\\n' is still there. I fix it with input.takeByte().","metadata":{"transformedAt":"2026-08-18T18:33:48.840Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":13,"totalLines":247,"estimatedTokens":1880}}7{"id":"stack-61466724","source":"stackoverflow","questionId":61466724,"title":"Generation of types in zig","tags":["zig"],"text":"Title: Generation of types in zig\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nIs it possible to create a `comptime` function in zig that would generate a new struct type? The function would receive an array of strings and an array of types. The strings are the names of subsequent struct fields.\n\n========================================\n\nTop Answer:\nThis has been implemented now as https://github.com/ziglang/zig/pull/6099\n\n```\nconst builtin = @import(\"std\").builtin;\nconst A = @Type(.{\n .Struct = .{\n .layout = .Auto,\n .fields = &[_]builtin.TypeInfo.StructField{\n .{ .name = \"one\", .field_type = i32, .default_value = null, .is_comptime = false, .alignment = 0 },\n },\n .decls = &[_]builtin.TypeInfo.Declaration{},\n .is_tuple = false,\n },\n});\ntest \"\" {\n const a: A = .{ .one = 25 };\n}\n```\n\nThe TypeInfo struct is defined here.\n\n========================================\n\nCode:\n```text\ncomptime\n```\n\n```text\nfields\n```\n\n```text\ndecls\n```\n\n```rust\nconst builtin = @import(\"std\").builtin;\nconst A = @Type(.{\n .Struct = .{\n .layout = .Auto,\n .fields = &[_]builtin.TypeInfo.StructField{\n .{ .name = \"one\", .field_type = i32, .default_value = null, .is_comptime = false, .alignment = 0 },\n },\n .decls = &[_]builtin.TypeInfo.Declaration{},\n .is_tuple = false,\n },\n});\ntest \"\" {\n const a: A = .{ .one = 25 };\n}\n```\n\n========================================\n\nComments:\n- Thanks. I was guessing it was not possible (or else the doc would brag about it).","metadata":{"transformedAt":"2026-08-18T18:33:48.840Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":4,"totalLines":67,"estimatedTokens":375}}8{"id":"stack-76441595","source":"stackoverflow","questionId":76441595,"title":"How do I split a string in zig by a specific character?","tags":["split","zig"],"text":"Title: How do I split a string in zig by a specific character?\nTags: split, zig\nSource: Stack Overflow\n\nQuestion:\nI have a simple sentence in a string. I want to print each word on a new line or otherwise just do some calculation on each word?\n\nIs there something similar to python's `\"Hello World\".split()` in zig? Something like this:\n\n```\nvar arr = std.strings.split(\"Hello world\");\n```\n\n========================================\n\nTop Answer:\nAs of Nov 2024 `std.mem.split` is deprecated\n\nYou can instead use `splitScalar`\n\n```\nconst std = @import(\"std\");\n\npub fn main() !void {\n var it = std.mem.splitScalar(u8, \"Hello World\", ' ');\n while (it.next()) |x| {\n std.debug.print(\"{s}\\n\", .{x});\n }\n}\n```\n\nThere is also splitSequence, if you wish to split by a sequence, example:\n\n`var it = std.mem.splitSequence(u8, httpResponse, \"\\r\\n\")`\n\n========================================\n\nCode:\n```text\nvar arr = std.strings.split(\"Hello world\");\n```\n\n```text\n\"Hello World\".split()\n```\n\n```none\nconst std = @import(\"std\");\n\npub fn main() !void {\n var it = std.mem.split(u8, \"Hello World\", \" \");\n while (it.next()) |x| {\n std.debug.print(\"{s}\\n\", .{x});\n }\n}\n```\n\n```text\nmem\n```\n\n```text\n.split\n```\n\n```text\nSplitIterator\n```\n\n```text\n.next()\n```\n\n```text\n.next()\n```\n\n```text\nconst std = @import(\"std\");\n\npub fn main() !void {\n var it = std.mem.splitScalar(u8, \"Hello World\", ' ');\n while (it.next()) |x| {\n std.debug.print(\"{s}\\n\", .{x});\n }\n}\n```\n\n```text\nstd.mem.split\n```\n\n```text\nsplitScalar\n```\n\n```text\nvar it = std.mem.splitSequence(u8, httpResponse, \"\\r\\n\")\n```\n\n```none\nconst std = @import(\"std\");\n \n pub fn main() !void{\n \n const stdout = std.io.getStdOut().writer();\n \n const input = \"Hello World\";\n \n//this is to split by spaces\n var iter = std.mem.splitAny(u8, input, \" \");\n\n while (iter.next()) |word| {\n try stdout.print(\"{s}\\n\", .{word});\n}\n}\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.840Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":13,"totalLines":117,"estimatedTokens":473}}9{"id":"stack-72558202","source":"stackoverflow","questionId":72558202,"title":"Can I pass commandline arguments when invoking \"zig build run\"?","tags":["command-line-arguments","zig"],"text":"Title: Can I pass commandline arguments when invoking \"zig build run\"?\nTags: command-line-arguments, zig\nSource: Stack Overflow\n\nQuestion:\nI'm just starting with the new programming language Zig and finding documentation pretty sparse.\n\nI can build and run the current project by invoking `zig build run`.\n\nI can also do `zig run src/main.zig` assuming standard project layout.\n\nBut in neither case can I find a way to pass along commandline arguments to my project.\n\nI know that after building I can invoke my project as a binary as `zig-out/bin/ foo bar` but is there a way to do it straight from `build run`?\n\nJust trying the obvious `zig build run foo bar` tells me `Cannot run step 'foo' because it does not exist`.\n\nNone of the commandline switches for zig itself seem to do what I want and I can't find anyone discussing this by Googling for it.\n\n========================================\n\nTop Answer:\nInitial setup:\n\n```\nconst run_exe = b.addRunArtifact(exe);\nconst run_step = b.step(\"run\", \"Run the application\");\nrun_step.dependOn(&run_exe.step);\n```\n\nFor Zig 0.16\n\n```\nif (b.args) |args| run_exe.addArgs(args);\n```\n\nFor Zig 0.17+\n\n```\nrun_exe.addPassthruArgs();\n```\n\nReference: https://muhammad-fiaz.github.io/args.zig/guide/getting-started\n\n========================================\n\nCode:\n```text\nzig build run\n```\n\n```text\nzig run src/main.zig\n```\n\n```text\nzig-out/bin/<my project's name> foo bar\n```\n\n```text\nbuild run\n```\n\n```text\nzig build run foo bar\n```\n\n```text\nCannot run step 'foo' because it does not exist\n```\n\n```bash\nzig build run -- foo bar\n```\n\n```text\n--\n```\n\n```text\nzig build run -- <args>\n```\n\n```text\nconst run_exe = b.addRunArtifact(exe);\nconst run_step = b.step(\"run\", \"Run the application\");\nrun_step.dependOn(&run_exe.step);\n```\n\n```text\nif (b.args) |args| run_exe.addArgs(args);\n```\n\n```text\nrun_exe.addPassthruArgs();\n```\n\n========================================\n\nComments:\n- Thanks! I don't use *nix commandlines regularly enough for me to immediately recall that standard feature. It could benefit from being in the help assuming I'm not the only one.\n- Looks like this doesn't work on Windows.\n- Whoops, it does work. You just need to use `run_step.addArgs()` like in zig.news/xq/zig-build-explained-part-1-59lf","metadata":{"transformedAt":"2026-08-18T18:33:48.840Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":12,"totalLines":103,"estimatedTokens":563}}10{"id":"stack-64684978","source":"stackoverflow","questionId":64684978,"title":"Why is infix const required for arrays of strings?","tags":["arrays","constants","zig"],"text":"Title: Why is infix const required for arrays of strings?\nTags: arrays, constants, zig\nSource: Stack Overflow\n\nQuestion:\nI am learning zig slowly, but I don't understand const and how it interacts with arrays/types - I'm going through https://ziglang.org/documentation/0.6.0/#Introduction but they use const a lot for strings.\n\nThis compiles:\n\n```\nvar n = [_][]const u8 {\"test 1\", \"test4\", \"test 6\", \"zz\"};\n```\n\nWithout the `const` is an error:\n\n```\nvar n = [_][] u8 {\"test 1\", \"test4\", \"test 6\", \"zz\"};\n\nerror: expected type '[]u8', found '*const [6:0]u8'\n```\n\nsimilarly, putting const on the left is the same error:\n\n```\nconst n = [_][]u8 {\"test 1\", \"test4\", \"test 6\", \"zz\"};\n```\n\nWhat is putting the const keyword in the middle that way actually directing the compiler to do?\n\n========================================\n\nCode:\n```text\nvar n = [_][]const u8 {\"test 1\", \"test4\", \"test 6\", \"zz\"};\n```\n\n```text\nvar n = [_][] u8 {\"test 1\", \"test4\", \"test 6\", \"zz\"};\n\nerror: expected type '[]u8', found '*const [6:0]u8'\n```\n\n```text\nconst n = [_][]u8 {\"test 1\", \"test4\", \"test 6\", \"zz\"};\n```\n\n```text\nconst\n```\n\n```text\nvar move: [3][]u8 = undefined;\nvar ziga: [4]u8 = [_]u8{ 'z', 'i', 'g', 's' };\nconst zigs: []u8 = ziga[0..];\nmove[0] = zigs;\nmove[0][1] = 'a';\n```\n\n```text\nvar belong_to_us = [_][]const u8{ \"all\", \"your\", \"base\", \"are\" };\nvar bomb = [_][]const u8{ \"someone\", \"set\", \"up\", \"us\" };\nbelong_to_us = bomb;\n```\n\n```text\nbomb[0][0] = 'x'; // error: cannot assign to constant\n```\n\n```text\nconst signal: [3][]const u8 = [_][]const u8{ \"we\", \"get\", \"signal\" };\nconst go: [3][]const u8 = [_][]const u8{ \"move\", \"every\", \"zig\" };\nsignal = go; // error: cannot assign to constant\n```\n\n```text\nvar what: [4]u8 = [_]u8{ 'w', 'h', 'a', 't' };\nconst signal: [3][]u8 = [_][]u8{ zigs, what[0..], zigs };\nsignal[0][1] = 'f'; // Legal!\nsignal[1] = zigs; // error: cannot assign to constant\n```\n\n```text\nconst\n```\n\n```text\n[_][] u8\n```\n\n```text\nu8\n```\n\n```text\n[_][] const u8\n```\n\n```text\nconst u8\n```\n\n```text\n*const [_:0]u8\n```\n\n```text\n*const [6:0] u8\n```\n\n```text\nconst u8\n```\n\n```text\n[_][]u8\n```\n\n```text\n[_][] const u8\n```\n\n```text\nconst [_][] const u8\n```\n\n```text\nconst [_][]u8\n```\n\n```text\nu8\n```\n\n========================================\n\nComments:\n- String literals in zig are constant, unlike C where you can assign a string to a char * pointer, then change the contents of the string. `var` is deducing the type from your description, but the array description must match the array literal, and that means `const` strings. Putting `const` on the left just means you're not going to change `n`, but it's still describing an array of non-const items, and assigning an array of const strings.\n- Could you also add an explanation of what a `*const [6:0]u8` is, since that is what the compiler found?\n- Upvoted partially for the answer, partially for the Zero Wing reference =D\n- @NealFultz Updated.","metadata":{"transformedAt":"2026-08-18T18:33:48.840Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":22,"totalLines":140,"estimatedTokens":728}}11{"id":"stack-72736997","source":"stackoverflow","questionId":72736997,"title":"How to pass a C string into a Zig function expecting a Zig string?","tags":["c","zig"],"text":"Title: How to pass a C string into a Zig function expecting a Zig string?\nTags: c, zig\nSource: Stack Overflow\n\nQuestion:\nTrying to use a Zig library expecting a string... but I get a string buffer from a C library.\n\nThat means that I need to pass a value of type `[*c]u8` to a function that accepts `[:0]const u8`.\n\nHow to do that?\n\nI found this way so far:\n\n```\nconst buffer: [*c]u8 = callC();\nconst str = std.mem.span(@ptrCast([*:0]const u8, buffer));\n```\n\nWhich looks more complicated than it should (and makes a copy??).\n\nThe Zig docs says that:\n\nString literals are const pointers\nto null-terminated arrays of u8.\n\nSo I thought they are compatible C strings and a very simple cast like `@as([*:0]const u8, buffer)` should suffice?\n\n========================================\n\nCode:\n```text\nconst buffer: [*c]u8 = callC();\nconst str = std.mem.span(@ptrCast([*:0]const u8, buffer));\n```\n\n```text\n[*c]u8\n```\n\n```text\n[:0]const u8\n```\n\n```text\n@as([*:0]const u8, buffer)\n```\n\n```text\nconst std = @import(\"std\");\n\ntest \"convert c string to [*:0]u8\" {\n const c_string: [*c]const u8 = \"some c string\";\n const as_ptr: [*:0]const u8 = c_string;\n _ = as_ptr;\n}\n```\n\n```text\nconst std = @import(\"std\");\n\ntest \"convert c string to zig string\" {\n const c_string: [*c]const u8 = \"some c string\";\n const as_slice: [:0]const u8 = std.mem.span(c_string);\n\n try std.testing.expectEqualStrings(as_slice, \"some c string\");\n}\n```\n\n```text\nconst buffer: [*c]u8 = callC();\nconst str = std.mem.span(@ptrCast([*:0]const u8, buffer));\n```\n\n```text\n[*:0]u8\n```\n\n```text\n[:0]u8\n```\n\n```text\n[*:0]u8\n```\n\n```text\n0\n```\n\n```text\n[:0]u8\n```\n\n```text\nstruct {ptr: [*:0]u8, len: usize}\n```\n\n```text\n@pointerCast\n```\n\n```text\n[*c]u8\n```\n\n```text\n[*:0]u8\n```\n\n```text\n[]const u8\n```\n\n```text\n[:0]const u8\n```\n\n```text\nstd.mem.span\n```\n\n========================================\n\nComments:\n- I might be wrong, but: `@ptrCast([*:0]const u8, buffer)` should suffice. But why use pointers when you can use wonderful slices? Then just `std.mem.span(buffer)`.","metadata":{"transformedAt":"2026-08-18T18:33:48.840Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":19,"totalLines":125,"estimatedTokens":510}}12{"id":"stack-68552110","source":"stackoverflow","questionId":68552110,"title":"zig print float precision","tags":["zig"],"text":"Title: zig print float precision\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nIn zig it is possible to print float values in decimal notation by using \"{d}\". This will automatically print the value at full precision. Is there way to specify the number of digits? Either for each value, or as some kind of global setting?\n\n========================================\n\nCode:\n```text\nformat(w, \"{d:.1}\", .{0.05}) == \"0.1\"\nformat(w, \"{d:.3}\", .{0.05}) == \"0.050\"\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.840Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":1,"totalLines":14,"estimatedTokens":115}}13{"id":"stack-69474179","source":"stackoverflow","questionId":69474179,"title":"How to create an empty slice of slices","tags":["slice","zig"],"text":"Title: How to create an empty slice of slices\nTags: slice, zig\nSource: Stack Overflow\n\nQuestion:\nHow do I construct `[]const []const u8` without using an allocator?\n\nI can do\n\n```\nvar slice: []const []const u8 = undefined;\nslice.len = 0;\n// use slice\n```\n\nBut there surely must be a better way.\n\n========================================\n\nCode:\n```text\nvar slice: []const []const u8 = undefined;\nslice.len = 0;\n// use slice\n```\n\n```text\n[]const []const u8\n```\n\n```text\nvar foo: []const []const u8 = &.{};\n```\n\n========================================\n\nComments:\n- Oh, wow. It's so much better than `&[_][]u8 {}`.\n- This makes use of Type Coercion: Tuples to Arrays.","metadata":{"transformedAt":"2026-08-18T18:33:48.840Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":3,"totalLines":39,"estimatedTokens":166}}14{"id":"stack-72607441","source":"stackoverflow","questionId":72607441,"title":"How can I pass a Zig String literal to C","tags":["c","zig"],"text":"Title: How can I pass a Zig String literal to C\nTags: c, zig\nSource: Stack Overflow\n\nQuestion:\nA Zig String literal is a single-item pointer to a null-terminated byte array, which is perfect to be used as a C's `char *` String!\n\nHowever, when I try to use this simple C function from Zig:\n\n```\nint count_bytes(const char *str) {\n int count = 0;\n while(str[count]) {\n count++;\n }\n return count;\n}\n```\n\nZig caller:\n\n```\nconst std = @import(\"std\");\nconst c = @cImport({\n @cInclude(\"add.c\");\n});\nconst testing = std.testing;\n\ntest \"should be able to count string length\" {\n try testing.expectEqual(0, c.count_bytes(\"\"));\n}\n```\n\nI get this error:\n\n```\n./src/main.zig:16:46: error: expected type '[*c]u8', found '*const [0:0]u8'\n try testing.expectEqual(0, c.count_bytes(\"\"));\n ^\n./src/main.zig:16:46: note: cast discards const qualifier\n try testing.expectEqual(0, c.count_bytes(\"\"));\n ^\n```\n\nThis article explains about Zig String literals in a similar situation, but I was unable to use the trick to make the String non-const:\n\n```\ntest \"should be able to count string length\" {\n var cstr = \"\".*;\n try testing.expectEqual(0, c.count_bytes(&cstr));\n}\n```\n\nResult is an even stranger error:\n\n```\n./src/main.zig:17:45: error: expected type 'comptime_int', found 'c_int'\n try testing.expectEqual(0, c.count_bytes(&cstr));\n ^\n```\n\nI also tried casting the String to a C Pointer as shown in the Zig Docs:\n\n```\ntest \"should be able to count string length\" {\n var cstr: [*c]u8 = &\"\".*;\n try testing.expectEqual(0, c.count_bytes(cstr));\n}\n```\n\nWhich also gives an error:\n\n```\n./src/main.zig:16:27: error: expected type '[*c]u8', found '*const [0:0]u8'\n var cstr: [*c]u8 = &\"\".*;\n ^\n./src/main.zig:16:27: note: cast discards const qualifier\n var cstr: [*c]u8 = &\"\".*;\n ^\n```\n\nHow can I do this?\n\nEDIT:\n\nI am getting suggestions that do not work with Zig 0.9, which is the latest stable release as I am writing this.\n\nPlease try this out first if you think you know a solution... put the C file at `src-c/add.c`, and the Zig file at `src/main.zig`,\nthen run this to try:\n\n```\nzig test src/main.zig -I src-c\n```\n\n========================================\n\nCode:\n```c\nint count_bytes(const char *str) {\n int count = 0;\n while(str[count]) {\n count++;\n }\n return count;\n}\n```\n\n```text\nconst std = @import(\"std\");\nconst c = @cImport({\n @cInclude(\"add.c\");\n});\nconst testing = std.testing;\n\ntest \"should be able to count string length\" {\n try testing.expectEqual(0, c.count_bytes(\"\"));\n}\n```\n\n```text\n./src/main.zig:16:46: error: expected type '[*c]u8', found '*const [0:0]u8'\n try testing.expectEqual(0, c.count_bytes(\"\"));\n ^\n./src/main.zig:16:46: note: cast discards const qualifier\n try testing.expectEqual(0, c.count_bytes(\"\"));\n ^\n```\n\n```text\ntest \"should be able to count string length\" {\n var cstr = \"\".*;\n try testing.expectEqual(0, c.count_bytes(&cstr));\n}\n```\n\n```text\n./src/main.zig:17:45: error: expected type 'comptime_int', found 'c_int'\n try testing.expectEqual(0, c.count_bytes(&cstr));\n ^\n```\n\n```text\ntest \"should be able to count string length\" {\n var cstr: [*c]u8 = &\"\".*;\n try testing.expectEqual(0, c.count_bytes(cstr));\n}\n```\n\n```text\n./src/main.zig:16:27: error: expected type '[*c]u8', found '*const [0:0]u8'\n var cstr: [*c]u8 = &\"\".*;\n ^\n./src/main.zig:16:27: note: cast discards const qualifier\n var cstr: [*c]u8 = &\"\".*;\n ^\n```\n\n```text\nzig test src/main.zig -I src-c\n```\n\n```text\nchar *\n```\n\n```text\nsrc-c/add.c\n```\n\n```text\nsrc/main.zig\n```\n\n```text\n./src/main.zig:17:45: error: expected type 'comptime_int', found 'c_int'\n try testing.expectEqual(0, c.count_bytes(&cstr));\n ^\n\nWould be slightly clearer if it was like this:\n./src/main.zig:17:45: error: expected type 'comptime_int', found 'c_int'\n try testing.expectEqual(0, c.count_bytes(&cstr));\n ~~~~~~~~~~~~~~~~~~~~\n```\n\n```text\ntry testing.expectEqual(@as(c_int, 0), c.count_bytes(\"\"));\n```\n\n```text\n(\n```\n\n```text\nstd.testing.expectEqual\n```\n\n```text\nfn expectEqual(a: anytype, b: @TypeOf(a)) void\n```\n\n```text\nb\n```\n\n```text\na\n```\n\n```text\na\n```\n\n```text\ncomptime_int\n```\n\n```text\ncomptime_int\n```\n\n```text\nexpectEqual\n```\n\n```text\ncount_bytes\n```\n\n```text\nint count_bytes(char *str)\n```\n\n```text\nint count_bytes(const char *str)\n```\n\n========================================\n\nComments:\n- Have you tried: `int count_bytes(const char *)`? If you're not modifying it on the C side, const is a good idea.\n- I am assuming the C code is not mine (though this is just an exercise for me to see if Zig can be used effectively to test C code), but even after trying to add const to the C code I don't get this to work.\n- I originally did not have the const in the C parameter... forgot to add it... then after adding it I ran into the c_int error which threw me off completely... now everything makes sense, thanks for your assistance.","metadata":{"transformedAt":"2026-08-18T18:33:48.841Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":25,"totalLines":242,"estimatedTokens":1274}}15{"id":"stack-76535068","source":"stackoverflow","questionId":76535068,"title":"How can I parse an integer from a string in Zig?","tags":["string","integer","zig"],"text":"Title: How can I parse an integer from a string in Zig?\nTags: string, integer, zig\nSource: Stack Overflow\n\nQuestion:\nWhat is the best way to parse an integer from a string in Zig and specify the resulting integer type?\n\n```\nconst foo = \"22\";\n```\n\nHow would I convert `foo` to an `i32`, for example?\n\n========================================\n\nCode:\n```text\nconst foo = \"22\";\n```\n\n```text\nfoo\n```\n\n```text\ni32\n```\n\n```none\nconst foo = \"22\";\n\nconst integer = try std.fmt.parseInt(i32, foo, 10);\n```\n\n```text\ni32\n```\n\n```text\nu64\n```\n\n========================================\n\nComments:\n- Have you tried anything yet? Have you looked through the docs? Have you got any failed examples? Have you explored the errors you have gotten? Being more specific may help. This may help, it took me 30 seconds to find github.com/ziglang/zig/issues/4142#issuecomment-573286768 - Note I did not down vote your question.\n- @DanielTate I've searched around and gotten a basic answer from the docs, however I'm a novice in Zig and I'd like to get an answer from someone more experienced that can give a detailed response. I also thought since there were no answers to this on Stackoverflow, this question could be useful for other people searching for an answer.\n- I understand, unfortunately the community here doesn't like questions like this, they like specificity. Outlining the exact operations you are looking to achieve with at least one psudo code example or failed attempt will make for a much higher quality question. It looks like you're asking 3 questions here ( from a glance )\n- Your example is not accurate. The `fmt.parseInt` function returns the error union, so the type of `integer` is not `i32` but `ParseIntError!i32` in this case. You have to use `try` keyword to get the value type: `const integer = try std.fmt.parseInt(i32, foo, 10);`.\n- @KindFrog Thank you for the correction, I'll make sure to edit the answer.\n- Please, use `try` instead of `catch unreachable`. You can only use this only because you're parsing a known string; you could have just written `const integer = 22;`. But if someone is looking for ways to parse a number, they'll likely have an unknown string and will need to handle errors properly. This answer will only confuse them.","metadata":{"transformedAt":"2026-08-18T18:33:48.841Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":6,"totalLines":51,"estimatedTokens":564}}16{"id":"stack-73345643","source":"stackoverflow","questionId":73345643,"title":"How to use the zig compiler in order to compile nim code?","tags":["compilation","nim-lang","zig"],"text":"Title: How to use the zig compiler in order to compile nim code?\nTags: compilation, nim-lang, zig\nSource: Stack Overflow\n\nQuestion:\nNim turns its own code into C code and compiles that using C-compilers.\nZig has its own compiler that has many nice features that would make you want to use it, such as allowing you to choose which glibc version to dynamically link against, or easier cross-compilation.\n\nTherefore, I would like to compile my nim-code using the zig compiler, but is that even possible?\n\n========================================\n\nTop Answer:\nWrite a Nim program (zigcc.nim compiles to zigcc.exe):\n\n```\nimport std/osproc\nimport os\n\nvar pStr: string = \"zig cc\"\n\nfor i in 1..paramCount():\n pStr.add(\" \"¶mStr(i))\ndiscard execShellCmd(pStr)\n```\n\nSet your environment path variables with nim.exe & zig.exe paths,\ncopy zigcc.exe to Zig homedir\nand call Nim like this:\n\n```\nnim c --cc:clang --clang.exe=\"zigcc\" --clang.linkerexe=\"zigcc\" yourFileName.nim\n```\n\nAnd magic happens...\n\n========================================\n\nCode:\n```bash\n#!/bin/sh\nzig cc $@\n```\n\n```bash\n#!/bin/sh\nnim c \\\n--cc:clang \\\n--clang.exe=\"zigcc\" \\\n--clang.linkerexe=\"zigcc\" \\\n--forceBuild:on \\\n--opt:speed \\\nsrc/<YOUR_MAIN_FILE>.nim\n```\n\n```text\n--passC:\"-target x86_64-linux-gnu.X.XX -fno-sanitize=undefined\" \\\n--passL:\"-target x86_64-linux-gnu.X.XX -fno-sanitize=undefined\" \\\n```\n\n```text\nzigcc\n```\n\n```text\nzigcc\n```\n\n```text\n/usr/local/bin\n```\n\n```text\nzigcc\n```\n\n```text\nnimble install https://github.com/enthus1ast/zigcc\n```\n\n```text\nzigcc\n```\n\n```text\nimport std/osproc\nimport os\n\nvar pStr: string = \"zig cc\"\n\nfor i in 1..paramCount():\n pStr.add(\" \"¶mStr(i))\ndiscard execShellCmd(pStr)\n```\n\n```text\nnim c --cc:clang --clang.exe=\"zigcc\" --clang.linkerexe=\"zigcc\" yourFileName.nim\n```\n\n========================================\n\nComments:\n- That should be `zig cc \"$@\"`","metadata":{"transformedAt":"2026-08-18T18:33:48.841Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":11,"totalLines":103,"estimatedTokens":467}}17{"id":"stack-68454051","source":"stackoverflow","questionId":68454051,"title":"zig structs, pointers, field access","tags":["zig"],"text":"Title: zig structs, pointers, field access\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI was trying to implement vector algebra with generic algorithms and ended up playing with iterators. I have found two examples of not obvious and unexpected behaviour:\n\n- if I have pointer `p` to a struct (instance) with field `fi`, I can access the field as simply as `p.fi` (rather than `p.*.fi`)\n\n- if I have a \"member\" function `fun(this: *Self)` (where `Self = @This()`) and an instance `s` of the struct, I can call the function as simply as `s.fun()` (rather than `(&s).fun()`)\n\nMy questions are:\n\n- is it documented (or in any way mentioned) somewhere? I've looked through both language reference and guide from ziglearn.org and didn't find anything\n\n- what is it that we observe in these examples? syntactic sugar for two particular cases or are there more general rules from which such behavior can be deduced?\n\n- are there more examples of weird pointers' behaviour?\n\n========================================\n\nTop Answer:\nI first learned this syntax by going through the ziglings course, which is linked to on ziglang.org.\n\nin exercise 43 (https://github.com/ratfactor/ziglings/blob/main/exercises/043_pointers5.zig)\n\n```\n// Note that you don't need to dereference the \"pv\" pointer to access\n// the struct's fields:\n//\n// YES: pv.x\n// NO: pv.*.x\n//\n// We can write functions that take pointer arguments:\n//\n// fn foo(v: *Vertex) void {\n// v.x += 2;\n// v.y += 3;\n// v.z += 7;\n// }\n//\n// And pass references to them:\n//\n// foo(&v1);\n```\n\nThe ziglings course goes quite in-depth on a few language topics, so it's definitely work checking out if you're interested.\n\nWith regards to other syntax: as the previous answer mentioned, you don't need to dereference array pointers. I'm not sure about anything else (I thought function pointers worked the same, but I just ran some tests and they do not.)\n\n========================================\n\nCode:\n```text\np\n```\n\n```text\nfi\n```\n\n```text\np.fi\n```\n\n```text\np.*.fi\n```\n\n```text\nfun(this: *Self)\n```\n\n```text\nSelf = @This()\n```\n\n```text\ns\n```\n\n```text\ns.fun()\n```\n\n```text\n(&s).fun()\n```\n\n```zig\nconst std = @import(\"std\");\n\npub fn main() !void {\n const arr = [_]u8{1,2,3};\n const foo = &arr;\n\n std.debug.print(\"{}\", .{arr[2]});\n std.debug.print(\"{}\", .{foo[2]});\n}\n```\n\n```text\n[]\n```\n\n```text\n// Note that you don't need to dereference the \"pv\" pointer to access\n// the struct's fields:\n//\n// YES: pv.x\n// NO: pv.*.x\n//\n// We can write functions that take pointer arguments:\n//\n// fn foo(v: *Vertex) void {\n// v.x += 2;\n// v.y += 3;\n// v.z += 7;\n// }\n//\n// And pass references to them:\n//\n// foo(&v1);\n```\n\n========================================\n\nComments:\n- thanks, the example with indexes is great, I bet there's `ptr.*[n]` somewhere in my code waiting to be corrected","metadata":{"transformedAt":"2026-08-18T18:33:48.841Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":12,"totalLines":129,"estimatedTokens":718}}18{"id":"stack-75171967","source":"stackoverflow","questionId":75171967,"title":"Convert i32 into f32","tags":["type-conversion","zig"],"text":"Title: Convert i32 into f32\nTags: type-conversion, zig\nSource: Stack Overflow\n\nQuestion:\nHow can I convert a i32 into a f32 in Zig Language?\n\nI want to count appearances of values in a for loop and afterwards get the percentages in a smooth floating number.\n\n```\nvar partial : i32 = 0;\nvar total : i32 = 2000;\n \n\nfor (arr[0..total]) |value| {\n if(value < 200) inCircle = inCircle + 1;\n}\n\nconst result = partial / total;\n```\n\n========================================\n\nCode:\n```text\nvar partial : i32 = 0;\nvar total : i32 = 2000;\n \n\nfor (arr[0..total]) |value| {\n if(value < 200) inCircle = inCircle + 1;\n}\n\nconst result = partial / total;\n```\n\n```text\nconst result = @as(f32, @floatFromInt(partial)) / @as(f32, @floatFromInt(total));\n```\n\n```text\nconst result = @intToFloat(f32, partial) / @intToFloat(f32, total);\n```\n\n```text\n@floatFromInt\n```\n\n```text\n@as\n```\n\n```text\n@intToFloat\n```\n\n========================================\n\nComments:\n- Thanks, that was to conversion method I've looked for. Can you provide a documentation link as well?\n- @CitrusPunk It's in the answer: ziglang.org/documentation/master/#intToFloat\n- I do get it's important to be explicit, but the 0.10 => 0.11 change feels ... verbose. Is there a design rationale for this?\n- @sigint The 0.11 changes make the code more streamlined, but as a side effect the code becomes more verbose in some situations. See this answer and this section of the 0.11 changelog.","metadata":{"transformedAt":"2026-08-18T18:33:48.841Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":6,"totalLines":63,"estimatedTokens":360}}19{"id":"stack-65157883","source":"stackoverflow","questionId":65157883,"title":"How to import zig modules dynamically?","tags":["zig"],"text":"Title: How to import zig modules dynamically?\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI'm using zig `0.7.0.` and I'm trying to import a list of zig source files from an array. Each source file has a `main` function (whose return type is `!void`) that I would like to call. The array `module_names` is known at compile time.\n\nHere is what I tried to do:\n\n```\nconst std = @import(\"std\");\nconst log = std.log;\n\nconst module_names = [_][]const u8{\n \"01.zig\", \"02.zig\", \"03.zig\", \"04.zig\", \"05.zig\",\n};\n\npub fn main() void {\n var arena = std.heap.ArenaAllocator.init(std.heap.page_allocator);\n defer arena.deinit();\n\n for (module_names) |module_name, i| {\n const module = @import(module_name); // this fails\n log.info(\"i {}\", .{i});\n try module.main();\n }\n}\n```\n\nEven if the array is known at compile time, `@import(module_name)` gives me this error:\n\n```\n./src/main.zig:13:32: error: unable to evaluate constant expression\n const module = @import(module_name);\n ^\n./src/main.zig:13:24: note: referenced here\n const module = @import(module_name);\n```\n\nI could understand the error if the array would be dynamically generated and only known at runtime, but here the `module_names` array is known at compile time. So I am a bit confused...\n\nAlternatively, I also tried to wrap the entire `main` body in a `comptime` block:\n\n```\npub fn main() void {\n comptime {\n var arena = std.heap.ArenaAllocator.init(std.heap.page_allocator);\n defer arena.deinit();\n\n for (module_names) |module_name, i| {\n const module = @import(module_name); // no errors here\n log.info(\"i {}\", .{i});\n try module.main();\n }\n }\n}\n```\n\nHere `@import(module_name)` gives me no errors, but the `log.info` fails with this other error:\n\n```\n/home/jack/.zig/lib/zig/std/mutex.zig:59:87: error: unable to evaluate constant expression\n if (@cmpxchgWeak(usize, &self.state, 0, MUTEX_LOCK, .Acquire, .Monotonic) != null)\n ^\n/home/jack/.zig/lib/zig/std/mutex.zig:65:35: note: called from here\n return self.tryAcquire() orelse {\n ^\n/home/jack/.zig/lib/zig/std/log.zig:145:60: note: called from here\n const held = std.debug.getStderrMutex().acquire();\n ^\n/home/jack/.zig/lib/zig/std/log.zig:222:16: note: called from here\n log(.info, scope, format, args);\n ^\n./src/main.zig:26:21: note: called from here\n log.info(\"i {}\", .{i});\n```\n\nIs this kind of dynamic import possible in zig?\n\n========================================\n\nTop Answer:\nAs of Zig 0.8.0, the operand to `@import` is required to be a string literal.\n\nA Zig compiler wants to know all the possibly imported files so that it can eagerly go find them and compile them when you kick off a compilation process. The design of the language is constrained by making it possible for a fast compiler to exist.\n\nSo what can we do? I think this accomplishes the task in an equivalent manner:\n\n```\nconst std = @import(\"std\");\nconst log = std.log;\n\nconst modules = struct {\n pub const module_01 = @import(\"01.zig\");\n pub const module_02 = @import(\"02.zig\");\n pub const module_03 = @import(\"03.zig\");\n pub const module_04 = @import(\"04.zig\");\n pub const module_05 = @import(\"05.zig\");\n};\n\npub fn main() void {\n var arena = std.heap.ArenaAllocator.init(std.heap.page_allocator);\n defer arena.deinit();\n\n inline for (@typeInfo(modules).Struct.decls) |decl, i| {\n const module = @field(modules, decl.name);\n log.info(\"i {d}\", .{i});\n try module.main();\n }\n}\n```\n\nAnd the neat thing here is that, indeed, the compiler is able to eagerly fetch all 5 of those files and kick-start the compilation process, even before running the compile-time code to determine which one actually gets imported. Win-win.\n\n========================================\n\nCode:\n```text\nconst std = @import(\"std\");\nconst log = std.log;\n\nconst module_names = [_][]const u8{\n \"01.zig\", \"02.zig\", \"03.zig\", \"04.zig\", \"05.zig\",\n};\n\npub fn main() void {\n var arena = std.heap.ArenaAllocator.init(std.heap.page_allocator);\n defer arena.deinit();\n\n for (module_names) |module_name, i| {\n const module = @import(module_name); // this fails\n log.info(\"i {}\", .{i});\n try module.main();\n }\n}\n```\n\n```text\n./src/main.zig:13:32: error: unable to evaluate constant expression\n const module = @import(module_name);\n ^\n./src/main.zig:13:24: note: referenced here\n const module = @import(module_name);\n```\n\n```text\npub fn main() void {\n comptime {\n var arena = std.heap.ArenaAllocator.init(std.heap.page_allocator);\n defer arena.deinit();\n\n for (module_names) |module_name, i| {\n const module = @import(module_name); // no errors here\n log.info(\"i {}\", .{i});\n try module.main();\n }\n }\n}\n```\n\n```text\n/home/jack/.zig/lib/zig/std/mutex.zig:59:87: error: unable to evaluate constant expression\n if (@cmpxchgWeak(usize, &self.state, 0, MUTEX_LOCK, .Acquire, .Monotonic) != null)\n ^\n/home/jack/.zig/lib/zig/std/mutex.zig:65:35: note: called from here\n return self.tryAcquire() orelse {\n ^\n/home/jack/.zig/lib/zig/std/log.zig:145:60: note: called from here\n const held = std.debug.getStderrMutex().acquire();\n ^\n/home/jack/.zig/lib/zig/std/log.zig:222:16: note: called from here\n log(.info, scope, format, args);\n ^\n./src/main.zig:26:21: note: called from here\n log.info(\"i {}\", .{i});\n```\n\n```text\n0.7.0.\n```\n\n```text\nmain\n```\n\n```text\n!void\n```\n\n```text\nmodule_names\n```\n\n```text\n@import(module_name)\n```\n\n```text\nmodule_names\n```\n\n```text\nmain\n```\n\n```text\ncomptime\n```\n\n```text\n@import(module_name)\n```\n\n```text\nlog.info\n```\n\n```text\npub fn main() !void {\n var arena = std.heap.ArenaAllocator.init(std.heap.page_allocator);\n defer arena.deinit();\n\n inline for (module_names) |module_name, i| {\n const module = @import(module_name);\n log.info(\"i {}\", .{i});\n try module.main();\n }\n}\n```\n\n```text\n@import\n```\n\n```text\nzig\n```\n\n```text\n@import\n```\n\n```text\ncomptime\n```\n\n```text\nmodule_name\n```\n\n```text\ncomptime\n```\n\n```text\nfor\n```\n\n```text\ncomptime\n```\n\n```text\nlog\n```\n\n```text\ncomptime\n```\n\n```text\nconst std = @import(\"std\");\nconst log = std.log;\n\nconst modules = struct {\n pub const module_01 = @import(\"01.zig\");\n pub const module_02 = @import(\"02.zig\");\n pub const module_03 = @import(\"03.zig\");\n pub const module_04 = @import(\"04.zig\");\n pub const module_05 = @import(\"05.zig\");\n};\n\npub fn main() void {\n var arena = std.heap.ArenaAllocator.init(std.heap.page_allocator);\n defer arena.deinit();\n\n inline for (@typeInfo(modules).Struct.decls) |decl, i| {\n const module = @field(modules, decl.name);\n log.info(\"i {d}\", .{i});\n try module.main();\n }\n}\n```\n\n```text\n@import\n```\n\n========================================\n\nComments:\n- `inline for` is the right way to do this if you need to do runtime stuff in the loop too.\n- Yes, it looks like `inline for` is the right construct to use here. I also tried to build an `ArrayList` by appending `module_name` in a `comptime` block, but that didn't work. I also realized that the title of my question is a bit misleading: since I know the modules at compile time, I am not importing them dynamically at all. I still don't know if actual dynamic imports (i.e. imports at runtime) are supported in zig.","metadata":{"transformedAt":"2026-08-18T18:33:48.841Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":27,"totalLines":303,"estimatedTokens":1870}}20{"id":"stack-75957413","source":"stackoverflow","questionId":75957413,"title":"Formating strings with comptime values in Zig","tags":["string","formatting","metaprogramming","zig"],"text":"Title: Formating strings with comptime values in Zig\nTags: string, formatting, metaprogramming, zig\nSource: Stack Overflow\n\nQuestion:\nI am trying to create a polymorphic function that accepts only built-in vectors (as in `@Vector`) of length 4. The length of a vector is comptime-known, so I would like to add more information in the compile time error message. `@typeName` can be used to convert types to comptime strings, but what can one use for comptime values?\n\n```\n/// v[3] == 1\n/// v must be a built-in vector of length 4\npub fn ispoint(v: anytype) bool {\n const T = @TypeOf(v);\n switch (@typeInfo(T)) {\n .Vector => |info| {\n if (info.len != 4) {\n // TODO: report length of provided argument\n @compileError(\"Not a valid tuple, found Vector of length ???\");\n }\n return v[3] == 1;\n },\n else => @compileError(\"`ispoint` expected a `@Vector(4, T)`, found \" ++ @typeName(T)),\n }\n}\n```\n\n========================================\n\nCode:\n```none\n/// v[3] == 1\n/// v must be a built-in vector of length 4\npub fn ispoint(v: anytype) bool {\n const T = @TypeOf(v);\n switch (@typeInfo(T)) {\n .Vector => |info| {\n if (info.len != 4) {\n // TODO: report length of provided argument\n @compileError(\"Not a valid tuple, found Vector of length ???\");\n }\n return v[3] == 1;\n },\n else => @compileError(\"`ispoint` expected a `@Vector(4, T)`, found \" ++ @typeName(T)),\n }\n}\n```\n\n```text\n@Vector\n```\n\n```text\n@typeName\n```\n\n```none\n@compileError(\n std.fmt.comptimePrint(\n \"Not a valid tuple, found a vector of length {}\",\n .{info.len}\n )\n);\n```\n\n```text\ncomptimePrint\n```\n\n```text\nstd.fmt\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.841Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":6,"totalLines":70,"estimatedTokens":422}}21{"id":"stack-65187214","source":"stackoverflow","questionId":65187214,"title":"zig creates a C library but not usable by C","tags":["c","zig"],"text":"Title: zig creates a C library but not usable by C\nTags: c, zig\nSource: Stack Overflow\n\nQuestion:\nI'm able to get Zig to create a C library but when I attempt to use said library from a C program, it fails to find the definition of the included function.\n\nMy library definition:\n\n```\nconst std = @import(\"std\");\n\nexport fn removeAll(name: [*]const u8, len: u32) u32 {\n const n: []const u8 = name[0..len];\n std.fs.cwd().deleteTree(n) catch |err| {\n return 1;\n };\n return 0;\n}\n\ntest \"basic remove functionality\" {\n}\n```\n\nbuild.zig\n\n```\nconst Builder = @import(\"std\").build.Builder;\n\npub fn build(b: *Builder) void {\n const mode = b.standardReleaseOptions();\n const lib = b.addStaticLibrary(\"removeall\", \"src/main.zig\");\n lib.setBuildMode(mode);\n switch (mode) {\n .Debug, .ReleaseSafe => lib.bundle_compiler_rt = true,\n .ReleaseFast, .ReleaseSmall => lib.disable_stack_probing = true,\n }\n lib.force_pic = true;\n lib.setOutputDir(\"build\");\n lib.install();\n\n var main_tests = b.addTest(\"src/main.zig\");\n main_tests.setBuildMode(mode);\n\n const test_step = b.step(\"test\", \"Run library tests\");\n test_step.dependOn(&main_tests.step);\n}\n```\n\n`zig build` creates the build directory with the `libremoveall.a` static library.\n\nMy C program:\n\n```\n#include \n\nint removeAll(char *, int);\n\nint main(int argc, char **argv)\n{\n removeAll(\"/tmp/mytest/abc\", 15);\n return 0;\n}\n```\n\nWhen I attempt to include it in my C program, it get the following error:\n\n```\ngcc -o main build/libremoveall.a main.c\n/usr/bin/ld: /tmp/cckS27fw.o: in function 'main':\nmain.c:(.text+0x20): undefined reference to 'removeAll'\n```\n\nAny ideas on what I'm doing wrong?\nThanks\n\n**EDIT**\n\nThanks Paul R and stark, flipping the order worked. Can you help me understand why the order matter?\n\n========================================\n\nCode:\n```text\nconst std = @import(\"std\");\n\nexport fn removeAll(name: [*]const u8, len: u32) u32 {\n const n: []const u8 = name[0..len];\n std.fs.cwd().deleteTree(n) catch |err| {\n return 1;\n };\n return 0;\n}\n\ntest \"basic remove functionality\" {\n}\n```\n\n```text\nconst Builder = @import(\"std\").build.Builder;\n\npub fn build(b: *Builder) void {\n const mode = b.standardReleaseOptions();\n const lib = b.addStaticLibrary(\"removeall\", \"src/main.zig\");\n lib.setBuildMode(mode);\n switch (mode) {\n .Debug, .ReleaseSafe => lib.bundle_compiler_rt = true,\n .ReleaseFast, .ReleaseSmall => lib.disable_stack_probing = true,\n }\n lib.force_pic = true;\n lib.setOutputDir(\"build\");\n lib.install();\n\n var main_tests = b.addTest(\"src/main.zig\");\n main_tests.setBuildMode(mode);\n\n const test_step = b.step(\"test\", \"Run library tests\");\n test_step.dependOn(&main_tests.step);\n}\n```\n\n```text\n#include <stdio.h>\n\nint removeAll(char *, int);\n\nint main(int argc, char **argv)\n{\n removeAll(\"/tmp/mytest/abc\", 15);\n return 0;\n}\n```\n\n```text\ngcc -o main build/libremoveall.a main.c\n/usr/bin/ld: /tmp/cckS27fw.o: in function 'main':\nmain.c:(.text+0x20): undefined reference to 'removeAll'\n```\n\n```text\nzig build\n```\n\n```text\nlibremoveall.a\n```\n\n========================================\n\nComments:\n- Try switching the order of main.c and the lib on your command line.\n- put the library after main.c\n- I also suggest objdump -ing the .a file to be sure the function is actually there as well.","metadata":{"transformedAt":"2026-08-18T18:33:48.841Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":6,"totalLines":153,"estimatedTokens":830}}22{"id":"stack-79776806","source":"stackoverflow","questionId":79776806,"title":"Using zig to compile C to web assembly","tags":["c","webassembly","zig"],"text":"Title: Using zig to compile C to web assembly\nTags: c, webassembly, zig\nSource: Stack Overflow\n\nQuestion:\nI believe that it should be possible to use zig to compile a simple c library to web assembly.\n\nI am using the following c code\n\n```\n// add.c\nint add (int first, int second)\n{\n return first + second;\n}\n```\n\nOnce compiled to web assembly I am trying to run it in the browser using the following HTML.\n\n```\n\n \n \n \n (async() => {\n const response = await fetch('add.wasm');\n const bytes = await response.arrayBuffer();\n const { instance } = await WebAssembly.instantiate(bytes);\n\n console.log('The answer is: ' + instance.exports.add(1, 2));\n })();\n \n \n\n```\n\nTo compile the code I have been using a command similar to:\n\n```\n$ zig cc --target=wasm32-freestanding -Wl,--no-entry -Wl,--export-all-symbols -o add.wasm add.c\n```\n\nHowever when I look at the output in the browser console I get the error message `Uncaught (in promise) TypeError: instance.exports.add is not a function`. This implies that the function `add` is being optimised away or not exported.\n\nI have tried adding the `-shared` and `-dynamic` switches to the command line and these are not supported for the web assembly target (at least for the version of zig I am using).\n\nIs there a way to ensure that `add` gets exported?\n\nI serve up the HTML and compiled add.wasm using `python -m http.server`.\n\nI am using zig 0.15.1. At the time of writing this is the latest release other than the nightly build.\n\n========================================\n\nCode:\n```text\n// add.c\nint add (int first, int second)\n{\n return first + second;\n}\n```\n\n```text\n<!DOCTYPE html>\n<!-- add.html -->\n<html>\n <head></head>\n <body>\n <script type=\"module\">\n (async() => {\n const response = await fetch('add.wasm');\n const bytes = await response.arrayBuffer();\n const { instance } = await WebAssembly.instantiate(bytes);\n\n console.log('The answer is: ' + instance.exports.add(1, 2));\n })();\n </script>\n </body>\n</html>\n```\n\n```text\n$ zig cc --target=wasm32-freestanding -Wl,--no-entry -Wl,--export-all-symbols -o add.wasm add.c\n```\n\n```text\nUncaught (in promise) TypeError: instance.exports.add is not a function\n```\n\n```text\nadd\n```\n\n```text\n-shared\n```\n\n```text\n-dynamic\n```\n\n```text\nadd\n```\n\n```text\npython -m http.server\n```\n\n```text\nzig cc -target wasm32-freestanding -Wl,--no-entry -Wl,--export=add -o add.wasm add.c\n```\n\n```text\n--export-all-symbols\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.841Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":11,"totalLines":117,"estimatedTokens":613}}23{"id":"stack-71298820","source":"stackoverflow","questionId":71298820,"title":"Create a struct with String parameter","tags":["string","compiler-errors","zig"],"text":"Title: Create a struct with String parameter\nTags: string, compiler-errors, zig\nSource: Stack Overflow\n\nQuestion:\nI just want to create a struct with variable String (utf-8 text).\n\n```\nconst Person = struct {\n name: [_]u8, \n\n};\n```\n\nIs it possible? Or I have to set maximum length of string (e.g. `name: [255]u8;`)? When I pass to compiler it says:\n\n```\nperson.zig:5:12: error: unable to infer array size\n name: [_]u8,\n```\n\nAnyway I miss native String type instead of having to handle with bytes. Is there any library for that?\n\n========================================\n\nCode:\n```text\nconst Person = struct {\n name: [_]u8, \n\n};\n```\n\n```text\nperson.zig:5:12: error: unable to infer array size\n name: [_]u8,\n```\n\n```text\nname: [255]u8;\n```\n\n```text\nconst Person = struct {\n name: []const u8,\n};\n```\n\n```text\nconst std = @import(\"std\");\n\nconst Person = struct {\n name: std.ArrayList(u8),\n};\n\ntest \"person\" {\n const allocator = std.testing.allocator;\n\n var person: Person = .{\n .name = std.ArrayList(u8).init(allocator),\n };\n defer person.name.deinit();\n try person.name.appendSlice(\"First \");\n try person.name.appendSlice(\"Last\");\n try person.name.writer().print(\". Formatted string: {s}\", .{\"demo\"});\n\n try std.testing.expectEqualSlices(u8, \"First Last. Formatted string: demo\", person.name.items);\n}\n```\n\n```text\n[]u8\n```\n\n```text\n[]const u8\n```\n\n========================================\n\nComments:\n- `name: []const u8,` works but ` name: [] u8,` does not\n- @somenxavier `[]u8` is for a mutable slice of bytes. It doesn't work if you pass a double quoted string to it because those are `[]const u8` and stored in readonly memory in the program's data section.","metadata":{"transformedAt":"2026-08-18T18:33:48.841Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":7,"totalLines":83,"estimatedTokens":426}}24{"id":"stack-72709702","source":"stackoverflow","questionId":72709702,"title":"How do I get the full path of a `std.fs.Dir`?","tags":["zig"],"text":"Title: How do I get the full path of a `std.fs.Dir`?\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nIs there any way to access the full path of a `std.fs.Dir` struct? I've looked through all of the methods in the source but I can't find anything that gets path-related information on the directory.\n\n========================================\n\nCode:\n```text\nstd.fs.Dir\n```\n\n```none\nconst std = @import(\"std\");\n\npub fn main() !void {\n var arena = std.heap.ArenaAllocator.init(std.heap.page_allocator);\n defer arena.deinit();\n const alloc = arena.allocator();\n\n std.log.info(\"cwd: {s}\", .{\n try std.fs.cwd().realpathAlloc(alloc, \".\"),\n });\n}\n```\n\n```text\nrealpath\n```\n\n```text\nstd.os.getFdPath\n```\n\n========================================\n\nComments:\n- Ah, I didn't realize that it would work for just having `\".\"` as the input path. Thank you!\n- The creator of Zig has a proposal to remove this function and many contributors agree with it, do note it is subject to removal\n- It's not likely to be removed as long as Zig wants to maintain compatibility with c libraries (which do need full real paths)","metadata":{"transformedAt":"2026-08-18T18:33:48.841Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":4,"totalLines":42,"estimatedTokens":280}}25{"id":"stack-79337517","source":"stackoverflow","questionId":79337517,"title":"Constant struct fields in Zig","tags":["zig"],"text":"Title: Constant struct fields in Zig\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nDabbling with Zig and have a question about const fields in structs. In the simple struct below I have started to implement a simple matrix data structure. Presumably once I have instantiated a Matrix, the `rows` and `columns` fields will never change (and maybe this should be true for `data` too). However, my understanding is that Zig will only allow constant struct members if they are `comptime`. But there are many cases where the dimensions of my matrix will only be known at runtime (e.g. reading the data from a file) but should remain constant thereafter. Is there any way to enforce constness of the struct members?\n\n```\npub const Matrix = struct {\n\n rows: u32,\n cols: u32,\n data: []const f32,\n\n /// Creates an uninitialized Matrix\n pub fn new(rows: u32, cols: u32) !Matrix {\n const data = try std.heap.page_allocator.alloc(f32, rows*cols);\n return Matrix{\n .rows = rows,\n .cols = cols,\n .data = data,\n };\n }\n\n}\n```\n\n========================================\n\nCode:\n```text\npub const Matrix = struct {\n\n rows: u32,\n cols: u32,\n data: []const f32,\n\n /// Creates an uninitialized Matrix\n pub fn new(rows: u32, cols: u32) !Matrix {\n const data = try std.heap.page_allocator.alloc(f32, rows*cols);\n return Matrix{\n .rows = rows,\n .cols = cols,\n .data = data,\n };\n }\n\n}\n```\n\n```text\nrows\n```\n\n```text\ncolumns\n```\n\n```text\ndata\n```\n\n```text\ncomptime\n```\n\n```text\nconst\n```\n\n```text\nconst\n```\n\n```text\nconst\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.841Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":8,"totalLines":77,"estimatedTokens":392}}26{"id":"stack-77247871","source":"stackoverflow","questionId":77247871,"title":"How do I initialize a slice of slices in Zig?","tags":["slice","zig"],"text":"Title: How do I initialize a slice of slices in Zig?\nTags: slice, zig\nSource: Stack Overflow\n\nQuestion:\nI'm trying to initialize a slice of slices of strings -- i.e. a `[][][]const u8`, but it doesn't seem to be possible:\n\n```\nvar x: [][][]const u8 = [][][]const u8{};\n```\n\nThis the compiler to say: `error: type '[][][]const u8' does not support array initialization syntax`.\n\n```\nvar x: [][][]const u8 = .{};\n```\n\nThis works with slices of one or two levels apparently, but not here: `error: expected type '[][][]const u8', found '@TypeOf(.{})`.\n\nI wanted to know how to initialize it with some elements inside, but I can't even initialize an empty one!\n\n========================================\n\nCode:\n```js\nvar x: [][][]const u8 = [][][]const u8{};\n```\n\n```js\nvar x: [][][]const u8 = .{};\n```\n\n```text\n[][][]const u8\n```\n\n```text\nerror: type '[][][]const u8' does not support array initialization syntax\n```\n\n```text\nerror: expected type '[][][]const u8', found '@TypeOf(.{})\n```\n\n```zig\nvar x: [][][]const u8 = &.{};\n```\n\n```zig\nvar y: []const []const u8 = &.{\n \"hello\",\n \"world\",\n};\n\nvar z: []const []const []const u8 = &.{\n &.{\n \"hello\",\n },\n &.{\n \"world\",\n },\n};\n```\n\n```zig\nvar w: [][][]const u8 = try allocator.alloc([][]const u8, 10);\ndefer allocator.free(w);\n// ...\n```\n\n```text\n&.{}\n```\n\n```text\nconst\n```\n\n========================================\n\nComments:\n- So after allocating I just assign to positions in the slice? Like `w[0] = ...` (presumably I'll have to allocate and assign the sub-slices too)? (I did this and it worked, just asking if this is the more idiomatic approach.)\n- The idiomatic approach is to... use what's appropriate for the situation: (a) If the data is known at compile time and won't change during execution, use `&.{ ... }`. (b) If the data is only used in the function and had has a known and reasonable maximum size, use a buffer on the stack. E.g. `var buffer: [128]u8 = undefined; const str = try std.fmt.bufPrintZ(&buffer, \"...\", .{ ... }); use_printed_string(str);` (c) If none of this applies, then using an allocator is your last choice. But even then, you can use a custom allocator like `ArenaAllocator` for more control.","metadata":{"transformedAt":"2026-08-18T18:33:48.841Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":10,"totalLines":83,"estimatedTokens":552}}27{"id":"stack-61422445","source":"stackoverflow","questionId":61422445,"title":"Malloc to a list of struct in Zig?","tags":["zig"],"text":"Title: Malloc to a list of struct in Zig?\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nHow can I dynamically allocate a memory space and get a pointer to a list of structs in Zig.\n\nLike in C :\n\n```\nstruct Foo* my_array_of_foo = (struct Foo*) malloc(10*sizeof(Foo));\n```\n\n========================================\n\nCode:\n```text\nstruct Foo* my_array_of_foo = (struct Foo*) malloc(10*sizeof(Foo));\n```\n\n```golang\nconst allocator: *std.mem.Allocator = std.heap.page_allocator; // this is not the best choice of allocator, see below.\nconst my_slice_of_foo: []Foo = try allocator.alloc(Foo, 10);\ndefer allocator.free(my_slice_of_foo);\n```\n\n```golang\npub fn main() !void {\n var gpa = std.heap.GeneralPurposeAllocator(.{}){};\n defer std.debug.assert(!gpa.deinit());\n const allocator = &gpa.allocator;\n}\n```\n\n```rs\ntest \"allocate stuff\" {\n const allocator = std.testing.allocator;\n}\n```\n\n```golang\nconst allocator = ... pick an allocator;\nvar arena_allocator = std.heap.ArenaAllocator.init(allocator);\ndefer arena_allocator.deinit();\nconst arena = &arena_allocator.allocator;\n```\n\n```text\nallocator.free(my_slice_of_foo)\n```\n\n```text\nstruct {ptr: [*]type, len: usize}\n```\n\n```text\n.create(type)\n```\n\n```text\n.alloc(type, count)\n```\n\n```text\nstd.heap.page_allocator\n```\n\n```text\n.free()\n```\n\n========================================\n\nComments:\n- You might want to add a ` catch` close after the alloc call to handle errors. For a quick workaround, just do: `const my_slice_of_foo: []Foo = allocator.alloc(Foo, 10) catch unreachable;`","metadata":{"transformedAt":"2026-08-18T18:33:48.841Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":11,"totalLines":75,"estimatedTokens":384}}28{"id":"stack-64936132","source":"stackoverflow","questionId":64936132,"title":"How do I print a UTF-16 string in Zig?","tags":["unicode","utf-16","zig"],"text":"Title: How do I print a UTF-16 string in Zig?\nTags: unicode, utf-16, zig\nSource: Stack Overflow\n\nQuestion:\nI've been trying to code a UTF-16 string structure, and although the standard library provides a `unicode` module, it doesn't seem to provide a way to print out a slice of `u16`.\nI've tried this:\n\n```\nconst std = @import(\"std\");\nconst unicode = std.unicode;\nconst stdout = std.io.getStdOut().outStream();\n\npub fn main() !void {\n const unicode_str = unicode.utf8ToUtf16LeStringLiteral(\"😎 hello! 😎\");\n try stdout.print(\"{}\\n\", .{unicode_str});\n}\n```\n\nThis outputs:\n\n```\n[12:0]u16@202e9c\n```\n\nIs there a way to print a unicode string (`[]u16`) without converting it back into a non-unicode string (`[]u8`)?\n\n========================================\n\nCode:\n```text\nconst std = @import(\"std\");\nconst unicode = std.unicode;\nconst stdout = std.io.getStdOut().outStream();\n\npub fn main() !void {\n const unicode_str = unicode.utf8ToUtf16LeStringLiteral(\"😎 hello! 😎\");\n try stdout.print(\"{}\\n\", .{unicode_str});\n}\n```\n\n```text\n[12:0]u16@202e9c\n```\n\n```text\nunicode\n```\n\n```text\nu16\n```\n\n```text\n[]u16\n```\n\n```text\n[]u8\n```\n\n```rs\nconst utf8string = try std.unicode.utf16leToUtf8Alloc(alloc, utf16le);\n```\n\n```rs\nvar writer = std.io.getStdOut().writer();\nvar it = std.unicode.Utf16LeIterator.init(utf16le);\nwhile (try it.nextCodepoint()) |codepoint| {\n var buf: [4]u8 = [_]u8{undefined} ** 4;\n const len = try std.unicode.utf8Encode(codepoint, &buf);\n try writer.writeAll(buf[0..len]);\n}\n```\n\n```text\n[]const u8\n```\n\n```text\n[]const u16\n```\n\n```text\n[]const u21\n```\n\n```text\n[]const u8\n```\n\n========================================\n\nComments:\n- who said that UTF-8 is non-Unicode? All UTF encodings (UTF-1/7/8/9/16/32...) can represent all Unicode code points\n- @phuclv I apologize, I have fallen prey to the informal use of the word \"unicode\" to mean \"non-ASCII\". (e.g. python 3 unicode support)\n- Is there a way to widen the standard output stream to utf-16?\n- @Sapphire_Brick Output streams currently write bytes and byte slices only. You can propose adding a utf-16 writer and formatter if you have a compelling use case like a platform or code that requires utf-16.","metadata":{"transformedAt":"2026-08-18T18:33:48.841Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":12,"totalLines":98,"estimatedTokens":547}}29{"id":"stack-70189554","source":"stackoverflow","questionId":70189554,"title":"How can you create a buffer of the same size as a file?","tags":["zig"],"text":"Title: How can you create a buffer of the same size as a file?\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI would like to avoid making a set size buffer because of things like a file being too big, or small enough that there is empty space in the buffer. An `ArenaAllocator` sounds promising since you can allocate more space as needed. Is there a \"proper\" way to do this, i.e. load a .json file passed as a command line argument into a buffer?\n\n========================================\n\nTop Answer:\nOn 0.10.0-dev.2345+9747303d1, here's what worked for me:\n\n```\nconst std = @import(\"std\");\n\npub fn main() !void {\n var file = try std.fs.cwd().openFile(\"test.ts\", .{ .mode = .read_only });\n const file_size = (try file.stat()).size;\n const allocator = std.heap.page_allocator;\n var buffer = try allocator.alloc(u8, file_size);\n try file.reader().readNoEof(buffer);\n\n std.debug.print(\"{s}\\n\", .{buffer});\n}\n```\n\n`OpenFlags` for `.openFile` is defined here:\nhttps://github.com/ziglang/zig/blob/master/lib/std/fs/file.zig#L80\n\n========================================\n\nCode:\n```text\nArenaAllocator\n```\n\n```none\nconst file = try std.fs.cwd().openFile(\"file.txt\", .{}));\ndefer file.close();\n\nconst file_size = (try file.stat()).size;\nconst buffer = try allocator.alloc(u8, file_size);\n```\n\n```none\ntry file.reader().readNoEof(buffer);\n```\n\n```none\nconst size_limit = std.math.maxInt(u32); // or any other suitable limit\nconst result = try file.readToEndAlloc(allocator, size_limit);\n```\n\n```text\nreadNoEof\n```\n\n```text\nFile\n```\n\n```text\nreadToEndAlloc\n```\n\n```rs\nconst std = @import(\"std\");\n\npub fn main() !void {\n var gpa = std.heap.GeneralPurposeAllocator(.{}){};\n defer _ = gpa.deinit();\n const allocator = &gpa.allocator;\n const args = try std.process.argsAlloc(allocator);\n defer std.process.argsFree(allocator, args);\n const file = try std.fs.cwd().openFile(args[1], .{});\n const file_content = try file.readToEndAlloc(allocator, 1024 * 1024); // 1MB max read size\n defer allocator.free(file_content);\n std.debug.print(\"{s}\", .{file_content});\n}\n```\n\n```text\nGeneralPurposeAllocator\n```\n\n```rs\nconst std = @import(\"std\");\n\npub fn main() !void {\n var file = try std.fs.cwd().openFile(\"test.ts\", .{ .mode = .read_only });\n const file_size = (try file.stat()).size;\n const allocator = std.heap.page_allocator;\n var buffer = try allocator.alloc(u8, file_size);\n try file.reader().readNoEof(buffer);\n\n std.debug.print(\"{s}\\n\", .{buffer});\n}\n```\n\n```text\nOpenFlags\n```\n\n```text\n.openFile\n```\n\n```text\nconst std = @import(\"std\");\n\npub fn main() !void {\n var gpa = std.heap.GeneralPurposeAllocator(.{}){};\n defer _ = gpa.deinit();\n const allocator = &gpa.allocator();\n var file = try std.fs.cwd().openFile(\"./sample.txt\", .{});\n const file_content = try file.readToEndAlloc(allocator.*, 10 * 1024 * 1024); // 10MB read\n defer allocator.free(file_content);\n std.debug.print(\"{s}\", .{file_content});\n}\n```\n\n```rust\nconst std = @import(\"std\");\n\nfn readFile(gpa: std.mem.Allocator, filename: []const u8) ![]u8 {\n const file = try std.fs.cwd().openFile(filename, .{ .mode = .read_only });\n defer file.close();\n\n // Buffer unneeded since we're using allocRemaining()\n var file_reader = file.reader(&.{});\n return file_reader.interface.allocRemaining(gpa, .unlimited);\n}\n\n\npub fn main() !void {\n const alloc = std.heap.smp_allocator;\n const filename = \"test.txt\";\n\n const contents = try readFile(alloc, filename);\n defer alloc.free(contents);\n\n std.debug.print(\"{s}\", .{contents});\n}\n```\n\n```text\nstd.fs.File.readToEndAlloc()\n```\n\n```text\nstd.fs.File.reader()\n```\n\n```text\nstd.Io.Reader.allocRemaining()\n```\n\n========================================\n\nComments:\n- This works in conjunction with the answer @sigod provided, thank you\n- On master 0.9.0 I had to replace `.{ open = true }` with `std.fs.O_RDONLY` but this probably works for stable\n- If the file is available at compile time, you could use the `@embedFIle` function: ziglang.org/documentation/master/#embedFile","metadata":{"transformedAt":"2026-08-18T18:33:48.841Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":17,"totalLines":163,"estimatedTokens":1014}}30{"id":"stack-73289873","source":"stackoverflow","questionId":73289873,"title":"Declaring pointer to function type, with a function name","tags":["zig"],"text":"Title: Declaring pointer to function type, with a function name\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI found a bit strange feature of Zig when I played with function pointers.\n\nHere is a simple example of a function pointer type:\n\n```\nconst std = @import(\"std\");\nconst print = std.debug.print;\n\nconst aFunc = fn (x: i32) void;\n\nfn theFunc(x: i32) void {\n print(\"have {}\\n\", .{x});\n}\n\npub fn main() void {\n const f: aFunc = theFunc;\n f(3);\n}\n```\n\nThis code compiles and runs ok.\n\nNow change it like this, adding a name to the `aFunc` type definition:\n\n```\nconst std = @import(\"std\");\nconst print = std.debug.print;\n\nconst aFunc = fn someFunc (x: i32) void;\n\nfn theFunc(x: i32) void {\n print(\"have {}\\n\", .{x});\n}\n\npub fn main() void {\n const f: aFunc = theFunc;\n f(3);\n}\n```\n\nThis code is also ok, but shouldn't the compiler emit an error or warning about **someFunc**?\nThis name is useless - when I tried to use it instead of **aFunc** there was an compilation error.\n\nCompiler version:\n\n```\n$ /opt/zig/zig version\n0.10.0-dev.3431+4a4f3c50c\n```\n\nIt looks like the zig source parser treats\n\n```\nconst aFunc = fn someFunc (x: i32) void;\n```\n\nas if it is function definition, but silently drops **someFunc**.\n\n========================================\n\nCode:\n```text\nconst std = @import(\"std\");\nconst print = std.debug.print;\n\nconst aFunc = fn (x: i32) void;\n\nfn theFunc(x: i32) void {\n print(\"have {}\\n\", .{x});\n}\n\npub fn main() void {\n const f: aFunc = theFunc;\n f(3);\n}\n```\n\n```text\nconst std = @import(\"std\");\nconst print = std.debug.print;\n\nconst aFunc = fn someFunc (x: i32) void;\n\nfn theFunc(x: i32) void {\n print(\"have {}\\n\", .{x});\n}\n\npub fn main() void {\n const f: aFunc = theFunc;\n f(3);\n}\n```\n\n```text\n$ /opt/zig/zig version\n0.10.0-dev.3431+4a4f3c50c\n```\n\n```text\nconst aFunc = fn someFunc (x: i32) void;\n```\n\n```text\naFunc\n```\n\n========================================\n\nComments:\n- This is likely a bug in zig - report it at github.com/ziglang/zig/issues . I would expect a name to not be allowed in a function type\n- bug report created github.com/ziglang/zig/issues/12660\n- FYI the bug was fixed already.\n- I know, It was fixed next day after I reported it","metadata":{"transformedAt":"2026-08-18T18:33:48.841Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":5,"totalLines":118,"estimatedTokens":548}}31{"id":"stack-77253648","source":"stackoverflow","questionId":77253648,"title":"Is there a way to initialize an array or slice of bytes to zeroes in Zig?","tags":["arrays","byte","slice","zero","zig"],"text":"Title: Is there a way to initialize an array or slice of bytes to zeroes in Zig?\nTags: arrays, byte, slice, zero, zig\nSource: Stack Overflow\n\nQuestion:\nApparently Zig used to provide this feature in an easy way, but it was removed in `6a5e61`.\n\nWhat is the recommended approach now for when such a behavior is needed? To manually iterate through the array/slice and set all bytes to zero?\n\n========================================\n\nTop Answer:\nas of Zig 0.11 (dunno when this was introduced), you can use the pattern repeat operator `**` like so:\n\n```\nconst array_of_zeroes = [_]u32{0} ** 10;\n```\n\nThis works with more complicated contents, too:\n\n```\nconst things = [_]Thing{Thing.init()} ** 10;\nconst text = \"ab\" ** 15; // ababababab...\n```\n\n========================================\n\nCode:\n```text\n6a5e61\n```\n\n```text\nvar a: [10]u8 = undefined;\n@memset(&a, 0);\n// or\n// var a = std.mem.zeroes([10]u8);\n\nstd.log.info(\"{any}\", .{ a });\n```\n\n```text\ninfo: { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }\n```\n\n```text\nstd.mem.zeroes\n```\n\n```text\n@memset\n```\n\n```text\nconst array_of_zeroes = [_]u32{0} ** 10;\n```\n\n```text\nconst things = [_]Thing{Thing.init()} ** 10;\nconst text = \"ab\" ** 15; // ababababab...\n```\n\n```text\n**\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.841Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":8,"totalLines":65,"estimatedTokens":303}}32{"id":"stack-74173508","source":"stackoverflow","questionId":74173508,"title":"How do I pass a stream or writer parameter to a function in Zig?","tags":["zig"],"text":"Title: How do I pass a stream or writer parameter to a function in Zig?\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI'm trying to pass the output stream to a function but can't get it right. This sample code shows a couple of the things I've tried\n\n```\n// Attempts to pass stream or writer to a function\nconst std = @import(\"std\");\npub fn main() !void {\n\n // #1\n try print1(std.io.getStdOut(), \"Hello, \");\n\n // #2\n try print2(std.io.getStdOut().writer(), \"world!\");\n\n}\n\n// error: 'File' is not marked 'pub'\npub fn print1(file: std.io.File, str: []const u8) !void\n{\n try file.writer().print(\"{s}\", .{str});\n}\n\n// error: expected type 'type', found 'fn(comptime type, comptime type, comptime anytype) type'\nfn print2(writer: std.io.Writer, str: []const u8) !void\n{\n try writer.print(\"{s}\", .{str});\n}\n```\n\nI'm using Zig 0.10.0\n\n========================================\n\nTop Answer:\n`io.Writer` is a generic data structure. I.e. it's a function that returns a type. You cannot use it as a function argument, but you can:\n\n- Use `anytype`.\n\n- Use an alias, like `fs.File.Writer`.\n\n- Use a \"proxy\" type, like `fs.File`, on which you'll call `writer()`.\n\n- Use full specialization, like `io.Writer(fs.File, fs.File.WriteError, fs.File.write)`.\n\n`anytype` is required for functions that must accept arbitrary writers. Otherwise, it might be nicer to use an alias or a \"proxy\" type.\n\n========================================\n\nCode:\n```js\n// Attempts to pass stream or writer to a function\nconst std = @import(\"std\");\npub fn main() !void {\n\n // #1\n try print1(std.io.getStdOut(), \"Hello, \");\n\n // #2\n try print2(std.io.getStdOut().writer(), \"world!\");\n\n}\n\n// error: 'File' is not marked 'pub'\npub fn print1(file: std.io.File, str: []const u8) !void\n{\n try file.writer().print(\"{s}\", .{str});\n}\n\n// error: expected type 'type', found 'fn(comptime type, comptime type, comptime anytype) type'\nfn print2(writer: std.io.Writer, str: []const u8) !void\n{\n try writer.print(\"{s}\", .{str});\n}\n```\n\n```text\nconst std = @import(\"std\");\n\npub fn main() !void {\n const stdout = std.io.getStdOut();\n const writer = stdout.writer();\n\n // #1\n // Pass `stdout` to a function:\n try print1(stdout, \"Hello, \");\n\n // #2\n // Pass a `Writer` to a function:\n try print2(writer, \"world!\\n\");\n\n // #3\n // Pass a `Writer` to a function:\n try print3(writer, \"Hello, again!\\n\");\n}\n\nfn print1(file: std.fs.File, str: []const u8) !void {\n try file.writer().print(\"{s}\", .{str});\n}\n\n// Explicit type annotation for `writer`:\nfn print2(writer: std.fs.File.Writer, str: []const u8) !void {\n try writer.print(\"{s}\", .{str});\n}\n\n// The type of `writer` is inferred when the function is called:\nfn print3(writer: anytype, str: []const u8) !void {\n try writer.print(\"{s}\", .{str});\n}\n```\n\n```none\n$ zig run print_stream.zig \nHello, world!\nHello, again!\n```\n\n```text\nstd.io.getStdOut()\n```\n\n```text\nFile\n```\n\n```text\nFile\n```\n\n```text\nstd.fs\n```\n\n```text\nstd.io.getStdOut().writer()\n```\n\n```text\nWriter\n```\n\n```text\nstd.fs.File\n```\n\n```text\nwriter\n```\n\n```text\nanytype\n```\n\n```text\nio.Writer\n```\n\n```text\nanytype\n```\n\n```text\nfs.File.Writer\n```\n\n```text\nfs.File\n```\n\n```text\nwriter()\n```\n\n```text\nio.Writer(fs.File, fs.File.WriteError, fs.File.write)\n```\n\n```text\nanytype\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.842Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":19,"totalLines":183,"estimatedTokens":819}}33{"id":"stack-56792050","source":"stackoverflow","questionId":56792050,"title":"How to include (msvc) libc when building c code with the Zig compiler","tags":["windows","build","libc","zig"],"text":"Title: How to include (msvc) libc when building c code with the Zig compiler\nTags: windows, build, libc, zig\nSource: Stack Overflow\n\nQuestion:\nI've recently discovered zig and find it very interesting. I'm now trying to learn how to use zig as a cross compiler and, the following builds and runs fine (on Windows)\n\n```\nzig cc -Wno-everything src/ctest.c\n```\n\nhowever, when I use the build-exe command or build script, the (Windows) libc cannot be found and linked \n\n```\nc:\\zigctest>zig build\n\nZig is unable to provide a libc for the chosen target 'x86_64-unknown-windows-msvc'.\nThe target is non-native, so Zig also cannot use the native libc installation.\nChoose a target which has a libc available, or provide a libc installation text file.\nSee `zig libc --help` for more details.\nThe following command exited with error code 1:\nc:\\zigctest\\zig.exe build-exe --library c --c-source -Wno-everything C:\\zigctest\\src\\ctest.c --cache-dir C:\\zigctest\\zig-cache --name ctest -target x86_64-windows-msvc --cache on\nexec failed\nC:\\zigctest\\lib\\zig\\std\\build.zig:768:36: 0x7ff76fece654 in std.build.Builder::std.build.Builder.exec (build.obj)\n std.debug.panic(\"exec failed\")\n...\n```\n\nIf I could see what zig cc really does, maybe I could figure it out (but zig cc does not seem to allow the --verbose-cc flag). Or how can I get zig to link with msvc (or any other working libc) on Windows? For completeness, the build.zig script is effectively:\n\n```\n...\nconst cflags = [][]const u8{\n\"-Wno-everything\",\n};\n\nconst exe = b.addExecutable(\"ctest\", null);\nexe.linkSystemLibrary(\"c\");\nexe.setBuildMode(mode);\nexe.setTarget(builtin.Arch.x86_64, .windows, .msvc);\nexe.addCSourceFile(\"src/ctest.c\",cflags);\n...\n```\n\n========================================\n\nCode:\n```text\nzig cc -Wno-everything src/ctest.c\n```\n\n```text\nc:\\zigctest>zig build\n\nZig is unable to provide a libc for the chosen target 'x86_64-unknown-windows-msvc'.\nThe target is non-native, so Zig also cannot use the native libc installation.\nChoose a target which has a libc available, or provide a libc installation text file.\nSee `zig libc --help` for more details.\nThe following command exited with error code 1:\nc:\\zigctest\\zig.exe build-exe --library c --c-source -Wno-everything C:\\zigctest\\src\\ctest.c --cache-dir C:\\zigctest\\zig-cache --name ctest -target x86_64-windows-msvc --cache on\nexec failed\nC:\\zigctest\\lib\\zig\\std\\build.zig:768:36: 0x7ff76fece654 in std.build.Builder::std.build.Builder.exec (build.obj)\n std.debug.panic(\"exec failed\")\n...\n```\n\n```text\n...\nconst cflags = [][]const u8{\n\"-Wno-everything\",\n};\n\nconst exe = b.addExecutable(\"ctest\", null);\nexe.linkSystemLibrary(\"c\");\nexe.setBuildMode(mode);\nexe.setTarget(builtin.Arch.x86_64, .windows, .msvc);\nexe.addCSourceFile(\"src/ctest.c\",cflags);\n...\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.842Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":3,"totalLines":79,"estimatedTokens":698}}34{"id":"stack-68461599","source":"stackoverflow","questionId":68461599,"title":"zig maxValue of integer and float types","tags":["zig"],"text":"Title: zig maxValue of integer and float types\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nzig used to have @maxValue to query the max value for integer types, but I think it was removed several versions ago. Is there a replacement? I can´t find it.\n\n========================================\n\nCode:\n```text\nstd.math.maxInt()\n```\n\n========================================\n\nComments:\n- The link is broken. Here; ziglang.org/documentation/master/std/#std.math.maxInt","metadata":{"transformedAt":"2026-08-18T18:33:48.842Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":1,"totalLines":18,"estimatedTokens":116}}35{"id":"stack-77192323","source":"stackoverflow","questionId":77192323,"title":"How to import zig module from another module?","tags":["import","build","zig"],"text":"Title: How to import zig module from another module?\nTags: import, build, zig\nSource: Stack Overflow\n\nQuestion:\nAssuming following folder structure:\n\n```\nsrc/\n lib.zig\n module_a/\n file_a.zig\n file_a_test.zig\n module_b/\n file_b.zig\n file_b_test.zig\n tools/\n tools.zig\n tools_test.zig\n```\n\nHow should I structure my `build.zig` in order to be somehow able to use:\n\n```\nconst tools = @import(\"tools\")\n```\n\nin my two other modules: `module_a` and `module_b`?\n\nI also want to be able to run the tests somehow, so they don't break, for example in this fassion:\n\n```\nzig test src/module_a/file_a_test.zig\n```\n\nThis is NOT an application, I don't have a `main.zig` file.\nI can have a `lib.zig` file though somewhere under `src` directory if it's needed.\n\nTried to look for a simple answer on Reddit and on StackOverflow, but couldn't find any. All the solutions use either an old `std.build.Pkg` system, or `b.addModule` but with a `main.zig` build target.\n\n========================================\n\nTop Answer:\nI am brand new to Zig - so hoping that I am not helping somebody into the ditch but I have had trouble with this (and the code above) using Zig 0.13.0. After looking into the Zig code I found the answer to be\n\nbuild.zig\n\n```\nconst u = b.createModule(.{ .root_source_file = b.path(\"src/utils/utils.zig\")});\nexe.root_module.addImport(\"utils\", u);\n```\n\nmain.zig (or other source)\n\n```\nconst utils = @import(\"utils\");\n\npub fn main() !void {\n std.debug.print(\"{}\", .{utils.A.TypeA.get_a()});\n // etc\n}\n```\n\nIn looking at the Zig build system, it is obvious that there is a lot of change, lagging documentation coupled with a whole lot of complexity which one will only conquer with hard yards. The above code may or may not be helpful to you - I merely post it as it would have been helpful to me.\n\n========================================\n\nCode:\n```text\nsrc/\n lib.zig\n module_a/\n file_a.zig\n file_a_test.zig\n module_b/\n file_b.zig\n file_b_test.zig\n tools/\n tools.zig\n tools_test.zig\n```\n\n```text\nconst tools = @import(\"tools\")\n```\n\n```text\nzig test src/module_a/file_a_test.zig\n```\n\n```text\nbuild.zig\n```\n\n```text\nmodule_a\n```\n\n```text\nmodule_b\n```\n\n```text\nmain.zig\n```\n\n```text\nlib.zig\n```\n\n```text\nsrc\n```\n\n```text\nstd.build.Pkg\n```\n\n```text\nb.addModule\n```\n\n```text\nmain.zig\n```\n\n```text\nsrc/\n lib.zig\n lib_test.zig\n module_a/\n file_a.zig\n file_a_test.zig\n module_b/\n file_b.zig\n file_b_test.zig\n tools/\n tools.zig\n tools_test.zig\n```\n\n```text\nconst std = @import(\"std\");\n\ntest {\n _ = @import(\"module_a/file_a_test.zig\");\n _ = @import(\"module_b/file_b_test.zig\");\n _ = @import(\"tools/tools_test.zig\");\n}\n\ntest \"my custom lib test\" {\n try std.testing.assert(1 == 1)\n}\n```\n\n```text\nconst std = @import(\"std\");\n\npub fn build(b: *std.Build) void {\n const target = b.standardTargetOptions(.{});\n const optimize = b.standardOptimizeOption(.{});\n\n const tools = b.addModule(\"tools\", .{ .source_file = .{ .path = \"src/tools/tools.zig\" } });\n const module_a = b.addModule(\"module-a\", .{ .source_file = .{ .path = \"src/module_a/file_a.zig\" } });\n const module_b = b.addModule(\"module-b\", .{ .source_file = .{ .path = \"src/module_b/file_b.zig\" } });\n \n const unit_tests = b.addTest(.{\n .root_source_file = .{ .path = \"src/lib_test.zig\" },\n .target = target,\n .optimize = optimize,\n });\n unit_tests.addModule(\"tools\", tools);\n unit_tests.addModule(\"module-a\", module_a);\n unit_tests.addModule(\"module-b\", module_b);\n \n const run_unit_tests = b.addRunArtifact(unit_tests);\n\n const test_step = b.step(\"test\", \"Run unit tests\");\n test_step.dependOn(&run_unit_tests.step);\n}\n```\n\n```text\nzig build test\n```\n\n```text\nlib_test.zig\n```\n\n```text\nbuild.zig\n```\n\n```text\ntools\n```\n\n```text\n.zig\n```\n\n```text\nconst u = b.createModule(.{ .root_source_file = b.path(\"src/utils/utils.zig\")});\nexe.root_module.addImport(\"utils\", u);\n```\n\n```text\nconst utils = @import(\"utils\");\n\npub fn main() !void {\n std.debug.print(\"{}\", .{utils.A.TypeA.get_a()});\n // etc\n}\n```\n\n========================================\n\nComments:\n- I've removed some unnecessary code pieces and adjusted the text below so that it resembles the code better.\n- This seems not to work when you try to import the module in another file of the project as module like @import(\"tools\"), I get en error: error: file exists in multiple modules.","metadata":{"transformedAt":"2026-08-18T18:33:48.842Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":22,"totalLines":221,"estimatedTokens":1112}}36{"id":"stack-77074657","source":"stackoverflow","questionId":77074657,"title":"How to objcopy a bin file as part of a Zig build script","tags":["zig"],"text":"Title: How to objcopy a bin file as part of a Zig build script\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nHow can I export a binary output from my elf output as part of my Zig build process?\nThis should happen as part of the default build command `zig build`.\n\nI am using Zig 0.11.\n\nMy `build.zig` contains the code below. I have added comments to describe what I *think* should be happening.\n\n```\nconst std = @import(\"std\");\nconst Builder = std.build.Builder;\n\npub fn build(b: *Builder) void {\n const optimization = std.builtin.OptimizeMode.ReleaseFast;\n const cpu_model = &std.Target.arm.cpu.cortex_m0;\n\n // elf should be a build step that emits output.elf\n const elf = b.addExecutable(.{\n .name = \"output.elf\",\n .root_source_file = .{ .path = \"src/startup.zig\" },\n .target = .{\n .cpu_arch = .thumb,\n .os_tag = .freestanding,\n .abi = .none,\n .cpu_model = .{ .explicit = cpu_model },\n },\n .optimize = optimization,\n });\n\n elf.setLinkerScript(.{ .path = \"src/STM32Z/MCU/STM32L052.ld\" });\n \n // bin should be a build step that objcopy's output.bin from output.elf\n const bin = b.addObjCopy(.{ elf.getEmittedBin(), .{\n .format = .bin,\n });\n // This step requires output.elf to exist\n bin.step.dependOn(&elf.step);\n \n // This is the step that I want to be completed when I run `zig build`.\n // I would expect zig build to generate the elf and then the bin file\n b.default_step = &bin.step;\n}\n```\n\nThis builds with no error at all. Yet a zig-out directory is not created, so I cannot find either `output.elf` or `output.bi`.\n\nI'm not really clear on:\n\n- If `elf.getEmittedBin()` is the correct thing to pass into the `b.addObjCopy` method\n\n- How to debug what steps are getting run at all.\n\n- How to declare what my output artifact is and where it should go. I assume I have to somehow specify that output.bin is the thing I want.\n\n========================================\n\nTop Answer:\nTurns out I was actually pretty close to the solution.\n\nI just needed a step to copy the bin file to my `zig-out` directory. This step was `b.addInstallBinFile(bin.getOutput(), \"output.bin\");`\n\nI was mostly confused with the nomenclature here - the build outputs seem to be referred to as \"install artifacts\" or \"install files\". This makes some sense in hindsight.\n\nMy full final build script here:\n\n```\nconst std = @import(\"std\");\nconst Builder = std.build.Builder;\n\npub fn build(b: *Builder) void {\n const optimization = std.builtin.OptimizeMode.ReleaseSmall;\n const cpu_model = &std.Target.arm.cpu.cortex_m0;\n\n // Build the elf\n const elf = b.addExecutable(.{\n .name = \"output.elf\",\n .root_source_file = .{ .path = \"src/startup.zig\" },\n .target = .{\n .cpu_arch = .thumb,\n .os_tag = .freestanding,\n .abi = .none,\n .cpu_model = .{ .explicit = cpu_model },\n },\n .optimize = optimization,\n .single_threaded = true,\n });\n elf.setLinkerScript(.{ .path = \"src/STM32Z/MCU/STM32L052.ld\" });\n\n // Copy the elf to the output directory.\n const copy_elf = b.addInstallArtifact(elf, .{});\n b.default_step.dependOn(©_elf.step);\n\n // Copy the bin out of the elf\n const bin = b.addObjCopy(elf.getEmittedBin(), .{\n .format = .bin,\n });\n bin.step.dependOn(&elf.step);\n\n // Copy the bin to the output directory\n const copy_bin = b.addInstallBinFile(bin.getOutput(), \"output.bin\");\n b.default_step.dependOn(©_bin.step);\n}\n```\n\n========================================\n\nCode:\n```none\nconst std = @import(\"std\");\nconst Builder = std.build.Builder;\n\npub fn build(b: *Builder) void {\n const optimization = std.builtin.OptimizeMode.ReleaseFast;\n const cpu_model = &std.Target.arm.cpu.cortex_m0;\n\n // elf should be a build step that emits output.elf\n const elf = b.addExecutable(.{\n .name = \"output.elf\",\n .root_source_file = .{ .path = \"src/startup.zig\" },\n .target = .{\n .cpu_arch = .thumb,\n .os_tag = .freestanding,\n .abi = .none,\n .cpu_model = .{ .explicit = cpu_model },\n },\n .optimize = optimization,\n });\n\n elf.setLinkerScript(.{ .path = \"src/STM32Z/MCU/STM32L052.ld\" });\n \n // bin should be a build step that objcopy's output.bin from output.elf\n const bin = b.addObjCopy(.{ elf.getEmittedBin(), .{\n .format = .bin,\n });\n // This step requires output.elf to exist\n bin.step.dependOn(&elf.step);\n \n // This is the step that I want to be completed when I run `zig build`.\n // I would expect zig build to generate the elf and then the bin file\n b.default_step = &bin.step;\n}\n```\n\n```text\nzig build\n```\n\n```text\nbuild.zig\n```\n\n```text\noutput.elf\n```\n\n```text\noutput.bi\n```\n\n```text\nelf.getEmittedBin()\n```\n\n```text\nb.addObjCopy\n```\n\n```none\nb.installArtifact(elf); // as normal\n\nconst bin = elf.addObjCopy(.{.format: .bin}); // no need for the elf emitted path\nconst installBin = b.addInstallBinFile(bin.getOutput(), \"output.bin\");\nb.getInstallStep().dependOn(&installBin.step);\n```\n\n```none\nconst std = @import(\"std\");\nconst Builder = std.build.Builder;\n\npub fn build(b: *Builder) void {\n const optimization = std.builtin.OptimizeMode.ReleaseSmall;\n const cpu_model = &std.Target.arm.cpu.cortex_m0;\n\n // Build the elf\n const elf = b.addExecutable(.{\n .name = \"output.elf\",\n .root_source_file = .{ .path = \"src/startup.zig\" },\n .target = .{\n .cpu_arch = .thumb,\n .os_tag = .freestanding,\n .abi = .none,\n .cpu_model = .{ .explicit = cpu_model },\n },\n .optimize = optimization,\n .single_threaded = true,\n });\n elf.setLinkerScript(.{ .path = \"src/STM32Z/MCU/STM32L052.ld\" });\n\n b.installArtifact(elf);\n\n const bin = elf.addObjCopy(.{.format: .bin});\n const installBin = b.addInstallBinFile(bin.getOutput(), \"output.bin\");\n b.getInstallStep().dependOn(&installBin.step);\n}\n```\n\n```text\nstd.Build.Step.Compile.addObjCopy\n```\n\n```text\nconst std = @import(\"std\");\nconst Builder = std.build.Builder;\n\npub fn build(b: *Builder) void {\n const optimization = std.builtin.OptimizeMode.ReleaseSmall;\n const cpu_model = &std.Target.arm.cpu.cortex_m0;\n\n // Build the elf\n const elf = b.addExecutable(.{\n .name = \"output.elf\",\n .root_source_file = .{ .path = \"src/startup.zig\" },\n .target = .{\n .cpu_arch = .thumb,\n .os_tag = .freestanding,\n .abi = .none,\n .cpu_model = .{ .explicit = cpu_model },\n },\n .optimize = optimization,\n .single_threaded = true,\n });\n elf.setLinkerScript(.{ .path = \"src/STM32Z/MCU/STM32L052.ld\" });\n\n // Copy the elf to the output directory.\n const copy_elf = b.addInstallArtifact(elf, .{});\n b.default_step.dependOn(©_elf.step);\n\n // Copy the bin out of the elf\n const bin = b.addObjCopy(elf.getEmittedBin(), .{\n .format = .bin,\n });\n bin.step.dependOn(&elf.step);\n\n // Copy the bin to the output directory\n const copy_bin = b.addInstallBinFile(bin.getOutput(), \"output.bin\");\n b.default_step.dependOn(©_bin.step);\n}\n```\n\n```text\nzig-out\n```\n\n```text\nb.addInstallBinFile(bin.getOutput(), \"output.bin\");\n```\n\n========================================\n\nComments:\n- That is way cleaner - cheers. I couldn't tell you if this was possible in zig 0.11 - the documentation was (and is) pretty poor for a lot of the stdlib api's. Part of being a new language I suppose.","metadata":{"transformedAt":"2026-08-18T18:33:48.842Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":13,"totalLines":265,"estimatedTokens":1836}}37{"id":"stack-76329659","source":"stackoverflow","questionId":76329659,"title":"How to get the field value in comptime in zig","tags":["zig"],"text":"Title: How to get the field value in comptime in zig\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI want to make a deserializer in Zig. Now I could iterate the field information in comptime. But I want to get the field default value in struct. Is there a way to get them? For example, I want to get the `zzzz`'s value `100` in `getIntOrDefault`.\n\n```\nconst std = @import(\"std\");\nconst meta = std.meta;\nconst trait = meta.trait;\nconst assert = std.debug.assert;\n\npub fn deserializeInto(ptr: anytype) !void {\n const T = @TypeOf(ptr);\n comptime assert(trait.is(.Pointer)(T));\n\n const C = comptime meta.Child(T);\n\n ptr.* = switch (C) {\n []const u8 => \"test string\",\n else => switch (@typeInfo(C)) {\n .Struct => try deserializeStruct(C),\n .Int => try getIntOrDefault(C),\n else => @compileError(\"Unsupported deserialization type \" ++ @typeName(C) ++ \"\\n\"),\n },\n };\n}\n\npub fn getIntOrDefault(comptime T: type) !T {\n return 2;\n}\n\npub fn deserializeStruct(comptime T: type) !T {\n var value: T = undefined;\n inline for (meta.fields(T)) |struct_field| {\n try deserializeInto(&@field(value, struct_field.name));\n }\n return value;\n}\n\npub fn main() !void {\n const T = struct {\n wwww: []const u8,\n zzzz: u32 = 100,\n };\n\n var v: T = undefined;\n\n try deserializeInto(&v);\n std.debug.print(\"zzzz value is {d}\\n\", .{v.zzzz});\n}\n```\n\n========================================\n\nCode:\n```text\nconst std = @import(\"std\");\nconst meta = std.meta;\nconst trait = meta.trait;\nconst assert = std.debug.assert;\n\npub fn deserializeInto(ptr: anytype) !void {\n const T = @TypeOf(ptr);\n comptime assert(trait.is(.Pointer)(T));\n\n const C = comptime meta.Child(T);\n\n ptr.* = switch (C) {\n []const u8 => \"test string\",\n else => switch (@typeInfo(C)) {\n .Struct => try deserializeStruct(C),\n .Int => try getIntOrDefault(C),\n else => @compileError(\"Unsupported deserialization type \" ++ @typeName(C) ++ \"\\n\"),\n },\n };\n}\n\npub fn getIntOrDefault(comptime T: type) !T {\n return 2;\n}\n\npub fn deserializeStruct(comptime T: type) !T {\n var value: T = undefined;\n inline for (meta.fields(T)) |struct_field| {\n try deserializeInto(&@field(value, struct_field.name));\n }\n return value;\n}\n\npub fn main() !void {\n const T = struct {\n wwww: []const u8,\n zzzz: u32 = 100,\n };\n\n var v: T = undefined;\n\n try deserializeInto(&v);\n std.debug.print(\"zzzz value is {d}\\n\", .{v.zzzz});\n}\n```\n\n```text\nzzzz\n```\n\n```text\n100\n```\n\n```text\ngetIntOrDefault\n```\n\n```text\nconst std = @import(\"std\");\n\npub fn main() !void {\n const TestStruct = struct {\n foo: u32 = 123,\n };\n std.log.info(\"{}\", .{ TestStruct{} });\n\n const foo_field = @typeInfo(TestStruct).Struct.fields[0];\n std.log.info(\"field name: {s}\", .{ foo_field.name });\n\n if (foo_field.default_value) |dvalue| {\n const dvalue_aligned: *const align(foo_field.alignment) anyopaque = @alignCast(dvalue);\n const value = @as(*const foo_field.type, @ptrCast(dvalue_aligned)).*;\n std.log.info(\"default value: {}\", .{ value });\n }\n}\n```\n\n```text\n$ zig build run\ninfo: main.main.TestStruct{ .foo = 123 }\ninfo: field name: foo\ninfo: default value: 123\n```\n\n```text\nconst dvalue_aligned = @alignCast(foo_field.alignment, dvalue);\nconst value = @ptrCast(*const foo_field.type, dvalue_aligned).*;\nstd.log.info(\"default value: {}\", .{ value });\n```\n\n```text\n@typeInfo(T).Struct.fields[...].default_value\n```\n\n```text\nanyopaque\n```\n\n```text\n@ptrCast\n```\n\n```text\n@ptrCast\n```\n\n========================================\n\nComments:\n- Is manual construction of a `Pointer` type really the only way to accomplish this?\n- I noticed that you used `.size` and `.alignment` in the code. If I don't know the type of foo, how can get those infomation and construct a Pointer type?\n- @Hanaasagi `.size` and `.alignment` and not related to the type of `foo`. Anyway, I've done some experiments and found a simpler way to do this. See updated answer.","metadata":{"transformedAt":"2026-08-18T18:33:48.842Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":11,"totalLines":171,"estimatedTokens":995}}38{"id":"stack-77550212","source":"stackoverflow","questionId":77550212,"title":"What is the type of `std.io.getStdOut().writer();` in zig?","tags":["writer","zig"],"text":"Title: What is the type of `std.io.getStdOut().writer();` in zig?\nTags: writer, zig\nSource: Stack Overflow\n\nQuestion:\nI cannot initialize a global variable with the stdout in zig:\n\n```\nvar out = std.io.getStdOut().writer();\n```\n\nThen I tried to initialize in the `fn main` and declare the global variables as optional (initialized by null).\n\nMy problem is that I don't know which is the type of `std.io.getStdOut().writer();`.\n\nI tried something like:\n\n```\nvar out: std.fs.Writer? = null\n//...\nfn main() !void {\n out = std.io.getStdOut().writer();\n //...\n out.print(\"ok: {}\", \"ok\");\n}\n```\n\nAlso I tried reflection:\n\n```\nvar stdout: @typeInfo(@TypeOf(std.io.getStdOut().writer())).Fn.return_type.? = null;\n```\n\nI need to know how I can declare a variable or a function returning a Writer (i.e. something that has the usual print function inside).\n\n### Edited\n\nTied twice using zig version 0.12.0-dev.1150+3c22cecee and 0.11.0\n\nWith writer.zig file containing:\n\n```\nconst std = @import(\"std\");\n\nvar out = std.io.getStdOut().writer();\n\npub fn main() anyerror!void {\n try out.print(\"{any}\\n\", .{@TypeOf(out)});\n}\n```\n\nI get ***error: unable to evaluate comptime expression***\n\n```\nzig build-exe writer.zig && writer.exe \nC:\\bin\\zig\\lib\\std\\os\\windows.zig:1944:28: error: unable to evaluate comptime expression\n break :blk asm volatile (\n ^~~\nC:\\bin\\zig\\lib\\std\\os\\windows.zig:1959:15: note: called from here\n return teb().ProcessEnvironmentBlock;\n ~~~^~\nC:\\bin\\zig\\lib\\std\\io.zig:37:30: note: called from here\n return os.windows.peb().ProcessParameters.hStdOutput;\n ~~~~~~~~~~~~~~^~\nC:\\bin\\zig\\lib\\std\\io.zig:51:34: note: called from here\n .handle = getStdOutHandle(),\n ~~~~~~~~~~~~~~~^~\nwriter.zig:3:27: note: called from here\nvar out = std.io.getStdOut().writer();\n ~~~~~~~~~~~~~~~~^~\nreferenced by:\n main: writer.zig:6:9\n callMain: C:\\bin\\zig\\lib\\std\\start.zig:583:32\n remaining reference traces hidden; use '-freference-trace' to see all reference traces\n```\n\n========================================\n\nCode:\n```text\nvar out = std.io.getStdOut().writer();\n```\n\n```text\nvar out: std.fs.Writer? = null\n//...\nfn main() !void {\n out = std.io.getStdOut().writer();\n //...\n out.print(\"ok: {}\", \"ok\");\n}\n```\n\n```text\nvar stdout: @typeInfo(@TypeOf(std.io.getStdOut().writer())).Fn.return_type.? = null;\n```\n\n```text\nconst std = @import(\"std\");\n\nvar out = std.io.getStdOut().writer();\n\npub fn main() anyerror!void {\n try out.print(\"{any}\\n\", .{@TypeOf(out)});\n}\n```\n\n```text\nzig build-exe writer.zig && writer.exe \nC:\\bin\\zig\\lib\\std\\os\\windows.zig:1944:28: error: unable to evaluate comptime expression\n break :blk asm volatile (\n ^~~\nC:\\bin\\zig\\lib\\std\\os\\windows.zig:1959:15: note: called from here\n return teb().ProcessEnvironmentBlock;\n ~~~^~\nC:\\bin\\zig\\lib\\std\\io.zig:37:30: note: called from here\n return os.windows.peb().ProcessParameters.hStdOutput;\n ~~~~~~~~~~~~~~^~\nC:\\bin\\zig\\lib\\std\\io.zig:51:34: note: called from here\n .handle = getStdOutHandle(),\n ~~~~~~~~~~~~~~~^~\nwriter.zig:3:27: note: called from here\nvar out = std.io.getStdOut().writer();\n ~~~~~~~~~~~~~~~~^~\nreferenced by:\n main: writer.zig:6:9\n callMain: C:\\bin\\zig\\lib\\std\\start.zig:583:32\n remaining reference traces hidden; use '-freference-trace' to see all reference traces\n```\n\n```text\nfn main\n```\n\n```text\nstd.io.getStdOut().writer();\n```\n\n```text\n% cat test.zig\n\nconst std = @import(\"std\");\n\nvar out = std.io.getStdOut().writer();\n\npub fn main() anyerror!void {\n try out.print(\"{any}\\n\", .{@TypeOf(out)});\n}\n\n% zig build-exe test.zig && ./test\nio.writer.Writer(fs.file.File,error{AccessDenied,Unexpected,DiskQuota,FileTooBig,InputOutput,NoSpaceLeft,DeviceBusy,InvalidArgument,BrokenPipe,SystemResources,OperationAborted,NotOpenForWriting,LockViolation,WouldBlock,ConnectionResetByPeer},(function 'write'))\n```\n\n========================================\n\nComments:\n- Relevant: How do I pass a stream or writer parameter to a function in Zig?\n- You are right. I must put an executable example. Also the versions of the compiler. I'm running it in Windows 11\n- My question is about what is the type of **std.io.getStdOut().writer();** because I want to create a function that can return that or a variable that was initialy `null`. I need that as an improvement of setting it initialy (something that I cannot do it in Windows).\n- Well, you have the type in the last line of my example (it does not solve the bug but at least you have the information).","metadata":{"transformedAt":"2026-08-18T18:33:48.842Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":8,"totalLines":160,"estimatedTokens":1144}}39{"id":"stack-70307231","source":"stackoverflow","questionId":70307231,"title":"How to free keys of StringHashMap?","tags":["zig"],"text":"Title: How to free keys of StringHashMap?\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI was trying\n\n```\ntest \"foo\" {\n var map = std.StringHashMap(void).init(std.testing.allocator);\n defer {\n while (map.keyIterator().next()) |key| {\n std.testing.allocator.free(key);\n }\n map.deinit();\n }\n}\n```\n\nBut got compile error\n\n```\n/snap/zig/4365/lib/std/mem.zig:2749:9: error: expected []T or *[_]T, passed *[]const u8\n @compileError(\"expected []T or *[_]T, passed \" ++ @typeName(sliceType));\n ^\n/snap/zig/4365/lib/std/mem.zig:2756:59: note: called from here\npub fn sliceAsBytes(slice: anytype) SliceAsBytesReturnType(@TypeOf(slice)) {\n ^\n/snap/zig/4365/lib/std/mem.zig:2756:59: note: called from here\npub fn sliceAsBytes(slice: anytype) SliceAsBytesReturnType(@TypeOf(slice)) {\n ^\n./main.zig:169:39: note: called from here\n std.testing.allocator.free(key);\n ^\n./main.zig:165:12: note: called from here\ntest \"foo\" {\n```\n\nHelp would be appreciated! If you could if you face the same situation, what would you search in the search engine, or find in the zig std code base to figure out the solution, would be great too! As I still have a hard time to figure out solution myself. Thank you!\n\n========================================\n\nCode:\n```text\ntest \"foo\" {\n var map = std.StringHashMap(void).init(std.testing.allocator);\n defer {\n while (map.keyIterator().next()) |key| {\n std.testing.allocator.free(key);\n }\n map.deinit();\n }\n}\n```\n\n```text\n/snap/zig/4365/lib/std/mem.zig:2749:9: error: expected []T or *[_]T, passed *[]const u8\n @compileError(\"expected []T or *[_]T, passed \" ++ @typeName(sliceType));\n ^\n/snap/zig/4365/lib/std/mem.zig:2756:59: note: called from here\npub fn sliceAsBytes(slice: anytype) SliceAsBytesReturnType(@TypeOf(slice)) {\n ^\n/snap/zig/4365/lib/std/mem.zig:2756:59: note: called from here\npub fn sliceAsBytes(slice: anytype) SliceAsBytesReturnType(@TypeOf(slice)) {\n ^\n./main.zig:169:39: note: called from here\n std.testing.allocator.free(key);\n ^\n./main.zig:165:12: note: called from here\ntest \"foo\" {\n```\n\n```text\nerror: expected []T or *[_]T, passed *[]const u8\n```\n\n```js\ntest \"foo\" {\n var map = std.StringHashMap(void).init(std.testing.allocator);\n defer {\n var keyIter = map.keyIterator();\n while (keyIter.next()) |key| {\n std.testing.allocator.free(key.*);\n }\n map.deinit();\n }\n}\n```\n\n```text\n[]const u8\n```\n\n```text\nkey.*\n```\n\n```text\nnext()\n```\n\n```text\nmap.keyIterator()\n```\n\n```text\nvar\n```\n\n========================================\n\nComments:\n- This shows me, that Zig is more like C than C++ when it comes to memory management. In a sense it's good and in another sense it's bad, as it needs such boilerplate and error-prone code.","metadata":{"transformedAt":"2026-08-18T18:33:48.842Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":9,"totalLines":113,"estimatedTokens":731}}40{"id":"stack-76647633","source":"stackoverflow","questionId":76647633,"title":"How to do generics in a struct field in zig","tags":["generics","struct","zig"],"text":"Title: How to do generics in a struct field in zig\nTags: generics, struct, zig\nSource: Stack Overflow\n\nQuestion:\nI'm very new to zig and I'm wondering how to create a struct field that can have a compile time known type\n\nfor example something similar to the `comptime` keyword when used with a function parameter, I want to do the same thing to a struct field that is an array\n\n**example of `comptime` in function:**\n\n```\nfn exampleFn(comptime t: type, allocator: std.mem.Allocator) ![]t {\n var array: []t = try allocator.alloc(t, 3);\n return array;\n}\n```\n\nhere I can specify any type to be the type of the output array (this is the best example I could come up with)\n\n**example of what I want to be able to do:**\n\n```\nconst List = struct {\n content_type: type,\n data: ?[].content_type,\n};\n```\n\nis there any way I could do something like this and still be able to use the struct in runtime?\n\n========================================\n\nCode:\n```text\nfn exampleFn(comptime t: type, allocator: std.mem.Allocator) ![]t {\n var array: []t = try allocator.alloc(t, 3);\n return array;\n}\n```\n\n```text\nconst List = struct {\n content_type: type,\n data: ?[].content_type,\n};\n```\n\n```text\ncomptime\n```\n\n```text\ncomptime\n```\n\n```zig\nconst std = @import(\"std\");\n\nfn Foo(comptime value_type: type) type {\n return struct {\n value: value_type,\n };\n}\n\nconst FooU8 = Foo(u8);\n\npub fn main() void {\n var foo = FooU8{\n .value = 1,\n };\n // foo.value = 257; // error: type 'u8' cannot represent integer value '257'\n std.log.info(\"{}\", .{ foo.value });\n}\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.842Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":5,"totalLines":75,"estimatedTokens":394}}41{"id":"stack-67769916","source":"stackoverflow","questionId":67769916,"title":"Search ArrayList of Structs in zig","tags":["zig"],"text":"Title: Search ArrayList of Structs in zig\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI expect this is a question with a very simple answer about how to do this well in zig.\n\nI want to search an ArrayList of some struct to find a record by one of the fields.\n\nIn C++ I would consider using std::find_if and a lambda but there doesn't seem to be anything like this in the zig standard library unless I missed something.\n\nIs there a better / more idiomatic way than the simple loop like below?\n\n```\nconst std = @import(\"std\");\n\nconst Person = struct {\n id: i32,\n name: []const u8\n};\n\npub fn main() !void {\n\n const allocator = std.heap.page_allocator;\n\n var data = std.ArrayList(Person).init(allocator);\n defer data.deinit();\n\n try data.append(.{.id = 1, .name = \"John\"});\n try data.append(.{.id = 2, .name = \"Dave\"});\n try data.append(.{.id = 8, .name = \"Bob\"});\n try data.append(.{.id = 5, .name = \"Steve\"});\n\n // Find the id of the person with name \"Bob\"\n //\n // -- IS THERE A BETTER WAY IN ZIG THAN THIS LOOP BELOW? --\n //\n var item_index: ?usize = null;\n for (data.items) | person, index | {\n if (std.mem.eql(u8, person.name, \"Bob\")) {\n item_index = index;\n }\n }\n\n std.debug.print(\"Found index is {}\\n\", .{item_index});\n\n}\n```\n\n========================================\n\nCode:\n```text\nconst std = @import(\"std\");\n\nconst Person = struct {\n id: i32,\n name: []const u8\n};\n\npub fn main() !void {\n\n const allocator = std.heap.page_allocator;\n\n var data = std.ArrayList(Person).init(allocator);\n defer data.deinit();\n\n try data.append(.{.id = 1, .name = \"John\"});\n try data.append(.{.id = 2, .name = \"Dave\"});\n try data.append(.{.id = 8, .name = \"Bob\"});\n try data.append(.{.id = 5, .name = \"Steve\"});\n\n // Find the id of the person with name \"Bob\"\n //\n // -- IS THERE A BETTER WAY IN ZIG THAN THIS LOOP BELOW? --\n //\n var item_index: ?usize = null;\n for (data.items) | person, index | {\n if (std.mem.eql(u8, person.name, \"Bob\")) {\n item_index = index;\n }\n }\n\n std.debug.print(\"Found index is {}\\n\", .{item_index});\n\n\n}\n```\n\n```text\nconst item_index = for (data.items) |person, index| {\n if (std.mem.eql(u8, person.name, \"Bob\")) break index;\n} else null;\n```\n\n```text\nindex\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.842Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":3,"totalLines":98,"estimatedTokens":563}}42{"id":"stack-76206472","source":"stackoverflow","questionId":76206472,"title":"How to change the local cache directory for the zig build system?","tags":["build","directory","zig"],"text":"Title: How to change the local cache directory for the zig build system?\nTags: build, directory, zig\nSource: Stack Overflow\n\nQuestion:\nMotivation: my source files are on a network (samba) .\n\n```\nzig build\n```\n\nfails with\n\nerror: Unexpected\n\n. To overcome it (otherwise I have to delete the ./zig-cache/ folder before every build) and to save time (and potentially the SSD drive) I want to use RAMdrive for the local cache. I modified my build.zig like this:\n\n```\nconst std=@import(\"std\");\nconst Builder=@import(\"std\").build.Builder;\n\npub fn build(b:*Builder) void {\n b.cache_root=.{.path=\"I:/my_build_cache\",.handle=std.fs.openDirAbsolute(\"I:/\",.{}) catch unreachable};\n const target=b.standardTargetOptions(.{});\n[...]\n```\n\nwhere *I:/* is my RAMdrive. It kind of works (one time), but does not solve my problem, because zig still creates the ./zig-cache/ folder to build the build.exe which then uses I:/my_build_cache for the other artifacts. For context, this is on Windows, but a solution for Linux is equally welcome. Can I set up some environment variables to influence zig.exe earlier in the build process or (worst case) give it some command-line argument to specify the local cache directory?\n\n========================================\n\nTop Answer:\n```\nzig build --help | grep cache\n --cache-dir [path] Override path to local Zig cache directory\n --global-cache-dir [path] Override path to global Zig cache directory\n```\n\nSo yeah, just an alternative solution for people who don't want to use the environment variable like mentioned in the other answer\n\n========================================\n\nCode:\n```text\nzig build\n```\n\n```text\nconst std=@import(\"std\");\nconst Builder=@import(\"std\").build.Builder;\n\npub fn build(b:*Builder) void {\n b.cache_root=.{.path=\"I:/my_build_cache\",.handle=std.fs.openDirAbsolute(\"I:/\",.{}) catch unreachable};\n const target=b.standardTargetOptions(.{});\n[...]\n```\n\n```text\nZIG_LOCAL_CACHE_DIR\n```\n\n```text\nzig build --help | grep cache\n --cache-dir [path] Override path to local Zig cache directory\n --global-cache-dir [path] Override path to global Zig cache directory\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.842Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":4,"totalLines":66,"estimatedTokens":533}}43{"id":"stack-49892119","source":"stackoverflow","questionId":49892119,"title":"Zig \"translate c\" doesn't translate main function","tags":["c","zig"],"text":"Title: Zig \"translate c\" doesn't translate main function\nTags: c, zig\nSource: Stack Overflow\n\nQuestion:\nI created a C file:\n\n```\nint main() {\n return 1;\n}\n```\n\nI used Zig's `translate-c` command line option to generate a zig file, and I only get some global variable declarations like\n\n```\npub const __GCC_ATOMIC_TEST_AND_SET_TRUEVAL = 1;\npub const __FLT16_MAX_EXP__ = 15;\npub const __BIGGEST_ALIGNMENT__ = 16;\npub const __SIZEOF_FLOAT__ = 4;\npub const __INT64_FMTd__ = c\"ld\";\npub const __STDC_VERSION__ = c_long(201112);\n... // and many\n```\n\nAnd no `main` function is found. But if I change the function name to `myFunction` like this:\n\n```\nint myFunction(int a) {\n return a;\n}\n```\n\nA function appears when I re-generate it:\n\n```\npub export fn myFunction(a: c_int) c_int {\n return a;\n}\n```\n\nAm I missing something? What's the rule of zig's `translate-c` function?\n\n========================================\n\nCode:\n```text\nint main() {\n return 1;\n}\n```\n\n```text\npub const __GCC_ATOMIC_TEST_AND_SET_TRUEVAL = 1;\npub const __FLT16_MAX_EXP__ = 15;\npub const __BIGGEST_ALIGNMENT__ = 16;\npub const __SIZEOF_FLOAT__ = 4;\npub const __INT64_FMTd__ = c\"ld\";\npub const __STDC_VERSION__ = c_long(201112);\n... // and many\n```\n\n```text\nint myFunction(int a) {\n return a;\n}\n```\n\n```text\npub export fn myFunction(a: c_int) c_int {\n return a;\n}\n```\n\n```text\ntranslate-c\n```\n\n```text\nmain\n```\n\n```text\nmyFunction\n```\n\n```text\ntranslate-c\n```\n\n```text\ntest.c:1:5: warning: unsupported type: 'FunctionNoProto'\ntest.c:1:5: warning: unable to resolve prototype of function 'main'\n```\n\n```text\npub export fn main() c_int {\n return 1;\n}\n```\n\n```text\n--verbose-cimport\n```\n\n```text\nvoid\n```\n\n========================================\n\nComments:\n- Did you create the tag `zig`? If so you might want to give it a short desciption in the wiki.\n- I don't know about zig. But return 1 seems like the compiler would just replace the function call with 1.\n- @KamiKaze Yes I did and the wiki edit is awaiting peer review.\n- have you tried replacing the main function with something that is not deterministic at compile time?\n- ...e.g. `int main() { int a; scanf(\"%d\", a); return a;`. Now, the compiler cannot forsee/optimize the result of `main()`.\n- Is it this zig?\n- Yes @Scheff, My edit to the tag wiki is awaiting review\n- @KamiKaze Yes, I've found this! The \"constexpr\" like functions are optimized! Thanks guys.\n- Zig now supports this example and I've updated my answer to reflect that.","metadata":{"transformedAt":"2026-08-18T18:33:48.842Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":12,"totalLines":121,"estimatedTokens":617}}44{"id":"stack-76410773","source":"stackoverflow","questionId":76410773,"title":"How to print a number as hexadecimal in Zig?","tags":["hex","zig"],"text":"Title: How to print a number as hexadecimal in Zig?\nTags: hex, zig\nSource: Stack Overflow\n\nQuestion:\n```\nconst std = @import(\"std\");\n\npub fn main() void {\n const foo: u8 = 128;\n std.debug.print(\"{}\\n\", .{foo}); // \"128\"\n}\n```\n\nThe above prints `128` as expected.\n\nHow can the value be printed as hexadecimal instead?\n\n========================================\n\nCode:\n```text\nconst std = @import(\"std\");\n\npub fn main() void {\n const foo: u8 = 128;\n std.debug.print(\"{}\\n\", .{foo}); // \"128\"\n}\n```\n\n```text\n128\n```\n\n```text\nconst std = @import(\"std\");\n\npub fn main() void {\n // Tested with Zig v0.10.1\n\n const foo: u8 = 26;\n std.debug.print(\"0x{x}\\n\", .{foo}); // \"0x1a\"\n std.debug.print(\"0x{X}\\n\", .{foo}); // \"0x1A\"\n\n const bar: u16 = 1;\n std.debug.print(\"0x{x}\\n\", .{bar}); // \"0x1\"\n std.debug.print(\"0x{x:2}\\n\", .{bar}); // \"0x 1\"\n std.debug.print(\"0x{x:4}\\n\", .{bar}); // \"0x 1\"\n std.debug.print(\"0x{x:0>4}\\n\", .{bar}); // \"0x0001\"\n\n const baz: u16 = 43;\n std.debug.print(\"0x{x:0>4}\\n\", .{baz}); // \"0x002b\"\n std.debug.print(\"0x{X:0>8}\\n\", .{baz}); // \"0x0000002B\"\n\n const qux: u32 = 0x1a2b3c;\n std.debug.print(\"0x{X:0>2}\\n\", .{qux}); // \"0x1A2B3C\" (not cut off)\n std.debug.print(\"0x{x:0>8}\\n\", .{qux}); // \"0x001a2b3c\"\n}\n```\n\n```text\nx\n```\n\n```text\nX\n```\n\n========================================\n\nComments:\n- Posted within the same second as the question... How is that possible?\n- @PeterMortensen Self-answer is an explicit feature of SO. Read more at stackoverflow.com/help/self-answer","metadata":{"transformedAt":"2026-08-18T18:33:48.842Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":5,"totalLines":73,"estimatedTokens":388}}45{"id":"stack-68421136","source":"stackoverflow","questionId":68421136,"title":"import zig package from another zig package","tags":["zig"],"text":"Title: import zig package from another zig package\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI can import an package in my executable with `exe.addPackagePath(\"name\", \"path\")` and usae it with `const name = @import(\"name\");`. Now I want to include the package in another package, but I don´t understand how. Can I create an object for the package to set addPackagePath() on?\n\n========================================\n\nTop Answer:\nIn zig 0.11.0-dev.2317+46b2f1f70:\n\n```\nb.addModule(.{\n .name = package_name,\n .source_file = .{ .path = package_path },\n});\n```\n\n- Example from https://github.com/zig-postgres/zig-postgres/blob/005fb0b27f2d658224a3c39b6e4536668d8ed9f6/build.zig#L25\n\n- More info https://devlog.hexops.com/2023/zig-0-11-breaking-build-changes/\n\nIn zig 0.11.0-dev.1503+17404f8e6:\n\n```\nconst pkg_postgres = std.build.Pkg{\n .name = \"postgres\",\n .source = std.build.FileSource{\n .path = \"deps/zig-postgres/src/postgres.zig\",\n },\n};\n...\nexe.addPackage(pkg_postgres);\n```\n\n- https://zenn.dev/ousttrue/books/b2ec4e93bdc5c4/viewer/4a67f3#pkg.path\n\n- https://github.com/capy-ui/capy/blob/ab6d8df7123f27ae814003a31c5fda6eb6c2acd0/build_capy.zig#L25\n\n========================================\n\nCode:\n```text\nexe.addPackagePath(\"name\", \"path\")\n```\n\n```text\nconst name = @import(\"name\");\n```\n\n```text\naddPackagePath\n```\n\n```text\nPkg\n```\n\n```text\naddPackage\n```\n\n```text\nPkg\n```\n\n```text\nb.addModule(.{\n .name = package_name,\n .source_file = .{ .path = package_path },\n});\n```\n\n```text\nconst pkg_postgres = std.build.Pkg{\n .name = \"postgres\",\n .source = std.build.FileSource{\n .path = \"deps/zig-postgres/src/postgres.zig\",\n },\n};\n...\nexe.addPackage(pkg_postgres);\n```\n\n```text\n/src/main.zig\n/src/foobar/foobar.zig\n```\n\n```text\n// src/foobar/foobar.zig\n\npub fn foo()[*:0] const u8 {\n return \"bar\";\n}\n```\n\n```text\nconst foobar_module = b.createModule(.{\n .source_file = .{ .path = \"src/foobar/foobar.zig\"},\n .dependencies = &.{},\n});\n\nexe.addModule(\"foobar\", foobar_module);\n```\n\n```text\nconst std = @import(\"std\");\nconst game = @import(\"game\");\n\n\npub fn main() !void {\n // Prints to stderr (it's a shortcut based on `std.io.getStdErr()`)\n std.debug.print(\"Foobar: {s}\\n\", .{foobar.foo()});\n}\n```\n\n```text\nFoobar: bar\n```\n\n```text\nfoobar.zig\n```\n\n```text\nsrc/main.zig\n```\n\n```text\nzig build\n```\n\n```text\nconst foo = b.createModule(.{.source_file = .{.path = \"../foo/src/main.zig\"}});\nexe.addModule(\"foo\", foo);\n```\n\n```c\nconst my_module = b.addModule(\"my_module\", .{\n .root_source_file = b.path(\"src/modules/my_module.zig\"),\n});\n\nexe.root_module.addImport(\"my_module\", my_module);\n```\n\n========================================\n\nComments:\n- I'm getting: error: root struct of file 'Build' has no member named 'Pkg' const pkg_postgres = std.build.Pkg{\n- Have you seen this devlog.hexops.com/2023/zig-0-11-breaking-build-changes?\n- You can see working example here github.com/zig-postgres/zig-postgres/blob/main/build.zig","metadata":{"transformedAt":"2026-08-18T18:33:48.842Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":18,"totalLines":153,"estimatedTokens":739}}46{"id":"stack-78493804","source":"stackoverflow","questionId":78493804,"title":"How do I compare two UTF-8 strings ignoring case in Zig language?","tags":["arrays","string","string-comparison","zig"],"text":"Title: How do I compare two UTF-8 strings ignoring case in Zig language?\nTags: arrays, string, string-comparison, zig\nSource: Stack Overflow\n\nQuestion:\nI have two strings. Assume the following:\n\n```\nconst a = \"Zig\";\nconst b = \"zig\";\n```\n\nI want the comparison to be case - insensitive and characters will be any UTF-8 character.\n\nWhen I run the following code:\n\n```\nconst a = \"Zig\";\nconst b = \"zig\";\nconst is_equal = std.mem.eql(u8, a, b);\nstd.debug.print(\"is_equal: {}\\n\", .{is_equal});\n```\n\nI got:\n\n```\nis_equal: false\n```\n\nI want `is_equal` to be true. How do I do that?\n\n========================================\n\nCode:\n```zig\nconst a = \"Zig\";\nconst b = \"zig\";\n```\n\n```zig\nconst a = \"Zig\";\nconst b = \"zig\";\nconst is_equal = std.mem.eql(u8, a, b);\nstd.debug.print(\"is_equal: {}\\n\", .{is_equal});\n```\n\n```bash\nis_equal: false\n```\n\n```text\nis_equal\n```\n\n```zig\nconst Normalizer = @import(\"ziglyph\").Normalizer;\nconst testing = @import(\"std\").testing;\n\nvar allocator = std.testing.allocator;\n\nvar norm = try Normalizer.init(allocator);\ndefer norm.deinit();\n\nconst str_1 = \"Jos\\u{E9}\";\nconst str_2 = \"Jos\\u{65}\\u{301}\";\nconst str_3 = \"JOSÉ\";\n\n// Normalized, case-sensitive comparison.\ntry testing.expect(try norm.eqlBy(str_1, str_2, .normalize));\n\n// Normalized, case-insensitive comparison.\ntry testing.expect(try norm.eqlBy(str_2, str_3, .norm_ignore));\n```\n\n```text\nstd.ascii.eqlIgnoreCase\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.842Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":6,"totalLines":77,"estimatedTokens":349}}47{"id":"stack-77761538","source":"stackoverflow","questionId":77761538,"title":"Pointer to array, returning an array in Zig","tags":["arrays","pointers","zig"],"text":"Title: Pointer to array, returning an array in Zig\nTags: arrays, pointers, zig\nSource: Stack Overflow\n\nQuestion:\nI need to create an array in some function (having **size** as an arg) then return it for easy declare in a single clean line. It already causes a lot of questions as:\n\n- As I know, Zig has no hidden control and memory allocation, so if **I pass an array** as an argument **will it be cloned**, like ints (as it should), or **will a pointer be created**, as in C or Java?\n\n- Can functions **return an array**? If they can, do I need `const` or `comptime` as a length value?\n\n- If I need to **pass a pointer to array** (or its address) how do I declare it, extract a value from it?\n\n- If I need to pass a pointer instead of `const length: usize` how do I do this? If I pass `&size` compiler says\n\nfunction expects `*usize` not `const *usize`\n\nbut I cant rewrite it to `const length: *usize` because length should be `comptime`.\n\nHere is example of code I need:\n\n```\nconst std = @import(\"std\");\n\npub fn sorted_array(comptime len: usize) *[]i32 {\n comptime var array: [len]i32 = undefined;\n for (&array, 0..) |*item, i| {\n item.* = @intCast(i);\n }\n return &array;\n}\n\npub fn main() void {\n const size: usize = 10;\n const array: *[]i32 = sorted_array(size);\n for (&array.*) |*item| {\n std.debug.print(\"{} \", .{item.*});\n }\n}\n```\n\nBut it does not compile. I also have the same code with what I need, which compiles, but it is written in C:\n\n```\n#include \n#include \n\nint* sorted_array(const size_t* size) {\n int* array = (int*)malloc(sizeof(int) * *size);\n for (size_t i = 0; i I will code it to do some sorts right after. I would appreciate it if you answered my questions and recode my beginner Zig tries.\n\n========================================\n\nCode:\n```text\nconst std = @import(\"std\");\n\npub fn sorted_array(comptime len: usize) *[]i32 {\n comptime var array: [len]i32 = undefined;\n for (&array, 0..) |*item, i| {\n item.* = @intCast(i);\n }\n return &array;\n}\n\npub fn main() void {\n const size: usize = 10;\n const array: *[]i32 = sorted_array(size);\n for (&array.*) |*item| {\n std.debug.print(\"{} \", .{item.*});\n }\n}\n```\n\n```text\n#include <stdio.h>\n#include <malloc.h>\n\nint* sorted_array(const size_t* size) {\n int* array = (int*)malloc(sizeof(int) * *size);\n for (size_t i = 0; i < *size; i++)\n array[i] = i;\n return array;\n}\n\nint main(void) {\n\n const size_t size = 1000;\n int* array = sorted_array(&size);\n\n return 0;\n}\n```\n\n```text\nconst\n```\n\n```text\ncomptime\n```\n\n```text\nconst length: usize\n```\n\n```text\n&size\n```\n\n```text\n*usize\n```\n\n```text\nconst *usize\n```\n\n```text\nconst length: *usize\n```\n\n```text\ncomptime\n```\n\n```text\nfn create_sorted_array(allocator: std.mem.Allocator, len: *const usize) ![]i32 {\n const array = try allocator.alloc(i32, len.*);\n for (array, 0..) |*item, i| {\n item.* = @intCast(i);\n }\n return array;\n}\n```\n\n```text\nfn sorted(comptime len: *const usize) [len.*]i32 {\n const array: [len.*]i32 = undefined;\n // ...\n return array;\n}\n```\n\n```text\ncomptime\n```\n\n```text\n*[xxx]i32\n```\n\n```text\npointer.*\n```\n\n```text\n&size\n```\n\n```text\n*usize\n```\n\n```text\nconst *usize\n```\n\n```text\n*const usize\n```\n\n```text\nconst length: *usize\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.842Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":20,"totalLines":175,"estimatedTokens":814}}48{"id":"stack-78833818","source":"stackoverflow","questionId":78833818,"title":"Specify output directory and binary name to zig build-exe","tags":["zig"],"text":"Title: Specify output directory and binary name to zig build-exe\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI struggle to find any equivalent of C compiler's `cc -o ` in documentation of `zig build-exe`. Only thing that I found is option `--name`, but It cannot specify path, only name of unit.\n\nIs there any way to do so in command, or using ***build.zig*** file is the only way?\n\n========================================\n\nCode:\n```text\ncc <srcs> -o <path/and/binary/name>\n```\n\n```text\nzig build-exe\n```\n\n```text\n--name\n```\n\n```text\n-femit-bin=path/to/output_file\n```\n\n========================================\n\nComments:\n- That is it! Thank you\n- Thanks this works. I miss a -o flag though 🙁","metadata":{"transformedAt":"2026-08-18T18:33:48.842Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":4,"totalLines":33,"estimatedTokens":174}}49{"id":"stack-78057208","source":"stackoverflow","questionId":78057208,"title":"zig allocators dont need dealloc?","tags":["memory-leaks","zig"],"text":"Title: zig allocators dont need dealloc?\nTags: memory-leaks, zig\nSource: Stack Overflow\n\nQuestion:\nI have been using zig some days and start to learn about allocators. By what I know, zig doesn't have garbage collector, so something like the following code must bring an error:\n\n```\nconst std = @import (\"std\");\nconst alloc_1 = std.heap.page_allocator;\n\npub fn main () !void {\n const arr = try alloc_1.alloc (u8, 3);\n arr[0] = 0;\n}\n```\n\nI have using valgrind to track the memory leak with the next command `valgrind --leak-check=full --track-origins=yes ./allocators` and get this:\n\n```\n==23890== Memcheck, a memory error detector\n==23890== Copyright (C) 2002-2022, and GNU GPL'd, by Julian Seward et al.\n==23890== Using Valgrind-3.22.0 and LibVEX; rerun with -h for copyright info\n==23890== Command: ./allocators\n==23890== \n==23890== \n==23890== HEAP SUMMARY:\n==23890== in use at exit: 0 bytes in 0 blocks\n==23890== total heap usage: 0 allocs, 0 frees, 0 bytes allocated\n==23890== \n==23890== All heap blocks were freed -- no leaks are possible\n==23890== \n==23890== For lists of detected and suppressed errors, rerun with: -s\n==23890== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 0 from 0)\n```\n\nso basically the memory is cleared despite I don't dealloc it.\n\n========================================\n\nTop Answer:\ni don't think that valgrind works with llvm but idk you may prefer doing something like\n\n```\nconst memory = try allocator.alloc(u8, 100);\ndefer allocator.free(memory);\n```\n\nref: https://zig.guide/standard-library/allocators/\n\n========================================\n\nCode:\n```zig\nconst std = @import (\"std\");\nconst alloc_1 = std.heap.page_allocator;\n\npub fn main () !void {\n const arr = try alloc_1.alloc (u8, 3);\n arr[0] = 0;\n}\n```\n\n```text\n==23890== Memcheck, a memory error detector\n==23890== Copyright (C) 2002-2022, and GNU GPL'd, by Julian Seward et al.\n==23890== Using Valgrind-3.22.0 and LibVEX; rerun with -h for copyright info\n==23890== Command: ./allocators\n==23890== \n==23890== \n==23890== HEAP SUMMARY:\n==23890== in use at exit: 0 bytes in 0 blocks\n==23890== total heap usage: 0 allocs, 0 frees, 0 bytes allocated\n==23890== \n==23890== All heap blocks were freed -- no leaks are possible\n==23890== \n==23890== For lists of detected and suppressed errors, rerun with: -s\n==23890== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 0 from 0)\n```\n\n```text\nvalgrind --leak-check=full --track-origins=yes ./allocators\n```\n\n```none\nconst std = @import(\"std\");\n\npub fn main() !void {\n var gpa = std.heap.GeneralPurposeAllocator(.{}){};\n defer if (gpa.deinit() == .leak) std.os.exit(1);\n const alloc = gpa.allocator();\n\n const arr = try alloc.alloc (u8, 3);\n arr[0] = 0;\n}\n```\n\n```bash\nerror(gpa): memory address 0x104568000 leaked: \na.zig:9:33: 0x10443c7b7 in main (a)\n const arr = try alloc.alloc (u8, 3);\n ^\n/.../lib/std/start.zig:583:37: 0x10443cf83 in main (a)\n const result = root.main() catch |err| {\n ^\n???:?:?: 0x18d7dd0df in ??? (???)\n???:?:?: 0x6017ffffffffffff in ??? (???)\n\nExited with code [1]\n```\n\n```text\nconst memory = try allocator.alloc(u8, 100);\ndefer allocator.free(memory);\n```\n\n========================================\n\nComments:\n- I don't think Valgrind works with the \"non-C\" Zig allocators: cryptocode.github.io/blog/docs/valgrind-zig\n- what happens if you use `std.heap.c_allocator`\n- Yes, this have worked. I don't really know so much about allocators so this disturb me a little bit.\n- @Mr.Barbo valgrind only cares about `malloc` so this is why `std.heap.c_allocator` works.\n- but how it works? `malloc` acllocations have a \"signature\" that `valgrind` can keep track on? is something about the operating system? I don't know much about it.\n- Valgrind most definitely does work with custom allocators. However you need to instrument your code so that it knows about them.","metadata":{"transformedAt":"2026-08-18T18:33:48.842Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":6,"totalLines":125,"estimatedTokens":984}}50{"id":"stack-79314395","source":"stackoverflow","questionId":79314395,"title":"Deinit global and static local variable","tags":["zig"],"text":"Title: Deinit global and static local variable\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI'm having trouble with memory management in Zig (using v0.13.0), regarding *global* and *static local* variables deinitialization.\n\nI've written the following program, but memory leaks, and thus the program panics when enabling safety for the *GeneralPurposeAllocator*. I've read the documentation, especially the part regarding static local variables, but it doesn't mention (or it's in another section and I've missed it) anything on how to deinit the memory.\n\n```\nconst std = @import(\"std\");\n\nconst key_t = u32;\nconst value_t = u128;\nconst computed_map_t = std.AutoHashMap(key_t, value_t);\n\nvar default_gpa: std.heap.GeneralPurposeAllocator(.{}) = undefined;\nconst default_allocator = default_gpa.allocator();\n\npub fn fibonacci(value: key_t) value_t {\n const _state = struct {\n // How do I deinit this map on program end ?\n // Or is it possible to mark it as \"ok to leak\" ?\n var previously_computed = computed_map_t.init(default_allocator);\n };\n\n if (value == 0) return 0;\n if (value == 1 or value == 2) return 1;\n\n // Fallback \"dumb\" implementation because HashMap cannot be used in comptime\n if (@inComptime()) {\n return fibonacci(value - 2) + fibonacci(value - 1);\n } else {\n if (_state.previously_computed.get(value)) |res| {\n return res;\n } else {\n const res = fibonacci(value - 2) + fibonacci(value - 1);\n _state.previously_computed.put(value, res) catch {\n @panic(\"Something went wrong\");\n };\n return res;\n }\n }\n}\n\npub fn main() !void {\n default_gpa = @TypeOf(default_gpa){};\n defer {\n if (.leak == default_gpa.deinit()) {\n @panic(\"GPA leaked !\");\n }\n }\n\n const value = 5;\n const result = fibonacci(value);\n std.debug.print(\"fibonacci({d}) = {d}\\n\", .{ value, result });\n}\n```\n\nI've thought about initializing the map in the main function and passing it to the `fibonacci` function as a pointer, but it kinda defeats the point (this map is only useful in the function, so I'd like to keep the scope of this variable restrained to the function scope).\n\nIs there something I missed? Alternativly, do you have any \"hacks\" on how to achieve this in a clean way?\n\n========================================\n\nCode:\n```none\nconst std = @import(\"std\");\n\nconst key_t = u32;\nconst value_t = u128;\nconst computed_map_t = std.AutoHashMap(key_t, value_t);\n\nvar default_gpa: std.heap.GeneralPurposeAllocator(.{}) = undefined;\nconst default_allocator = default_gpa.allocator();\n\npub fn fibonacci(value: key_t) value_t {\n const _state = struct {\n // How do I deinit this map on program end ?\n // Or is it possible to mark it as \"ok to leak\" ?\n var previously_computed = computed_map_t.init(default_allocator);\n };\n\n if (value == 0) return 0;\n if (value == 1 or value == 2) return 1;\n\n // Fallback \"dumb\" implementation because HashMap cannot be used in comptime\n if (@inComptime()) {\n return fibonacci(value - 2) + fibonacci(value - 1);\n } else {\n if (_state.previously_computed.get(value)) |res| {\n return res;\n } else {\n const res = fibonacci(value - 2) + fibonacci(value - 1);\n _state.previously_computed.put(value, res) catch {\n @panic(\"Something went wrong\");\n };\n return res;\n }\n }\n}\n\npub fn main() !void {\n default_gpa = @TypeOf(default_gpa){};\n defer {\n if (.leak == default_gpa.deinit()) {\n @panic(\"GPA leaked !\");\n }\n }\n\n const value = 5;\n const result = fibonacci(value);\n std.debug.print(\"fibonacci({d}) = {d}\\n\", .{ value, result });\n}\n```\n\n```text\nfibonacci\n```\n\n```none\nvar fib_map: computed_map_t = undefined;\n\npub fn fib(key: key_t) value_t {\n const _state = struct {\n previously_computed = fib_map,\n }\n}\n\npub fn main() void {\n fib_map = computed_map_t.init(allocator);\n defer fib_map.deinit();\n _ = fib(5);\n ...\n}\n```\n\n```none\npub fn MapMemoizer(comptime K: type, comptime V: type, comptime implFn: fn(key: K) V) type {\n return struct {\n allocator: Allocator,\n map: Map = undefined,\n implFn: fn(key: K) V = implFn,\n \n Self = @This();\n const Map = std.AutoHashMap(K, V);\n\n pub fn init(allocator: Allocator, realFn: fn(key: K) V) !Self {\n return .{\n .allocator = allocator,\n .map = try Map.init(allocator),\n .realFn = realFn,\n };\n }\n\n pub fn deinit(self: *Self) void {\n self.map.deinit();\n }\n\n pub fn call(self: *Self, key: K) V {\n if (self.map.get(key)) |value| {\n return value;\n } else {\n const value = self.realFn(key);\n self.map.put(key, value);\n }\n }\n }\n}\n\npub fn fibonacci(key: key_t) value_t {\n // fib stuff..\n}\n\nconst FibMemoizer = MapMemoizer(key_t, value_t, fibonacci);\n\npub fn main() !void {\n var fib = try FibMemoizer.init(allocator);\n defer fib.deinit();\n\n const result = fib.call(5);\n}\n```\n\n========================================\n\nComments:\n- You've got a good question here -- but *do* please keep it to one question to a question; the \"bonus question\" should be asked separately. That way we don't have conflicts about which answer to accept if there's one that answers the main question well but ignores the \"bonus question\", while another addresses the \"bonus question\" correctly while leaving the main question unanswered, etc; enforcing scoping rules also makes handling duplicates less messy.\n- Thanks for the detailled answer. I suspected what I was trying to do wasn't possible, as there is no real \"scope exit\" to trigger a defer statement, and the variable is hidden away, but I hoped there would be some builtin to do things at program exit. About your generic approach, it's great, but in this case it has a major drawback, you can't save the intermediate results produced by the recursive calls.","metadata":{"transformedAt":"2026-08-18T18:33:48.843Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":4,"totalLines":189,"estimatedTokens":1498}}51{"id":"stack-77604505","source":"stackoverflow","questionId":77604505,"title":"In Zig, what is the right way to iterate over the fields of an enum?","tags":["enums","zig"],"text":"Title: In Zig, what is the right way to iterate over the fields of an enum?\nTags: enums, zig\nSource: Stack Overflow\n\nQuestion:\nI'm trying to iterate over all the fields in an Enum (really I just want to the values), in my `enum` in Zig:\n\n```\nconst std = @import(\"std\");\n\nconst MyEnum = enum(u8) {\n NONE = 0,\n ONE,\n TWO,\n};\n\npub fn main() void {\n std.debug.assert(@typeInfo(MyEnum).Enum.fields.len == 3);\n std.debug.assert(std.mem.eql(u8, @typeInfo(MyEnum).Enum.fields[0].name, \"NONE\"));\n std.debug.assert(@typeInfo(MyEnum).Enum.fields[0].value == 0);\n\n for (std.meta.fields(MyEnum)) |f| {\n std.debug.print(\"{}\\n\", .{ f.value });\n }\n\n for (@typeInfo(MyEnum).Enum.fields) |f| {\n std.debug.print(\"{}\\n\", .{ f.value });\n }\n}\n```\n\nThe asserts at the top just show I've got the basics right. Neither of the `for` loops compile, I get:\n\n```\n... error: values of type '[]const builtin.Type.EnumField' must be comptime-known, but index value is runtime-known\n```\n\nAFAICT, all the content of the enum is \"comptime-known\", so I'm not sure why the error is complaining about `EnumField`...\n\nI'm running a locally-built zig 0.12.0-dev.1782+dd188307b sync'd in the last couple of days.\n\n========================================\n\nTop Answer:\nIn Zig v0.16.0 whenever I need to iterate over some enums, I prefer this way:\n\n```\nconst States = {prepare, iterate, calculate, terminate};\nconst ListOfStates = std.enums.values(States);\n\n// Now I can iterate over the States. The \"state\" variable\n// also has the correct type.\n\nfor (ListOfStates) |state| {\n if (state == States.calculate) {\n // etc.\n }\n}\n```\n\n========================================\n\nCode:\n```text\nconst std = @import(\"std\");\n\nconst MyEnum = enum(u8) {\n NONE = 0,\n ONE,\n TWO,\n};\n\npub fn main() void {\n std.debug.assert(@typeInfo(MyEnum).Enum.fields.len == 3);\n std.debug.assert(std.mem.eql(u8, @typeInfo(MyEnum).Enum.fields[0].name, \"NONE\"));\n std.debug.assert(@typeInfo(MyEnum).Enum.fields[0].value == 0);\n\n for (std.meta.fields(MyEnum)) |f| {\n std.debug.print(\"{}\\n\", .{ f.value });\n }\n\n for (@typeInfo(MyEnum).Enum.fields) |f| {\n std.debug.print(\"{}\\n\", .{ f.value });\n }\n}\n```\n\n```text\n... error: values of type '[]const builtin.Type.EnumField' must be comptime-known, but index value is runtime-known\n```\n\n```text\nenum\n```\n\n```text\nfor\n```\n\n```text\nEnumField\n```\n\n```text\nconst std = @import(\"std\");\n\nconst MyEnum = enum(u8) {\n NONE = 0,\n ONE,\n TWO,\n};\n\npub fn main() void {\n std.debug.assert(@typeInfo(MyEnum).@\"enum\".fields.len == 3);\n std.debug.assert(std.mem.eql(u8, @typeInfo(MyEnum).@\"enum\".fields[0].name, \"NONE\"));\n std.debug.assert(@typeInfo(MyEnum).@\"enum\".fields[0].value == 0);\n\n inline for (std.meta.fields(MyEnum)) |f| {\n std.debug.print(\"{}\\n\", .{f.value});\n }\n\n inline for (@typeInfo(MyEnum).@\"enum\".fields) |f| {\n std.debug.print(\"{}\\n\", .{f.value});\n }\n}\n```\n\n```text\nfor\n```\n\n```text\ninline for\n```\n\n```none\nconst States = {prepare, iterate, calculate, terminate};\nconst ListOfStates = std.enums.values(States);\n\n// Now I can iterate over the States. The \"state\" variable\n// also has the correct type.\n\nfor (ListOfStates) |state| {\n if (state == States.calculate) {\n // etc.\n }\n}\n```\n\n========================================\n\nComments:\n- Ah, now the bit about \"index value\" in the error makes more sense... I hadn't realized the enum metadata is strictly available at comptime.\n- @P.T. in general any type of meta/type information is only available at compile time, because otherwise you'd always incur the overhead of storing it even when you don't need it.\n- What's the equivalent of this in modern Zig? On `0.14.0-dev.2362+a47aa9dd9` I get `no field named 'Enum' in union 'builtin.Type'`\n- Ah - per here, it appears we need to change `.Enum.` to `.@\"enum\"`\n- See ziglang.org/download/0.14.0/…","metadata":{"transformedAt":"2026-08-18T18:33:48.843Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":9,"totalLines":157,"estimatedTokens":969}}52{"id":"stack-68609919","source":"stackoverflow","questionId":68609919,"title":"Using zig compiler as a library","tags":["compilation","zig"],"text":"Title: Using zig compiler as a library\nTags: compilation, zig\nSource: Stack Overflow\n\nQuestion:\nIs there a way to use zig compiler as a library inside zig?\nAfter looking both in zig documentation, issues and on the internet, I can't find an answer to this question.\n\nIn one of the issues it is said that this can be done at the current time, but I couldn't find any examples of how to do it.\n\n========================================\n\nCode:\n```golang\nvar zig = std.ChildProcess.init(&.{\"zig\", \"build-exe\", \"demo.zig\"}, allocator);\ntry zig.spawn();\ntry zig.wait();\n```\n\n```rs\n// build.zig\n\nconst std = @import(\"std\");\n\npub fn build(b: *std.build.Builder) !void {\n const target = b.standardTargetOptions(.{});\n\n const mode = b.standardReleaseOptions();\n\n const exe_options = b.addOptions();\n\n const mem_leak_frames: u32 = b.option(u32, \"mem-leak-frames\", \"How many stack frames to print when a memory leak occurs. Tests get 2x this amount.\") orelse 4;\n const skip_non_native = b.option(bool, \"skip-non-native\", \"Main test suite skips non-native builds\") orelse false;\n\n const enable_logging = b.option(bool, \"log\", \"Whether to enable logging\") orelse false;\n const enable_link_snapshots = b.option(bool, \"link-snapshot\", \"Whether to enable linker state snapshots\") orelse false;\n\n exe_options.addOption(u32, \"mem_leak_frames\", mem_leak_frames);\n exe_options.addOption(bool, \"skip_non_native\", skip_non_native);\n exe_options.addOption(bool, \"have_llvm\", false);\n exe_options.addOption(bool, \"llvm_has_m68k\", false);\n exe_options.addOption(bool, \"llvm_has_csky\", false);\n exe_options.addOption(bool, \"llvm_has_ve\", false);\n exe_options.addOption(bool, \"llvm_has_arc\", false);\n\n const version = \"0.0.0\";\n\n exe_options.addOption([:0]const u8, \"version\", try b.allocator.dupeZ(u8, version));\n\n const semver = try std.SemanticVersion.parse(version);\n exe_options.addOption(std.SemanticVersion, \"semver\", semver);\n\n exe_options.addOption(bool, \"enable_logging\", enable_logging);\n exe_options.addOption(bool, \"enable_link_snapshots\", enable_link_snapshots);\n exe_options.addOption(bool, \"enable_tracy\", false);\n exe_options.addOption(bool, \"enable_tracy_callstack\", false);\n exe_options.addOption(bool, \"enable_tracy_allocation\", false);\n exe_options.addOption(bool, \"is_stage1\", false);\n exe_options.addOption(bool, \"omit_stage2\", false);\n\n const exe = b.addExecutable(\"tmp\", \"sample.zig\");\n exe.setTarget(target);\n exe.setBuildMode(mode);\n exe.addOptions(\"build_options\", exe_options);\n exe.addPackage(.{\n .name = \"zig\",\n .path = .{ .path = \"src/main.zig\" },\n .dependencies = &[_]std.build.Pkg{\n .{ .name = \"build_options\", .path = exe_options.getSource() },\n },\n });\n exe.install();\n\n const run_cmd = exe.run();\n run_cmd.step.dependOn(b.getInstallStep());\n if (b.args) |args| {\n run_cmd.addArgs(args);\n }\n\n const run_step = b.step(\"run\", \"Run the app\");\n run_step.dependOn(&run_cmd.step);\n}\n```\n\n```rs\n// sample.zig\n\nconst zig = @import(\"zig\");\n\npub fn main() !void {\n return zig.main(); // just calls into the zig compiler main function. you'll have to look into how https://github.com/ziglang/zig/blob/master/src/main.zig works in order to do more complicated stuff.\n}\n```\n\n```text\n0.9.0-dev.1611+f3ba72cf5\n```\n\n```text\nzig build run -Dskip-non-native -- build-exe demo.zig\n```\n\n========================================\n\nComments:\n- As the zig compiler is partially written in zig, there are, in the standard library, all the facilities to parse zig in zig. Look at: github.com/ziglang/zig/tree/master/lib/std/zig. I am not sure you will be able to compile it though (produce a binary) as zig uses llvm as a backend. You would probably need to also include the llvm library for this.\n- @LukeSkywalker After trying to do it for a couple of days I gave up. Hopefully it will be easier when they get to the stage 2 compiler (self-hosting)","metadata":{"transformedAt":"2026-08-18T18:33:48.843Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":5,"totalLines":107,"estimatedTokens":999}}53{"id":"stack-76433397","source":"stackoverflow","questionId":76433397,"title":"Idiomatic way to free item memory in a zig ArrayList([] const u8)","tags":["zig"],"text":"Title: Idiomatic way to free item memory in a zig ArrayList([] const u8)\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI have an ArrayList([]const u8). I pass a pointer to it into functions that append to it. They append the results of calls to std.fmt.allocPrint(). To free everything up, the top-level function deinits the ArrayList after it frees all the items:\n\n```\nvar typeLines = std.ArrayList([]const u8).init(allocator);\ndefer typeLines.deinit();\ndefer for (typeLines.items) |line| {\n allocator.free(line);\n};\n```\n\nThis works. But I have some cases now where the called functions should append constant strings. So I can't simply loop through the items and free them all.\n\nI've thought about checking each item's type to see if I need to free it, or maybe keeping a separate ArrayList of just the items that need to be freed. What's the idiomatic way to identify which items need to be freed?\n\n========================================\n\nTop Answer:\nI ended up putting the []const u8 slice in a struct with a bool flag:\n\n```\nconst Line = struct {\n text: []const u8,\n freeIt: bool,\n};\n```\n\nI used the Line struct in the ArrayList:\n\n```\nvar typeLines = std.ArrayList(Line).init(allocator);\ndefer typeLines.deinit();\ndefer for (typeLines.items) |line| {\n if (line.freeIt) {\n allocator.free(line.text);\n }\n};\n```\n\nThis lets the called functions control whether or not the caller frees their additions to the ArrayList:\n\n```\nvar s = try std.fmt.allocPrint(allocator, \"\\npub const {s} = struct {{\\n\", .{typeName});\ntry typeLines.append(Line{ .text = s, .freeIt = true });\n\ntry typeLines.append(Line{ .text = \"\\n};\\n\", .freeIt = false });\n```\n\n========================================\n\nCode:\n```text\nvar typeLines = std.ArrayList([]const u8).init(allocator);\ndefer typeLines.deinit();\ndefer for (typeLines.items) |line| {\n allocator.free(line);\n};\n```\n\n```text\nvar arena = std.heap.ArenaAllocator.init(allocator);\ndefer arena.deinit();\n\nvar typeLines = std.ArrayList(Line).init(allocator);\ndefer typeLines.deinit();\n\n...\nvar s = try std.fmt.allocPrint(arena.allocator(), \"\\npub const {s} = struct {{\\n\", .{typeName});\ntry typeLines.append(s);\n\ntry typeLines.append(\"\\n};\\n\");\n```\n\n```text\nArenaAllocator\n```\n\n```text\nconst Line = struct {\n text: []const u8,\n freeIt: bool,\n};\n```\n\n```text\nvar typeLines = std.ArrayList(Line).init(allocator);\ndefer typeLines.deinit();\ndefer for (typeLines.items) |line| {\n if (line.freeIt) {\n allocator.free(line.text);\n }\n};\n```\n\n```text\nvar s = try std.fmt.allocPrint(allocator, \"\\npub const {s} = struct {{\\n\", .{typeName});\ntry typeLines.append(Line{ .text = s, .freeIt = true });\n\ntry typeLines.append(Line{ .text = \"\\n};\\n\", .freeIt = false });\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.843Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":6,"totalLines":104,"estimatedTokens":677}}54{"id":"stack-72573442","source":"stackoverflow","questionId":72573442,"title":"Zig std.log.info not printing anything with cross-compiled to AARCH64 binary","tags":["zig"],"text":"Title: Zig std.log.info not printing anything with cross-compiled to AARCH64 binary\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI have copied a hello world Zig program and it runs fine locally on my Mac:\n\n```\nconst std = @import(\"std\");\n\npub fn main() anyerror!void {\n // Note that info level log messages are by default printed only in Debug\n // and ReleaseSafe build modes.\n std.log.info(\"All your codebase are belong to us.\", .{});\n}\n\ntest \"basic test\" {\n try std.testing.expectEqual(10, 3 + 7);\n}\n```\n\nI then cross-compiled it to ARM:\n\n```\nzig build-exe src/main.zig -O ReleaseSmall --strip -target aarch64-linux\n```\n\nSeems to compile the right thing:\n\n```\n$ file ./main\n./main: ELF 64-bit LSB executable, ARM aarch64, version 1 (SYSV), statically linked, stripped\n```\n\nThen I copied it to my Raspberry Pi running Ubuntu 22.\n\nIt also shows the file is recognized and runs without error, but it just doesn't print anything. I tried redirecting both stdout and stderr to a file but nothing comes out.\n\nWhat can be the problem?\n\n========================================\n\nTop Answer:\nTurns out the code I had copied was not the \"real\" hello world. It only prints to the console when it's built in debug mode.\n\nThe production-grade hello world in Zig is this:\n\n```\nconst std = @import(\"std\");\n\npub fn main() !void {\n const stdout = std.io.getStdOut().writer();\n try stdout.print(\"Hello, {s}!\\n\", .{\"world\"});\n}\n```\n\nCompiling this the same way, it works both on Mac and when compiled to aarch64-linux and executed on my Raspberry Pi.\n\n========================================\n\nCode:\n```text\nconst std = @import(\"std\");\n\npub fn main() anyerror!void {\n // Note that info level log messages are by default printed only in Debug\n // and ReleaseSafe build modes.\n std.log.info(\"All your codebase are belong to us.\", .{});\n}\n\ntest \"basic test\" {\n try std.testing.expectEqual(10, 3 + 7);\n}\n```\n\n```text\nzig build-exe src/main.zig -O ReleaseSmall --strip -target aarch64-linux\n```\n\n```text\n$ file ./main\n./main: ELF 64-bit LSB executable, ARM aarch64, version 1 (SYSV), statically linked, stripped\n```\n\n```text\npub const log_level: std.log.Level = .info;\n```\n\n```text\nconst std = @import(\"std\");\n\npub fn main() !void {\n const stdout = std.io.getStdOut().writer();\n try stdout.print(\"Hello, world!\\n\", .{});\n}\n```\n\n```text\nstd.log.info\n```\n\n```text\nconst std = @import(\"std\");\n\npub fn main() !void {\n const stdout = std.io.getStdOut().writer();\n try stdout.print(\"Hello, {s}!\\n\", .{\"world\"});\n}\n```\n\n========================================\n\nComments:\n- i am using Zig 0.10 I've just now downloaded from the Downloads page.","metadata":{"transformedAt":"2026-08-18T18:33:48.843Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":7,"totalLines":114,"estimatedTokens":660}}55{"id":"stack-75762207","source":"stackoverflow","questionId":75762207,"title":"How to test multiple files in Zig?","tags":["testing","zig"],"text":"Title: How to test multiple files in Zig?\nTags: testing, zig\nSource: Stack Overflow\n\nQuestion:\nIn main.zig I am importing some file lexer.zig that contains some tests\n\n```\nconst lxr = @import(\"lexer\");\n\nsome code\n\ntest {\n std.testing.refAllDecls(@This());\n}\n```\n\nHowever when running `zig build test`, the tests in lexer.zig are ignored.\n\nHere are the relevant lines of the `build.zig` file\n\n```\nconst exe = b.addExecutable(\"main\", \"src/main.zig\");\nexe.addPackagePath(\"lexer\", \"src/lexer.zig\");\n\nconst exe_tests = b.addTest(\"src/main.zig\");\nexe_tests.addPackagePath(\"lexer\", \"src/lexer.zig\");\n\nconst test_step = b.step(\"test\", \"Run unit tests\");\ntest_step.dependOn(&exe_tests.step);\n```\n\n========================================\n\nTop Answer:\nI found that unless the import is marked `pub` it will not be tested. I have a standard build.zig file as generated by `zig init-exe` as of version 0.11.\n\nThis will test all tests for the imports marked pub. I am not sure if this is a good practice though, especially for an executable or library with private interfaces. Here is a simple example:\n\nmain.zig\n\n```\npub const lxr = @import(\"lexer.zig\");\n\npub fn main() void {}\n\ntest {\n std.testing.refAllDecls(@This());\n}\n```\n\nlexer.zig\n\n```\nconst std = @import(\"std\");\n\ntest \"lexer test\" {\n try std.testing.expect(0 == 1);\n}\n```\n\n========================================\n\nCode:\n```text\nconst lxr = @import(\"lexer\");\n\nsome code\n\ntest {\n std.testing.refAllDecls(@This());\n}\n```\n\n```text\nconst exe = b.addExecutable(\"main\", \"src/main.zig\");\nexe.addPackagePath(\"lexer\", \"src/lexer.zig\");\n\nconst exe_tests = b.addTest(\"src/main.zig\");\nexe_tests.addPackagePath(\"lexer\", \"src/lexer.zig\");\n\nconst test_step = b.step(\"test\", \"Run unit tests\");\ntest_step.dependOn(&exe_tests.step);\n```\n\n```text\nzig build test\n```\n\n```text\nbuild.zig\n```\n\n```text\ncomptime {\n _ = @import(\"lexer.zig\");\n // And all other files\n}\n```\n\n```text\nlexer.zig\n```\n\n```text\nlexer.zig\n```\n\n```text\nrefAllDecl\n```\n\n```text\ntests.zig\n```\n\n```text\nbuild.zig\n```\n\n```text\nb.addTest(\"src/main.zig\")\n```\n\n```text\nb.addTest(\"src/tests.zig\")\n```\n\n```text\npub const lxr = @import(\"lexer.zig\");\n\npub fn main() void {}\n\ntest {\n std.testing.refAllDecls(@This());\n}\n```\n\n```text\nconst std = @import(\"std\");\n\ntest \"lexer test\" {\n try std.testing.expect(0 == 1);\n}\n```\n\n```text\npub\n```\n\n```text\nzig init-exe\n```\n\n========================================\n\nComments:\n- Great, thank you, what is the reason to use comptime here?\n- @John It forces Zig to import the files. You could try dropping the `comptime`, you'll find that the tests get excluded again.\n- I have one last question if you don't mind, when to import as a package and when to import as a file? Thanks\n- Packages are for third-party libraries. Unless you're making part of the project into an independent library, you should always import as a file.","metadata":{"transformedAt":"2026-08-18T18:33:48.843Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":16,"totalLines":161,"estimatedTokens":716}}56{"id":"stack-78189804","source":"stackoverflow","questionId":78189804,"title":"How to define a comptime array of arrays of divergent size","tags":["multidimensional-array","literals","zig"],"text":"Title: How to define a comptime array of arrays of divergent size\nTags: multidimensional-array, literals, zig\nSource: Stack Overflow\n\nQuestion:\nI am very new to zig and doing a very simple coding exercise. The question is about scoring words in scrabble and presents a table. As a sort of challenge I wanted to replicate the scoring table as an array of arrays where the index of the outer array represent the points for a letter and the inner arrays contain the letters that match that score. Then I wanted to convert this to a lookup table (really just a flat array of scores) in `comptime`. I also wanted to be able to change the table without having to change any of the conversion code.\n\nI'm currently having difficulty with the very initial part, declaring the multi dimensional input array. I've tried this:\n\n```\nconst point_letters = [_][_]u8 {\n [_]u8{'A', 'E', 'I', 'O', 'U', 'L', 'N', 'R', 'S', 'T',},\n [_]u8{'D', 'G',},\n [_]u8{'B', 'C', 'M', 'P',},\n [_]u8{'F', 'H', 'V', 'W', 'Y',},\n [_]u8{'K',},\n [_]u8{},\n [_]u8{},\n [_]u8{'J', 'X',},\n [_]u8{},\n [_]u8{'Q', 'Z',},\n};\n```\n\nas well as\n\n```\nconst point_letters = [_](*[_]u8){\n ([_]u8{'A', 'E', 'I', 'O', 'U', 'L', 'N', 'R', 'S', 'T',}).*,\n ([_]u8{'D', 'G',}).*,\n ([_]u8{'B', 'C', 'M', 'P',}).*,\n ([_]u8{'F', 'H', 'V', 'W', 'Y',}).*,\n ([_]u8{'K',}).*,\n ([_]u8{}).*,\n ([_]u8{}).*,\n ([_]u8{'J', 'X',}).*,\n ([_]u8{}).*,\n ([_]u8{'Q', 'Z',}).*,\n};\n```\n\nBut they both give the same error pointing at the size for the inner arrays:\n\nerror: unable to infer array size\n\n========================================\n\nTop Answer:\nThis seems to work:\n\n```\nconst std = @import(\"std\");\n\npub fn main() void {\n const point_letters = [10][]const u8{ \"AEIOULNRST\", \"DG\", \"BCMP\", \"FHVWY\", \"K\", \"\", \"\", \"JX\", \"\", \"QZ\" };\n std.debug.print(\"Point_letters = {s}\\n\", .{point_letters[0]});\n}\n```\n\nBut I'm not sure this would work for Scrabble, and not sure if this represents exactly what you have there, mainly the empty elements. A set might work better, but there's no such primitive type. Anyhow, you can search for specific letters in these strings, as explained here, for instance (using `std.mem`)\n\n========================================\n\nCode:\n```zig\nconst point_letters = [_][_]u8 {\n [_]u8{'A', 'E', 'I', 'O', 'U', 'L', 'N', 'R', 'S', 'T',},\n [_]u8{'D', 'G',},\n [_]u8{'B', 'C', 'M', 'P',},\n [_]u8{'F', 'H', 'V', 'W', 'Y',},\n [_]u8{'K',},\n [_]u8{},\n [_]u8{},\n [_]u8{'J', 'X',},\n [_]u8{},\n [_]u8{'Q', 'Z',},\n};\n```\n\n```zig\nconst point_letters = [_](*[_]u8){\n ([_]u8{'A', 'E', 'I', 'O', 'U', 'L', 'N', 'R', 'S', 'T',}).*,\n ([_]u8{'D', 'G',}).*,\n ([_]u8{'B', 'C', 'M', 'P',}).*,\n ([_]u8{'F', 'H', 'V', 'W', 'Y',}).*,\n ([_]u8{'K',}).*,\n ([_]u8{}).*,\n ([_]u8{}).*,\n ([_]u8{'J', 'X',}).*,\n ([_]u8{}).*,\n ([_]u8{'Q', 'Z',}).*,\n};\n```\n\n```text\ncomptime\n```\n\n```zig\nconst point_letters = [_][]u8 {\n @constCast(&[_]u8{'A', 'E', 'I', 'O', 'U', 'L', 'N', 'R', 'S', 'T',}),\n @constCast(&[_]u8{'D', 'G',}),\n // …\n};\n```\n\n```zig\nfn slice(comptime a: anytype) []u8 {\n return @constCast(&a);\n}\n\nconst point_letters = [_][]u8 {\n slice([_]u8{'A', 'E', 'I', 'O', 'U', 'L', 'N', 'R', 'S', 'T',}),\n slice([_]u8{'D', 'G',}),\n // …\n};\n```\n\n```zig\nconst point_letters = [_][]const u8 {\n &[_]u8{'A', 'E', 'I', 'O', 'U', 'L', 'N', 'R', 'S', 'T',},\n &[_]u8{'D', 'G',},\n // …\n};\n```\n\n```text\npoint_letters\n```\n\n```text\n[_][]u8\n```\n\n```text\n&[_]u8{ … }\n```\n\n```text\n[_]u8{ … }\n```\n\n```text\n@constCast\n```\n\n```text\n@ptrCast\n```\n\n```text\n&[_]u8{ … }\n```\n\n```text\npoint_letters\n```\n\n```text\n[_][]const u8\n```\n\n```text\nu8\n```\n\n```text\n&[_]u8{'A', 'E', …}\n```\n\n```text\n\"AEIOULNRST\"\n```\n\n```zig\nconst std = @import(\"std\");\n\npub fn main() void {\n const point_letters = [10][]const u8{ \"AEIOULNRST\", \"DG\", \"BCMP\", \"FHVWY\", \"K\", \"\", \"\", \"JX\", \"\", \"QZ\" };\n std.debug.print(\"Point_letters = {s}\\n\", .{point_letters[0]});\n}\n```\n\n```text\nstd.mem\n```\n\n========================================\n\nComments:\n- This is a great answer to my specific problem, but it isn't as widely applicable as the other answer -- what if instead of slices of u8 we had arrays of structs -- hence I marked the other one as correct. But thank you for writing it up anyway. It's still very useful. I think it's also very interesting that we don't have to cast it to a slice like an array. I was wondering why, and found this to be very informative: zig.news/kristoff/what-s-a-string-literal-in-zig-31e9","metadata":{"transformedAt":"2026-08-18T18:33:48.843Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":20,"totalLines":191,"estimatedTokens":1118}}57{"id":"stack-77115835","source":"stackoverflow","questionId":77115835,"title":"Does Zig call defer after block breaks?","tags":["zig"],"text":"Title: Does Zig call defer after block breaks?\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nGiven the following snippet, does the call to unlock occur after the break or before?\n\n```\nvar input_data: InputState = blk: {\n user.input_mutex.lock();\n defer user.input_mutex.unlock();\n break :blk user.input;\n};\n```\n\n========================================\n\nTop Answer:\nYes, at least as of zig version `0.12.0-dev.167+dd6a9caea`\n\nRunning the following snippet:\n\n```\nconst std = @import(\"std\");\n\nfn getRandom() !u64 {\n var seed: u64 = undefined;\n try std.os.getrandom(std.mem.asBytes(&seed));\n std.debug.print(\"test seed: {}\\n\", .{seed});\n return seed;\n}\n\npub fn main() !void {\n var value = blk: {\n defer std.debug.print(\"defer test seed\\n\", .{});\n break :blk try getRandom();\n };\n _ = value;\n}\n```\n\nWill show the following in console output:\n\n```\ntest seed: 6866361107008308078\ndefer test seed\n```\n\n========================================\n\nCode:\n```text\nvar input_data: InputState = blk: {\n user.input_mutex.lock();\n defer user.input_mutex.unlock();\n break :blk user.input;\n};\n```\n\n```text\ndefer\n```\n\n```text\nbreak\n```\n\n```text\nerrdefer\n```\n\n```text\nerrdefer\n```\n\n```text\nreturn error.SomeError\n```\n\n```text\nconst std = @import(\"std\");\n\nfn getRandom() !u64 {\n var seed: u64 = undefined;\n try std.os.getrandom(std.mem.asBytes(&seed));\n std.debug.print(\"test seed: {}\\n\", .{seed});\n return seed;\n}\n\npub fn main() !void {\n var value = blk: {\n defer std.debug.print(\"defer test seed\\n\", .{});\n break :blk try getRandom();\n };\n _ = value;\n}\n```\n\n```text\ntest seed: 6866361107008308078\ndefer test seed\n```\n\n```text\n0.12.0-dev.167+dd6a9caea\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.843Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":9,"totalLines":106,"estimatedTokens":419}}58{"id":"stack-65876143","source":"stackoverflow","questionId":65876143,"title":"does zig cc expose a linker (ld)?","tags":["zig"],"text":"Title: does zig cc expose a linker (ld)?\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI am trying to compile xz with `zig cc` on Linux without build tools except zig:\n\n```\n$ zig version\n0.8.0-dev.1039+bea791b63\n$ export CC=\"zig cc\"\n$ ./configure\n\nchecking for ld used by zig cc... no\nconfigure: error: no acceptable ld found in $PATH\n```\n\nWhich is true: system does not have a linker. And zig doesn't advertise one:\n\n```\n$ zig cc -print-prog-name=ld\nld\n```\n\nCan/does `zig cc` provide a linker?\n\n========================================\n\nCode:\n```text\n$ zig version\n0.8.0-dev.1039+bea791b63\n$ export CC=\"zig cc\"\n$ ./configure\n<...>\nchecking for ld used by zig cc... no\nconfigure: error: no acceptable ld found in $PATH\n```\n\n```text\n$ zig cc -print-prog-name=ld\nld\n```\n\n```text\nzig cc\n```\n\n```text\nzig cc\n```\n\n```text\nzig ld.lld\n```\n\n```text\nzig ld\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.843Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":6,"totalLines":59,"estimatedTokens":213}}59{"id":"stack-77304731","source":"stackoverflow","questionId":77304731,"title":"How to declare a multiline string in Zig?","tags":["string","multiline","string-literals","zig"],"text":"Title: How to declare a multiline string in Zig?\nTags: string, multiline, string-literals, zig\nSource: Stack Overflow\n\nQuestion:\nHow can I write a string that spans over multiple lines in Zig?\n\nFor example:\n\n```\nvar str = `hello\nsecond line\nworld\nfourth line\n`\n```\n\n========================================\n\nTop Answer:\nFollowing the previous excellent response, it seems like you are referring to the Zig documentation, specifically section 5.3.2, Multiline-String-Literals. I believe implementing this example would look something like this:\n\n```\nconst print = @import(\"std\").debug.print;\nconst mem = @import(\"std\").mem; // will be used to compare bytes\n\nconst hello_world_in_c =\n \\\\#include \n \\\\\n \\\\int main(int argc, char **argv) {\n \\\\ printf(\"hello world\\n\");\n \\\\ return 0;\n \\\\}\n;\n\npub fn main() void {\n print(\"{s}\\n\", .{hello_world_in_c});\n}\n```\n\nOutput:\n\n### \n\n```\ninclude \n\nint main(int argc, char **argv) {\n printf(\"hello world\\n\");\n return 0;\n}\n```\n\n========================================\n\nCode:\n```golang\nvar str = `hello\nsecond line\nworld\nfourth line\n`\n```\n\n```js\nconst str =\n \\\\hello\n \\\\second line\n \\\\world\n \\\\fourth line\n;\n```\n\n```js\nconst array_of_multiline_strings = [_][]const u8{\n \\\\hello\n \\\\world\n ,\n \\\\goodbye\n \\\\world\n};\n```\n\n```text\n\\\\\n```\n\n```text\n;\n```\n\n```text\nconst print = @import(\"std\").debug.print;\nconst mem = @import(\"std\").mem; // will be used to compare bytes\n\nconst hello_world_in_c =\n \\\\#include <stdio.h>\n \\\\\n \\\\int main(int argc, char **argv) {\n \\\\ printf(\"hello world\\n\");\n \\\\ return 0;\n \\\\}\n;\n\npub fn main() void {\n print(\"{s}\\n\", .{hello_world_in_c});\n}\n```\n\n```text\ninclude <stdio.h>\n\nint main(int argc, char **argv) {\n printf(\"hello world\\n\");\n return 0;\n}\n```\n\n========================================\n\nComments:\n- ziglang.org/documentation/master/#Multiline-String-Literals","metadata":{"transformedAt":"2026-08-18T18:33:48.843Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":7,"totalLines":122,"estimatedTokens":470}}60{"id":"stack-64454924","source":"stackoverflow","questionId":64454924,"title":"How can I create multidimensional arrays of arbitrary sizes?","tags":["arrays","multidimensional-array","zig"],"text":"Title: How can I create multidimensional arrays of arbitrary sizes?\nTags: arrays, multidimensional-array, zig\nSource: Stack Overflow\n\nQuestion:\nI am writing a function in Zig that should accept multidimensional arrays of arbitrary sizes. There can be limits but I am unable to hardcode the sizes in advance.\n\nHere is an example:\n\n```\nconst warn = @import(\"std\").debug.warn;\n\nfn printMap(map: []const [4]bool) void {\n for (map) |row| {\n for (row) |tile| {\n warn(\"{}\\t\", .{tile});\n }\n warn(\"\\n\", .{});\n }\n}\n\npub fn main() !void {\n const map = [_][4]bool{\n [_]bool{ false, false, false, false },\n [_]bool{ false, true, true, false },\n [_]bool{ false, true, true, false },\n [_]bool{ false, false, false, false },\n };\n printMap(map[0..]);\n}\n```\n\nThis compiles and runs but if I change the function signature to\n\n```\nfn printMap(map: []const []bool) void\n```\n\nI receive the error\n\n```\nexpected type '[]const []bool', found '[]const [4]bool'\n```\n\nIs this possible to express in Zig?\n\n========================================\n\nCode:\n```text\nconst warn = @import(\"std\").debug.warn;\n\nfn printMap(map: []const [4]bool) void {\n for (map) |row| {\n for (row) |tile| {\n warn(\"{}\\t\", .{tile});\n }\n warn(\"\\n\", .{});\n }\n}\n\npub fn main() !void {\n const map = [_][4]bool{\n [_]bool{ false, false, false, false },\n [_]bool{ false, true, true, false },\n [_]bool{ false, true, true, false },\n [_]bool{ false, false, false, false },\n };\n printMap(map[0..]);\n}\n```\n\n```text\nfn printMap(map: []const []bool) void\n```\n\n```text\nexpected type '[]const []bool', found '[]const [4]bool'\n```\n\n```text\nvar a = [_]bool{ false, false, true };\nvar b = [_]bool{ false, true, false };\n\nconst map = [_][]bool{\n a[0..], // Make it a slice using slice syntax\n &b, // Or make it a slice by coercing *[N]T to []T\n};\n\nvar c: []const []bool = map[0..]; // Pass it as a slice of slices\nprintMap(c);\n```\n\n```text\nfn buildMap(x: u8, y: u8, allocator: *std.mem.Allocator) ![][]bool {\n var map: [][]bool = undefined;\n map = try allocator.alloc([]bool, x);\n for (map) |*row| {\n row.* = try allocator.alloc(bool, y);\n }\n return map;\n}\n```\n\n```text\nmap\n```\n\n```text\n[4][4]bool\n```\n\n```text\nprintMap\n```\n\n```text\n[][]bool\n```\n\n```text\nprintMap(map: []const []bool)\n```\n\n```text\nprintMap(map: []const []bool)\n```\n\n========================================\n\nComments:\n- Glad to help, I'm still playing with Zig myself, so can't promise it's the best way to do it =D","metadata":{"transformedAt":"2026-08-18T18:33:48.843Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":11,"totalLines":132,"estimatedTokens":629}}61{"id":"stack-77145268","source":"stackoverflow","questionId":77145268,"title":"Fatal error: 'stdio.h' file not found in compiling c file","tags":["zig"],"text":"Title: Fatal error: 'stdio.h' file not found in compiling c file\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI downloaded `libwsclient` c library as `git clone https://github.com/payden/libwsclient.git`\nInside the generated folder `libwsclient` I wrote `build.zig` as:\n\n```\nconst Builder = @import(\"std\").build.Builder;\n\npub fn build(b: *Builder) void {\n const target = b.standardTargetOptions(.{});\n const mode = b.standardOptimizeOption(.{});\n const lib = b.addStaticLibrary(.{\n .name = \"wsclientlib\",\n .root_source_file = .{ .path = \"wsclient.c\" },\n .target = target,\n .optimize = mode,\n });\n b.installArtifact(lib);\n}\n```\n\nAnd tried to build the library as `zig build` but I got the below:\n\n```\n[hasany@hasan-20tes1n300 libwsclient]$ zig build\nzig build-lib wsclientlib Debug native: error: error(compilation): clang failed with stderr: /home/hasany/Documents/zig-tutorial/chrome-development-tool/libwsclient/wsclient.c:1:10: fatal error: 'stdio.h' file not found\n\nzig build-lib wsclientlib Debug native: error: the following command failed with 1 compilation errors:\n/usr/bin/zig build-lib /home/hasany/Documents/zig-tutorial/chrome-development-tool/libwsclient/wsclient.c --cache-dir /home/hasany/Documents/zig-tutorial/chrome-development-tool/libwsclient/zig-cache --global-cache-dir /home/hasany/.cache/zig --name wsclientlib -static --listen=- \nBuild Summary: 0/3 steps succeeded; 1 failed (disable with --summary none)\ninstall transitive failure\n└─ install wsclientlib transitive failure\n └─ zig build-lib wsclientlib Debug native 1 errors\n/home/hasany/Documents/zig-tutorial/chrome-development-tool/libwsclient/wsclient.c:1:1: error: unable to build C object: clang exited with code 1\n```\n\n========================================\n\nTop Answer:\n\"Porting\" the wclient build system to the Zig build system might be possible, but there is a lot of (implicit) configuration in the current autogen+configure+Makefile.am build system it uses. At a minimum the current wsclient build includes more files than just \"wsclient.c\" (there is also \"base64.c\" and \"sha1.c\").\n\nDepending on what you are trying to accomplish, you might have better luck if\nyou the libwsclient build instructions to build the wsclient library, then link the built library into your Zig program.\n\n========================================\n\nCode:\n```rs\nconst Builder = @import(\"std\").build.Builder;\n\npub fn build(b: *Builder) void {\n const target = b.standardTargetOptions(.{});\n const mode = b.standardOptimizeOption(.{});\n const lib = b.addStaticLibrary(.{\n .name = \"wsclientlib\",\n .root_source_file = .{ .path = \"wsclient.c\" },\n .target = target,\n .optimize = mode,\n });\n b.installArtifact(lib);\n}\n```\n\n```text\n[hasany@hasan-20tes1n300 libwsclient]$ zig build\nzig build-lib wsclientlib Debug native: error: error(compilation): clang failed with stderr: /home/hasany/Documents/zig-tutorial/chrome-development-tool/libwsclient/wsclient.c:1:10: fatal error: 'stdio.h' file not found\n\nzig build-lib wsclientlib Debug native: error: the following command failed with 1 compilation errors:\n/usr/bin/zig build-lib /home/hasany/Documents/zig-tutorial/chrome-development-tool/libwsclient/wsclient.c --cache-dir /home/hasany/Documents/zig-tutorial/chrome-development-tool/libwsclient/zig-cache --global-cache-dir /home/hasany/.cache/zig --name wsclientlib -static --listen=- \nBuild Summary: 0/3 steps succeeded; 1 failed (disable with --summary none)\ninstall transitive failure\n└─ install wsclientlib transitive failure\n └─ zig build-lib wsclientlib Debug native 1 errors\n/home/hasany/Documents/zig-tutorial/chrome-development-tool/libwsclient/wsclient.c:1:1: error: unable to build C object: clang exited with code 1\n```\n\n```text\nlibwsclient\n```\n\n```text\ngit clone https://github.com/payden/libwsclient.git\n```\n\n```text\nlibwsclient\n```\n\n```text\nbuild.zig\n```\n\n```text\nzig build\n```\n\n```text\nlib.linkLibC();\n```\n\n```text\nbuild.zig\n```\n\n```text\n-lc\n```\n\n```text\nzig build-lib\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.843Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":11,"totalLines":114,"estimatedTokens":998}}62{"id":"stack-79734179","source":"stackoverflow","questionId":79734179,"title":"How can I iterate over struct fields at compile time in Zig to generate a serializer?","tags":["serialization","reflection","code-generation","compile-time","zig"],"text":"Title: How can I iterate over struct fields at compile time in Zig to generate a serializer?\nTags: serialization, reflection, code-generation, compile-time, zig\nSource: Stack Overflow\n\nQuestion:\nI'm learning Zig and I'm trying to write a generic function that automatically serializes any struct into JSON. In languages like Rust or Go, there are libraries that can iterate over the fields of a struct at compile time. I was hoping to do something similar in Zig using `@typeInfo`.\n\nHere is a simplified example of what I'm trying to do:\n\n```\nconst std = @import(\"std\");\n\nconst Example = struct {\n a: i32,\n b: []const u8,\n c: bool,\n};\n\npub fn toJson(comptime T: type, value: T) []const u8 {\n // iterate over T's fields here\n // return a JSON string like {\"a\":1,\"b\":\"hello\",\"c\":true}\n}\n```\n\nI tried inspecting `@typeInfo(T)` and matching on `TypeInfo.Struct` to get the `fields` array, but I can't figure out how to loop over it in a way that works at compile time. If I write a normal `for` loop inside the function, Zig complains that it cannot evaluate it at compile time. If I try to use `inline for`, I get \"expected comptime expression\" errors. I've also looked at examples in the standard library but they use hard-coded field names.\n\nWhat I've tried:\n\n- Using `@typeInfo(T).Struct.fields` inside an `inline for` loop. The compiler errors with \"`index` is not comptime-known\".\n\n- Attempting to build a `[]const u8` by concatenating the field names and values, but I run into lifetime and allocation issues since I can't allocate memory at comptime.\n\n- Searching the docs and examples for \"reflection\" or \"struct fields\" but most examples are about enums.\n\nIs there a supported way in Zig (0.11 or 0.12) to iterate over the fields of a struct at compile time so I can generate code based on them? Or is this not possible and I need to manually write serialization functions for each struct?\n\nAny pointers or examples would be greatly appreciated!\n\n========================================\n\nCode:\n```text\nconst std = @import(\"std\");\n\nconst Example = struct {\n a: i32,\n b: []const u8,\n c: bool,\n};\n\npub fn toJson(comptime T: type, value: T) []const u8 {\n // iterate over T's fields here\n // return a JSON string like {\"a\":1,\"b\":\"hello\",\"c\":true}\n}\n```\n\n```text\n@typeInfo\n```\n\n```text\n@typeInfo(T)\n```\n\n```text\nTypeInfo.Struct\n```\n\n```text\nfields\n```\n\n```text\nfor\n```\n\n```text\ninline for\n```\n\n```text\n@typeInfo(T).Struct.fields\n```\n\n```text\ninline for\n```\n\n```text\nindex\n```\n\n```text\n[]const u8\n```\n\n```none\nconst std = @import(\"std\");\n\ntest \"fields\" {\n const U1s = packed struct {\n a: u1,\n b: u1,\n c: u1,\n };\n\n const x = U1s{ .a = 1, .b = 0, .c = 0 };\n inline for (std.meta.fields(@TypeOf(x))) |f| {\n std.debug.print(f.name ++ \" {}\\n\", .{ @as(f.type, @field(x, f.name)) });\n }\n}\n```\n\n```text\n$ zig build test\ntest\n└─ run test stderr\na 1\nb 0\nc 0\n```\n\n```text\n@TypeOf\n```\n\n```text\n@field\n```\n\n========================================\n\nComments:\n- Why not 0.14? Why 0.11 or 0.12?","metadata":{"transformedAt":"2026-08-18T18:33:48.843Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":15,"totalLines":134,"estimatedTokens":760}}63{"id":"stack-77613946","source":"stackoverflow","questionId":77613946,"title":"Casting in Zig (like usize to i32 and more)","tags":["casting","zig"],"text":"Title: Casting in Zig (like usize to i32 and more)\nTags: casting, zig\nSource: Stack Overflow\n\nQuestion:\nAs in other higher then asm level languages like Java, i want to cast values, compare it and more.\n\nFor example filling array like this:\n\n```\nvar array: [10]i32 = undefined;\n\n for (0..array.len) |i|\n array[i] = i;\n```\n\nBut compiler says:\n\n```\nC:\\Zig\\projects\\test\\src>zig run main.zig\nmain.zig:7:20: error: expected type 'i32', found 'usize'\n array[i] = i;\n ^\nmain.zig:7:20: note: signed 32-bit int cannot represent all possible unsigned 64-bit values\nreferenced by:\n callMain: C:\\Zig\\lib\\std\\start.zig:585:32\n initEventLoopAndCallMain: C:\\Zig\\lib\\std\\start.zig:519:34\n remaining reference traces hidden; use '-freference-trace' to see all reference traces\n```\n\nand i have no idea how to fix this, because all ways to do this before doesnt work. And also i need u32 to i32, f32 to i32 and so for later. Please help me\n\n========================================\n\nCode:\n```text\nvar array: [10]i32 = undefined;\n\n for (0..array.len) |i|\n array[i] = i;\n```\n\n```text\nC:\\Zig\\projects\\test\\src>zig run main.zig\nmain.zig:7:20: error: expected type 'i32', found 'usize'\n array[i] = i;\n ^\nmain.zig:7:20: note: signed 32-bit int cannot represent all possible unsigned 64-bit values\nreferenced by:\n callMain: C:\\Zig\\lib\\std\\start.zig:585:32\n initEventLoopAndCallMain: C:\\Zig\\lib\\std\\start.zig:519:34\n remaining reference traces hidden; use '-freference-trace' to see all reference traces\n```\n\n```text\nvar array: [10]i32 = undefined;\n\nfor (0..array.len) |i|\n array[i] = @intCast(i);\n```\n\n```text\n@intCast\n```\n\n```text\n@intCast\n```\n\n========================================\n\nComments:\n- \" because all ways to do this before doesnt work.\" what ways before this don't work?\n- Does this answer your question? How do I (unsafely) cast from `u64` to `i64` in Zig?\n- @sigod actualy it is! thanks","metadata":{"transformedAt":"2026-08-18T18:33:48.843Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":5,"totalLines":75,"estimatedTokens":481}}64{"id":"stack-77466479","source":"stackoverflow","questionId":77466479,"title":"compile CPython extension written in Zig on Windows","tags":["windows","visual-c++","cpython","zig"],"text":"Title: compile CPython extension written in Zig on Windows\nTags: windows, visual-c++, cpython, zig\nSource: Stack Overflow\n\nQuestion:\nZig is able to import C libraries and therefore it can be used to write a CPython extension and compile it. This is potentially really useful for me.\n\nHere's my simple.zig Python extension\n\n```\nconst py = @cImport({\n @cDefine(\"PY_SSIZE_T_CLEAN\", {});\n @cInclude(\"Python.h\");\n});\nconst std = @import(\"std\");\nconst print = std.debug.print;\n\nconst PyObject = py.PyObject;\nconst PyMethodDef = py.PyMethodDef;\nconst PyModuleDef = py.PyModuleDef;\nconst PyModuleDef_Base = py.PyModuleDef_Base;\nconst Py_BuildValue = py.Py_BuildValue;\nconst PyModule_Create = py.PyModule_Create;\nconst METH_NOARGS = py.METH_NOARGS;\n\nfn hello(self: [*c]PyObject, args: [*c]PyObject) callconv(.C) [*]PyObject {\n _ = self;\n _ = args;\n print(\"welcom to ziglang\\n\", .{});\n return Py_BuildValue(\"\");\n}\n\nvar Methods = [_]PyMethodDef{\n PyMethodDef{\n .ml_name = \"hello\",\n .ml_meth = hello,\n .ml_flags = METH_NOARGS,\n .ml_doc = null,\n },\n PyMethodDef{\n .ml_name = null,\n .ml_meth = null,\n .ml_flags = 0,\n .ml_doc = null,\n },\n};\n\nvar module = PyModuleDef{\n .m_base = PyModuleDef_Base{\n .ob_base = PyObject{\n .ob_refcnt = 1,\n .ob_type = null,\n },\n .m_init = null,\n .m_index = 0,\n .m_copy = null,\n },\n .m_name = \"simple\",\n .m_doc = null,\n .m_size = -1,\n .m_methods = &Methods,\n .m_slots = null,\n .m_traverse = null,\n .m_clear = null,\n .m_free = null,\n};\n\npub export fn PyInit_simple() [*]PyObject {\n return PyModule_Create(&module);\n}\n```\n\nWhen I compile my CPython extension written in Zig with the Zig compiler, Python is unable to import the DLL. I am using Windows 10.\n\n```\nzig build-lib -lc -dynamic -target x86_64-windows-msvc -I\"C:\\Users\\me\\Anaconda3\\include\" -L\"C:\\Users\\me\\Anaconda3\\libs\" -l\"python39\" simple.zig\n```\n\nWhen I try to import simple.dll, Python says no module found. I am using the os module to add the directory containing my extension DLL to the extension search locations, as I believe is required on Windows since Python 3.8.\n\n```\nimport os\nos.add_dll_directory(r\"C:\\Users\\me\\my_zig_project\")\nimport simple\nModuleNotFoundError: No module named 'simple'\n```\n\nI suspect the problem is that CPython on Windows is compiled with the MSVC compiler (version of MSVC depends on Python version) and the Zig compiler is not compatible somehow even though I specify target environment as Windows MSVC.\n\nIs there a way to compile a CPython extension written in Zig to run on Windows?\n\nA minimal example would be greatly appreciated if it is possible.\n\n========================================\n\nTop Answer:\nI haven't been able to use the typical `setuptools` methods to create Python modules using Zig, but I have been able to use the `wheel` module to create modules which link DLL files compiled with Zig that can then be installed with Pip. Here is a minimal example.\n\nYou will need to install the `setuptools` and `wheel` modules first if they aren't already installed on your system. I took inspiration from this informative SO answer.\n\nCreate a directory structure like this:\n\n```\nhello_zig_mod/\n|\n|-- setup.py\n|\n|-- hello/\n |\n |-- __init__.py\n |\n |-- hello.zig\n```\n\nThe `hello.zig` file is the Zig code that will be compiled to a DLL:\n\n```\nconst std = @import(\"std\");\n\npub export fn message(msg: [*c]const u8) void {\n std.debug.print(\"Hello, {s}!\\n\", .{std.mem.span(msg)});\n}\n```\n\nThe `__init__.py` file is a Python file used to initialize the module. It links to the DLL and wraps the `message` function found there in a Python function:\n\n```\nfrom ctypes import *\nimport os\nlib_path = os.path.join(os.path.dirname(__file__), 'hello.dll')\nlib = CDLL(lib_path)\n\ndef message(msg):\n lib.message(bytes(msg, 'utf-8'))\n```\n\nThe `setup.py` file is used to build a wheel that can be installed by Pip. You can read more about the details of this file at the answer I linked above.\n\n```\nfrom setuptools import setup, Distribution\n\nclass BinaryDistribution(Distribution):\n def has_ext_modules(foo):\n return True\n\nsetup(\n name=\"hello\",\n packages=['hello'],\n package_data={\n 'hello':['hello.dll'],\n },\n distclass=BinaryDistribution\n)\n```\n\nGo into the `hello/` directory and build a dynamic library with the Zig compiler.\n\n```\n> zig build-lib .\\hello.zig -dynamic\n```\n\nThis will build the DLL along with some other artifacts. Now go back to the `hello_zig_mod` directory and build the wheel:\n\n```\n> python setup.py bdist_wheel\n```\n\nThis will build the wheel in `dist\\` as a `.whl` file along with other artifacts. You can now finally install the wheel with Pip:\n\n```\n> pip install .\\dist\\hello-0.0.0-cp312-cp312-win_amd64.whl\n```\n\nChecking in a Python REPL:\n\n```\n>>> import hello\n>>> hello.message(\"Zig Module\")\nHello, Zig Module!\n```\n\n========================================\n\nCode:\n```text\nconst py = @cImport({\n @cDefine(\"PY_SSIZE_T_CLEAN\", {});\n @cInclude(\"Python.h\");\n});\nconst std = @import(\"std\");\nconst print = std.debug.print;\n\nconst PyObject = py.PyObject;\nconst PyMethodDef = py.PyMethodDef;\nconst PyModuleDef = py.PyModuleDef;\nconst PyModuleDef_Base = py.PyModuleDef_Base;\nconst Py_BuildValue = py.Py_BuildValue;\nconst PyModule_Create = py.PyModule_Create;\nconst METH_NOARGS = py.METH_NOARGS;\n\nfn hello(self: [*c]PyObject, args: [*c]PyObject) callconv(.C) [*]PyObject {\n _ = self;\n _ = args;\n print(\"welcom to ziglang\\n\", .{});\n return Py_BuildValue(\"\");\n}\n\nvar Methods = [_]PyMethodDef{\n PyMethodDef{\n .ml_name = \"hello\",\n .ml_meth = hello,\n .ml_flags = METH_NOARGS,\n .ml_doc = null,\n },\n PyMethodDef{\n .ml_name = null,\n .ml_meth = null,\n .ml_flags = 0,\n .ml_doc = null,\n },\n};\n\nvar module = PyModuleDef{\n .m_base = PyModuleDef_Base{\n .ob_base = PyObject{\n .ob_refcnt = 1,\n .ob_type = null,\n },\n .m_init = null,\n .m_index = 0,\n .m_copy = null,\n },\n .m_name = \"simple\",\n .m_doc = null,\n .m_size = -1,\n .m_methods = &Methods,\n .m_slots = null,\n .m_traverse = null,\n .m_clear = null,\n .m_free = null,\n};\n\npub export fn PyInit_simple() [*]PyObject {\n return PyModule_Create(&module);\n}\n```\n\n```text\nzig build-lib -lc -dynamic -target x86_64-windows-msvc -I\"C:\\Users\\me\\Anaconda3\\include\" -L\"C:\\Users\\me\\Anaconda3\\libs\" -l\"python39\" simple.zig\n```\n\n```text\nimport os\nos.add_dll_directory(r\"C:\\Users\\me\\my_zig_project\")\nimport simple\nModuleNotFoundError: No module named 'simple'\n```\n\n```text\nconst py = @cImport({\n @cDefine(\"PY_SSIZE_T_CLEAN\", {});\n @cInclude(\"Python.h\");\n});\nconst std = @import(\"std\");\nconst print = std.debug.print;\n\nconst PyObject = py.PyObject;\nconst PyMethodDef = py.PyMethodDef;\nconst PyModuleDef = py.PyModuleDef;\nconst PyModuleDef_Base = py.PyModuleDef_Base;\nconst Py_BuildValue = py.Py_BuildValue;\nconst PyModule_Create = py.PyModule_Create;\nconst METH_NOARGS = py.METH_NOARGS;\n\nfn hello(self: [*c]PyObject, args: [*c]PyObject) callconv(.C) [*]PyObject {\n _ = self;\n _ = args;\n print(\"welcome to ziglang\\n\", .{});\n return Py_BuildValue(\"\");\n}\n\nvar Methods = [_]PyMethodDef{\n PyMethodDef{\n .ml_name = \"hello\",\n .ml_meth = hello,\n .ml_flags = METH_NOARGS,\n .ml_doc = null,\n },\n PyMethodDef{\n .ml_name = null,\n .ml_meth = null,\n .ml_flags = 0,\n .ml_doc = null,\n },\n};\n\nvar module = PyModuleDef{\n .m_base = PyModuleDef_Base{\n .ob_base = PyObject{\n .ob_refcnt = 1,\n .ob_type = null,\n },\n .m_init = null,\n .m_index = 0,\n .m_copy = null,\n },\n .m_name = \"simple\",\n .m_doc = null,\n .m_size = -1,\n .m_methods = &Methods,\n .m_slots = null,\n .m_traverse = null,\n .m_clear = null,\n .m_free = null,\n};\n\npub export fn PyInit_simple() [*]PyObject {\n return PyModule_Create(&module);\n}\n```\n\n```text\nzig build-lib -lc -dynamic -I\"<directory containing Python.h>\" -L\"<directory containing python3.lib>\" -l\"python3\" simple.zig\n```\n\n```text\n>>> import simple\n>>> simple.hello()\nwelcome to ziglang\n```\n\n```none\nhello_zig_mod/\n|\n|-- setup.py\n|\n|-- hello/\n |\n |-- __init__.py\n |\n |-- hello.zig\n```\n\n```text\nconst std = @import(\"std\");\n\npub export fn message(msg: [*c]const u8) void {\n std.debug.print(\"Hello, {s}!\\n\", .{std.mem.span(msg)});\n}\n```\n\n```py\nfrom ctypes import *\nimport os\nlib_path = os.path.join(os.path.dirname(__file__), 'hello.dll')\nlib = CDLL(lib_path)\n\ndef message(msg):\n lib.message(bytes(msg, 'utf-8'))\n```\n\n```py\nfrom setuptools import setup, Distribution\n\nclass BinaryDistribution(Distribution):\n def has_ext_modules(foo):\n return True\n\nsetup(\n name=\"hello\",\n packages=['hello'],\n package_data={\n 'hello':['hello.dll'],\n },\n distclass=BinaryDistribution\n)\n```\n\n```none\n> zig build-lib .\\hello.zig -dynamic\n```\n\n```none\n> python setup.py bdist_wheel\n```\n\n```none\n> pip install .\\dist\\hello-0.0.0-cp312-cp312-win_amd64.whl\n```\n\n```none\n>>> import hello\n>>> hello.message(\"Zig Module\")\nHello, Zig Module!\n```\n\n```text\nsetuptools\n```\n\n```text\nwheel\n```\n\n```text\nsetuptools\n```\n\n```text\nwheel\n```\n\n```text\nhello.zig\n```\n\n```text\n__init__.py\n```\n\n```text\nmessage\n```\n\n```text\nsetup.py\n```\n\n```text\nhello/\n```\n\n```text\nhello_zig_mod\n```\n\n```text\ndist\\\n```\n\n```text\n.whl\n```\n\n========================================\n\nComments:\n- [SO]: How to create a Minimal, Reproducible Example (reprex (mcve)). Add some minimal code, build and run commands, and output.\n- “A minimal example would be greatly appreciated if it is possible”, back to you: Please show us what you’re trying to do – a minimal module written in zig, how you’re compiling it, and how you’re trying to use it from python.\n- @Cubic hopefully I've addressed your points now.\n- Thanks. I was hoping to build an extension without using any other Python tools like setuptools but thanks for your example - it's a valid way to do it and has guided me to the missing piece of the puzzle, that I needed to rename simple.dll to simple.pyd. I need to include the -lc flag to the zig build-lib command so that it includes libc else I get io.h not found.","metadata":{"transformedAt":"2026-08-18T18:33:48.843Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":26,"totalLines":451,"estimatedTokens":2536}}65{"id":"stack-70102667","source":"stackoverflow","questionId":70102667,"title":"Converting a slice to an array","tags":["zig"],"text":"Title: Converting a slice to an array\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI have a slice that I have guaranteed (in runtime) that its length is at least 8. I want to convert that slice to an array because I need to use `std.mem.bytesAsValue()` in order to create an `f64` from raw bytes (for context, I'm implementing a binary serialization format).\n\nI solved it like this, but I'd like to know if there is a better syntax for achieving the same goal:\n\n```\nvar array: [8]u8 = undefined;\n array[0] = slice[0];\n array[1] = slice[1];\n array[2] = slice[2];\n array[3] = slice[3];\n array[4] = slice[4];\n array[5] = slice[5];\n array[6] = slice[6];\n array[7] = slice[7];\n```\n\n========================================\n\nTop Answer:\nyou can do this by dereferencing the slice\n\n```\nvar array = slice[0..8].*;\n```\n\nor using `std.mem.copy`\n\n```\nstd.mem.copy(u8, &array, slice[0..2]);\n```\n\nwhile i think you can just need to put `slice[0..8]` as argument instead creating a variable\n\n========================================\n\nCode:\n```text\nvar array: [8]u8 = undefined;\n array[0] = slice[0];\n array[1] = slice[1];\n array[2] = slice[2];\n array[3] = slice[3];\n array[4] = slice[4];\n array[5] = slice[5];\n array[6] = slice[6];\n array[7] = slice[7];\n```\n\n```text\nstd.mem.bytesAsValue()\n```\n\n```text\nf64\n```\n\n```text\n@ptrCast(*f64, slice.ptr)\n```\n\n```rs\nvar array = slice[0..8].*;\n```\n\n```rs\nstd.mem.copy(u8, &array, slice[0..2]);\n```\n\n```text\nstd.mem.copy\n```\n\n```text\nslice[0..8]\n```\n\n========================================\n\nComments:\n- Thanks. The first method gave the error `error: attempt to dereference non-pointer type '[]u8'` but the second method worked.\n- so you need to remove `.*`\n- @AndréStaltz `slice[0..8].*` should work correctly - `slice` is []u8, `slice[0..8]` is *[8]u8, `slice[0..8].*` should be `[8]u8`. I'm not sure why you're getting that error\n- Thanks for the tips! In my case, I actually have `slice[start..end]` not `slice[0..8]` so I got an error `cast increases pointer alignment`. I suppose the `0..8` informs the compiler that the size is exactly 8, while `start..end` doesn't, even if I have a runtime check that the diff between end and start is 8.\n- This is a solvable problem and it's not related to the size, if you were to pass to `bitCast` a value with the wrong size you would get a different error telling you that in explicit terms. I can't fully explain memory alignment in a SO comment, but tldr: \"well-formed\" f64 values must have their memory address always divisible by `@sizeOf(f64)` (which is 8). Your error is caused by the fact that the compiler is not sure that you will always increment `start` by 8 (or a multiple) every time. You can use `@alignCast` to make that promise (it's also safety checked by Zig at runtime).\n- Here's a godbolt that shows this zig.godbolt.org/z/zdo3T7a6n\n- Almost forgot: if you can't keep that promise (that `start` will always be a multiple of 8), then you can either go back to your copying code or you can tell Zig that you're going to reinterpret the memory in your byte array as a \"weirdly-aligned\" `f64`, which you can then copy into a normal `f64` variable (by dereferencing the pointer), which basically instructs the compiler to do the copy for you. I was already doing the copy in the second godbolt example. The align cast version is preferable because it might use better instructions depending on the target architecture.\n- Final godbolt example: zig.godbolt.org/z/rcbrezvzv","metadata":{"transformedAt":"2026-08-18T18:33:48.844Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":8,"totalLines":92,"estimatedTokens":872}}66{"id":"stack-67196385","source":"stackoverflow","questionId":67196385,"title":"What happen when program reach unreachable on ReleaseFast? (Zig lang)","tags":["unreachable-code","zig"],"text":"Title: What happen when program reach unreachable on ReleaseFast? (Zig lang)\nTags: unreachable-code, zig\nSource: Stack Overflow\n\nQuestion:\nI read on Zig Doc it has undefined behavior. is that it? isn't there any way tho predict the behavior of the code after hitting unreachable?\nlike if it's process next line or try to continue like unreachable never been there!\n\n========================================\n\nTop Answer:\nThat's it. If you could guarantee how the code would behave in any given scenario, that would be *defined* behavior.\n\nIf you want to know why undefined behavior exists, see here for a start.\n\n========================================\n\nCode:\n```text\nunreachable\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.844Z","totalAnswersIncluded":1,"totalCodeBlocksIncluded":1,"totalLines":21,"estimatedTokens":171}}67{"id":"stack-75909875","source":"stackoverflow","questionId":75909875,"title":"How to `#define` in build.zig for an imported C library","tags":["build","zig"],"text":"Title: How to `#define` in build.zig for an imported C library\nTags: build, zig\nSource: Stack Overflow\n\nQuestion:\nBased on my research `*LibExeObjStep`'s `defineCMacro` allows me to `#define` just like I would in C but it's not getting included in the package output:\n\n`--pkg-begin raygui C:\\git\\raylib-zig-experiments\\lib\\raygui-zig.zig --pkg-end -D RAYGUI_IMPLEMENTATION` (Note: it comes after `--pkg-end`)\n\nThis is the relevant snippet of my build.zig file where I'm attempting to include a c library:\n\n```\npub fn addRaygui(exe: *LibExeObjStep, target: std.zig.CrossTarget) *std.build.LibExeObjStep {\n const b = exe.builder;\n // Standard release options allow the person running `zig build` to select\n // between Debug, ReleaseSafe, ReleaseFast, and ReleaseSmall.\n const mode = b.standardReleaseOptions();\n\n const raygui = b.addStaticLibrary(\"raygui\", srcdir ++ \"/raygui.h\");\n exe.defineCMacro(\"RAYGUI_IMPLEMENTATION\", null);\n raygui.setTarget(target);\n raygui.setBuildMode(mode);\n // Make raylib.h available for import to raygui.h\n raygui.addIncludePath(\"raylib/src\");\n raygui.linkLibC();\n\n const raylib_flags = &[_][]const u8{\n \"-std=gnu99\",\n \"-DPLATFORM_DESKTOP\",\n \"-DGL_SILENCE_DEPRECATION=199309L\",\n \"-fno-sanitize=undefined\", // https://github.com/raysan5/raylib/issues/1891\n };\n raygui.addCSourceFiles(&.{\n srcdir ++ \"/raygui.c\",\n }, raylib_flags);\n\n return raygui;\n}\n```\n\nHow do I structure my build.zig file so that the defineCMacro is invoked INSIDE of the package?\n\n========================================\n\nCode:\n```text\npub fn addRaygui(exe: *LibExeObjStep, target: std.zig.CrossTarget) *std.build.LibExeObjStep {\n const b = exe.builder;\n // Standard release options allow the person running `zig build` to select\n // between Debug, ReleaseSafe, ReleaseFast, and ReleaseSmall.\n const mode = b.standardReleaseOptions();\n\n const raygui = b.addStaticLibrary(\"raygui\", srcdir ++ \"/raygui.h\");\n exe.defineCMacro(\"RAYGUI_IMPLEMENTATION\", null);\n raygui.setTarget(target);\n raygui.setBuildMode(mode);\n // Make raylib.h available for import to raygui.h\n raygui.addIncludePath(\"raylib/src\");\n raygui.linkLibC();\n\n const raylib_flags = &[_][]const u8{\n \"-std=gnu99\",\n \"-DPLATFORM_DESKTOP\",\n \"-DGL_SILENCE_DEPRECATION=199309L\",\n \"-fno-sanitize=undefined\", // https://github.com/raysan5/raylib/issues/1891\n };\n raygui.addCSourceFiles(&.{\n srcdir ++ \"/raygui.c\",\n }, raylib_flags);\n\n return raygui;\n}\n```\n\n```text\n*LibExeObjStep\n```\n\n```text\ndefineCMacro\n```\n\n```text\n#define\n```\n\n```text\n--pkg-begin raygui C:\\git\\raylib-zig-experiments\\lib\\raygui-zig.zig --pkg-end -D RAYGUI_IMPLEMENTATION\n```\n\n```text\n--pkg-end\n```\n\n```text\nraygui.defineCMacroRaw(\"RAYGUI_IMPLEMENTATION\");\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.844Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":7,"totalLines":97,"estimatedTokens":692}}68{"id":"stack-74709155","source":"stackoverflow","questionId":74709155,"title":"Am I using ArrayLists wrong in Zig when performing simple variable assignment changes function behaviour?","tags":["zig"],"text":"Title: Am I using ArrayLists wrong in Zig when performing simple variable assignment changes function behaviour?\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI have been doing Advent of Code this year, to learn Zig, and I discovered something during Day 5 that really confused me. So: mild spoilers for Day 5 of Advent of Code 2022, I guess?\n\nI decided to implement my solution to Day 5 as an ArrayList of ArrayLists of U8s, which has ended up working well. My full solution file is here (probably terribly un-idiomatic Zig, but we all have to start somewhere).\n\nAs part of my solution, I have a function, which I call moveCrates, on a struct which wraps my arraylist of arraylists.\n\nThe relevant part of the struct declaration looks as so:\n\n```\nconst BunchOfStacks = struct {\n stacks: ArrayList(ArrayList(u8)),\n ...\n```\n\nThis function is here, and looks like this:\n\n```\nfn moveCrates(self: *BunchOfStacks, amount: usize, source: usize, dest: usize) !void {\n const source_height = self.stacks.items[source - 1].items.len;\n const crate_slice = self.stacks.items[source - 1].items[(source_height - amount)..];\n try self.stacks.items[dest - 1].appendSlice(crate_slice);\n self.stacks.items[source - 1].shrinkRetainingCapacity(source_height - amount);\n }\n```\n\nYou can note that I refer 3 times to the source list by the very verbose reference `self.stacks.items[source - 1]`. This is not how I first wrote this function. I first wrote it like below:\n\n```\nfn moveCrates(self: *BunchOfStacks, amount: usize, source: usize, dest: usize) !void {\n var source_list: ArrayList(u8) = self.stacks.items[source - 1];\n const source_height = source_list.items.len;\n const crate_slice = source_list.items[(source_height - amount)..];\n try self.stacks.items[dest - 1].appendSlice(crate_slice);\n source_list.shrinkRetainingCapacity(source_height - amount);\n }\n```\n\nBut this second form, where I make a local variable for my convenience, DOES NOT GIVE THE CORRECT RESULTS! It compiles fine, but seems to always point `source_list` to the same internal `ArrayList(u8)` (whichever one it first picks) regardless of what the value of `source` is. This means that the test example produces incorrect output.\n\nThis function is called within a loop, like so:\n\n```\nwhile (instructions.next()) |_| {\n // First part is the verb, this is always \"move\" so skip it\n // Get the amount next\n const amount: usize = try std.fmt.parseInt(usize, instructions.next().?, 10);\n // now skip _from_\n _ = instructions.next();\n // Now get source\n const source: usize = try std.fmt.parseInt(usize, instructions.next().?, 10);\n // Now skip _to_\n _ = instructions.next();\n // Now get dest\n const dest: usize = try std.fmt.parseInt(usize, instructions.next().?, 10);\n\n var crates_moved: usize = 0;\n while (crates_moved Ultimately, as you can see, I have just avoided making variable assignments in the function and this passes the test (and the puzzle).\n\nI have checked for issues in the zig repo that might be related, and cannot find anything immediately obvious (search used is this). I've looked on StackOverflow, and found this question, which does have some similarity to my issue (pointers seem a bit whack in while loops), but it's not the same.\n\nI've scoured the zig documentation on loops and assignment, on the site, but don't see anything calling out this behaviour specifically.\nI'm assuming I've either completely misunderstood something (or missed something that isn't well documented), or this is a bug — the language is under heavy active dev, after all.\n\nI'm expecting that an assignment like I perform should work as expected — being a simple shorthand to avoid having to write out the repeated `self.stacks.items[source - 1]`, so I'm hopeful that this is something that I'm just doing wrong. Zig version is `v0.11.0-dev.537+36da3000c`\n\n========================================\n\nCode:\n```text\nconst BunchOfStacks = struct {\n stacks: ArrayList(ArrayList(u8)),\n ...\n```\n\n```text\nfn moveCrates(self: *BunchOfStacks, amount: usize, source: usize, dest: usize) !void {\n const source_height = self.stacks.items[source - 1].items.len;\n const crate_slice = self.stacks.items[source - 1].items[(source_height - amount)..];\n try self.stacks.items[dest - 1].appendSlice(crate_slice);\n self.stacks.items[source - 1].shrinkRetainingCapacity(source_height - amount);\n }\n```\n\n```text\nfn moveCrates(self: *BunchOfStacks, amount: usize, source: usize, dest: usize) !void {\n var source_list: ArrayList(u8) = self.stacks.items[source - 1];\n const source_height = source_list.items.len;\n const crate_slice = source_list.items[(source_height - amount)..];\n try self.stacks.items[dest - 1].appendSlice(crate_slice);\n source_list.shrinkRetainingCapacity(source_height - amount);\n }\n```\n\n```text\nwhile (instructions.next()) |_| {\n // First part is the verb, this is always \"move\" so skip it\n // Get the amount next\n const amount: usize = try std.fmt.parseInt(usize, instructions.next().?, 10);\n // now skip _from_\n _ = instructions.next();\n // Now get source\n const source: usize = try std.fmt.parseInt(usize, instructions.next().?, 10);\n // Now skip _to_\n _ = instructions.next();\n // Now get dest\n const dest: usize = try std.fmt.parseInt(usize, instructions.next().?, 10);\n\n var crates_moved: usize = 0;\n while (crates_moved < amount) : (crates_moved += 1) {\n try stacks_part1.moveCrates(1, source, dest);\n }\n try stacks_part2.moveCrates(amount, source, dest);\n }\n```\n\n```text\nself.stacks.items[source - 1]\n```\n\n```text\nsource_list\n```\n\n```text\nArrayList(u8)\n```\n\n```text\nsource\n```\n\n```text\nself.stacks.items[source - 1]\n```\n\n```text\nv0.11.0-dev.537+36da3000c\n```\n\n```text\nvar source_list: ArrayList(u8) = self.stacks.items[source - 1];\n```\n\n```text\nvar source_list: *ArrayList(u8) = &self.stacks.items[source - 1];\n```\n\n```text\nitems\n```\n\n```text\nshrinkRetainingCapacity\n```\n\n```text\nitems\n```\n\n========================================\n\nComments:\n- That works brilliantly! Thank you so much. I still don't quite understand it fully, but I'll mull it over; this is very helpful.","metadata":{"transformedAt":"2026-08-18T18:33:48.844Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":15,"totalLines":168,"estimatedTokens":1555}}69{"id":"stack-67434791","source":"stackoverflow","questionId":67434791,"title":"Simple log analysis with Zig","tags":["zig"],"text":"Title: Simple log analysis with Zig\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nMotivated by https://benhoyt.com/writings/count-words/ , I have played a bit with rewriting an internal log analysis script in several languages (I will not go as far as in the article!).\n\nAfter Go (by myself) and Rust (with some help from SO), I am currently stuck with Zig. I have more or less understood https://github.com/benhoyt/countwords/blob/master/simple.zig but still having a hard time with translating my original along these lines... Notably, using a Hash with tuple keys, handling name of months in parsing and printing...\n\nOriginal script in Python:\n\n```\nimport sys\n\nmonths = { \"Jan\": 1, \"Feb\": 2, \"Mar\": 3, \"Apr\": 4, \"May\": 5, \"Jun\": 6,\n \"Jul\": 7, \"Aug\": 8, \"Sep\": 9, \"Oct\": 10, \"Nov\": 11, \"Dec\": 12 }\n\nmonths_r = { v:k for k,v in months.items() }\n\ntotals = {}\n\nfor line in sys.stdin:\n if \"redis\" in line and \"Partial\" in line:\n f1, f2 = line.split()[:2]\n w = (months[f1], int(f2))\n totals[w] = totals.get(w, 0) + 1\n\nfor k in sorted(totals.keys()):\n print(months_r[k[0]], k[1], totals[k])\n```\n\nCould someone fluent with recent Zig give a hand?\n\nThanks a lot!\n\n========================================\n\nCode:\n```text\nimport sys\n\nmonths = { \"Jan\": 1, \"Feb\": 2, \"Mar\": 3, \"Apr\": 4, \"May\": 5, \"Jun\": 6,\n \"Jul\": 7, \"Aug\": 8, \"Sep\": 9, \"Oct\": 10, \"Nov\": 11, \"Dec\": 12 }\n\nmonths_r = { v:k for k,v in months.items() }\n\ntotals = {}\n\nfor line in sys.stdin:\n if \"redis\" in line and \"Partial\" in line:\n f1, f2 = line.split()[:2]\n w = (months[f1], int(f2))\n totals[w] = totals.get(w, 0) + 1\n\nfor k in sorted(totals.keys()):\n print(months_r[k[0]], k[1], totals[k])\n```\n\n```text\nconst std = @import(\"std\");\n\nconst Key = struct { month: u4, day: u5 };\n\nfn keyHash(key: Key) u64 {\n return @as(u64, key.month) << 32 | @as(u64, key.day);\n}\n\nconst Totals = std.HashMap(\n Key,\n usize,\n keyHash,\n std.hash_map.getAutoEqlFn(Key),\n std.hash_map.default_max_load_percentage,\n);\n\nconst Item = struct { key: Key, count: usize };\n\nfn itemSort(context: void, lhs: Item, rhs: Item) bool {\n return keyHash(lhs.key) < keyHash(rhs.key);\n}\n\n// zig fmt: off\nconst months = std.ComptimeStringMap(u4, .{\n .{ \"Jan\", 1 }, .{ \"Feb\", 2 }, .{ \"Mar\", 3 },\n .{ \"Apr\", 4 }, .{ \"May\", 5 }, .{ \"Jun\", 6 },\n .{ \"Jul\", 7 }, .{ \"Aug\", 8 }, .{ \"Sep\", 9 },\n .{ \"Oct\", 10 }, .{ \"Nov\", 11 }, .{ \"Dec\", 12 },\n});\n\nconst months_r = [_][]const u8{\n \"(padding)\",\n \"Jan\", \"Feb\", \"Mar\",\n \"Apr\", \"May\", \"Jun\",\n \"Jul\", \"Aug\", \"Sep\",\n \"Oct\", \"Nov\", \"Dec\",\n};\n// zig fmt: on\n\npub fn main() !void {\n var gpa = std.heap.GeneralPurposeAllocator(.{}){};\n defer if (gpa.deinit()) std.log.err(\"memory leak detected\", .{});\n const allocator = &gpa.allocator;\n\n var totals = Totals.init(allocator);\n defer totals.deinit();\n\n const stdin = std.io.bufferedReader(std.io.getStdIn().reader()).reader();\n var buf: [4096]u8 = undefined;\n while (try stdin.readUntilDelimiterOrEof(&buf, '\\n')) |line| {\n if (std.mem.indexOf(u8, line, \"redis\") == null or std.mem.indexOf(u8, line, \"Partial\") == null)\n continue;\n\n var it = std.mem.tokenize(line, &std.ascii.spaces);\n const month = months.get(it.next().?).?;\n const day = try std.fmt.parseUnsigned(u5, it.next().?, 10);\n\n const res = try totals.getOrPut(.{ .month = month, .day = day });\n if (res.found_existing)\n res.entry.value += 1\n else\n res.entry.value = 1;\n }\n\n var stdout = std.io.bufferedWriter(std.io.getStdOut().writer());\n defer stdout.flush() catch std.log.err(\"stdout flushing failed\", .{});\n const out = stdout.writer();\n\n var items = try allocator.alloc(Item, totals.count());\n defer allocator.free(items);\n\n {\n var it = totals.iterator();\n var i: usize = 0;\n while (it.next()) |kv| : (i += 1) {\n items[i] = .{ .key = kv.key, .count = kv.value };\n }\n }\n\n std.sort.sort(Item, items, {}, itemSort);\n\n for (items) |it| {\n try out.print(\"{s} {d} {d}\\n\", .{ months_r[it.key.month], it.key.day, it.count });\n }\n}\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.844Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":2,"totalLines":145,"estimatedTokens":1042}}70{"id":"stack-76386819","source":"stackoverflow","questionId":76386819,"title":"expected type 'i32', found 'usize'","tags":["arrays","casting","zig"],"text":"Title: expected type 'i32', found 'usize'\nTags: arrays, casting, zig\nSource: Stack Overflow\n\nQuestion:\nI'm currently trying to solve some leetcode problems in Zig, and I'm doing the two sum problem. Here's what the entirety of my code looks like:\n\n```\nconst std = @import(\"std\");\nconst allocator = std.heap.page_allocator;\n\nfn two_sum(nums: []i32, target: i32) []i32{\n var map = std.AutoArrayHashMap(i32, i32).init(allocator);\n defer map.deinit();\n var res = [2]i32{-1, -1};\n for (nums, 0..) |n, i| { // n is the number; i is the index\n if (map.get(target - n)) |v| {\n res[0] = v;\n res[1] = @as(i32, i);\n return &res;\n }\n try map.put(n, @as(i32, i));\n }\n return &res;\n}\n\npub fn main() !void {\n var arr = [_]i32{1, 5, 8, 9, 6};\n var x = two_sum(&arr, 9);\n for (x) |n| {\n std.debug.print(\"{d}\", .{n});\n }\n}\n```\n\nHowever, when I run the code, I get this error:\n\n```\nerror: expected type 'i32', found 'usize'\n res[1] = @as(i32, i);\n ^\n```\n\nWhy is zig interpreting 1 as a `usize` and not an `i32`? And what can be done to fix this?\n\nI tried using an explicit type cast:\nres[@as(i32, 1)] = @as(i32, i);\n\nHowever, that didn't work either.\n\n========================================\n\nCode:\n```text\nconst std = @import(\"std\");\nconst allocator = std.heap.page_allocator;\n\nfn two_sum(nums: []i32, target: i32) []i32{\n var map = std.AutoArrayHashMap(i32, i32).init(allocator);\n defer map.deinit();\n var res = [2]i32{-1, -1};\n for (nums, 0..) |n, i| { // n is the number; i is the index\n if (map.get(target - n)) |v| {\n res[0] = v;\n res[1] = @as(i32, i);\n return &res;\n }\n try map.put(n, @as(i32, i));\n }\n return &res;\n}\n\npub fn main() !void {\n var arr = [_]i32{1, 5, 8, 9, 6};\n var x = two_sum(&arr, 9);\n for (x) |n| {\n std.debug.print(\"{d}\", .{n});\n }\n}\n```\n\n```text\nerror: expected type 'i32', found 'usize'\n res[1] = @as(i32, i);\n ^\n```\n\n```text\nusize\n```\n\n```text\ni32\n```\n\n```text\nconst std = @import(\"std\");\nconst allocator = std.heap.page_allocator;\n\nfn two_sum(nums: []i32, target: i32) ![2]i32 { // return error union\n var map = std.AutoArrayHashMap(i32, i32).init(allocator);\n defer map.deinit();\n var res = [2]i32{ -1, -1 };\n for (nums, 0..) |n, i| {\n if (map.get(target - n)) |v| {\n res[0] = v;\n res[1] = @intCast(i32, i); // use `@intCast` instead of `@as`\n return res; // just return the array\n }\n try map.put(n, @intCast(i32, i)); // use `@intCast` instead of `@as`\n }\n return res; // just return the array\n}\n\npub fn main() !void {\n var arr = [_]i32{1, 5, 8, 9, 6};\n var x = try two_sum(&arr, 9); // `two_sum` returns an error union\n for (x) |n| {\n std.debug.print(\"{d}\", .{n});\n }\n std.debug.print(\"\\n\", .{});\n}\n```\n\n```text\ni\n```\n\n```text\nusize\n```\n\n```text\nusize\n```\n\n```text\ni32\n```\n\n```text\n@as\n```\n\n```text\ni32\n```\n\n```text\nusize\n```\n\n```text\n@intCast\n```\n\n```text\n@as\n```\n\n```text\n@intCast\n```\n\n```text\ntwo_sum\n```\n\n```text\ntry\n```\n\n```text\nmap.put\n```\n\n```text\ntwo_sum\n```\n\n```text\ntwo_sum\n```\n\n```text\ntry\n```\n\n```text\nres\n```\n\n========================================\n\nComments:\n- i can't reproduce this with latest zig (master)","metadata":{"transformedAt":"2026-08-18T18:33:48.844Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":22,"totalLines":196,"estimatedTokens":826}}71{"id":"stack-76646044","source":"stackoverflow","questionId":76646044,"title":"error: use of undeclared identifier 'c_char'","tags":["zig"],"text":"Title: error: use of undeclared identifier 'c_char'\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI'm trying to make game engine and game on this on zig (and C++), but I'm getting this following error:\n\nmain.zig:75:54: error: use of undeclared identifier 'c_char'\nconst zipArchive = zip.zip_open(std.mem.ptrCast(*c_char, zipFilePath.toSlice().ptr), 0, null);\n\ncurrently my main.zig look like this:\n\n```\nconst std = @import(\"std\");\n// const garchive = @import(\"archive_files.zig\");\n\nconst zip = @cImport({\n @cInclude(\"zip.h\");\n});\n\nconst c = @cImport({\n @cInclude(\"SDL.h\");\n});\n\npub fn main() anyerror!void {\n std.log.info(\"ROOFTOPS 2 PORT.\", .{});\n std.log.info(\"\\t\\tBY LXCHN1v1\", .{});\n\n //var gpa = std.heap.GeneralPurposeAllocator(.{}){};\n //const allocator = gpa.allocator();\n\n std.log.info(\"trying to read rooftops.dconf\", .{});\n //var game_config = dconfparser.readDConfig(\"rooftops.dconf\");\n\n // load_config(\"rooftops2.dconf\");\n\n const main_archive_path = \"main/game_00.garc\";\n const init_script_name = \"scripts/init.hesl\";\n\n const initData = try loadFileFromZipArchive(main_archive_path, init_script_name);\n\n std.debug.print(\"INIT SCRIPT DATA:\\n{}\\n\", .{initData});\n\n _ = c.SDL_Init(c.SDL_INIT_VIDEO);\n defer c.SDL_Quit();\n\n var window = c.SDL_CreateWindow(\"ROOFTOPS2\", c.SDL_WINDOWPOS_CENTERED, c.SDL_WINDOWPOS_CENTERED, 800, 600, 0);\n defer c.SDL_DestroyWindow(window);\n\n var renderer = c.SDL_CreateRenderer(window, 0, c.SDL_RENDERER_PRESENTVSYNC);\n defer c.SDL_DestroyRenderer(renderer);\n\n mainloop: while (true) {\n var sdl_event: c.SDL_Event = undefined;\n while (c.SDL_PollEvent(&sdl_event) != 0) {\n switch (sdl_event.type) {\n c.SDL_QUIT => break :mainloop,\n else => {},\n }\n }\n\n _ = c.SDL_SetRenderDrawColor(renderer, 0xff, 0xff, 0xff, 0xff);\n _ = c.SDL_RenderClear(renderer);\n var rect = c.SDL_Rect{ .x = 0, .y = 0, .w = 60, .h = 60 };\n const a = 0.001 * @intToFloat(f32, c.SDL_GetTicks());\n const t = 2 * std.math.pi / 3.0;\n const r = 100 * @cos(0.1 * a);\n rect.x = 290 + @floatToInt(i32, r * @cos(a));\n rect.y = 170 + @floatToInt(i32, r * @sin(a));\n _ = c.SDL_SetRenderDrawColor(renderer, 0xff, 0, 0, 0xff);\n _ = c.SDL_RenderFillRect(renderer, &rect);\n rect.x = 290 + @floatToInt(i32, r * @cos(a + t));\n rect.y = 170 + @floatToInt(i32, r * @sin(a + t));\n _ = c.SDL_SetRenderDrawColor(renderer, 0, 0xff, 0, 0xff);\n _ = c.SDL_RenderFillRect(renderer, &rect);\n rect.x = 290 + @floatToInt(i32, r * @cos(a + 2 * t));\n rect.y = 170 + @floatToInt(i32, r * @sin(a + 2 * t));\n _ = c.SDL_SetRenderDrawColor(renderer, 0, 0, 0xff, 0xff);\n _ = c.SDL_RenderFillRect(renderer, &rect);\n c.SDL_RenderPresent(renderer);\n }\n}\n\nfn loadFileFromZipArchive(zipFilePath: []const u8, fileName: []const u8) ![]u8 {\n //const zipArchive = zip.zip_open(cast(*c_char, zipFilePath.toSlice().ptr), 0, null);\n //const zipArchive = zip.zip_open(zipFilePath.ptr.*c_char, 0, null);\n const zipArchive = zip.zip_open(std.mem.ptrCast(*c_char, zipFilePath.toSlice().ptr), 0, null);\n\n if (zipArchive == null) {\n return error.FailedToOpenZipArchive;\n }\n\n const index = zip.zip_name_locate(zipArchive, cast(*c_char, fileName.toSlice().ptr), 0);\n if (index I don't has idea how to fix this, (chatgpt doesn't help)\n\nby code you can understand what I want to do, if more precisely I want to force it to open a game archive of the zip format, and there take the file for initiation, ie init.hesl ( it's essentially a lua script ) which has everything to initiate, ie parameters for the window, default game parameters, that is, if there is no file in settings/ , and so on\n\n========================================\n\nCode:\n```text\nconst std = @import(\"std\");\n// const garchive = @import(\"archive_files.zig\");\n\nconst zip = @cImport({\n @cInclude(\"zip.h\");\n});\n\nconst c = @cImport({\n @cInclude(\"SDL.h\");\n});\n\npub fn main() anyerror!void {\n std.log.info(\"ROOFTOPS 2 PORT.\", .{});\n std.log.info(\"\\t\\tBY LXCHN1v1\", .{});\n\n //var gpa = std.heap.GeneralPurposeAllocator(.{}){};\n //const allocator = gpa.allocator();\n\n std.log.info(\"trying to read rooftops.dconf\", .{});\n //var game_config = dconfparser.readDConfig(\"rooftops.dconf\");\n\n // load_config(\"rooftops2.dconf\");\n\n const main_archive_path = \"main/game_00.garc\";\n const init_script_name = \"scripts/init.hesl\";\n\n const initData = try loadFileFromZipArchive(main_archive_path, init_script_name);\n\n std.debug.print(\"INIT SCRIPT DATA:\\n{}\\n\", .{initData});\n\n _ = c.SDL_Init(c.SDL_INIT_VIDEO);\n defer c.SDL_Quit();\n\n var window = c.SDL_CreateWindow(\"ROOFTOPS2\", c.SDL_WINDOWPOS_CENTERED, c.SDL_WINDOWPOS_CENTERED, 800, 600, 0);\n defer c.SDL_DestroyWindow(window);\n\n var renderer = c.SDL_CreateRenderer(window, 0, c.SDL_RENDERER_PRESENTVSYNC);\n defer c.SDL_DestroyRenderer(renderer);\n\n mainloop: while (true) {\n var sdl_event: c.SDL_Event = undefined;\n while (c.SDL_PollEvent(&sdl_event) != 0) {\n switch (sdl_event.type) {\n c.SDL_QUIT => break :mainloop,\n else => {},\n }\n }\n\n _ = c.SDL_SetRenderDrawColor(renderer, 0xff, 0xff, 0xff, 0xff);\n _ = c.SDL_RenderClear(renderer);\n var rect = c.SDL_Rect{ .x = 0, .y = 0, .w = 60, .h = 60 };\n const a = 0.001 * @intToFloat(f32, c.SDL_GetTicks());\n const t = 2 * std.math.pi / 3.0;\n const r = 100 * @cos(0.1 * a);\n rect.x = 290 + @floatToInt(i32, r * @cos(a));\n rect.y = 170 + @floatToInt(i32, r * @sin(a));\n _ = c.SDL_SetRenderDrawColor(renderer, 0xff, 0, 0, 0xff);\n _ = c.SDL_RenderFillRect(renderer, &rect);\n rect.x = 290 + @floatToInt(i32, r * @cos(a + t));\n rect.y = 170 + @floatToInt(i32, r * @sin(a + t));\n _ = c.SDL_SetRenderDrawColor(renderer, 0, 0xff, 0, 0xff);\n _ = c.SDL_RenderFillRect(renderer, &rect);\n rect.x = 290 + @floatToInt(i32, r * @cos(a + 2 * t));\n rect.y = 170 + @floatToInt(i32, r * @sin(a + 2 * t));\n _ = c.SDL_SetRenderDrawColor(renderer, 0, 0, 0xff, 0xff);\n _ = c.SDL_RenderFillRect(renderer, &rect);\n c.SDL_RenderPresent(renderer);\n }\n}\n\n\nfn loadFileFromZipArchive(zipFilePath: []const u8, fileName: []const u8) ![]u8 {\n //const zipArchive = zip.zip_open(cast(*c_char, zipFilePath.toSlice().ptr), 0, null);\n //const zipArchive = zip.zip_open(zipFilePath.ptr.*c_char, 0, null);\n const zipArchive = zip.zip_open(std.mem.ptrCast(*c_char, zipFilePath.toSlice().ptr), 0, null);\n\n if (zipArchive == null) {\n return error.FailedToOpenZipArchive;\n }\n\n const index = zip.zip_name_locate(zipArchive, cast(*c_char, fileName.toSlice().ptr), 0);\n if (index < 0) {\n zip.zip_close(zipArchive);\n return error.FileNotFoundInZipArchive;\n }\n\n var fileInfo = zip.zip_stat_t{};\n if (zip.zip_stat_index(zipArchive, index, 0, &fileInfo) != 0) {\n zip.zip_close(zipArchive);\n return error.FailedToGetFileInfo;\n }\n\n const file = zip.zip_fopen_index(zipArchive, index, 0);\n if (file == null) {\n zip.zip_close(zipArchive);\n return error.FailedToOpenFileInZipArchive;\n }\n\n const fileSize = @intCast(usize, fileInfo.size);\n var buffer: [0]u8 = undefined;\n const bytesRead = zip.zip_fread(file, buffer.ptr, fileSize);\n if (bytesRead < 0) {\n zip.zip_fclose(file);\n zip.zip_close(zipArchive);\n return error.FailedToReadFileFromZipArchive;\n }\n\n zip.zip_fclose(file);\n zip.zip_close(zipArchive);\n\n return buffer[0..bytesRead];\n}\n```\n\n```text\nconst zipArchive = zip.zip_open(zipFilePath[0..:0], 0, null);\n```\n\n```text\nc_char\n```\n\n```text\n[]const u8\n```\n\n```text\n[0..:0]\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.844Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":5,"totalLines":230,"estimatedTokens":1905}}72{"id":"stack-77249845","source":"stackoverflow","questionId":77249845,"title":"How do I check if two arrays are equal in Zig?","tags":["arrays","zig"],"text":"Title: How do I check if two arrays are equal in Zig?\nTags: arrays, zig\nSource: Stack Overflow\n\nQuestion:\nIf I have two arrays of the same length -- for example, two `[32]u8` --, how can I compare them?\n\n========================================\n\nCode:\n```text\n[32]u8\n```\n\n```js\nvar array1: [32]u8 = undefined;\nvar array2: [32]u8 = undefined;\nif (std.mem.eql(u8, array1, array2)) {\n std.debug.print(\"they are equal!\\n\", .{});\n}\n```\n\n```text\nstd.mem.eql\n```\n\n```text\nstd.mem.startsWith\n```\n\n========================================\n\nComments:\n- worth pointing out though that looping and checking for equality and using `std.mem.eql` are *not* equivalent. This works for primitive types, but as soon as you have e.g. structs with padding or anything else which has a notion of equality other than \"identical bit patterns\" this won't work anymore.","metadata":{"transformedAt":"2026-08-18T18:33:48.844Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":4,"totalLines":34,"estimatedTokens":212}}73{"id":"stack-74927824","source":"stackoverflow","questionId":74927824,"title":"Checking if a pointer in NULL","tags":["zig"],"text":"Title: Checking if a pointer in NULL\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nIs there a nicer way of achieving the same result as the following code in a nicer way?\n\n```\nif (window == @intToPtr(?*c.GLFWwindow, 0))\n```\n\nI want to check if a pointer to any kind of object (in this case, a nullable [of course] pointer to a GLFWwindow) is NULL. Is there a better way of doing this so that I don't have to write `@intToPtr(?*T, 0))` every time I need a NULL pointer (of course a very common occurrence when interfacing with C libraries)\n\nI tried searching for a solution for a while but found nothing. Maybe if there isn't a way to do this specific thing in zig, perhaps there's a way to define a C-like macro `GLFWwindowNULL` to `@intToPtr(?*c.GLFWwindow, 0))`?\n\n========================================\n\nCode:\n```js\nif (window == @intToPtr(?*c.GLFWwindow, 0))\n```\n\n```text\n@intToPtr(?*T, 0))\n```\n\n```text\nGLFWwindowNULL\n```\n\n```text\n@intToPtr(?*c.GLFWwindow, 0))\n```\n\n```js\nif (window == null)\n```\n\n```text\nnull\n```\n\n========================================\n\nComments:\n- Sorry, I posted this and immediately found the answer. I have answered the question now.","metadata":{"transformedAt":"2026-08-18T18:33:48.844Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":6,"totalLines":46,"estimatedTokens":291}}74{"id":"stack-75623924","source":"stackoverflow","questionId":75623924,"title":"Zig `Segmentation fault at address`","tags":["zig"],"text":"Title: Zig `Segmentation fault at address`\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nTrying to build a Huffman Code using `zig` but getting `Segmentation fault at address 0x7ff700000002`.\n\nI am printing two values:\n\nExpected:\n\n```\ntree: huffman.Node{ .freq = 15, .value = null, .left = huffman.Node{ .freq = 9, .value = null, .left = huffman.Node{ .freq = 0, .value = 328965, .left = huffman.Node{ ... }, .right = huffman.Node{ ... } }, .right = huffman.Node{ .freq = 2977642760, .value = 32759, .left = huffman.Node{ ... }, .right = null } }, .right = huffman.Node{ .freq = 2977642800, .value = 32759, .left = huffman.Node{ .freq = 3, .value = 197379, .left = null, .right = null }, .right = huffman.Node{ .freq = 2977643128, .value = null, .left = huffman.Node{ ... }, .right = huffman.Node{ ... } } } }\ntree: huffman.Node{ .freq = 9, .value = null, .left = huffman.Node{ .freq = 5, .value = 328965, .left = null, .right = null }, .right = huffman.Node{ .freq = 4, .value = 263172, .left = null, .right = null } }\n```\n\nBut get:\n\n```\ntree: huffman.Node{ .freq = 15, .value = null, .left = huffman.Node{ .freq = 9, .value = null, .left = huffman.Node{ .freq = 0, .value = 328965, .left = huffman.Node{ ... }, .right = huffman.Node{ ... } }, .right = huffman.Node{ .freq = 2977642760, .value = 32759, .left = huffman.Node{ ... }, .right = null } }, .right = huffman.Node{ .freq = 2977642800, .value = 32759, .left = huffman.Node{ .freq = 3, .value = 197379, .left = null, .right = null }, .right = huffman.Node{ .freq = 2977643128, .value = null, .left = huffman.Node{ ... }, .right = huffman.Node{ ... } } } }\ntree: huffman.Node{ .freq = 9, .value = null, .left = huffman.Node{ .freq = 32, .value = 0, .left = huffman.Node{ .freq = Segmentation fault at address 0x7ff700000002\n```\n\n(Issue on the second line)\n\nI think it's something on how I am allocating memory, as clearly the `.freq = 32` is totally unexpected and wrong, but tried reading the docs and still can't find why this happens\n\n```\n...\n var tree = build_tree(array);\n var code_map = std.HashMap(u32, u32, hash_u32, std.hash_map.default_max_load_percentage).init(gpa);\n // defer code_map.deinit();\n try traverse_tree(1, tree, &code_map); // Code contains an 1 at the start of it\n return code_map;\n}\n\nfn traverse_tree(code: u32, tree: Node, map: *std.hash_map.HashMap(u32, u32, hash_u32, std.hash_map.default_max_load_percentage)) !void {\n std.debug.print(\"tree: {?} \\n\", .{tree});\n if (tree.value != null) {\n try map.put(tree.value.?, code);\n } else {\n try traverse_tree(code * 2, tree.left.?.*, map);\n try traverse_tree(code * 2 + 1, tree.right.?.*, map);\n }\n}\n\nfn build_tree(array: []Node) Node {\n var i: u32 = 1;\n var current: Node = array[0];\n while (i If I log the `current` variable in the `build_tree` function, the output of it is the expected one.\n\n========================================\n\nCode:\n```text\ntree: huffman.Node{ .freq = 15, .value = null, .left = huffman.Node{ .freq = 9, .value = null, .left = huffman.Node{ .freq = 0, .value = 328965, .left = huffman.Node{ ... }, .right = huffman.Node{ ... } }, .right = huffman.Node{ .freq = 2977642760, .value = 32759, .left = huffman.Node{ ... }, .right = null } }, .right = huffman.Node{ .freq = 2977642800, .value = 32759, .left = huffman.Node{ .freq = 3, .value = 197379, .left = null, .right = null }, .right = huffman.Node{ .freq = 2977643128, .value = null, .left = huffman.Node{ ... }, .right = huffman.Node{ ... } } } }\ntree: huffman.Node{ .freq = 9, .value = null, .left = huffman.Node{ .freq = 5, .value = 328965, .left = null, .right = null }, .right = huffman.Node{ .freq = 4, .value = 263172, .left = null, .right = null } }\n```\n\n```text\ntree: huffman.Node{ .freq = 15, .value = null, .left = huffman.Node{ .freq = 9, .value = null, .left = huffman.Node{ .freq = 0, .value = 328965, .left = huffman.Node{ ... }, .right = huffman.Node{ ... } }, .right = huffman.Node{ .freq = 2977642760, .value = 32759, .left = huffman.Node{ ... }, .right = null } }, .right = huffman.Node{ .freq = 2977642800, .value = 32759, .left = huffman.Node{ .freq = 3, .value = 197379, .left = null, .right = null }, .right = huffman.Node{ .freq = 2977643128, .value = null, .left = huffman.Node{ ... }, .right = huffman.Node{ ... } } } }\ntree: huffman.Node{ .freq = 9, .value = null, .left = huffman.Node{ .freq = 32, .value = 0, .left = huffman.Node{ .freq = Segmentation fault at address 0x7ff700000002\n```\n\n```text\n...\n var tree = build_tree(array);\n var code_map = std.HashMap(u32, u32, hash_u32, std.hash_map.default_max_load_percentage).init(gpa);\n // defer code_map.deinit();\n try traverse_tree(1, tree, &code_map); // Code contains an 1 at the start of it\n return code_map;\n}\n\nfn traverse_tree(code: u32, tree: Node, map: *std.hash_map.HashMap(u32, u32, hash_u32, std.hash_map.default_max_load_percentage)) !void {\n std.debug.print(\"tree: {?} \\n\", .{tree});\n if (tree.value != null) {\n try map.put(tree.value.?, code);\n } else {\n try traverse_tree(code * 2, tree.left.?.*, map);\n try traverse_tree(code * 2 + 1, tree.right.?.*, map);\n }\n}\n\nfn build_tree(array: []Node) Node {\n var i: u32 = 1;\n var current: Node = array[0];\n while (i < (array.len - 1)) {\n if (array[i + 1].freq < current.freq) {\n var starting_i = i;\n var ending_i = i;\n while (i < array.len and array[i].freq < current.freq) {\n ending_i += 1;\n i += 1;\n }\n var new_node = build_tree(array[starting_i..ending_i]);\n var tmp = current;\n current = Node{ .freq = tmp.freq + new_node.freq, .value = null, .right = &tmp, .left = &new_node };\n } else {\n var item = array[i];\n var tmp = current;\n current = Node{ .freq = tmp.freq + item.freq, .value = null, .right = &tmp, .left = &item };\n i += 1;\n }\n }\n // Do the last item separatedly. We check if it is smaller to array.len as it might be used in another node before,\n // meaning that i would be grater to array.len\n if (i < array.len) {\n var last = array[array.len - 1];\n var tmp = current;\n current = Node{ .freq = tmp.freq + last.freq, .value = null, .right = &tmp, .left = &last };\n }\n return current;\n}\nconst Node = struct {\n freq: u32,\n value: ?u32,\n left: ?*Node,\n right: ?*Node,\n};\n```\n\n```text\nzig\n```\n\n```text\nSegmentation fault at address 0x7ff700000002\n```\n\n```text\n.freq = 32\n```\n\n```text\ncurrent\n```\n\n```text\nbuild_tree\n```\n\n```text\nvar last = array[array.len - 1];\n```\n\n```text\nbuild_tree\n```\n\n```text\nNode\n```\n\n```text\nNode\n```\n\n```text\narray\n```\n\n```text\nbuild_tree\n```\n\n```text\nNode\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.844Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":15,"totalLines":168,"estimatedTokens":1679}}75{"id":"stack-73086494","source":"stackoverflow","questionId":73086494,"title":"How to allocate a struct of incomplete type in Zig?","tags":["posix","zig"],"text":"Title: How to allocate a struct of incomplete type in Zig?\nTags: posix, zig\nSource: Stack Overflow\n\nQuestion:\nI would like to use POSIX regex routines in Zig, but I can't work out how to allocate a pattern buffer (`regex_t`). I think the problem is because it is defined as `typedef struct re_pattern_buffer regex_t` (in my case, on a GNU system), and Zig cannot therefore tell how big it is.\n\nIn a standard `zig init-exe` project (Zig master as of today), I have the following `main.zig`:\n\n```\nconst std = @import(\"std\");\nconst c = @cImport({@cInclude(\"regex.h\");});\n\npub fn main() anyerror!void {\n var re: c.regex_t = undefined;\n std.log.info(\"address of re {}\", .{re});\n}\n```\n\nIn an otherwise default `build.zig`, I add a line `exe.linkLibC();`.\n\nThen, `zig build` gives the following error:\n\n```\n./src/main.zig:5:5: error: variable of type '.cimport:2:11.struct_re_pattern_buffer' not allowed\n var re: c.regex_t = undefined;\n ^\n```\n\nThis is fair enough, but I cannot work out what I should do! I can see a couple of potential workarounds:\n\n- Use `struct re_pattern_buffer` directly; but this is not portable, as it's not part of the POSIX standard (though at least musl and glibc use it as the underlying struct of `regex_t`).\n\n- Write a C function that `malloc`s and returns a `regex_t`, and use that. Should be fine, as all the POSIX APIs take a `regex_t *`, so Zig doesn't need to know how big a `regex_t` is if it only ever has to handle pointers.\n\nBut it would be nice to be able to do without either of these workarounds. Any hints?\n\n========================================\n\nCode:\n```text\nconst std = @import(\"std\");\nconst c = @cImport({@cInclude(\"regex.h\");});\n\npub fn main() anyerror!void {\n var re: c.regex_t = undefined;\n std.log.info(\"address of re {}\", .{re});\n}\n```\n\n```text\n./src/main.zig:5:5: error: variable of type '.cimport:2:11.struct_re_pattern_buffer' not allowed\n var re: c.regex_t = undefined;\n ^\n```\n\n```text\nregex_t\n```\n\n```text\ntypedef struct re_pattern_buffer regex_t\n```\n\n```text\nzig init-exe\n```\n\n```text\nmain.zig\n```\n\n```text\nbuild.zig\n```\n\n```text\nexe.linkLibC();\n```\n\n```text\nzig build\n```\n\n```text\nstruct re_pattern_buffer\n```\n\n```text\nregex_t\n```\n\n```text\nmalloc\n```\n\n```text\nregex_t\n```\n\n```text\nregex_t *\n```\n\n```text\nregex_t\n```\n\n```rs\n// found by adding `--verbose-cimport` to the zig build\npub const struct_re_pattern_buffer = opaque {};\npub const regex_t = struct_re_pattern_buffer;\n```\n\n```c\nstruct re_pattern_buffer\n{\n … // http://hte.sourceforge.net/doxygenized-0.8.0pre1/structre__pattern__buffer.html\n};\ntypedef struct re_pattern_buffer regex_t;\n```\n\n```text\npub const struct_re_dfa_t = opaque {}; // (no file):28:1: warning: struct demoted to opaque type - has bitfield\n```\n\n```text\nregex_t* alloc_regex_t(void);\nvoid free_regex_t(regex_t* ptr);\n```\n\n```c\n// header:\n#include <stdint.h>\nsize_t my_sizeof_regex_t();\nuint16_t my_alignof_regex_t();\n\n// source:\n#include <stdint.h>\n#include <stdalign.h>\n#include <regex.h>\n\nsize_t my_sizeof_regex_t() {\n return sizeof(regex_t);\n}\n\nuint16_t my_alignof_regex_t() {\n return alignof(regex_t);\n}\n```\n\n```text\nvar re_zig_slice = try allocator.allocBytes(\n c.my_alignof_regex_t(),\n c.my_sizeof_regex_t(),\n 0,\n @returnAddress(),\n);\nvar re = @ptrCast(*c.regex_t, re_zig_slice.ptr);\ndefer try allocator.rawFree(@ptrCast([*]u8, re)[0..c.my_sizeof_regex_t()]), c.my_alignof_regex_t, @returnAddress());\n```\n\n```text\nstruct_re_pattern_buffer\n```\n\n```text\nopaque {};\n```\n\n```text\nallocWithOptions\n```\n\n```text\nfree\n```\n\n```text\n@alignCast\n```\n\n========================================\n\nComments:\n- Thanks very much @pfg for this detailed and comprehensive answer. I have subscribed to the issue you link to, and will use the easy workaround of custom C allocation functions for now.","metadata":{"transformedAt":"2026-08-18T18:33:48.844Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":26,"totalLines":186,"estimatedTokens":949}}76{"id":"stack-68154152","source":"stackoverflow","questionId":68154152,"title":"How to create a type '[*c]const [*c]const u8' for paramValues of PQexecParams","tags":["libpq","zig"],"text":"Title: How to create a type '[*c]const [*c]const u8' for paramValues of PQexecParams\nTags: libpq, zig\nSource: Stack Overflow\n\nQuestion:\nI'm trying to use the libpq library in zig. I'm trying to pass paramValues to PQexecParams. I'm just not sure how to create the required type.\n\nThe type required by the documentation is:\n\n```\nconst char * const *paramValues\n```\n\nSo something like:\n\n```\nconst char data[2][2] = {\"12\",\"me\"};\n```\n\nIf do something like this in zig:\n\n```\nconst paramValues = [_][]const u8 {\"12\",\"me\"};\n```\n\nI get this error:\n\n```\nerror: expected type '[*c]const [*c]const u8', found '[2][]const u8'\n```\n\n========================================\n\nCode:\n```text\nconst char * const *paramValues\n```\n\n```text\nconst char data[2][2] = {\"12\",\"me\"};\n```\n\n```text\nconst paramValues = [_][]const u8 {\"12\",\"me\"};\n```\n\n```text\nerror: expected type '[*c]const [*c]const u8', found '[2][]const u8'\n```\n\n```text\nconst paramValues = [_][*:0]const u8 {\"12\",\"me\"};\n\n PQexecParams(....., ¶mValues, ....);\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.844Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":5,"totalLines":55,"estimatedTokens":253}}77{"id":"stack-70150660","source":"stackoverflow","questionId":70150660,"title":"Why does this zig program fail to compile due to \"expected error union type, found 'error:124:18'\"?","tags":["zig"],"text":"Title: Why does this zig program fail to compile due to \"expected error union type, found 'error:124:18'\"?\nTags: zig\nSource: Stack Overflow\n\nQuestion:\n```\ntest \"error union if\" {\n var ent_num: error{UnknownEntity}!u32 = error.UnknownEntity;\n if (ent_num) |entity| {\n try expect(@TypeOf(entity) == u32);\n try expect(entity == 5);\n } else |err| {\n _ = err catch |err1| { // compiles fine when this block is removed\n std.debug.print(\"{s}\", .{err1});\n };\n std.debug.print(\"{s}\", .{err});\n }\n}\n```\n\n```\n./main.zig:125:5: error: expected error union type, found 'error:124:18'\n if (ent_num) |entity| {\n ^\n./main.zig:129:17: note: referenced here\n _ = err catch |err1| {\n```\n\n========================================\n\nCode:\n```text\ntest \"error union if\" {\n var ent_num: error{UnknownEntity}!u32 = error.UnknownEntity;\n if (ent_num) |entity| {\n try expect(@TypeOf(entity) == u32);\n try expect(entity == 5);\n } else |err| {\n _ = err catch |err1| { // compiles fine when this block is removed\n std.debug.print(\"{s}\", .{err1});\n };\n std.debug.print(\"{s}\", .{err});\n }\n}\n```\n\n```text\n./main.zig:125:5: error: expected error union type, found 'error:124:18'\n if (ent_num) |entity| {\n ^\n./main.zig:129:17: note: referenced here\n _ = err catch |err1| {\n```\n\n```rs\nconst std = @import(\"std\");\nconst expect = std.testing.expect;\n\ntest \"error union if\" {\n var ent_num: error{UnknownEntity}!u32 = error.UnknownEntity;\n const entity: u32 = ent_num catch |err| {\n std.debug.print(\"{s}\", .{err});\n return;\n };\n\n try expect(@TypeOf(entity) == u32);\n try expect(entity == 5);\n}\n```\n\n```text\nerror:124:18\n```\n\n```text\nerror{UnknownEntity}\n```\n\n```text\nif (my_var) |v| ...\n```\n\n```text\ntry\n```\n\n```text\ncatch\n```\n\n```text\ntry\n```\n\n```text\ncatch\n```\n\n========================================\n\nComments:\n- Thanks Ali, your explanation makes sense. One up question - why `if (ent_num) |entity| {` shows up in the compile error? Afaik that line is correct, ent_num is of type error union.\n- Another question, you mentioned \"try and catch can only be used for Error Union, not Error Set\", why does `_ = err catch {};` works instead? The example is in ziglearn.org/chapter-1/#payload-captures, you can find it by searching for `_ = err catch {};`.\n- sorry my bad. you can use `if`, `else` for error unions but can't understand how's `_ = error catch {}` works with error set. but still sure it's wrong.\n- Nit: I think the `err` in `err catch {};` is of type error, not error set.\n- Maybe `expr catch {}` without capture just works with any expression that evaluates to error value.\n- `_ = err catch {}` is odd; at this point in the program (inside the `else |err| {}` block) you already know `err` is an error, so you wouldn't need to apply the `catch` operator, which is supposed to extract the error value from an error union.\n- ziglang.org/documentation/master/#if `const a: anyerror!u32 = 0; if (a) |value| { try expect(value == 0); } else |err| { _ = err; unreachable; }`","metadata":{"transformedAt":"2026-08-18T18:33:48.844Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":10,"totalLines":108,"estimatedTokens":761}}78{"id":"stack-79444032","source":"stackoverflow","questionId":79444032,"title":"JS/C Interop with zig cc and wasm","tags":["javascript","c","webassembly","zig"],"text":"Title: JS/C Interop with zig cc and wasm\nTags: javascript, c, webassembly, zig\nSource: Stack Overflow\n\nQuestion:\nI am writing a webassembly demo in C to match a similar demo I wrote in zig.\n\nI am currently able to call C functions from JS, and interact with shared memory on either side. However, I can't seem to be able to expose JS variables and functions to the C program.\n\nIs anybody familiar with writing C this way? I wonder if the undefined symbols are getting optimized out somehow.\n\nI'm using `zig cc` (i.e. `clang`) to compile to wasm on zig version 0.13.0-dev.351+64ef45eb0, using clang 16.0.0 on macos Sequoia 15.0.1 (aarch64).\n\nThis is the code I've written thus far:\n\n### resource.c\n\n```\n#include \n\nvoid print_test(void); // the function I want to use\n\nconst unsigned char heap[4096];\n\nint __attribute__((export_name(\"memstart\")))\nmemstart() {\n return (int)&heap;\n}\n\nint __attribute__((export_name(\"return5\")))\nreturn5(int p) {\n return 5 * p;\n}\n\nint __attribute__((export_name(\"entryAt\")))\nentryAt(int p) {\n print_test();\n return heap[p];\n}\n```\n\n### index.html\n\n```\n\n \n For Stephen\n \n\n \n \n \n output goes gere\n Return 5\n Get nth byte\n \n \n const c = {};\n const encoder = new TextEncoder();\n const decoder = new TextDecoder();\n\n const importObject = {\n \"env\": {\n \"print_test\": () => console.log(\"test print\")\n }\n };\n\n WebAssembly.instantiateStreaming(fetch(\"resource.wasm\", importObject))\n .then(result => {\n const {memory, memstart, return5, entryAt} = result.instance.exports;\n console.log(memstart);\n c.buffer = new Uint8Array(memory.buffer, memstart());\n c.return5 = return5;\n c.entryAt = entryAt;\n });\n\n const button_r5 = document.getElementById(\"button_r5\");\n const button_nth = document.getElementById(\"button_nth\");\n const input = document.getElementById(\"input\");\n const bytes = document.getElementById(\"bytes\");\n const output = document.getElementById(\"output\");\n\n button_r5.addEventListener(\"click\", ()=>{\n output.textContent = c.return5(input.value);\n });\n\n button_nth.addEventListener(\"click\", ()=>{\n c.buffer.set(encoder.encode(bytes.value));\n output.textContent = c.entryAt(input.value);\n });\n \n \n\n```\n\n### Build command\n\n```\nzig cc -target wasm32-freestanding -g resource.c -lc -Wl,--no-entry -o resource.wasm\n```\n\n========================================\n\nCode:\n```c\n#include <stdlib.h>\n\nvoid print_test(void); // the function I want to use\n\nconst unsigned char heap[4096];\n\nint __attribute__((export_name(\"memstart\")))\nmemstart() {\n return (int)&heap;\n}\n\nint __attribute__((export_name(\"return5\")))\nreturn5(int p) {\n return 5 * p;\n}\n\nint __attribute__((export_name(\"entryAt\")))\nentryAt(int p) {\n print_test();\n return heap[p];\n}\n```\n\n```html\n<!DOCTYPE html>\n<html lang=\"en\">\n <head>\n <title>For Stephen</title>\n </head>\n\n <body>\n <input id=\"input\" type=\"number\" placeholder=\"int param...\"></input>\n <input id=\"bytes\" placeholder=\"bytes...\"></input>\n <pre id=\"output\">output goes gere</pre>\n <button id=\"button_r5\">Return 5</button>\n <button id=\"button_nth\">Get nth byte</button>\n <canvas id=\"my_canvas\"></canvas>\n <script>\n const c = {};\n const encoder = new TextEncoder();\n const decoder = new TextDecoder();\n\n const importObject = {\n \"env\": {\n \"print_test\": () => console.log(\"test print\")\n }\n };\n\n WebAssembly.instantiateStreaming(fetch(\"resource.wasm\", importObject))\n .then(result => {\n const {memory, memstart, return5, entryAt} = result.instance.exports;\n console.log(memstart);\n c.buffer = new Uint8Array(memory.buffer, memstart());\n c.return5 = return5;\n c.entryAt = entryAt;\n });\n\n const button_r5 = document.getElementById(\"button_r5\");\n const button_nth = document.getElementById(\"button_nth\");\n const input = document.getElementById(\"input\");\n const bytes = document.getElementById(\"bytes\");\n const output = document.getElementById(\"output\");\n\n button_r5.addEventListener(\"click\", ()=>{\n output.textContent = c.return5(input.value);\n });\n\n button_nth.addEventListener(\"click\", ()=>{\n c.buffer.set(encoder.encode(bytes.value));\n output.textContent = c.entryAt(input.value);\n });\n </script>\n </body>\n\n</html>\n```\n\n```bash\nzig cc -target wasm32-freestanding -g resource.c -lc -Wl,--no-entry -o resource.wasm\n```\n\n```text\nzig cc\n```\n\n```text\nclang\n```\n\n```text\n__attribute__((import_module(\"env\"), import_name(\"print_test\"))) void print_test();\n```\n\n```text\nvoid print_test() __attribute__((\n __import_module__(\"env\"),\n __import_name__(\"print_test\")\n));\n```\n\n```text\n__attribute__((__import_name__(\"print_test\"))) void print_test();\n```\n\n```text\nEM_IMPORT(NAME)\n```\n\n```text\n__attribute__((import_module(\"env\"), import_name(#NAME)))\n```\n\n========================================\n\nComments:\n- Maybe use `__attribute__((import_module(\"env\"), import_name(\"print_test\"))) void print_test();`?\n- @Inkeliz this works! Add it as an answer and I'll accept it.","metadata":{"transformedAt":"2026-08-18T18:33:48.844Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":10,"totalLines":222,"estimatedTokens":1311}}79{"id":"stack-66630797","source":"stackoverflow","questionId":66630797,"title":"How to create 2d arrays of containers in zig?","tags":["zig"],"text":"Title: How to create 2d arrays of containers in zig?\nTags: zig\nSource: Stack Overflow\n\nQuestion:\nI'm trying to alloc 2d arrays of HashMap(u32, u1) in Zig:\n\n```\nfn alloc2d(comptime t: type, m: u32, n: u32, allocator: *Allocator) callconv(.Inline) ![][]t {\n const array = try allocator.alloc([]t, m);\n for (array) |_, index| {\n array[index] = try allocator.alloc(t, n);\n }\n return array;\n}\n\nfn free2d(comptime t: type, array: [][]t, allocator: *Allocator) callconv(.Inline) void {\n for (array) |_, index| {\n allocator.free(array[index]);\n }\n allocator.free(array);\n}\n\ntest \"Alloc 2D Array\" {\n var gpa = std.heap.GeneralPurposeAllocator(.{}){};\n const allocator = &gpa.allocator;\n defer _ = gpa.deinit();\n\n const HashSet = std.AutoHashMap(u32, u1);\n var array = try alloc2d(*HashSet, 4, 4, allocator);\n defer free2d(*HashSet, array, allocator);\n\n for (array) |_, i| {\n for (array[i]) |_, j| {\n array[i][j] = &(HashSet.init(allocator));\n }\n }\n defer {\n for (array) |_, i| {\n for (array[i]) |_, j| {\n array[i][j].deinit();\n }\n }\n }\n}\n```\n\nHowever, when I test it, the debugger throw a seg fault.\n\nCan anyone tell me what is happening and how to fix it?\n\nThanks a lot!\n\n========================================\n\nCode:\n```text\nfn alloc2d(comptime t: type, m: u32, n: u32, allocator: *Allocator) callconv(.Inline) ![][]t {\n const array = try allocator.alloc([]t, m);\n for (array) |_, index| {\n array[index] = try allocator.alloc(t, n);\n }\n return array;\n}\n\nfn free2d(comptime t: type, array: [][]t, allocator: *Allocator) callconv(.Inline) void {\n for (array) |_, index| {\n allocator.free(array[index]);\n }\n allocator.free(array);\n}\n\ntest \"Alloc 2D Array\" {\n var gpa = std.heap.GeneralPurposeAllocator(.{}){};\n const allocator = &gpa.allocator;\n defer _ = gpa.deinit();\n\n const HashSet = std.AutoHashMap(u32, u1);\n var array = try alloc2d(*HashSet, 4, 4, allocator);\n defer free2d(*HashSet, array, allocator);\n\n for (array) |_, i| {\n for (array[i]) |_, j| {\n array[i][j] = &(HashSet.init(allocator));\n }\n }\n defer {\n for (array) |_, i| {\n for (array[i]) |_, j| {\n array[i][j].deinit();\n }\n }\n }\n}\n```\n\n```text\n...\n\nvar array = try alloc2d(HashSet, 4, 4, allocator);\ndefer free2d(HashSet, array, allocator);\n\nfor (array) |_, i| {\n for (array[i]) |_, j| {\n array[i][j] = HashSet.init(allocator);\n }\n}\n\n...\n```\n\n```text\nfor (array) |*outer| {\n for (outer.*) |*item| {\n item.* = <something>\n }\n}\n```\n\n```text\n*HashSet\n```\n\n```text\nHashSet\n```\n\n```text\narray\n```\n\n```text\n&(HashSet.init(allocator))\n```\n\n```text\ndeinit\n```\n\n```text\n[0][0] = (HashSet.init(allocator)...etc\n```\n\n```text\nZig\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.844Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":10,"totalLines":146,"estimatedTokens":687}}80{"id":"stack-71179787","source":"stackoverflow","questionId":71179787,"title":"Build variable length arguments array for @call","tags":["metaprogramming","quickcheck","zig"],"text":"Title: Build variable length arguments array for @call\nTags: metaprogramming, quickcheck, zig\nSource: Stack Overflow\n\nQuestion:\nI've recently started learning Zig.\nAs a little project I wanted to implement a small QuickCheck [1] style helper library for writing randomized tests.\n\nHowever, I can't figure out how to write a generic way to call a function with an arbitrary number of arguments.\n\nHere's a simplified version that can test functions with two arguments:\n\n```\nconst std = @import(\"std\");\nconst Prng = std.rand.DefaultPrng;\nconst Random = std.rand.Random;\nconst expect = std.testing.expect;\n\n// the thing we want to test\nfn some_property(a: u64, b: u64) !void {\n var tmp: u64 = undefined;\n var c1 = @addWithOverflow(u64, a, b, &tmp);\n var c2 = @addWithOverflow(u64, a, b, &tmp);\n\n expect(c1 == c2);\n}\n\n// helper for generating random arguments for the function under test\nfn gen(comptime T: ?type, rnd: Random) (T orelse undefined) {\n switch (T orelse undefined) {\n u64 => return rnd.int(u64),\n f64 => return rnd.float(f64),\n else => @compileError(\"unsupported type\"),\n }\n}\n\n/// tests if 'property' holds.\nfn for_all(property: anytype) !void {\n var rnd = Prng.init(0);\n\n const arg_types = @typeInfo(@TypeOf(property)).Fn.args;\n\n var i: usize = 0;\n while (i I've tried a few different things, but I can't figure out how to get the above code to work for functions with any number of arguments.\n\nThings I've tried:\n\n- Make `args` an array and fill it with an `inline for` loop. Doesn't work since `[]anytype` is not a valid type.\n\n- Use a bit of comptime magic to build a struct type whose fields hold the arguments for `@call`. This hits a TODO in the compiler: `error: TODO: struct args`.\n\n- Write generic functions that return an appropriate argument tuple call. I don't really like this one, since you need one function for every arity you want to support. But it doesn't seem to work anyway since `antype` is not a valid return type.\n\nI'm on Zig 0.9.1.\n\nAny insight would be appreciated.\n\n[1] https://hackage.haskell.org/package/QuickCheck\n\n========================================\n\nCode:\n```text\nconst std = @import(\"std\");\nconst Prng = std.rand.DefaultPrng;\nconst Random = std.rand.Random;\nconst expect = std.testing.expect;\n\n// the thing we want to test\nfn some_property(a: u64, b: u64) !void {\n var tmp: u64 = undefined;\n var c1 = @addWithOverflow(u64, a, b, &tmp);\n var c2 = @addWithOverflow(u64, a, b, &tmp);\n\n expect(c1 == c2);\n}\n\n// helper for generating random arguments for the function under test\nfn gen(comptime T: ?type, rnd: Random) (T orelse undefined) {\n switch (T orelse undefined) {\n u64 => return rnd.int(u64),\n f64 => return rnd.float(f64),\n else => @compileError(\"unsupported type\"),\n }\n}\n\n/// tests if 'property' holds.\nfn for_all(property: anytype) !void {\n var rnd = Prng.init(0);\n\n const arg_types = @typeInfo(@TypeOf(property)).Fn.args;\n\n var i: usize = 0;\n while (i < 100) {\n var a = gen(arg_types[0].arg_type, rnd.random());\n var b = gen(arg_types[1].arg_type, rnd.random());\n\n var args = .{a, b}; // <-- how do I build args for functions with any number of arguments?\n\n try @call(.{}, property, args);\n\n i += 1;\n }\n}\n\ntest \"test\" {\n try for_all(some_property);\n}\n```\n\n```text\nargs\n```\n\n```text\ninline for\n```\n\n```text\n[]anytype\n```\n\n```text\n@call\n```\n\n```text\nerror: TODO: struct args\n```\n\n```text\nantype\n```\n\n```text\nconst Args = std.meta.ArgsTuple(@TypeOf(property));\n\n var i: usize = 0;\n while (i < 1000) : (i += 1) {\n var args: Args = undefined;\n inline for (std.meta.fields(Args)) |field, index| {\n args[index] = gen(field.field_type, rnd.random());\n }\n\n try @call(.{}, property, args);\n }\n```\n\n```text\nstd.meta.ArgsTuple\n```\n\n```text\n@Type()\n```","metadata":{"transformedAt":"2026-08-18T18:33:48.844Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":10,"totalLines":155,"estimatedTokens":953}}81{"id":"stack-79504017","source":"stackoverflow","questionId":79504017,"title":"Zig as C Linux->Mac cross-compiler for go project with go-sqlite3 error: unable to find dynamic system library 'resolv'","tags":["go","cross-compiling","cgo","zig"],"text":"Title: Zig as C Linux->Mac cross-compiler for go project with go-sqlite3 error: unable to find dynamic system library 'resolv'\nTags: go, cross-compiling, cgo, zig\nSource: Stack Overflow\n\nQuestion:\nI'm building a Go application with native (CGO_ENABLED=1) SQLite support using https://github.com/mattn/go-sqlite3.\n\nI'm trying to get the builder docker image to a reasonable size. (goreleaser/goreleaser-cross works for all platforms, but is over 8GB).\n\nWhen using Zig (0.14.0) as the cross compiler, Linux and Windows targets build/run fine on both an Alpine and Debian/bookworm-image (go 1.24.1) but mac compilation fails with:\n\n```\n/usr/local/go/pkg/tool/linux_amd64/link: running zig failed: exit status 1\n/opt/zig/zig cc -target x86_64-macos -arch x86_64 -m64 -Wl,-headerpad,1144 -o $WORK/b001/exe/a.out /tmp/go-link-2504977538/go.o /tmp/go-link-2504977538/000000.o /tmp/go-link-2504977538/000001.o /tmp/go-link-2504977538/000002.o /tmp/go-link-2504977538/000003.o /tmp/go-link-2504977538/000004.o /tmp/go-link-2504977538/000005.o /tmp/go-link-2504977538/000006.o /tmp/go-link-2504977538/000007.o /tmp/go-link-2504977538/000008.o /tmp/go-link-2504977538/000009.o /tmp/go-link-2504977538/000010.o /tmp/go-link-2504977538/000011.o /tmp/go-link-2504977538/000012.o /tmp/go-link-2504977538/000013.o /tmp/go-link-2504977538/000014.o /tmp/go-link-2504977538/000015.o /tmp/go-link-2504977538/000016.o /tmp/go-link-2504977538/000017.o /tmp/go-link-2504977538/000018.o /tmp/go-link-2504977538/000019.o /tmp/go-link-2504977538/000020.o /tmp/go-link-2504977538/000021.o /tmp/go-link-2504977538/000022.o -lresolv -O2 -g -O2 -g -lpthread -framework CoreFoundation -framework Security\nerror: unable to find dynamic system library 'resolv' using strategy 'paths_first'. searched paths: none\n```\n\nWhat I understand is the resolv-library is supposed to be part of libc, so if Zig doesn't provide it (by not having a musl-implementation for Mac), it should come from a Mac SDK.\n\nI've also tried supplying it with:\n\n```\n(export GOOS=darwin && export GOARCH=amd64 && export CC=\"zig cc -target x86_64-macos --sysroot ${MACOS_SDK} -isysroot ${MACOS_SDK} -I${MACOS_SDK}/usr/include -Wno-nullability-completeness\" && go build -o dist/$GOOS/$GOARCH/)\n```\n\nTo no avail, still getting the \"unable to find dynamic system library\"...\n\nWhat might be missing? How can I get CGO Linux→Mac cross-compilation working with a recent Zig and Go?\n\n========================================\n\nCode:\n```none\n/usr/local/go/pkg/tool/linux_amd64/link: running zig failed: exit status 1\n/opt/zig/zig cc -target x86_64-macos -arch x86_64 -m64 -Wl,-headerpad,1144 -o $WORK/b001/exe/a.out /tmp/go-link-2504977538/go.o /tmp/go-link-2504977538/000000.o /tmp/go-link-2504977538/000001.o /tmp/go-link-2504977538/000002.o /tmp/go-link-2504977538/000003.o /tmp/go-link-2504977538/000004.o /tmp/go-link-2504977538/000005.o /tmp/go-link-2504977538/000006.o /tmp/go-link-2504977538/000007.o /tmp/go-link-2504977538/000008.o /tmp/go-link-2504977538/000009.o /tmp/go-link-2504977538/000010.o /tmp/go-link-2504977538/000011.o /tmp/go-link-2504977538/000012.o /tmp/go-link-2504977538/000013.o /tmp/go-link-2504977538/000014.o /tmp/go-link-2504977538/000015.o /tmp/go-link-2504977538/000016.o /tmp/go-link-2504977538/000017.o /tmp/go-link-2504977538/000018.o /tmp/go-link-2504977538/000019.o /tmp/go-link-2504977538/000020.o /tmp/go-link-2504977538/000021.o /tmp/go-link-2504977538/000022.o -lresolv -O2 -g -O2 -g -lpthread -framework CoreFoundation -framework Security\nerror: unable to find dynamic system library 'resolv' using strategy 'paths_first'. searched paths: none\n```\n\n```none\n(export GOOS=darwin && export GOARCH=amd64 && export CC=\"zig cc -target x86_64-macos --sysroot ${MACOS_SDK} -isysroot ${MACOS_SDK} -I${MACOS_SDK}/usr/include -Wno-nullability-completeness\" && go build -o dist/$GOOS/$GOARCH/)\n```\n\n```text\nFROM crazymax/osxcross:14.5-r0-alpine as osxcross\nFROM golang:1.24-alpine\n\nRUN apk update\nRUN apk add curl zip gettext clang lld musl-dev\n\nRUN go install github.com/jstemmer/go-junit-report/v2@latest\n\nRUN curl https://ziglang.org/download/0.14.0/zig-linux-x86_64-0.14.0.tar.xz | tar x -J -C /opt\nRUN ln -s /opt/zig* /opt/zig\n\nENV PATH=\"$PATH:/opt/zig\"\n\nRUN mkdir /.cache\nRUN chmod -R 777 /.cache\nRUN chmod -R 777 /go/pkg/mod\n\nCOPY --from=osxcross /osxcross /osxcross\n\nENV PATH=\"/osxcross/bin:$PATH\"\nENV LD_LIBRARY_PATH=\"/osxcross/lib:$LD_LIBRARY_PATH\"\n```\n\n```text\nsh '''#!/bin/sh\n export CGO_ENABLED=1\n \n #https://github.com/goreleaser/goreleaser-cross?tab=readme-ov-file#supported-toolchainsplatforms\n (export GOOS=darwin && export GOARCH=amd64 && export CC=\"o64-clang\" && go build -o dist/$GOOS/$GOARCH/)\n (export GOOS=darwin && export GOARCH=arm64 && export CC=\"oa64-clang\" && go build -o dist/$GOOS/$GOARCH/)\n #https://ziglang.org/download/0.14.0/release-notes.html#Support-Table\n (export GOOS=linux && export GOARCH=amd64 && export CC=\"zig cc -target x86_64-linux\" && go build -o dist/$GOOS/$GOARCH/)\n (export GOOS=windows && export GOARCH=amd64 && export CC=\"zig cc -target x86_64-windows\" && go build -o dist/$GOOS/$GOARCH/)\n\n go test -coverprofile=coverage.out -v 2>&1 ./... | go-junit-report -set-exit-code > report.xml\n'''\njunit testResults: 'report.xml'\n```\n\n========================================\n\nComments:\n- «What I understand is the resolv-library is supposed to *be part of libc,* so if Zig doesn't provide it (by not having a musl-implementation for Mac), it should come from a Mac SDK.» (emphasis mine)—this may be a problem with wording. Say, on Debian, it's indeed packaged as part of libc, but it's a separate library. Maybe you could solve your problem by installing a suitable pair of `libc6*-cross` packages matching the C cross-compiler called by zig for macosx target.\n- Hi! Were you building it for macOS on Apple silicon?","metadata":{"transformedAt":"2026-08-18T18:33:48.845Z","totalAnswersIncluded":0,"totalCodeBlocksIncluded":4,"totalLines":87,"estimatedTokens":1466}}82 