CANN Crypto 架构设计揭秘:分层依赖如何让密码算子高效复用
2026/9/30 0:30:47
051多路合并
多路归并(K-way Merge)将 k 个已排好序的序列合并为一个有序序列。
核心数据结构是最小堆(Min-Heap):
(当前值, 来自第几路, 该路下一个索引)这与 Knuth TAOCP 5.4 节描述的"胜者树(Winner Tree)"在功能上等价,最小堆实现更为简洁直观。
taocp_volume3/multiway_merge.c算法步骤:
HeapNode(value, stream_id, next_idx)压入最小堆while 堆非空: node = heap_pop() // 取出全局最小值 output[out_idx++] = node.value if node.next < sizes[node.stream]: // 该路还有元素 heap_push(HeapNode(arrays[node.stream][node.next], node.stream, node.next + 1))最小堆实现:
heap_sift_up:新元素压入后向上调整(O(log k))heap_sift_down:弹出堆顶后将末尾元素移至堆顶,向下调整(O(log k))正确性保证:堆不变式确保每次弹出的都是当前所有路"队头"中的最小值。
| 需求 ID | 描述 |
|---|---|
| REQ-01 | 实现kway_merge(arrays, sizes, k, output, total_size)合并 k 路有序数组 |
| REQ-02 | 使用最小堆作为优先级队列,保证 O(n log k) 时间复杂度 |
| REQ-03 | 支持路中含重复元素的情况,输出结果应保持有序(允许相等) |
| REQ-04 | k=1 的退化情形:直接输出单路内容 |
| REQ-05 | k=0 或 total_size=0 时返回 0,不崩溃 |
| REQ-06 | 堆使用动态内存分配,merge 完成后释放(无内存泄漏) |
| REQ-07 | 仅依赖<stdio.h>、<string.h>、<stdlib.h>,无外部库 |
| 标准 ID | 验收条件 |
|---|---|
| AC-01 | 2路归并 [1,3,5] 和 [2,4,6],输出恰好为 [1,2,3,4,5,6] |
| AC-02 | 3路归并 [1,4,7]、[2,5,8]、[3,6,9],输出恰好为 [1,2,3,4,5,6,7,8,9] |
| AC-03 | 4路归并每路4个元素(共16个),输出有序且包含所有16个不重复元素 |
| AC-04 | 含重复元素的3路归并(共12个元素),输出有序 |
| AC-05 | k=1 单路退化:输出与输入一致;k=0 调用返回0不崩溃 |
| AC-06 | gcc -std=c99 -Wall编译无警告无错误 |
| AC-07 | 所有测试通过(tests_failed == 0),程序返回 0 |