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

求更优/精简的同数位紧邻后继数算法(不使用itertools)

优化后的同数位紧邻后继数实现

你的原代码思路完全正确,已经抓住了找下一个排列的核心逻辑!不过我们可以从效率提升和代码精简两个方向做优化,同时让代码可读性更强:

优化点说明

  1. 利用降序特性替代排序:原代码中交换后对右边部分用sorted()排序,但实际上,我们找到的右边部分原本是严格降序的(因为我们是从右往左找到第一个“左小右大”的位置),所以交换后只需要反转右边部分就能得到升序,时间复杂度从O(k log k)降到O(k)(k为右边部分长度),效率更高。
  2. 用next()简化循环:把找基准点和交换点的循环换成next()生成器表达式,让代码更紧凑,同时逻辑更清晰。
  3. 变量名更语义化:比如用digits代替ns,pivot代替i,让代码一眼就能看懂每个变量的作用。

优化后的代码

def find_next(n):
    digits = list(map(int, str(n)))
    length = len(digits)
    
    # 从右往左找第一个左边数字小于右边数字的位置(pivot是右边部分的起始索引)
    pivot = next((i for i in reversed(range(1, length)) if digits[i] > digits[i-1]), -1)
    if pivot == -1:
        return n  # 没有更大的排列,返回原数
    
    # 在右边降序序列中,找第一个比基准数字大的元素(就是最小的那个更大元素)
    swap_idx = next((j for j in reversed(range(pivot, length)) if digits[j] > digits[pivot-1]), pivot)
    
    # 交换基准数字和找到的元素
    digits[pivot-1], digits[swap_idx] = digits[swap_idx], digits[pivot-1]
    
    # 反转右边部分(降序变升序,比排序高效)
    digits[pivot:] = digits[pivot:][::-1]
    
    return int(''.join(map(str, digits)))

n = int(input())
print(find_next(n))

测试验证

  • 输入123 → 输出132,符合预期
  • 输入1238 → 输出1283,符合预期
  • 输入4321 → 输出4321(没有更大的排列)
  • 输入132 → 输出213(正确的下一个排列)

这个版本既保留了原代码的正确性,又在效率和可读性上做了提升,而且完全不需要用到itertools库~

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.11 07:40:49