题目:一个整数所包含的数字的全部组合中,找到一个大于且仅大于原数的新整数
例如:输入 12345 返回 12354
输入 12354 返回 12435
输入 12435 返回 12453
解法:
思路:
1. 为了和原数接近,尽量保持高位不变,低位在最小的范围内变换顺序
2. 变换顺序的范围大小,取决于当前整数的逆序区域
例如:12354
54 为逆序区域,即当前这两位已经是最大组合,若想比原数大,则需要从倒数第三位开始改变
3. 倒数第三位是 3,则需要从逆序区域找到最小比 3 大的数字,与 3 交换位置
12453
4. 最后把逆序区域转换为 顺序,确保后两位尽可能的小
代码实现
function findNearestNumber(num:number):number {
let numArray = [...String(num)]
// 1. 找到逆序区域边界
let i = 0;
for (let index = numArray.length; index > 0; index--) {
if(Number(numArray[index - 1]) < Number(numArray[index])) {
i = index
break
}
}
// 当前数字为最大值
if(i === 0) {
return num
}
// 2. 找到逆序区最小且比逆序区前一位大的数字 交换位置
let min = numArray[i];
let minIndex = i
for (let index = i + 1; index < numArray.length; index++) {
if(numArray[index] < min) {
minIndex = index
}
}
let temp = numArray[i-1]
numArray[i-1] = numArray[minIndex]
numArray[minIndex] = temp;
//3. 逆序区域转换为顺序区域
for (let index = i, j = numArray.length -1; index < j; index++, j--) {
let temp = numArray[j];
numArray[j] = numArray[index];
numArray[index] = temp
}
return Number(numArray.join(''))
}
摘要总结自: 漫画算法 小灰的算法之旅