t27.aiEnglish

Обратно в три значения

Вы узнаете

Как порог превращает сумму нейрона обратно в трит и почему каждому краю мёртвой зоны нужен свой тест.

Нейрон тернарной сети складывает произведения тритов, и сумма может быть любым небольшим целым. quantize в activation_quantizer.t27 сжимает её обратно: выше порога возвращает 2 (P), ниже минус порога — 0 (N), между ними — 1 (Z). on_comb в конце делает её комбинационной: регистра нет, выход следует за входами. Браузер пропускает все 7 тестов, потому что его исполнитель пока не знает assert_eq; нативный t27c запускает все 7, все проходят, ни один не пустой. Запись меняет > на >= в строке 6, и сумма, равная порогу, уже считается P. Падает ровно один тест, quantize_boundary_hi, который ждёт Z от quantize(10, 10). Каждый байт в записи напечатала команда; инсценирован только набор текста.

Попробуйте

Найдите в записи изменённую строку и упавший тест; затем найдите в спеке quantize_boundary_lo и определите, какую замену одного символа в строке 7 он поймает.

Открыть интерактивный урок →

t27c on activation_quantizer.t27 -- Quantize at the edge, native
t27c on activation_quantizer.t27 -- Quantize at the edge, native ↗

t27c on the t27c lab (Railway), spec at t27 5ff0ec512: 7 tests pass natively; one > in the quantizer becoming >= fails exactly one test, quantize_boundary_hi; git restores the spec.

specs/ternary/activation_quantizer.t27

module ActivationQuantizer;
// Ternary activation quantizer for the BitNet engine: re-ternarize a signed
// accumulator to a packed trit {N=0b00, Z=0b01, P=0b10} using a symmetric
// threshold. v > +t -> P, v < -t -> N, else Z.
pub fn quantize(v: i16, threshold: i16) -> u8 {
    if (v > threshold) { return 2; }
    if (v < -threshold) { return 0; }
    return 1;
}

test quantize_positive { assert_eq(quantize(100, 10), 2); }
test quantize_negative { assert_eq(quantize(-100, 10), 0); }
test quantize_zero_band { assert_eq(quantize(5, 10), 1); }
test quantize_boundary_hi { assert_eq(quantize(10, 10), 1); }
test quantize_boundary_lo { assert_eq(quantize(-10, 10), 1); }
test quantize_just_over { assert_eq(quantize(11, 10), 2); }
test quantize_just_under { assert_eq(quantize(-11, 10), 0); }

// W696: the hardware boundary, DERIVED -- not chosen.
//
// T187 measured an exact equivalence over 617 specs: a module gets a data
// port iff the spec declares `on_comb` or `on_clock`. Without one the
// compiler emits `NO DATA PORTS -- this module cannot move a value across
// its boundary`, and synthesis optimises the whole thing away.
//
// The standing rule is that the default must NOT be guessed. Here no guess
// was made: `t27c entry-points` found exactly ONE function in this spec that
// takes a parameter, returns a value, has a body, and whose types all have a
// known width. With one candidate the choice is forced, so this forwards and
// invents nothing. 11 of 387 port-less specs qualified.
fn on_comb(v: i16, threshold: i16) -> u8 { return quantize(v, threshold); }

endmodule

Открыть спеку урока в плеере ↗

Все уроки