deadhead-space-freight-tycoon/packages/sim/test/rng.test.ts

52 lines
1.6 KiB
TypeScript

import { describe, expect, it } from "vitest";
import { createRng, deriveSeed } from "../src/index";
const sequence = (seed: number, length = 1000) => {
const rng = createRng(seed);
return Array.from({ length }, () => rng.next());
};
describe("seeded RNG", () => {
it("produces the same 1,000 values for the same seed", () => {
expect(sequence(42)).toEqual(sequence(42));
});
it("produces different sequences for different seeds", () => {
expect(sequence(42)).not.toEqual(sequence(43));
});
it("keeps next() in [0, 1)", () => {
for (const value of sequence(7, 10_000)) {
expect(value).toBeGreaterThanOrEqual(0);
expect(value).toBeLessThan(1);
}
});
it("keeps int() within inclusive bounds and reaches both ends", () => {
const rng = createRng(1);
const seen = new Set<number>();
for (let i = 0; i < 1000; i++) {
const value = rng.int(1, 5);
expect(value).toBeGreaterThanOrEqual(1);
expect(value).toBeLessThanOrEqual(5);
seen.add(value);
}
expect([...seen].sort()).toEqual([1, 2, 3, 4, 5]);
});
it("picks only list elements and throws on an empty list", () => {
const rng = createRng(3);
const list = ["a", "b", "c"];
for (let i = 0; i < 100; i++) {
expect(list).toContain(rng.pick(list));
}
expect(() => rng.pick([])).toThrow();
});
it("derives different child seeds for different labels", () => {
expect(deriveSeed(42, "board")).not.toBe(deriveSeed(42, "names"));
expect(deriveSeed(42, "board")).not.toBe(deriveSeed(43, "board"));
expect(deriveSeed(42, "board")).toBe(deriveSeed(42, "board"));
});
});