Skip to documentation
SLOP

tiny.preserves.predicates

Reference tiny.preserves predicates

Defined in tiny.preserves.

Predicates that test a value's shape.

API (11)

Actions

Public operations.

Types and contracts

Public types and contracts.

No direct callersNo direct callstiny.preservespredicates
Static calls · unresolved targets: unknown · external targets: unknown.

Source

Called byCallsNo direct callstiny.preservesisAtomtest sourcelib.preserves.src.predicatestest: isNull, isSymbol, isEmbedded, i...predicatesisAtom
Static calls · unresolved targets: 0 · external targets: 2.
Called byCallsNo direct callstiny.preservesisCompoundtest sourcelib.preserves.src.predicatestest: isNull, isSymbol, isEmbedded, i...predicatesisCompound
Static calls · unresolved targets: 0 · external targets: 2.
Called byCallsNo direct callstiny.preservesisEmbeddedtest sourcelib.preserves.src.predicatestest: isNull, isSymbol, isEmbedded, i...predicatesisEmbedded
Static calls · unresolved targets: 0 · external targets: 2.
Called byCallsNo direct callstiny.preservesisNulltest sourcelib.preserves.src.predicatestest: isNull, isSymbol, isEmbedded, i...predicatesisNull
Static calls · unresolved targets: 0 · external targets: 2.
Called byCallstiny.preservesisObservetest sourcelib.preserves.src.predicatestest: isObserve matches `<Observe ...predicatesisRecordpredicatesisObserve
Static calls · unresolved targets: 0 · external targets: 1.
Called byCallsNo direct callstiny.preservesisPatternFormtest sourcelib.preserves.src.predicatestest: isNull, isSymbol, isEmbedded, i...predicatesisPatternForm
Static calls · unresolved targets: 0 · external targets: 2.
Called byCallsNo direct callstiny.preservesisRecordpredicatesisObservetest sourcelib.preserves.src.predicatestest: isRecord matches label and arit...predicatesisRecord
Static calls · unresolved targets: 0 · external targets: 2.
Called byCallsNo direct callstiny.preservesisSymboltest sourcelib.preserves.src.predicatestest: isNull, isSymbol, isEmbedded, i...predicatesisSymbol
Static calls · unresolved targets: 0 · external targets: 2.
Called byCallsNo direct callstiny.preservesrecordAttributestest sourcelib.preserves.src.predicatestest: recordAttributes extracts dict ...predicatesrecordAttributes
Static calls · unresolved targets: 0 · external targets: 2.

Source: lib/preserves/src/predicates.zig

zig
//! Predicates that test a value's shape. None of them allocates.//!//! Code that dispatches on values needs one tested answer for each shape question, so every caller//! draws the line between atoms, compound values and patterns the same way.const std = @import("std");const value_mod = @import("value.zig");const domain_mod = @import("domain.zig");const symbols_mod = @import("symbols.zig");pub const Value = value_mod.Value;pub const NoEmbedded = domain_mod.NoEmbedded;/// Returns the entries of a record's attribute dictionary. The JSON encoder calls this function for/// the attributes of a record it writes as a `{"type": …}` object. A record with zero fields has an/// empty attribute list. A record whose one field is a dictionary with string keys has that/// dictionary's entries. The call returns null for any other value, including a record whose/// dictionary has a key other than a string. The entries point into `value`, and the call allocates/// nothing.pub fn recordAttributes(comptime D: type, value: Value(D)) ?[]const Value(D).DictionaryEntry {    domain_mod.assertIsDomain(D);    switch (value) {        .record => |r| {            if (r.fields.len == 0) return &.{};            if (r.fields.len != 1) return null;            switch (r.fields[0]) {                .dictionary => |d| {                    for (d) |entry| {                        switch (entry.key) {                            .string => {},                            else => return null,                        }                    }                    return d;                },                else => return null,            }        },        else => return null,    }}/// Returns true when `value` is a record. When `label` is given, its label is the symbol `label`,/// and when `arity` is given, it has `arity` fields. The `Observe` field readers call this function/// for a label and field-count check, and so does `isObserve`. A record with a label other than a/// symbol matches only when `label` is null. The package root's version takes the label as a/// `Symbol`.pub fn isRecord(comptime D: type, value: Value(D), label: ?[]const u8, arity: ?usize) bool {    domain_mod.assertIsDomain(D);    switch (value) {        .record => |r| {            if (label) |l| {                switch (r.label.*) {                    .symbol => |s| if (!std.mem.eql(u8, s, l)) return false,                    else => return false,                }            }            if (arity) |a| {                if (r.fields.len != a) return false;            }            return true;        },        else => return false,    }}/// Returns true when `value` is an `<Observe pattern observer>` record: labeled `Observe`, with two/// fields.pub fn isObserve(comptime D: type, value: Value(D)) bool {    return isRecord(D, value, symbols_mod.SYM_OBSERVE.name, 2);}/// Returns true when `value` is an embedded value.pub fn isEmbedded(comptime D: type, value: Value(D)) bool {    domain_mod.assertIsDomain(D);    return value == .embedded;}/// Returns true when `value` is a symbol.pub fn isSymbol(comptime D: type, value: Value(D)) bool {    domain_mod.assertIsDomain(D);    return value == .symbol;}/// Returns true when `value` is the symbol `null`, the value the package uses for JSON's null.pub fn isNull(comptime D: type, value: Value(D)) bool {    domain_mod.assertIsDomain(D);    return switch (value) {        .symbol => |s| std.mem.eql(u8, s, symbols_mod.SYM_NULL.name),        else => false,    };}/// Returns true for a record, sequence, set or dictionary. The call returns false for patterns and/// embedded values, even a capture that holds a record.pub fn isCompound(comptime D: type, value: Value(D)) bool {    domain_mod.assertIsDomain(D);    return switch (value) {        .record, .sequence, .set, .dictionary => true,        else => false,    };}/// Returns true for a discard, capture, bind or rest pattern.pub fn isPatternForm(comptime D: type, value: Value(D)) bool {    domain_mod.assertIsDomain(D);    return switch (value) {        .discard, .capture, .bind, .rest_pattern => true,        else => false,    };}/// Returns true for a boolean, double, integer, string, byte string or symbol. The call returns/// false for an embedded value.pub fn isAtom(comptime D: type, value: Value(D)) bool {    domain_mod.assertIsDomain(D);    return switch (value) {        .boolean, .double, .signed_integer, .string, .byte_string, .symbol => true,        else => false,    };}test "isRecord matches label and arity optionally" {    const V = Value(NoEmbedded);    const allocator = std.testing.allocator;    var arena = std.heap.ArenaAllocator.init(allocator);    defer arena.deinit();    const a = arena.allocator();    const label = try V.initSymbol(a, "Foo");    const fields = try a.alloc(V, 2);    fields[0] = V.initI128(1);    fields[1] = V.initI128(2);    const rec = try V.initRecord(a, label, fields);    try std.testing.expect(isRecord(NoEmbedded, rec, "Foo", 2));    try std.testing.expect(isRecord(NoEmbedded, rec, null, 2));    try std.testing.expect(isRecord(NoEmbedded, rec, "Foo", null));    try std.testing.expect(isRecord(NoEmbedded, rec, null, null));    try std.testing.expect(!isRecord(NoEmbedded, rec, "Bar", 2));    try std.testing.expect(!isRecord(NoEmbedded, rec, "Foo", 3));    try std.testing.expect(!isRecord(NoEmbedded, V.initBoolean(true), null, null));}test "isObserve matches `<Observe _ _>` records" {    const V = Value(NoEmbedded);    const allocator = std.testing.allocator;    var arena = std.heap.ArenaAllocator.init(allocator);    defer arena.deinit();    const a = arena.allocator();    const label = try V.initSymbol(a, "Observe");    const fields = try a.alloc(V, 2);    fields[0] = V{ .discard = {} };    fields[1] = V.initBoolean(true);    const rec = try V.initRecord(a, label, fields);    try std.testing.expect(isObserve(NoEmbedded, rec));    const wrong_arity = try V.initRecord(a, try V.initSymbol(a, "Observe"), try a.alloc(V, 0));    try std.testing.expect(!isObserve(NoEmbedded, wrong_arity));}test "isNull, isSymbol, isEmbedded, isAtom, isCompound, isPatternForm" {    const V = Value(NoEmbedded);    const allocator = std.testing.allocator;    var arena = std.heap.ArenaAllocator.init(allocator);    defer arena.deinit();    const a = arena.allocator();    const null_v = V{ .symbol = "null" };    try std.testing.expect(isNull(NoEmbedded, null_v));    try std.testing.expect(isSymbol(NoEmbedded, null_v));    try std.testing.expect(isAtom(NoEmbedded, null_v));    try std.testing.expect(!isCompound(NoEmbedded, null_v));    try std.testing.expect(!isPatternForm(NoEmbedded, null_v));    try std.testing.expect(!isEmbedded(NoEmbedded, null_v));    const not_null = V{ .symbol = "hello" };    try std.testing.expect(!isNull(NoEmbedded, not_null));    const seq = V.initSequence(try a.alloc(V, 0));    try std.testing.expect(isCompound(NoEmbedded, seq));    try std.testing.expect(!isAtom(NoEmbedded, seq));    const discard_v: V = .{ .discard = {} };    try std.testing.expect(isPatternForm(NoEmbedded, discard_v));    try std.testing.expect(!isAtom(NoEmbedded, discard_v));    try std.testing.expect(!isCompound(NoEmbedded, discard_v));}test "recordAttributes extracts dict entries only for single-dict-field records" {    const V = Value(NoEmbedded);    const allocator = std.testing.allocator;    var arena = std.heap.ArenaAllocator.init(allocator);    defer arena.deinit();    const a = arena.allocator();    const empty_entries: V.Dictionary = try a.alloc(V.DictionaryEntry, 0);    const d_empty = V.initDictionary(empty_entries);    const fields_empty = try a.alloc(V, 1);    fields_empty[0] = d_empty;    const rec_empty = try V.initRecord(a, try V.initSymbol(a, "Label"), fields_empty);    const got_empty = recordAttributes(NoEmbedded, rec_empty).?;    try std.testing.expectEqual(@as(usize, 0), got_empty.len);    const entries = try a.alloc(V.DictionaryEntry, 1);    entries[0] = .{ .key = try V.initString(a, "k"), .value = V.initI128(1) };    const d_one = V.initDictionary(entries);    const fields_one = try a.alloc(V, 1);    fields_one[0] = d_one;    const rec_one = try V.initRecord(a, try V.initSymbol(a, "Label"), fields_one);    const got_one = recordAttributes(NoEmbedded, rec_one).?;    try std.testing.expectEqual(@as(usize, 1), got_one.len);    try std.testing.expect(recordAttributes(NoEmbedded, V.initI128(0)) == null);    const bad_entries = try a.alloc(V.DictionaryEntry, 1);    bad_entries[0] = .{ .key = V.initI128(7), .value = V.initI128(1) };    const d_bad = V.initDictionary(bad_entries);    const fields_bad = try a.alloc(V, 1);    fields_bad[0] = d_bad;    const rec_bad = try V.initRecord(a, try V.initSymbol(a, "Label"), fields_bad);    try std.testing.expect(recordAttributes(NoEmbedded, rec_bad) == null);    const fields_two = try a.alloc(V, 2);    fields_two[0] = V.initI128(1);    fields_two[1] = V.initI128(2);    const rec_two = try V.initRecord(a, try V.initSymbol(a, "Label"), fields_two);    try std.testing.expect(recordAttributes(NoEmbedded, rec_two) == null);}

Source: lib/preserves/src/root.zig:115

zig
pub const predicates = @import("predicates.zig");

Audit

Definitions10
Public names10
Members0
Version26.7.0
Revisiondaab053ee433