Proximal Policy Optimization Algorithms
Paper β’ 1707.06347 β’ Published β’ 12
YAML Metadata Warning:empty or missing yaml metadata in repo card
Check out the documentation for more information.
Reinforcement Learning agent that masters fighting game strategies using PPO
Trained a deep RL agent to defeat M. Bison in Street Fighter 2 with 100% win rate (5/5 matches) using Proximal Policy Optimization and parallel environment training.
Win Rate: 100% (5/5 matches)
ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β STREET FIGHTER 2 ROM β
β (Genesis Emulator via Retro) β
ββββββββββββββββββββββββββββββ¬ββββββββββββββββββββββββββββββββββββ
β
βΌ
βββββββββββββββββββββββββββββββββββββββββ
β Environment Wrapper (Gymnasium) β
β ββββββββββββββββββββββββββββββββ β
β β’ Observation: 84x84 grayscale β
β β’ Action space: 12 discrete actions β
β β’ Reward: Health difference + bonus β
β β’ Frame stacking: 4 frames β
ββββββββββββββ¬βββββββββββββββββββββββββββ
β
βΌ
βββββββββββββββββββββββββββββββββββββββββββββββ
β Parallel Training (SubprocVecEnv) β
β ββββββββββββββββββββββββββββββββββ β
β 64 parallel environments running β
β simultaneously in separate processes β
ββββββββββββββ¬βββββββββββββββββββββββββββββββββ
β
βΌ
ββββββββββββββββββββββββββββββββββββββββββββββββ
β PPO Agent (Stable Baselines3) β
β βββββββββββββββββββββββββββββββ β
β β’ Policy: CNN (3 layers) β
β β’ Learning rate: 3e-4 β
β β’ Clip range: 0.2 β
β β’ GAE lambda: 0.95 β
β β’ Device: CUDA (GPU) β
β β’ Optimizer: Adam β
ββββββββββββββ¬ββββββββββββββββββββββββββββββββββ
β
βΌ
ββββββββββββββββββββββββββββββββββββββββββββββββ
β Reward Function β
β βββββββββββββββββββ β
β β
β reward = (Ξagent_hp - Ξenemy_hp) / 176 β
β - 0.0001 (time penalty) β
β + 1.0 (if win) β
β - 1.0 (if loss) β
β β
ββββββββββββββββββββββββββββββββββββββββββββββββ
# Health advantage reward (normalized)
delta_hp_diff = (current_agent_hp - self.agent_hp) -
(current_enemy_hp - self.enemy_hp)
reward = delta_hp_diff / 176.0 - 0.0001 # Small time penalty
# Terminal rewards
if win:
reward += 1.0 # Large win bonus
else:
reward -= 1.0 # Large loss penalty
Why this works:
# 64 parallel environments for sample efficiency
env = SubprocVecEnv([make_env(i) for i in range(64)],
start_method="fork")
# Frame stacking for temporal information
env = VecFrameStack(env, n_stack=4, channels_order="last")
Impact:
# Preprocess: 224x320 RGB β 84x84 grayscale
gray = cv2.cvtColor(observation, cv2.COLOR_BGR2GRAY)
resize = cv2.resize(gray, (84, 84), interpolation=cv2.INTER_CUBIC)
state = np.reshape(resize, (84, 84, 1))
Why 84x84:
# Custom discretizer for Street Fighter special moves
discretizer = StreetFighter2Discretizer(game)
# Enables complex combos:
# - Hadouken (fireball)
# - Shoryuken (uppercut)
# - Tatsumaki (hurricane kick)
Technical challenge: Converted continuous joystick inputs to discrete actions while preserving special move execution (requires frame-perfect timing).
# Training hyperparameters
Episodes per environment: 1,000
Parallel environments: 64 (SubprocVecEnv)
Total episodes: 64,000
Average episode length: 500 steps
Total timesteps: 32,000,000
# PPO parameters
Learning rate: 3e-4
Clip range: 0.2
GAE lambda: 0.95
Gamma (discount): 0.99
N-steps: 2048
Frame stack: 4
# Hardware
Device: CUDA (GPU)
Training time: ~12 hours on NVIDIA GPU
| Metric | Value |
|---|---|
| Win Rate | 100% (5/5) |
| Average Episode Length | 500 steps |
| Observation Dimensions | 84x84x4 (grayscale, stacked) |
| Action Space | 12 discrete actions |
| Training Timesteps | 32M |
| GPU Utilization | 95%+ (CUDA) |
| Parallel Environments | 64 (SubprocVecEnv) |
| Convergence Time | ~12 hours |
# Install dependencies
pip install -r requirements.txt
# Import Street Fighter ROM (required)
python -m retro.import /path/to/StreetFighterII.md
# Train from scratch (64 parallel environments)
python train.py --n_envs 64 --episodes_per_env 1000
# Resume from checkpoint
python train.py --resume train/checkpoint.zip
# Watch trained agent play
python replay.py --model train/checkpoint.zip --episodes 5
sf2-simple/
βββ train.py # PPO training script (main)
βββ wrapper.py # Custom Gymnasium environment
βββ discretizer.py # Action space discretizer (special moves)
βββ replay.py # Visualize trained agent gameplay
βββ requirements.txt # Python dependencies
βββ ken_bison_12.state # Game state (Ken vs Bison, round 1)
βββ train/
βββ checkpoint.zip # Trained model weights
What the agent learned:
Training insights:
MIT License