TinyAdd2Deployer commited on
Commit ·
beb6a05
1
Parent(s): cb8f591
Upload TinyAdd2LLM model files
Browse files- MODEL_CARD.md +28 -0
- README.md +60 -0
- chat.py +24 -0
- infer.py +24 -0
- model.py +70 -0
- model/add2_model.bin +3 -0
- requirements.txt +1 -0
MODEL_CARD.md
ADDED
|
@@ -0,0 +1,28 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
# Model Card: Tiny Add2 LLM 10MB
|
| 2 |
+
|
| 3 |
+
## Purpose
|
| 4 |
+
|
| 5 |
+
A small addition-only model for exactly two non-negative integers.
|
| 6 |
+
|
| 7 |
+
## Architecture
|
| 8 |
+
|
| 9 |
+
This is a lookup-table style mini model, not a general LLM. The model stores all sums for numbers from `0` to `2199` in a 10 MiB binary file.
|
| 10 |
+
|
| 11 |
+
## Strength
|
| 12 |
+
|
| 13 |
+
- Exact answers for supported range
|
| 14 |
+
- Very low CPU/RAM
|
| 15 |
+
- Works offline
|
| 16 |
+
- Simple code
|
| 17 |
+
|
| 18 |
+
## Weakness
|
| 19 |
+
|
| 20 |
+
- Not a real chatbot
|
| 21 |
+
- No reasoning outside two-number addition
|
| 22 |
+
- Default range is only `0..2199`
|
| 23 |
+
|
| 24 |
+
## Example
|
| 25 |
+
|
| 26 |
+
Input: `12 + 30`
|
| 27 |
+
|
| 28 |
+
Output: `42`
|
README.md
ADDED
|
@@ -0,0 +1,60 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
# Tiny Add2 LLM 10MB
|
| 2 |
+
|
| 3 |
+
This is a **tiny addition-only model package**. It is not a real general-purpose LLM like Llama/GPT. It is made for one job only:
|
| 4 |
+
|
| 5 |
+
> add exactly 2 non-negative numbers.
|
| 6 |
+
|
| 7 |
+
Example:
|
| 8 |
+
|
| 9 |
+
```bash
|
| 10 |
+
python infer.py "12 + 30"
|
| 11 |
+
# 42
|
| 12 |
+
```
|
| 13 |
+
|
| 14 |
+
## What is included
|
| 15 |
+
|
| 16 |
+
- `model/add2_model.bin` — 10 MB model file
|
| 17 |
+
- `model.py` — model loader
|
| 18 |
+
- `infer.py` — one-shot addition answer
|
| 19 |
+
- `chat.py` — simple chat mode
|
| 20 |
+
- `build_model.py` — rebuild the 10 MB model file
|
| 21 |
+
- `test_model.py` — quick tests
|
| 22 |
+
|
| 23 |
+
## Limit
|
| 24 |
+
|
| 25 |
+
Default model supports numbers from `0` to `2199`.
|
| 26 |
+
|
| 27 |
+
Valid inputs:
|
| 28 |
+
|
| 29 |
+
```text
|
| 30 |
+
12 + 30
|
| 31 |
+
add 15 and 7
|
| 32 |
+
100 plus 55
|
| 33 |
+
```
|
| 34 |
+
|
| 35 |
+
Invalid inputs:
|
| 36 |
+
|
| 37 |
+
```text
|
| 38 |
+
hello
|
| 39 |
+
12 + 30 + 5
|
| 40 |
+
-1 + 5
|
| 41 |
+
99999 + 1
|
| 42 |
+
```
|
| 43 |
+
|
| 44 |
+
## Run on PC
|
| 45 |
+
|
| 46 |
+
```bash
|
| 47 |
+
pip install -r requirements.txt
|
| 48 |
+
python infer.py "123 + 456"
|
| 49 |
+
python chat.py
|
| 50 |
+
```
|
| 51 |
+
|
| 52 |
+
## Rebuild model
|
| 53 |
+
|
| 54 |
+
```bash
|
| 55 |
+
python build_model.py --max-number 2199 --target-mb 10 --out model/add2_model.bin
|
| 56 |
+
```
|
| 57 |
+
|
| 58 |
+
## Hinglish note
|
| 59 |
+
|
| 60 |
+
Bhai, ye ek chhota **addition-only mini model** hai. Ye chatbot jaisa general answer nahi dega. Sirf 2 number add karega.
|
chat.py
ADDED
|
@@ -0,0 +1,24 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
from __future__ import annotations
|
| 2 |
+
|
| 3 |
+
from model import Add2ModelError, TinyAdd2LLM
|
| 4 |
+
|
| 5 |
+
|
| 6 |
+
def main() -> None:
|
| 7 |
+
model = TinyAdd2LLM.load("model/add2_model.bin")
|
| 8 |
+
print("Tiny Add2 LLM loaded.")
|
| 9 |
+
print(f"Limit: 0 to {model.max_number}. Type 'exit' to stop.")
|
| 10 |
+
print("Examples: 12 + 30 | add 15 and 7 | 100 plus 55")
|
| 11 |
+
|
| 12 |
+
while True:
|
| 13 |
+
user = input("You: ").strip()
|
| 14 |
+
if user.lower() in {"exit", "quit", "q"}:
|
| 15 |
+
print("Bye")
|
| 16 |
+
break
|
| 17 |
+
try:
|
| 18 |
+
print("TinyAdd2LLM:", model.answer(user))
|
| 19 |
+
except Add2ModelError as e:
|
| 20 |
+
print("TinyAdd2LLM:", e)
|
| 21 |
+
|
| 22 |
+
|
| 23 |
+
if __name__ == "__main__":
|
| 24 |
+
main()
|
infer.py
ADDED
|
@@ -0,0 +1,24 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
from __future__ import annotations
|
| 2 |
+
|
| 3 |
+
import argparse
|
| 4 |
+
from pathlib import Path
|
| 5 |
+
|
| 6 |
+
from model import Add2ModelError, TinyAdd2LLM
|
| 7 |
+
|
| 8 |
+
|
| 9 |
+
def main() -> None:
|
| 10 |
+
parser = argparse.ArgumentParser(description="Tiny Add2 LLM inference")
|
| 11 |
+
parser.add_argument("prompt", help="Example: '12 + 30'")
|
| 12 |
+
parser.add_argument("--model", default=str(Path("model") / "add2_model.bin"), help="Path to model file")
|
| 13 |
+
args = parser.parse_args()
|
| 14 |
+
|
| 15 |
+
try:
|
| 16 |
+
model = TinyAdd2LLM.load(args.model)
|
| 17 |
+
print(model.answer(args.prompt))
|
| 18 |
+
except (Add2ModelError, FileNotFoundError) as e:
|
| 19 |
+
print(f"ERROR: {e}")
|
| 20 |
+
raise SystemExit(1)
|
| 21 |
+
|
| 22 |
+
|
| 23 |
+
if __name__ == "__main__":
|
| 24 |
+
main()
|
model.py
ADDED
|
@@ -0,0 +1,70 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
from __future__ import annotations
|
| 2 |
+
|
| 3 |
+
import re
|
| 4 |
+
import struct
|
| 5 |
+
from dataclasses import dataclass
|
| 6 |
+
from pathlib import Path
|
| 7 |
+
from typing import Tuple
|
| 8 |
+
|
| 9 |
+
import numpy as np
|
| 10 |
+
|
| 11 |
+
MAGIC = b"ADD2LLM1" # 8 bytes
|
| 12 |
+
HEADER_STRUCT = "<8sIIII" # magic, max_number, rows, cols, table_bytes
|
| 13 |
+
HEADER_SIZE = struct.calcsize(HEADER_STRUCT)
|
| 14 |
+
|
| 15 |
+
|
| 16 |
+
class Add2ModelError(Exception):
|
| 17 |
+
"""Raised when input cannot be handled by the tiny addition model."""
|
| 18 |
+
|
| 19 |
+
|
| 20 |
+
@dataclass
|
| 21 |
+
class TinyAdd2LLM:
|
| 22 |
+
model_path: Path
|
| 23 |
+
max_number: int
|
| 24 |
+
table: np.ndarray
|
| 25 |
+
|
| 26 |
+
@classmethod
|
| 27 |
+
def load(cls, model_path: str | Path = "model/add2_model.bin") -> "TinyAdd2LLM":
|
| 28 |
+
path = Path(model_path)
|
| 29 |
+
if not path.exists():
|
| 30 |
+
raise FileNotFoundError(f"Model file not found: {path}")
|
| 31 |
+
|
| 32 |
+
with path.open("rb") as f:
|
| 33 |
+
header = f.read(HEADER_SIZE)
|
| 34 |
+
magic, max_number, rows, cols, table_bytes = struct.unpack(HEADER_STRUCT, header)
|
| 35 |
+
if magic != MAGIC:
|
| 36 |
+
raise Add2ModelError("Invalid model file: bad magic header")
|
| 37 |
+
raw = f.read(table_bytes)
|
| 38 |
+
|
| 39 |
+
table = np.frombuffer(raw, dtype=np.uint16).reshape((rows, cols))
|
| 40 |
+
return cls(model_path=path, max_number=max_number, table=table)
|
| 41 |
+
|
| 42 |
+
def add(self, a: int, b: int) -> int:
|
| 43 |
+
if not (0 <= a <= self.max_number and 0 <= b <= self.max_number):
|
| 44 |
+
raise Add2ModelError(
|
| 45 |
+
f"This 10MB model supports only numbers 0 to {self.max_number}. "
|
| 46 |
+
f"Got: {a}, {b}"
|
| 47 |
+
)
|
| 48 |
+
return int(self.table[a, b])
|
| 49 |
+
|
| 50 |
+
def answer(self, text: str) -> str:
|
| 51 |
+
a, b = parse_two_number_addition(text)
|
| 52 |
+
return str(self.add(a, b))
|
| 53 |
+
|
| 54 |
+
|
| 55 |
+
def parse_two_number_addition(text: str) -> Tuple[int, int]:
|
| 56 |
+
text = text.strip().lower()
|
| 57 |
+
patterns = [
|
| 58 |
+
r"^\s*(\d+)\s*\+\s*(\d+)\s*\??\s*$",
|
| 59 |
+
r"^\s*(\d+)\s+plus\s+(\d+)\s*\??\s*$",
|
| 60 |
+
r"^\s*add\s+(\d+)\s+and\s+(\d+)\s*\??\s*$",
|
| 61 |
+
r"^\s*what\s+is\s+(\d+)\s*\+\s*(\d+)\s*\??\s*$",
|
| 62 |
+
r"^\s*what\s+is\s+(\d+)\s+plus\s+(\d+)\s*\??\s*$",
|
| 63 |
+
]
|
| 64 |
+
for pattern in patterns:
|
| 65 |
+
match = re.match(pattern, text)
|
| 66 |
+
if match:
|
| 67 |
+
return int(match.group(1)), int(match.group(2))
|
| 68 |
+
raise Add2ModelError(
|
| 69 |
+
"I only understand two-number addition, like: 12 + 30, 12 plus 30, or add 12 and 30."
|
| 70 |
+
)
|
model/add2_model.bin
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:c5795578c5336e678f7240ab314a9d754b404fe1a07e95c0726d19427e951d08
|
| 3 |
+
size 10485760
|
requirements.txt
ADDED
|
@@ -0,0 +1 @@
|
|
|
|
|
|
|
| 1 |
+
numpy>=1.22
|