Define a PolyNode type
Description
Define a PolyNode type.
- Message struct embeds a poly: PolyNode field.
- PolyHelper(Message) gives tag identity and identifyNodeAs.
- init sets the tag on a stack value, no heap.
- isIt checks the tag; identifyNodeAs recovers the typed pointer.
Diagram
stack: var msg: Message
│
PolyHelper.init ──► msg.poly.tag set (no alloc)
│
MessagePolyHelper.identifyNodeAs ──► field access (no transfer)
(stack-allocated — no free needed)
Source
pub fn define_a_polynode_type(allocator: std.mem.Allocator, io: std.Io) !void {
_ = .{ allocator, io };
var msg: Message = .{ .text = "hello", .priority = 1 };
MessagePolyHelper.init(&msg);
try helpers.expect(error.DefineTypeFailed, MessagePolyHelper.isIt(msg.poly.tag), "expected Message tag");
try helpers.expect(error.DefineTypeFailed, !items.Event.EventPolyHelper.isIt(msg.poly.tag), "unexpected Event tag");
const poly: *polynode.PolyNode = &msg.poly;
const recovered: *Message = MessagePolyHelper.identifyNodeAs(poly) orelse return error.CastFailed;
try helpers.expect(error.DefineTypeFailed, std.mem.eql(u8, "hello", recovered.*.text), "wrong text");
try helpers.expect(error.DefineTypeFailed, recovered.*.priority == 1, "wrong priority");
}
pub const Message = struct {
poly: polynode.PolyNode = .{},
text: []const u8 = "",
priority: u8 = 0,
};
pub const MessagePolyHelper = polynode.PolyHelper(Message);
const items = @import("../items/items.zig");
const helpers = @import("../helpers/helpers.zig");
const polynode = @import("matryoshka").polynode;
const std = @import("std");