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

优化Bash脚本:高效比对文件第2、4列行对以缩短运行时间

高效解决方案:替换慢速Bash脚本

你的原始脚本运行缓慢的核心原因是每次循环都调用多个外部命令(sed、cut、cmp、wc),且反复读取磁盘上的文件。对于1732行数据,会产生约150万次外部进程调用和文件读取操作,这是巨大的性能瓶颈。

以下是两种高效的替代方案,均只需读取文件一次,所有处理在内存中完成:


方案1:使用Awk脚本(推荐,最快)

Awk专为文本处理设计,所有操作在单个进程内完成,无需频繁调用外部工具。

脚本代码(保存为collision.awk)

function abs(x) {
    return x < 0 ? -x : x
}

function count_diff(s1, s2) {
    diff = 0
    len1 = length(s1)
    len2 = length(s2)
    min_len = len1 < len2 ? len1 : len2
    
    for (i = 1; i <= min_len; i++) {
        if (substr(s1, i, 1) != substr(s2, i, 1)) {
            diff++
        }
    }
    
    diff += abs(len1 - len2)
    return diff
}

BEGIN {
    FS = "[[:space:]]+"  # 处理空格/制表符分隔的字段
}

NR == 1 { next }  # 跳过表头行

{
    # 用单空格连接字段,保证输出格式一致
    lines[NR] = $1 " " $2 " " $3 " " $4 " " $5
    idx2[NR] = $2
    idx4[NR] = $4
}

END {
    num_lines = NR
    output_file = "primer_collision.txt"
    
    for (i = 2; i <= num_lines; i++) {
        for (j = i + 1; j <= num_lines; j++) {
            diff2 = count_diff(idx2[i], idx2[j])
            diff4 = count_diff(idx4[i], idx4[j])
            
            if (diff2 < 3 && diff4 < 3) {
                print lines[i] > output_file
                print lines[j] > output_file
                print "" > output_file
            }
        }
    }
    
    close(output_file)
}

运行命令

awk -f collision.awk Lab_primers.tsv

方案2:使用Python脚本(更易读,跨平台)

如果你更熟悉Python,这个方案同样高效,逻辑与Awk一致:

脚本代码(保存为collision.py)

def count_diff(s1, s2):
    diff = 0
    min_len = min(len(s1), len(s2))
    for c1, c2 in zip(s1, s2):
        if c1 != c2:
            diff += 1
    diff += abs(len(s1) - len(s2))
    return diff

def main():
    # 读取输入文件
    with open('Lab_primers.tsv', 'r') as infile:
        lines = infile.readlines()
    
    # 解析数据(跳过表头)
    data = []
    for line in lines[1:]:
        parts = line.strip().split()
        full_line = ' '.join(parts)
        idx2 = parts[1]
        idx4 = parts[3]
        data.append((full_line, idx2, idx4))
    
    # 查找匹配对并写入输出
    with open('primer_collision.txt', 'w') as outfile:
        n = len(data)
        for i in range(n):
            line1, idx2_i, idx4_i = data[i]
            for j in range(i + 1, n):
                line2, idx2_j, idx4_j = data[j]
                if count_diff(idx2_i, idx2_j) < 3 and count_diff(idx4_i, idx4_j) < 3:
                    outfile.write(f"{line1}\n")
                    outfile.write(f"{line2}\n")
                    outfile.write("\n")

if __name__ == "__main__":
    main()

运行命令

python collision.py

性能预期

这两种方案的运行时间都会从30+分钟缩短到几秒到几分钟,具体取决于你的硬件配置。核心优化点:

  1. 仅读取输入文件一次,所有数据存入内存
  2. 避免了百万级的外部进程调用
  3. 字符差异计算在进程内完成,无额外开销

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.18 18:11:02