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

Advent of Code 2020第1天:为何O(n²)实现比O(n)方案运行更快?

算法时间复杂度与实测性能不符问题说明

现象

针对Advent of Code 2020第1天的题目实现了两种解法:

  • p1解法理论时间复杂度为O(n)
  • p2解法理论时间复杂度为O(n²)
    实测基准测试结果显示,复杂度更高的p2运行速度反而更快,基准测试数据如下:
BenchmarkP1   ​    12684         92239 ns/op
BenchmarkP2         3161         90705 ns/op

原因分析

这个结果和理论复杂度的差异是常数开销导致的,具体原因如下:

  • p1使用了哈希表(map)存储数据,哈希计算、碰撞处理、动态扩容都有额外的高常数开销
  • p2使用切片存储数据,遍历切片时数据存储在连续内存空间,CPU缓存命中率极高,遍历操作的常数开销极低
  • 该题的输入规模仅为200个左右的数字,n²的总运算量只有4万次左右,这个量级的运算对现代CPU来说可以在极短时间内完成,远低于哈希表操作的总开销
  • 两个解法都包含文件读取、字符串转整数的公共逻辑,这部分开销占总耗时的比例较高,进一步抹平了算法逻辑部分的理论复杂度差异

实现代码

O(n)解法p1

// O(n) 解法
func p1(value int) (int, int){
    m := make(map[int]int)

    f, err := os.Open("nums.txt")
    printError(err)
    defer f.Close()
    scanner := bufio.NewScanner(f)

    for scanner.Scan() {
        intVar, err := strconv.Atoi(scanner.Text())
        printError(err)
        m[intVar]=intVar
    }

    for _, key := range m {
        l, ok := m[value-key]
        if ok {
            return l, key
        }
    }
    return 0, 0
}

O(n²)解法p2

// O(n²) 解法
func p2(value int) (int, int){
    var data []int

    f, err := os.Open("nums.txt")
    printError(err)
    defer f.Close()
    scanner := bufio.NewScanner(f)

    for scanner.Scan() {
        intVar, err := strconv.Atoi(scanner.Text())
        printError(err)
        data= append(data, intVar)
    }

    for ki, i := range data {
        for kj, j := range data {
            if ki != kj && i+j == value {
                return i , j
            }
        }
    }
    return 0, 0
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.07 03:48:03