Download tests/test_generate.py from Frankenstein-Labs/Cortex-0: direct link, hf CLI and curl.
- Browser
- Download file 2.57 kB
-
https://huggingface.co/Frankenstein-Labs/Cortex-0/resolve/main/tests/test_generate.py
- Command line
-
hf download hf://Frankenstein-Labs/Cortex-0/tests/test_generate.py
-
curl -L -o test_generate.py https://huggingface.co/Frankenstein-Labs/Cortex-0/resolve/main/tests/test_generate.py
2.57 kB
| """Phase 2/3 — tests de la génération (échantillonnage écrit à la main).""" | |
| from __future__ import annotations | |
| import torch | |
| from src.generate import _apply_top_k, _apply_top_p, generate, generate_text | |
| from src.model.text_model import CortexTextLM, TextConfig | |
| from src.tokenizer import load_tokenizer | |
| TINY = TextConfig(vocab_size=32, n_layer=2, n_head=2, n_embd=32, ctx_len=16, dropout=0.0) | |
| def _tiny(): | |
| torch.manual_seed(0) | |
| return CortexTextLM(TINY).eval() | |
| def test_top_k_keeps_exactly_k_finite(): | |
| logits = torch.randn(1, 10) | |
| filtered = _apply_top_k(logits, 3) | |
| assert torch.isfinite(filtered).sum().item() == 3 | |
| def test_top_p_keeps_a_prefix_by_probability(): | |
| logits = torch.zeros(1, 5) | |
| logits[0, 0] = 10.0 # proba ~ 1 | |
| filtered = _apply_top_p(logits, 0.5) | |
| assert torch.isfinite(filtered[0, 0]) | |
| assert not torch.isfinite(filtered[0, 1:]).any() | |
| def test_greedy_is_deterministic(): | |
| model = _tiny() | |
| x = torch.randint(0, 32, (1, 4)) | |
| a = generate(model, x, max_new_tokens=5, greedy=True) | |
| b = generate(model, x, max_new_tokens=5, greedy=True) | |
| assert torch.equal(a, b) | |
| def test_generate_extends_sequence(): | |
| model = _tiny() | |
| x = torch.randint(0, 32, (1, 4)) | |
| out = generate(model, x, max_new_tokens=6, temperature=1.0) | |
| assert out.shape == (1, 10) | |
| assert torch.equal(out[:, :4], x) | |
| def test_generate_respects_ctx_len(): | |
| model = _tiny() | |
| x = torch.randint(0, 32, (1, 16)) | |
| out = generate(model, x, max_new_tokens=3, greedy=True) | |
| assert out.shape[1] == 19 # la condition est tronquée mais la sortie grandit | |
| def test_generate_stops_on_eos(monkeypatch): | |
| model = _tiny() | |
| x = torch.randint(0, 32, (1, 3)) | |
| eos = 7 | |
| # Force le modèle à toujours prédire eos. | |
| def fake_forward(input_ids, targets=None): | |
| logits = torch.full((input_ids.size(0), input_ids.size(1), 32), -100.0) | |
| logits[:, :, eos] = 100.0 | |
| return logits, None | |
| monkeypatch.setattr(model, "forward", fake_forward) | |
| out = generate(model, x, max_new_tokens=50, greedy=True, eos_id=eos) | |
| assert out.shape[1] == 4 # un seul nouveau token, puis arrêt | |
| def test_generate_text_with_real_tokenizer(): | |
| """Bout-en-bout avec le vrai tokenizer 32k : ne doit pas planter.""" | |
| tok = load_tokenizer() | |
| model = CortexTextLM( | |
| TextConfig(vocab_size=tok.vocab_size, n_layer=1, n_head=2, n_embd=32, ctx_len=32) | |
| ).eval() | |
| text = generate_text(model, tok, "Bonjour", max_new_tokens=5, greedy=True) | |
| assert isinstance(text, str) and len(text) > 0 | |