综合java案例,阵型克制关系有规律吗?

wen java案例 5

本文目录导读:

综合java案例,阵型克制关系有规律吗?

  1. 核心规律总结(先看结论)
  2. 综合案例代码(包含枚举 + 工厂模式)
  3. 代码运行结果分析
  4. 更复杂的规律:如何扩展到“双属性”或“五行”

这是一个非常经典的面向对象设计问题,也是很多游戏(如《火焰之纹章》《皇室战争》)的核心逻辑。

针对你问的“阵型克制关系有规律吗?”——有规律,但规律通常不是数学公式,而是“索引映射”或“循环链表”逻辑。

下面我提供一个综合 Java 案例,包含完整代码和三种常见的建模方式,并解释其规律。


核心规律总结(先看结论)

阵型克制的“规律”通常分三种:

  1. 三角循环(石头剪刀布):A克B,B克C,C克A。
    • 规律:使用 (攻方.ordinal() + 1) % 3 == 守方.ordinal()
  2. 线性链(火影查克拉属性):火 → 风 → 雷 → 土 → 水 → 火。
    • 规律:使用 Map 存储直接后继关系,查表即可。
  3. 属性双克(宝可梦):数值加减,存在免疫和抵抗。
    • 规律:使用二维数组矩阵 int[attacker][defender],值代表倍率(0.5,1,2,0)。

综合案例代码(包含枚举 + 工厂模式)

我们设计一个“光明与黑暗”主题的阵型系统。

阵型枚举PHALANX(枪阵),CAVALRY(骑兵),ARCHER(弓兵)。

克制规律:骑兵克弓兵,弓兵克枪兵,枪兵克骑兵(三角循环)。

完整可运行代码

import java.util.HashMap;
import java.util.Map;
/**
 * 综合案例:阵型克制系统
 * 展示了三种建模方式(Map、二维数组、循环取模),并集成策略模式。
 */
public class FormationSystem {
    // ---------- 1. 枚举定义(附带克制逻辑) ----------
    enum Formation {
        PHALANX("枪阵"), CAVALRY("骑兵"), ARCHER("弓兵");
        private final String displayName;
        Formation(String displayName) {
            this.displayName = displayName;
        }
        // 方式一:循环取模规律 (防御方是否被当前攻击方克制)
        public boolean counters(Formation defender) {
            // 规律:攻方ordinal值 + 1 取模3 == 守方ordinal值
            return (this.ordinal() + 1) % 3 == defender.ordinal();
        }
        public String getDisplayName() {
            return displayName;
        }
    }
    // ---------- 2. 核心业务类:BattleEngine ----------
    static class BattleEngine {
        private static final Map<String, Boolean> cache = new HashMap<>();
        // 方式二:使用 Map 存储克制关系(显式,也最灵活)
        private static final Map<Formation, Formation> counterMap = new HashMap<>();
        static {
            counterMap.put(Formation.PHALANX, Formation.CAVALRY); // 枪克骑
            counterMap.put(Formation.CAVALRY, Formation.ARCHER);  // 骑克弓
            counterMap.put(Formation.ARCHER, Formation.PHALANX);  // 弓克枪
        }
        // 方式三:经典二维数组矩阵 (倍率)
        private static final double[][] MATRIX = {
                // 攻击方 \ 防御方  PHALANX, CAVALRY, ARCHER
                /* PHALANX */ {1.0, 1.5, 0.5},
                /* CAVALRY */ {0.5, 1.0, 1.5},
                /* ARCHER */  {1.5, 0.5, 1.0}
        };
        /**
         * 使用Map判断是否克制(最直观,适合业务扩展)
         */
        public static boolean isCounterByMap(Formation attacker, Formation defender) {
            return counterMap.get(attacker) == defender;
        }
        /**
         * 使用取模公式判断(最简洁,符合数学规律)
         */
        public static boolean isCounterByMath(Formation attacker, Formation defender) {
            return (attacker.ordinal() + 1) % 3 == defender.ordinal();
        }
        /**
         * 使用矩阵计算伤害倍率(最强大,可以拓展至RPG)
         */
        public static double getDamageMultiplier(Formation attacker, Formation defender) {
            return MATRIX[attacker.ordinal()][defender.ordinal()];
        }
    }
    // ---------- 3. 策略模式(让阵型自己决定战斗方式) ----------
    interface BattleStrategy {
        double execute(Formation attacker, Formation defender);
    }
    static class SimpleStrategy implements BattleStrategy {
        @Override
        public double execute(Formation attacker, Formation defender) {
            if (attacker.counters(defender)) return 1.5; // 克制
            if (defender.counters(attacker)) return 0.5; // 被克制
            return 1.0;
        }
    }
    static class AdvancedStrategy implements BattleStrategy {
        @Override
        public double execute(Formation attacker, Formation defender) {
            return BattleEngine.getDamageMultiplier(attacker, defender);
        }
    }
    // ---------- 4. 测试运行 ----------
    public static void main(String[] args) {
        System.out.println("=== 验证三角循环规律: 骑(1)克弓(2) 且 弓(2)克枪(0) 且 枪(0)克骑(1) ===");
        BattleStrategy simple = new SimpleStrategy();
        BattleStrategy advanced = new AdvancedStrategy();
        // 测试全部组合
        for (Formation attacker : Formation.values()) {
            for (Formation defender : Formation.values()) {
                double ratio = simple.execute(attacker, defender);
                double matrixRatio = advanced.execute(attacker, defender);
                // 打印战斗格
                String effect = ratio > 1 ? "【克制】" : (ratio < 1 ? "【被克】" : "【均势】");
                System.out.printf("%-8s vs %-8s -> 策略伤害: %.1f | 矩阵伤害: %.1f %s%n",
                        attacker.getDisplayName(), defender.getDisplayName(),
                        ratio, matrixRatio, effect);
            }
        }
        // 验证数学规律与Map的结果一致性
        System.out.println("\n=== 一致性校验(Math vs Map) ===");
        boolean allMatch = true;
        for (Formation a : Formation.values()) {
            for (Formation d : Formation.values()) {
                if (BattleEngine.isCounterByMap(a, d) != BattleEngine.isCounterByMath(a, d)) {
                    allMatch = false;
                    System.out.println("不一致: " + a + " vs " + d);
                }
            }
        }
        System.out.println("所有计算方式完全一致: " + allMatch);
    }
}

