含重复元素的数字数组对比函数修复(Mastermind游戏场景)
解决Mastermind游戏中重复元素的匹配计数问题
我明白你遇到的问题了——当数组里有重复数字时,原函数的匹配逻辑就乱了。咱们先拆解下问题根源,再一步步修正。
原代码的核心问题
- 忽略重复元素的次数:使用
Set会自动去重,比如arr1=['5','5','3','4']转成Set后只剩{'5','3','4'},这会让代码误以为还有多余的5可以匹配,但实际上arr2里除了精确匹配的那个5,没有其他5了。 - 未排除精确匹配的元素:原逻辑在判断非精确匹配时,没有排除已经被统计为
exactMatches的元素,导致重复计数。
修正后的实现方案
我们需要分两步处理:先统计精确匹配,再在剩余元素中按实际出现次数统计数字匹配(不考虑位置)的数量。
function compareGuessVsRandom(arr1, arr2) { let exactMatches = 0; // 创建副本存储未精确匹配的元素,避免修改原数组 const remainingArr1 = []; const remainingArr2 = []; // 第一步:统计精确匹配,同时分离剩余元素 for (let i = 0; i < arr1.length; i++) { if (arr1[i] === arr2[i]) { exactMatches++; } else { remainingArr1.push(arr1[i]); remainingArr2.push(arr2[i]); } } // 统计剩余arr1中每个数字的出现次数 const numCountInArr1 = {}; for (const num of remainingArr1) { numCountInArr1[num] = (numCountInArr1[num] || 0) + 1; } let matchesByValue = 0; // 遍历剩余arr2,按可用次数统计数字匹配 for (const num of remainingArr2) { if (numCountInArr1[num] > 0) { matchesByValue++; numCountInArr1[num]--; // 匹配一次就减少计数,防止重复匹配 } } const result = { match: exactMatches === arr1.length, // 修正原逻辑:只有全部精确匹配才算完全猜对 exactMatches: exactMatches, matchesByValue: matchesByValue, }; console.log(result); return result; }
代码逻辑解释
- 精确匹配统计:遍历数组时,把位置和数字都匹配的元素计入
exactMatches,不匹配的元素分别存入两个剩余数组,这样就排除了已精确匹配的元素,避免重复计算。 - 剩余元素计数:用对象
numCountInArr1统计剩余arr1中每个数字的出现次数,确保我们知道每个数字还能匹配多少次。 - 数字匹配统计:遍历剩余arr2的每个数字,如果对应的计数还有剩余,就计入
matchesByValue,同时减少计数——这样就保证了重复元素不会被多算。
测试你的示例
对于arr1=['5','5','3','4']和arr2=['5','1','0','0']:
- 精确匹配的是第一个位置的
5,所以exactMatches=1。 - 剩余arr1为
['5','3','4'],剩余arr2为['1','0','0']。 - 遍历剩余arr2的元素时,
1、0都不在numCountInArr1中,所以matchesByValue=0,完全符合预期结果。
内容的提问来源于stack exchange,提问作者Dani
相关产品推荐
相关产品推荐

