You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Java Processing无类实现记忆卡牌游戏:洗牌功能异常求助

记忆卡牌游戏全局洗牌(含死亡卡牌)解决方案

问题说明

作业要求使用Java Processing制作记忆卡牌游戏,禁止使用类。已完成游戏主体功能,现在需要添加死亡卡牌:

  • 采用二维数组存储卡牌,死亡卡牌存入第三行(索引2)
  • 当前shuffle()函数仅在各行内部洗牌,导致死亡卡牌始终处于末尾,无法与其他卡牌混合打乱

原代码问题分析

原shuffle()函数对每一行单独执行洗牌逻辑,行与行之间没有任何元素交换,因此死亡卡牌所在的第三行永远和前两行的普通卡牌分离,无法实现全局混合。

解决方案

使用Fisher-Yates洗牌算法(公平高效的标准洗牌算法),将所有卡牌(包括前两行的普通卡牌和第三行的死亡卡牌)视为一个整体进行随机交换。核心思路是把二维数组的元素映射为一维索引,遍历每个位置并与随机位置交换所有卡牌数据(包括卡牌标识、坐标)。

步骤1:修正初始化代码

原初始化中死亡卡牌的坐标存储在第二行,容易导致数组越界,需改为存入第三行,与gekozenKaart数组保持一致:

for (int i=0; i<3; i++) {
    if (i == 0 || i == 1) {
      for (int j=0; j<aantalSetjes; j++) {
        y[i][j] = yKaart;
        x[i][j] = xKaart;
        gekozenKaart[i][j] = teller;
        teller +=1;
        if (teller > aantalSetjes) {
          teller = 1;
        }
        if (xKaart<=(kaartBreedte * getSpeelveldBreedteKeer())-kaartBreedte) {
          xKaart += kaartBreedte;
        } else if (xKaart>=(kaartBreedte * getSpeelveldBreedteKeer())-kaartBreedte) {
          xKaart=15;
          yKaart += kaartLengte;
        }
      }
    } else if (i == 2) {
      for (int j=0; j<getAantalDoodsKaarten(); j++) {
        // 修正:将死亡卡牌的坐标存入第三行,与gekozenKaart对应
        y[i][j] = yKaart;
        x[i][j] = xKaart;
        gekozenKaart[i][j] = teller;
        teller +=1;
        if (teller > getAantalDoodsKaarten()) {
          teller = 1;
        }
        if (xKaart<=(kaartBreedte * getSpeelveldBreedteKeer())-kaartBreedte) {
          xKaart += kaartBreedte;
        } else if (xKaart>=(kaartBreedte * getSpeelveldBreedteKeer())-kaartBreedte) {
          xKaart=15;
          yKaart += kaartLengte;
        }
      }
    }
}
shuffle();

步骤2:替换全局洗牌函数

重写shuffle()函数,实现跨行列的全局洗牌:

void shuffle() {
  // 计算所有卡牌的总数:2组普通卡牌 + 死亡卡牌数量
  int totalCards = 2 * aantalSetjes + getAantalDoodsKaarten();
  
  // Fisher-Yates洗牌:从最后一张牌向前遍历
  for (int k = totalCards - 1; k > 0; k--) {
    // 生成0到当前索引k之间的随机位置
    int randomIndex = int(random(0, k + 1));
    
    // 将一维索引转换为二维数组的(i,j)坐标
    int i1, j1, i2, j2;
    
    // 处理随机索引对应的二维位置
    if (randomIndex < aantalSetjes) {
      i1 = 0;
      j1 = randomIndex;
    } else if (randomIndex < 2 * aantalSetjes) {
      i1 = 1;
      j1 = randomIndex - aantalSetjes;
    } else {
      i1 = 2;
      j1 = randomIndex - 2 * aantalSetjes;
    }
    
    // 处理当前索引k对应的二维位置
    if (k < aantalSetjes) {
      i2 = 0;
      j2 = k;
    } else if (k < 2 * aantalSetjes) {
      i2 = 1;
      j2 = k - aantalSetjes;
    } else {
      i2 = 2;
      j2 = k - 2 * aantalSetjes;
    }
    
    // 交换卡牌标识(gekozenKaart)
    int tempGekozen = gekozenKaart[i1][j1];
    gekozenKaart[i1][j1] = gekozenKaart[i2][j2];
    gekozenKaart[i2][j2] = tempGekozen;
    
    // 交换x坐标
    float tempX = x[i1][j1];
    x[i1][j1] = x[i2][j2];
    x[i2][j2] = tempX;
    
    // 交换y坐标
    float tempY = y[i1][j1];
    y[i1][j1] = y[i2][j2];
    y[i2][j2] = tempY;
  }
}

效果说明

修改后,所有卡牌(普通卡牌和死亡卡牌)会被完全随机打乱,死亡卡牌不再固定在末尾位置,符合全局洗牌的需求。

内容的提问来源于stack exchange,提问作者bossman

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.10 09:46:03