@xudongh
2017-10-15T09:04:24.000000Z
字数 1904
阅读 1126
算法
1.假设有一个数,这个数的每一位数都不同,且每一位都不能为0,每一位数相加得到s。现在要求输入s,输出这个数的最大值。
即对于某个数s,s=a+b+c+d,其中a≠b≠c≠d≠0,求出abcd的最大值。
如此时程序输入s=9,则输出126。
实现思路:当位数最大时,此值最大;如果位数最大时不满足s=a+b+c+d,则位数减一,寻找满足条件的最大值。
因此,分两步进行,第一步寻找最大位数;
若第一步没有找到满足条件的值,位数减一,继续寻找。
代码实现:
function findNum(s) {if (s < 1 || s > 42) {return}var numArr = [1];var bit = 1;var numPlus = 1;while (numPlus < s) {numArr[bit] = ++bit;numPlus = bit * (1 + bit) / 2;}if (numPlus == s) {return parseInt(numArr.reverse().join(''));} else if (numPlus > s) {numArr.pop();var index = bit - 2;findNumStep2(index);return parseInt(numArr.reverse().join(''));}function findNumStep2(index) {var digit = index + 1;while (sumArr(numArr) !== s) {numArr[index] = ++digit;if (digit >= 9) {break;}}if (sumArr(numArr) !== s) {findNumStep2(--index);}return}function sumArr(arr) {var sum = 0;for (var i = 0; i < arr.length; i++) {sum += arr[i];}return sum}}// 假设s = 20findNum(20) // 95321
实现思路:一开始自己写得比较复杂,导致程序内存溢出了。后来优化下,也拆分代码,分别做回文判断和素数判断。
目前用的素数判断是比较粗暴拙劣的方法,在上网查了下关于素数判断的方法,有很多值得学习的算法(如费马小定理),有时间继续深究。
代码实现:
function isPP (min, max) {let result = []while (min < max) {if (isPalindrome(min) && isPrime(min)) {result.push(min)}min++}return result}function isPalindrome (num) {let str1 = num.toString()let str2 = str1.split('').reverse().join('')if (str1 === str2) {return true} else {return false}}function isPrime (num) {if (num < 2) return falseif (num !== 2 && num % 2 === 0) return falselet sqrtNum = Math.sqrt(num);for (let i = 3; i <= sqrtNum; i += 2) {if (num % i === 0) return false}return true}
3.对于给定字符串如'aaaabbcccd',其字符串价值为字符出现次数的平方和,即为4 * 4 + 2 * 2 + 3 * 3 + 1 * 1。输入字符串和整数k,k为可移除字符串中某一字符的次数。求出最小字符串价值。
实现思路:毫无疑问,被移除的字符一定是出现次数最大的字符。思路是构建二维数组,数组元素为字符和字符出现的次数。然后进行删除字符操作和统计字符串价值。
代码实现:
function strValue (s, k) {let result = 0let sArr = [...new Set(s)] // 去重的字符数组let count = []// 构建二维数组for (var i = 0;i < sArr.length; i++) {let n = s.match(new RegExp(sArr[i], 'g')).lengthcount[i] = [sArr[i], n];}// 二维数组的元素根据出现次数排序count.sort((a, b) => {return b[1] - a[1]})// 移除出现次数最多的字符,执行k次while (k--) count.shift()// 计算价值for (var j = 0; j < count.length; j++) {result += Math.pow(count[j][1], 2)}return result}