feat: refactor AlphaBetaSearch and ClassicalBot for improved evaluation and organization
This commit is contained in:
@@ -0,0 +1,173 @@
|
||||
# NNUE Training Pipeline
|
||||
|
||||
This directory contains the complete NNUE (Efficiently Updatable Neural Network) training pipeline for the Now-Chess bot.
|
||||
|
||||
## Overview
|
||||
|
||||
The pipeline generates 500,000 random chess positions, evaluates them with Stockfish, trains a neural network, and exports the weights as Scala code for integration into the engine.
|
||||
|
||||
## Prerequisites
|
||||
|
||||
Install Python dependencies:
|
||||
|
||||
```bash
|
||||
pip install -r requirements.txt
|
||||
```
|
||||
|
||||
Ensure Stockfish is installed. You can:
|
||||
- Install via package manager: `apt-get install stockfish` (Linux) or `brew install stockfish` (macOS)
|
||||
- Or download from [stockfish.org](https://stockfishchess.org)
|
||||
|
||||
Set the Stockfish path:
|
||||
```bash
|
||||
export STOCKFISH_PATH=/path/to/stockfish
|
||||
```
|
||||
|
||||
## Pipeline Steps
|
||||
|
||||
### Quick Run
|
||||
|
||||
Run the entire pipeline:
|
||||
|
||||
```bash
|
||||
chmod +x run_pipeline.sh
|
||||
./run_pipeline.sh
|
||||
```
|
||||
|
||||
This automatically runs all 4 steps in sequence and confirms each succeeds before continuing.
|
||||
|
||||
### Individual Steps
|
||||
|
||||
#### Step 1: Generate Positions
|
||||
|
||||
Generate 500,000 random chess positions:
|
||||
|
||||
```bash
|
||||
python3 generate_positions.py positions.txt
|
||||
```
|
||||
|
||||
Output: `positions.txt` (one FEN per line)
|
||||
- Plays 8-20 random opening moves
|
||||
- Filters out checks, captures available, and game-over positions
|
||||
- Shows progress bar with tqdm
|
||||
|
||||
#### Step 2: Label with Stockfish
|
||||
|
||||
Evaluate each position with Stockfish at depth 12:
|
||||
|
||||
```bash
|
||||
export STOCKFISH_PATH=/path/to/stockfish
|
||||
python3 label_positions.py positions.txt training_data.jsonl $STOCKFISH_PATH
|
||||
```
|
||||
|
||||
Output: `training_data.jsonl` (one JSON per line)
|
||||
- Format: `{"fen": "...", "eval": 123}` (centipawns)
|
||||
- Evals clamped to [-2000, 2000] to avoid mate score outliers
|
||||
- Supports resuming if interrupted (checks for existing entries)
|
||||
- Shows progress bar with tqdm
|
||||
|
||||
**Note:** This step is slow (~24-36 hours for 500K positions at depth 12). You can reduce games or use lower depth for testing.
|
||||
|
||||
#### Step 3: Train NNUE Model
|
||||
|
||||
Train the neural network:
|
||||
|
||||
```bash
|
||||
python3 train_nnue.py training_data.jsonl nnue_weights.pt
|
||||
```
|
||||
|
||||
Output: `nnue_weights.pt` (PyTorch model weights)
|
||||
|
||||
Architecture:
|
||||
- Input: 768 binary features (12 piece types × 64 squares)
|
||||
- Hidden 1: 256 neurons + ReLU
|
||||
- Hidden 2: 32 neurons + ReLU
|
||||
- Output: 1 neuron (sigmoid applied to eval/400)
|
||||
|
||||
Training:
|
||||
- 20 epochs, batch size 4096, Adam optimizer (lr=1e-3)
|
||||
- 90% train / 10% validation split
|
||||
- Saves best weights by validation loss
|
||||
- Shows train/val loss per epoch
|
||||
|
||||
**Note:** Requires GPU for reasonable speed (~2-4 hours). CPU falls back to ~8-16 hours.
|
||||
|
||||
#### Step 4: Export to Scala
|
||||
|
||||
Export weights as Scala code:
|
||||
|
||||
```bash
|
||||
python3 export_weights.py nnue_weights.pt ../src/main/scala/de/nowchess/bot/bots/nnue/NNUEWeights.scala
|
||||
```
|
||||
|
||||
Output: `NNUEWeights.scala`
|
||||
- Object with `val` arrays for each layer's weights and biases
|
||||
- Format: `Array[Float]` with precision sufficient for inference
|
||||
- Includes shape comments for reference
|
||||
|
||||
## Scala Integration
|
||||
|
||||
### Step 5: NNUE Evaluator
|
||||
|
||||
Create `NNUE.scala` in `src/main/scala/de/nowchess/bot/bots/nnue/`:
|
||||
|
||||
```scala
|
||||
package de.nowchess.bot.bots.nnue
|
||||
|
||||
class NNUE:
|
||||
// Load weights from NNUEWeights.scala
|
||||
// Convert Position to 768-feature vector
|
||||
// Run inference: l1→ReLU→l2→ReLU→l3
|
||||
// Return centipawn score
|
||||
```
|
||||
|
||||
### Step 6: Integration
|
||||
|
||||
Implement `NNUEBot` that uses the NNUE evaluator for move selection.
|
||||
|
||||
## File Reference
|
||||
|
||||
| File | Purpose |
|
||||
|------|---------|
|
||||
| `requirements.txt` | Python dependencies |
|
||||
| `generate_positions.py` | Step 1: Position generator |
|
||||
| `label_positions.py` | Step 2: Stockfish labeler |
|
||||
| `train_nnue.py` | Step 3: NNUE trainer |
|
||||
| `export_weights.py` | Step 4: Weight exporter |
|
||||
| `run_pipeline.sh` | Master script (runs steps 1-4) |
|
||||
| `positions.txt` | Output: Raw FENs (500K) |
|
||||
| `training_data.jsonl` | Output: FEN+eval pairs |
|
||||
| `nnue_weights.pt` | Output: Trained weights |
|
||||
| `../src/main/scala/.../NNUEWeights.scala` | Output: Scala weights |
|
||||
|
||||
## Tips
|
||||
|
||||
- **For testing:** Reduce `generate_positions.py` to 10,000 games for quick iteration
|
||||
- **Resume labeling:** Run step 2 again; it skips already-evaluated positions
|
||||
- **GPU acceleration:** Install CUDA for PyTorch to speed up training
|
||||
- **Stockfish tuning:** Lower depth (e.g., 8 instead of 12) for faster labeling
|
||||
- **Batch size:** Increase to 8192 if OOM; decrease if out of memory
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
**ImportError: No module named 'chess'**
|
||||
- Run: `pip install -r requirements.txt`
|
||||
|
||||
**Stockfish not found**
|
||||
- Check: `which stockfish` or set `export STOCKFISH_PATH=/full/path/to/stockfish`
|
||||
|
||||
**CUDA out of memory**
|
||||
- Reduce batch size in `train_nnue.py` (e.g., 2048)
|
||||
- Or use CPU: Remove CUDA check and device setup
|
||||
|
||||
**Training loss not decreasing**
|
||||
- Check data quality: Sample some entries from `training_data.jsonl`
|
||||
- Increase learning rate to 1e-2 or 5e-4 for experimentation
|
||||
- Verify Stockfish depth was sufficient (depth ≥ 10)
|
||||
|
||||
## References
|
||||
|
||||
- [NNUE Overview](https://www.chessprogramming.org/NNUE)
|
||||
- [python-chess](https://python-chess.readthedocs.io/)
|
||||
- [PyTorch](https://pytorch.org/)
|
||||
- [Stockfish](https://stockfishchess.org/)
|
||||
Reference in New Issue
Block a user