익명 유니언 리터럴

익명 유니언 리터럴 (Anonymous Union Literals)

유니언(union)을 초기화할 때마다 매번 타입 이름을 써 주는 건 번거로워요. Zig는 바로 그걸 덜어 주는 문법을 제공하는데, 길을 알려면 먼저 Anonymous Struct Literals 문법을 함께 봐야 해요. 이 문법을 쓰면 타입을 따로 지정하지 않고도 유니언을 초기화할 수 있어요.

출처: Zig Documentation

본문

구체적으로 말하면, 익명 구조체 리터럴(anonymous struct literal) 문법(.{ ... })을 그대로 가져다가 유니언 초기화에 쓸 수 있어요. 값의 타입을 컴파일러가 문맥에서 알아낼 수 있을 때는 타입 이름을 생략해도 된다는 뜻이에요. 코드로 확인해 볼게요.

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

const Number = union {
    int: i32,
    float: f64,
};

test "anonymous union literal syntax" {
    const i: Number = .{ .int = 42 };
    const f = makeNumber();
    try expectEqual(42, i.int);
    try expectEqual(12.34, f.float);
}

fn makeNumber() Number {
    return .{ .float = 12.34 };
}

i: Number = .{ .int = 42 }처럼 변수 선언에서 타입을 명시해 주면 오른쪽의 .{ .int = 42 }Number 유니언으로 초기화돼요. makeNumber()처럼 함수 반환 타입이 이미 Number로 정해져 있으면, return .{ .float = 12.34 }처럼 몸통에서는 타입을 또 쓸 필요가 없어요. 컴파일러가 반환 타입을 보고 알아서 Number로 해석해 주거든요.

실행해 보면 두 테스트가 모두 통과해요.

$ zig test test_anonymous_union.zig
1/1 test_anonymous_union.test.anonymous union literal syntax...OK
All 1 tests passed.

익명 문법은 어디에나 쓸 수 있는 게 아니라, 컴파일러가 기대하는 타입을 문맥에서 알 수 있을 때만 동작해요. 타입이 안 정해진 자리에서는 문법만 보고 어떤 유니언인지 알 수 없으니, 그럴 땐 타입을 명시해 줘야 해요.

더 알아보기

  • Anonymous Struct Literals — 같은 익명 문법이 구조체에서 어떻게 쓰이는지.
  • union — 유니언 타입 자체의 선언과 규칙.