1

https://ziglang.org/documentation/master/#struct

// Functions called at compile-time are memoized. This means you can
// do this:
try expect(LinkedList(i32) == LinkedList(i32));

IIUC, if functions called at compile-time are memoized, they should be pure function. But it seems this is promised by another mechanism: type valued expression must be comptime expression(raise "unable to evaluate constant expression" if any non-comptime expression is used) + there is no way to make a global comptime var(mutable).

But there is a "counterexample":

const std = @import("std");
const expect = std.testing.expect;

test {
    comptime var x: comptime_int = undefined;
    const ns = struct {
        fn foo() type {
            return struct {
                const v: i32 = x;
            };
        }
    };
    x = 10;
    const a = ns.foo();
    x = 20;
    const b = ns.foo();
    try expect(a == b);
    try expect(a.v == 20);
    try expect(b.v == 20);
}

But if the first access of v is before x = 20, the a.v and b.v will be 10.

const std = @import("std");
const expect = std.testing.expect;

test {
    comptime var x: comptime_int = undefined;
    const ns = struct {
        fn foo() type {
            return struct {
                const v: i32 = x;
            };
        }
    };
    x = 10;
    const a = ns.foo();
    try expect(a.v == 10);
    x = 20;
    const b = ns.foo();
    try expect(a == b);
    try expect(a.v == 10);
}
YouJiacheng
  • 449
  • 3
  • 11
  • That certainly is not the behaviour that I would expect. Seems like an artifact of lazy comptime evaluation combined with memoization? – Michael Pfaff Aug 05 '23 at 02:59

0 Answers0