「这是我参与11月更文挑战的第4天,活动详情查看:2021最后一次更文挑战」
题目
你在和朋友一起玩 猜数字(Bulls and Cows)游戏,该游戏规则如下:
写出一个秘密数字,并请朋友猜这个数字是多少。朋友每猜测一次,你就会给他一个包含下述信息的提示:
猜测数字中有多少位属于数字和确切位置都猜对了(称为 "Bulls", 公牛),
有多少位属于数字猜对了但是位置不对(称为 "Cows", 奶牛)。也就是说,这次猜测中有多少位非公牛数字可以通过重新排列转换成公牛数字。
给你一个秘密数字 secret 和朋友猜测的数字 guess ,请你返回对朋友这次猜测的提示。
提示的格式为 "xAyB" ,x 是公牛个数, y 是奶牛个数,A 表示公牛,B 表示奶牛。
请注意秘密数字和朋友猜测的数字都可能含有重复数字。
示例 1:
输入: secret = "1807", guess = "7810"
输出: "1A3B"
解释: 数字和位置都对(公牛)用 '|' 连接,数字猜对位置不对(奶牛)的采用斜体加粗标识。
"1807"-"7810"
示例 2:
输入: secret = "1123", guess = "0111"
输出: "1A1B"
解释: 数字和位置都对(公牛)用 '|' 连接,数字猜对位置不对(奶牛)的采用斜体加粗标识。
"1123" "1123"
| or |
"0111" "0111"
注意,两个不匹配的 1 中,只有一个会算作奶牛(数字猜对位置不对)。通过重新排列非公牛数字,其中仅有一个 1 可以成为公牛数字。
来源:力扣(LeetCode) 链接:leetcode-cn.com/problems/bu…
思路
leetcode-cn.com/problems/bu…
大佬比较牛逼的思路这里就不说了,放个链接可以看看,我的思路比较简单,暴力算法:
1.计算公牛个数
2.计算总共有多少元素是两个数组都有的
3.奶牛的数量就是共有的数量减去公牛数量
4.核心代码怎么找出两个数组共有的元素
代码
暴力算法(不推荐使用)
执行用时:164 ms, 在所有 JavaScript 提交中击败了6.72%的用户
内存消耗:39.7 MB, 在所有 JavaScript 提交中击败了68.91%的用户
思路:
传过来的参数有secret和guess,先把这两个参数转字符串方便后面进行分割,后面用split将字符串全部分割成字符数组。初始化A和B准备遍历循环,完全匹配则对A进行增加。
这里定义了filterData函数,这个函数的目的是循环判断数组a里的元素在b里面有没有,有的话就放入新建立的数组中。现在讲解一下每行代码的意思,首先先把参数中的两个数组进行拷贝,然后定义个result空数组,双重循环遍历两个数组,如果两个数组内容一样而且类型都是string就把这个添加到result,对应的arr1[i] 和 arr2[j] 都置为-1,然后返回这个result数组。
var getHint = function (secret, guess) {
let secretString = secret.toString();
let secretArr = secretString.split("");
let guessString = guess.toString();
let guessArr = guessString.split("");
let A = 0;
let B = 0;
for (let i in secretArr) {
if (secretArr[i] === guessArr[i]) {
A++;
}
}
B = filterData(secretArr, guessArr).length;
B = B - A;
let res = A + "A" + B + "B";
console.log(res);
return res;
};
function filterData(a, b) {
let arr1 = [...a];
let arr2 = [...b];
let result = [];
for (let i = 0; i < arr1.length; i++) {
for (let j = 0; j < arr2.length; j++) {
if (arr1[i] === arr2[j] && typeof (arr1[i]) === "string" && typeof (arr2[i]) === "string") {
result.push(arr1[i]);
arr1[i] = -1;
arr2[j] = -1
}
}
}
console.log(result);
return result;
}
getHint(1807, 7810);
// "1A3B"
getHint("1123", "0111");
// "1A1B"
getHint("11", "10");
// "1A0B"
getHint("1", "0");
// "0A0B"
getHint("1", "1");
// "1A0B"
求两个数组共有元素的代码
在LeetCode中有一题350题这个挺不错的,有兴趣可以看看这个题目的题解350. 两个数组的交集 II。这里我提供两个方案:
方案1:发现相同的元素,同时把两个数组对应的元素删除,依次循环得到最终答案
方案2:发现相同的元素,同时把两个数组对应的元素赋值其他类型的数据值,依次循环得到最终答案,这个方法需要判断元素类型,严格控制变量
下面对两个方案代码进行解释:
方案1:
循环判断数组a里的元素在b里面有没有,有的话就放入新建立的数组中,这是一个大的思路。首先对两个参数数组进行克隆(个人习惯,不太喜欢对原数组进行修改,这个可能会让占用内存变大),用result空数组存最后结果。然后用双重循环对两个数组进行遍历,找到一样的数就把这个一样的元素存到result数组,然后在arr1和arr2执行删除操作。最后将i置-1,重新开始循环,思路是这样的,代码执行效率会比较低。
方案2:
和方案1想法类似,但不是像方案1一样一直循环,这个只用一次双重循环,两个数组里面的元素相同就修改成别的内容,这个方案不太好的原因是要判断每个元素的类型,然后把这个内容改为别的类型的。
let arr3 = [1, 8, 0, 7];
let arr4 = [7, 8, 1, 0];
// let arr3 = [1, 1, 2, 3];
// let arr4 = [0, 1, 1, 1];
// let arr3 = [1, 1];
// let arr4 = [0, 1];
//方案1:
function differentData(a, b) {
let arr1 = [...a];
let arr2 = [...b];
let result = [];
console.log(arr1);
for (let i = 0; i <= arr1.length; ++i) {
for (let j = 0; j < arr2.length; j++) {
if(arr1[i] === arr2[j]){
result.push(arr1[i]);
console.log(result);
arr1.splice(i,1);
console.log(arr1);
arr2.splice(j,1);
console.log(arr2);
console.log("------");
i = -1;
}
}
}
console.log(result);
return result;
}
//方案2:
function differentData(a, b) { //循环判断数组a里的元素在b里面有没有,有的话就放入新建立的数组中
let arr1 = [...a];
let arr2 = [...b];
let result = [];
for (let i = 0; i < arr1.length; i++) {
for (let j = 0; j < arr2.length; j++) {
if (arr1[i] === arr2[j] && typeof (arr1[i]) === "string" && typeof (arr2[i]) === "string") {
result.push(arr1[i]);
arr1[i] = -1;
arr2[j] = -1
}
}
}
console.log(result);
return result;
}
let res = differentData(arr3, arr4);
console.log(`res是${res}`);
说明
本文是作者用于学习时,在LeetCode刷题所见所想,引用了部分力扣资源,代码是根据大佬们思路进行写的,比起大佬们的代码,我的代码肯定有很大的优化空间了,如果是学习的建议访问力扣官网进行学习,本博客仅记录我的成长过程!