代码运行结果分析

当你运行上述代码,控制台输出效果如下(节选):

=== 验证三角循环规律: 骑(1)克弓(2) 且 弓(2)克枪(0) 且 枪(0)克骑(1) ===
枪阵     vs 枪阵     -> 策略伤害: 1.0 | 矩阵伤害: 1.0 【均势】
枪阵     vs 骑兵     -> 策略伤害: 1.5 | 矩阵伤害: 1.5 【克制】
枪阵     vs 弓兵     -> 策略伤害: 0.5 | 矩阵伤害: 0.5 【被克】
骑兵     vs 枪阵     -> 策略伤害: 0.5 | 矩阵伤害: 0.5 【被克】
骑兵     vs 骑兵     -> 策略伤害: 1.0 | 矩阵伤害: 1.0 【均势】
骑兵     vs 弓兵     -> 策略伤害: 1.5 | 矩阵伤害: 1.5 【克制】
弓兵     vs 枪阵     -> 策略伤害: 1.5 | 矩阵伤害: 1.5 【克制】
弓兵     vs 骑兵     -> 策略伤害: 0.5 | 矩阵伤害: 0.5 【被克】
弓兵     vs 弓兵     -> 策略伤害: 1.0 | 矩阵伤害: 1.0 【均势】

更复杂的规律:如何扩展到“双属性”或“五行”

如果你觉得三角循环太简单,可以借鉴 《阴阳师》/《宝可梦》 的规律,假设你有5种阵型(风、林、火、山、雷),克制关系是一个五边形循环

规律仍然是:

(attacker.ordinal() + 1) % 5 == defender.ordinal()

如果你需要双向克制(例如火克风,但风也克火),规律会变成:

// 双向互克(胜负由数值决定)
int diff = Math.abs(attacker.ordinal() - defender.ordinal());
if (diff == 1 || diff == 4) { /* 互相克制 */ }

“阵型克制有规律吗?”

有,且主要规律是:

  1. 数学公式(attackIndex + shift) % totalTypes == defendIndex,适合循环克制。
  2. 表驱动(Map/Matrix):
    • 查表法(HashMap<Attack, Defense>)适合“唯一克星”;
    • 二维矩阵(double[][])适合“数值倍率”和“免疫”;
  3. 面向对象:把对抗逻辑封装在枚举的 counter() 方法里,职责清晰。

推荐方案:在真实项目中,优先使用二维矩阵,因为你可以额外存储“技能特效”“属性抗性”等扩展字段,后续加新阵型时0改动(只需扩展数组长度),且性能最优(数组下标访问)。

如果你需要我进一步演示“五行互生互克”的全代码(带生克关系的复杂矩阵),可以告诉我,我给你再补一版。

抱歉,评论功能暂时关闭!