# 成都麻将Ai ## 项目目录结构 #### **1. 项目根目录** - `README.md`:描述项目的目标、规则实现、训练流程和使用方法。 - `requirements.txt`:列出项目依赖的库,例如 `torch`、`gym`、`numpy` 等。 - `setup.py`:如果希望将项目打包为模块供他人使用,可以在此配置。 #### **2. 配置目录 (`configs/`)** - `training_config.yaml`:包含训练超参数,如学习率、批量大小、强化学习算法的参数。 - `game_rules.yaml`:定义麻将规则,如番种加分规则、牌的花色、缺一门规则等。 #### **3. 数据目录 (`data/`)** - `raw/`:存储原始麻将对局数据(如网络抓取或模拟对局)。 - `processed/`:存储格式化后的训练数据,例如 Numpy 数组或 Tensor 格式。 - `self_play/`:存储自我对弈产生的对局记录,用于强化学习。 #### **4. 模型目录 (`models/`)** - `checkpoints/`:保存模型的中间状态,用于断点恢复训练或版本管理。 - `trained_model.py`:最终导出的模型文件,可直接加载和部署。 #### **5. 核心代码目录 (`src/`)** ##### **游戏引擎 (`engine/`)** - `mahjong_engine.py`:实现成都麻将规则,包括摸牌、打牌、碰、杠、胡牌等逻辑。 - `game_state.py`:描述麻将局面状态的建模,包括手牌、牌河、明牌等。 - `utils.py`:通用工具函数,例如洗牌、牌序转换等。 ##### **AI 模块 (`ai/`)** - `model.py`:定义 AI 的深度学习模型(例如基于卷积或 Transformer 的网络)。 - `training.py`:训练脚本,包含监督学习或强化学习的逻辑。 - `evaluation.py`:评估模型表现的代码,支持对局胜率、番数统计等。 - `self_play.py`:实现自我对弈逻辑,用当前模型生成新训练数据。 ##### **强化学习环境 (`environment/`)** - `gym_env.py`:封装麻将引擎为 OpenAI Gym 环境,用于强化学习训练。 - `reward.py`:定义奖励函数,例如胡牌加分、放炮减分等。 ##### **数据处理 (`data_processing/`)** - `preprocess.py`:从原始数据中提取特征并转化为模型输入格式。 - `augmentation.py`:数据增强方法,例如随机调整牌序、模拟不同对局风格。 - `data_loader.py`:实现批量加载数据的逻辑。 ##### **单元测试 (`tests/`)** - 测试麻将引擎、AI 模型和强化学习环境的模块,确保代码可靠性。 #### **6. 脚本目录 (`scripts/`)** - `train.py`:启动训练流程,包括加载数据、定义模型和运行训练。 - `evaluate.py`:加载模型并运行评估对局。 - `self_play.py`:启动 AI 自我对弈,生成强化学习数据。 - `preprocess_data.py`:将原始数据预处理为训练格式。 #### **7. 日志目录 (`logs/`)** - 记录训练过程中的指标、对局日志和评估结果。 ## 成都麻将规则: - 成都麻将使用的是108张牌,包括条、筒、万三种花色,每种花色从1到9各四张,没有东南西北风牌和中发白字牌。 ### 基本规则 - **缺一门**:玩家必须选择缺少一种花色(条、筒、万中的任意一种),即只能用两种花色来胡牌。如果手中只有单一花色,则为清一色。 - **定缺**:游戏开始时,每位玩家需要扣下一张牌作为自己缺的那门,并且不能更改。如果本身就是两门牌,则可以报“天缺”而不扣牌。 - **起牌与打牌**:庄家通过掷骰子决定起牌位置,然后按顺序抓牌。庄家先出牌,之后每家依次摸牌打牌。 - **碰、杠**:允许碰牌和杠牌,但不允许吃牌。杠牌分为明杠和暗杠,明杠是其他玩家打出的牌被你碰后又摸到相同的牌;暗杠则是你自己摸到四张相同的牌。 - **胡牌**:胡牌的基本条件是拥有一个对子加上四个顺子或刻子(三个相同牌)。自摸为三家给分,点炮则由放炮者给分。n*AAA+m*ABC+DD ,mn可以等于0。 - **血战到底**:一家胡牌后,其他未胡牌的玩家继续游戏,直到只剩下最后一位玩家或者黄庄(所有牌都被摸完)为止。 ### 特殊规则 - **下雨**:指杠牌,分为明杠和暗杠,明杠只收一家的钱,而暗杠可以收三家的钱。 - **查叫**:当出现黄庄时,需要检查每个玩家是否已经听牌(即差一张牌就能胡牌的状态),如果没有听牌,则可能需要赔偿其他玩家。 ### 胡牌番数 - 根据不同的胡牌方式,有不同的计分方法。例如,清一色、带根(有额外的杠)、对子胡等都有相应的加分规则。 #### 详细番数计算 1. **平胡(基本胡)**:四坎牌加一对将,四坎牌可以是刻子或顺子,计为1番。 2. **清一色**: - 不带杠的清一色称为“素清”,计为2番。 - 带杠的清一色或清一色对子胡(简称“清对”)计为3番,称为“极品”。 - 带两杠的清一色或清一色对子胡带杠计为4番,称为“极中极”或“精品”。 3. **带幺九**: - **带幺九**:指玩家手上的牌全部是由1和9组成的顺子、刻子或对子。例如,123, 789, 111, 999, 11等。计为3番。 - **清带幺九**:指玩家手上的牌不仅全部由1和9组成,而且是同一花色(条、筒、万),即清一色的带幺九。计为1番。 4. **七对**:手牌由7个对子组成,计为2番。 5. **全求人**:所有牌都是通过碰、杠、吃别人打出的牌来完成的,计为6番。 6. **龙七对**:七对中有一对是三张相同的牌,计为12番。 7. **清七对**:全部由一种花色组成的七对,计为12番。 8. **杠上开花**:在杠牌之后立即自摸胡牌,计为1番。 9. **抢杠胡**:当其他玩家明杠时,你正好可以胡那张牌,计为1番。 10. **天胡**:庄家起牌后直接胡牌,计为12番。 11. **地胡**:闲家在第一轮打牌时就胡牌,计为12番。 12. **大对子**:手牌由四个对子加一个刻子组成,计为2番。 13. **小七对**:有六对加上一个对子,计为2番。 14. **金钩吊**:手上只剩下一张牌等别人打出,然后胡牌,计为1番。 15. **海底捞月**:最后一张牌被玩家摸到并胡牌,计为1番。 16. **海底炮**:最后一张牌被打出,导致玩家胡牌,计为1番。 这些番数可以叠加,例如,如果一个玩家同时满足了清一色和七对,那么他的总番数就是2番(清一色)+ 2番(七对)= 4番。 ### 计分规则 - **基本分值**:每番的具体分值可以根据不同的玩法和地区有所不同,但一般情况下,每番的分值可以设定为一个固定的数值,比如5分、10分等。 - **翻倍规则**:某些地方可能会有额外的翻倍规则,例如,如果胡牌者是在“海底捞月”或“杠上开花”等特殊情况下胡牌,可能会有额外的加分。 **自摸 **:是指玩家通过自己摸牌完成胡牌。自摸时,其他玩家都需要给赢家支付相应的分数。 ## 成都麻将规则建模 麻将游戏引擎建模代码于项目根src/engine/目录下。 ## PPO(Proximal Policy Optimization)算法 TensorBoard 通常会记录和可视化多种训练指标。你提到的这些图表代表了 PPO 训练过程中的不同方面。下面是对每个图表的解释: ### 1. `train/loss` - **含义**:总损失函数值。 - **用途**:这是所有损失项的综合,包括策略梯度损失、价值函数损失等。通过观察这个指标,可以了解整个训练过程中的总体损失趋势。 ### 2. `train/policy_gradient_loss` - **含义**:策略梯度损失。 - **用途**:这表示策略网络更新时的损失。PPO 通过剪裁来限制策略更新的幅度,以确保稳定的学习过程。观察这个指标可以帮助你了解策略更新的情况。 ### 3. `train/value_loss` - **含义**:价值函数损失。 - **用途**:这表示价值网络(用于估计状态值或状态-动作对的价值)的损失。价值函数的准确性对于评估策略的好坏非常重要。通过观察这个指标,可以了解价值网络的学习情况。 ### 4. `train/learning_rate` - **含义**:当前的学习率。 - **用途**:学习率是优化器的一个重要超参数,控制着每次更新时权重调整的幅度。观察学习率的变化可以帮助你了解学习率调度策略的效果。 ### 5. `train/explained_variance` - **含义**:解释方差。 - **用途**:这是一个衡量价值函数预测与实际回报之间差异的指标。解释方差越接近 1,说明价值函数的预测越准确。通过观察这个指标,可以评估价值函数的性能。 ### 6. `train/entropy_loss` - **含义**:熵损失。 - **用途**:熵损失鼓励策略具有一定的随机性,以防止过早收敛到局部最优解。通过观察这个指标,可以了解策略的探索程度。 ### 7. `train/clip_range` - **含义**:剪裁范围。 - **用途**:PPO 使用剪裁来限制策略更新的幅度,以确保稳定性。剪裁范围是一个重要的超参数,决定了剪裁的严格程度。观察这个指标可以帮助你了解剪裁策略的效果。 ### 8. `train/clip_fraction` - **含义**:被剪裁的比例。 - **用途**:这个指标表示有多少比例的更新被剪裁。如果剪裁比例很高,可能意味着你的策略更新过于激进,需要调整剪裁范围或其他超参数。 ### 9. `train/approx_kl` - **含义**:近似 KL 散度。 - **用途**:KL 散度衡量新旧策略之间的差异。PPO 通过控制 KL 散度来确保策略更新的稳定性。通过观察这个指标,可以了解策略更新的幅度和稳定性。 ### 总结 这些图表提供了关于 PPO 训练过程的全面视图,帮助你监控和调试模型。以下是每个图表的主要用途: - **`train/loss`**:总体损失,反映训练的整体进展。 - **`train/policy_gradient_loss`**:策略梯度损失,反映策略网络的更新情况。 - **`train/value_loss`**:价值函数损失,反映价值网络的学习情况。 - **`train/learning_rate`**:学习率,反映优化器的设置。 - **`train/explained_variance`**:解释方差,反映价值函数的准确性。 - **`train/entropy_loss`**:熵损失,反映策略的探索程度。 - **`train/clip_range`**:剪裁范围,反映策略更新的限制。 - **`train/clip_fraction`**:被剪裁的比例,反映策略更新的稳定性。 - **`train/approx_kl`**:近似 KL 散度,反映策略更新的幅度和稳定性。