增加性能测试
This commit is contained in:
208
docs/performance.md
Normal file
208
docs/performance.md
Normal file
@@ -0,0 +1,208 @@
|
||||
# ECS框架性能基准
|
||||
|
||||
本文档展示了ECS框架的真实性能数据和瓶颈分析。
|
||||
|
||||
## 🚀 快速测试
|
||||
|
||||
```bash
|
||||
# 在项目根目录运行
|
||||
node benchmark.js
|
||||
```
|
||||
|
||||
## 📊 性能基准数据
|
||||
|
||||
> 测试环境: Node.js, 现代桌面CPU
|
||||
> 测试时间: 2025年
|
||||
|
||||
### 1. 实体创建性能
|
||||
|
||||
| 实体数量 | 创建时间 | 创建速度 | 每个实体耗时 |
|
||||
|---------|---------|---------|-------------|
|
||||
| 1,000 | 1.11ms | 903,751个/秒 | 0.0011ms |
|
||||
| 5,000 | 3.47ms | 1,441,462个/秒 | 0.0007ms |
|
||||
| 10,000 | 6.91ms | 1,446,341个/秒 | 0.0007ms |
|
||||
| 20,000 | 7.44ms | 2,686,764个/秒 | 0.0004ms |
|
||||
| 50,000 | 22.73ms | 2,199,659个/秒 | 0.0005ms |
|
||||
|
||||
**结论**: ✅ 实体创建性能优秀,平均每秒可创建 **220万+个实体**
|
||||
|
||||
### 2. 组件访问性能
|
||||
|
||||
| 迭代次数 | 总耗时 | 访问速度 | 每次访问耗时 |
|
||||
|---------|--------|---------|-------------|
|
||||
| 100次 | 13.27ms | 37,678,407次/秒 | 0.027μs |
|
||||
| 500次 | 34.27ms | 72,957,553次/秒 | 0.014μs |
|
||||
| 1000次 | 68.85ms | 72,624,911次/秒 | 0.014μs |
|
||||
| 2000次 | 139.67ms | 71,598,669次/秒 | 0.014μs |
|
||||
|
||||
**结论**: ✅ 组件访问性能优秀,平均每秒可访问 **7200万+次**
|
||||
|
||||
### 3. 组件操作性能
|
||||
|
||||
| 迭代次数 | 总耗时 | 操作速度 | 每次操作耗时 |
|
||||
|---------|--------|---------|-------------|
|
||||
| 100次 | 36.89ms | 27,105,193次/秒 | 0.037μs |
|
||||
| 500次 | 147.42ms | 33,915,665次/秒 | 0.029μs |
|
||||
| 1000次 | 289.66ms | 34,522,936次/秒 | 0.029μs |
|
||||
|
||||
**结论**: ✅ 组件添加/删除性能优秀,平均每秒可操作 **3450万+次**
|
||||
|
||||
### 4. 查询系统性能
|
||||
|
||||
#### 4.1 单组件查询
|
||||
| 查询次数 | 总耗时 | 查询速度 | 每次查询耗时 |
|
||||
|---------|--------|---------|-------------|
|
||||
| 100次 | 10.37ms | 9,639次/秒 | 0.104ms |
|
||||
| 500次 | 41.17ms | 12,144次/秒 | 0.082ms |
|
||||
| 1000次 | 82.11ms | 12,178次/秒 | 0.082ms |
|
||||
|
||||
#### 4.2 多组件查询
|
||||
| 查询次数 | 总耗时 | 查询速度 | 每次查询耗时 |
|
||||
|---------|--------|---------|-------------|
|
||||
| 100次 | 11.22ms | 8,914次/秒 | 0.112ms |
|
||||
| 500次 | 54.85ms | 9,116次/秒 | 0.110ms |
|
||||
| 1000次 | 105.94ms | 9,439次/秒 | 0.106ms |
|
||||
|
||||
#### 4.3 复合查询 (组件+标签)
|
||||
| 查询次数 | 总耗时 | 查询速度 | 每次查询耗时 |
|
||||
|---------|--------|---------|-------------|
|
||||
| 100次 | 15.80ms | 6,327次/秒 | 0.158ms |
|
||||
| 500次 | 65.77ms | 7,602次/秒 | 0.132ms |
|
||||
| 1000次 | 135.01ms | 7,407次/秒 | 0.135ms |
|
||||
|
||||
**结论**: ⚠️ 查询性能正常,平均每秒可查询 **12000+次**
|
||||
|
||||
### 5. 性能极限测试
|
||||
|
||||
| 实体数量 | 创建时间 | 处理时间/帧 | FPS | 状态 |
|
||||
|---------|---------|------------|-----|------|
|
||||
| 10,000 | 1.55ms | 0.137ms | 7264.0 | ✅ |
|
||||
| 25,000 | 3.91ms | 0.432ms | 2311.4 | ✅ |
|
||||
| 50,000 | 12.40ms | 1.219ms | 820.0 | ✅ |
|
||||
| 100,000 | 58.93ms | 2.976ms | 335.9 | ✅ |
|
||||
| 200,000 | 51.43ms | 6.031ms | 165.8 | ✅ |
|
||||
|
||||
**结论**: 🚀 框架极限性能优秀,可处理 **20万个实体@165.8FPS** 仍维持高性能
|
||||
|
||||
## 🎯 性能瓶颈分析
|
||||
|
||||
### 主要瓶颈
|
||||
|
||||
1. **查询系统** (相对瓶颈)
|
||||
- 单组件查询: ~12,000次/秒
|
||||
- 多组件查询: ~9,400次/秒
|
||||
- 复合查询: ~7,400次/秒
|
||||
- **原因**: 需要遍历所有实体进行过滤
|
||||
|
||||
2. **大规模实体处理** (可接受)
|
||||
- 10万个实体: 335.9 FPS
|
||||
- 20万个实体: 165.8 FPS
|
||||
- **原因**: 线性时间复杂度,符合预期
|
||||
|
||||
### 非瓶颈项
|
||||
|
||||
✅ **实体创建**: 220万+个/秒,性能优秀
|
||||
✅ **组件访问**: 7200万+次/秒,性能优秀
|
||||
✅ **组件操作**: 3450万+次/秒,性能优秀
|
||||
✅ **系统处理**: 20万个实体@165.8FPS,性能优秀
|
||||
|
||||
## 📈 时间复杂度分析
|
||||
|
||||
| 操作类型 | 时间复杂度 | 性能等级 | 说明 |
|
||||
|---------|-----------|---------|------|
|
||||
| 实体创建 | O(1) | ✅ 优秀 | 常数时间创建 |
|
||||
| 组件访问 | O(1) | ✅ 优秀 | 哈希表查找 |
|
||||
| 组件操作 | O(1) | ✅ 优秀 | 常数时间添加/删除 |
|
||||
| 单组件查询 | O(n) | ⚠️ 正常 | 线性遍历实体 |
|
||||
| 多组件查询 | O(n×m) | ⚠️ 正常 | 遍历实体×组件数 |
|
||||
| 系统处理 | O(n) | ✅ 优秀 | 线性处理实体 |
|
||||
|
||||
## 💡 性能优化建议
|
||||
|
||||
### 对于查询密集型应用
|
||||
|
||||
1. **缓存查询结果**
|
||||
```typescript
|
||||
// 缓存常用查询
|
||||
const cachedPlayers = scene.getEntitiesWithComponents([Position, Player]);
|
||||
```
|
||||
|
||||
2. **减少查询频率**
|
||||
```typescript
|
||||
// 每5帧查询一次而不是每帧
|
||||
if (frameCount % 5 === 0) {
|
||||
updateEnemyList();
|
||||
}
|
||||
```
|
||||
|
||||
3. **使用更精确的查询**
|
||||
```typescript
|
||||
// 优先使用单组件查询
|
||||
const entities = scene.getEntitiesWithComponent(Position);
|
||||
```
|
||||
|
||||
### 对于大规模实体应用
|
||||
|
||||
1. **分批处理**
|
||||
```typescript
|
||||
// 分批处理大量实体
|
||||
const batchSize = 1000;
|
||||
for (let i = 0; i < entities.length; i += batchSize) {
|
||||
processBatch(entities.slice(i, i + batchSize));
|
||||
}
|
||||
```
|
||||
|
||||
2. **LOD系统**
|
||||
```typescript
|
||||
// 根据距离调整处理频率
|
||||
if (distance > 100) {
|
||||
if (frameCount % 10 !== 0) continue; // 远距离实体降低更新频率
|
||||
}
|
||||
```
|
||||
|
||||
## 🌍 实际应用指南
|
||||
|
||||
### 不同平台的建议
|
||||
|
||||
| 平台 | 推荐实体数量 | 查询频率 | 备注 |
|
||||
|------|-------------|---------|------|
|
||||
| 桌面端 | ≤100,000 | 高频查询可接受 | 性能充足 |
|
||||
| Web端 | ≤50,000 | 中等查询频率 | 考虑浏览器限制 |
|
||||
| 移动端 | ≤20,000 | 低频查询 | 性能和电池优化 |
|
||||
|
||||
### 游戏类型建议
|
||||
|
||||
| 游戏类型 | 典型实体数 | 主要瓶颈 | 优化重点 |
|
||||
|---------|-----------|---------|---------|
|
||||
| 2D平台游戏 | 1,000-5,000 | 无明显瓶颈 | 专注游戏逻辑 |
|
||||
| 2D射击游戏 | 5,000-20,000 | 碰撞检测 | 空间分割算法 |
|
||||
| RTS游戏 | 10,000-50,000 | 查询系统 | 缓存+分批处理 |
|
||||
| MMO游戏 | 50,000+ | 网络+查询 | 分区+优化查询 |
|
||||
|
||||
## 🔬 测试方法
|
||||
|
||||
### 运行完整基准测试
|
||||
|
||||
```bash
|
||||
# 项目根目录
|
||||
node benchmark.js
|
||||
```
|
||||
|
||||
### 自定义测试
|
||||
|
||||
```typescript
|
||||
// 在source目录下
|
||||
npm run test:framework:benchmark
|
||||
```
|
||||
|
||||
## 📝 测试环境
|
||||
|
||||
- **Node.js版本**: 16+
|
||||
- **TypeScript版本**: 5.8.3
|
||||
- **测试实体数**: 5,000个 (带position、velocity组件)
|
||||
- **测试迭代**: 多次取平均值
|
||||
- **硬件**: 现代桌面CPU
|
||||
|
||||
---
|
||||
|
||||
**结论**: ECS框架本身性能优秀,能够满足大多数应用需求。性能瓶颈主要来自于**业务逻辑的算法选择**而非框架架构。
|
||||
Reference in New Issue
Block a user