大文本按行去重(2G 左右文件)有什么好的解决方案吗?

2020-11-10 14:44:19 +08:00
 sl19981007

速度可以稍慢一点,但也不能太慢(一两个小时跑不完那种 不使用 Spark 之类的计算引擎 麻烦大佬们给小弟个解决方案

4924 次点击
所在节点    程序员
36 条回复
aloxaf
2020-11-10 14:52:20 +08:00
2G 算啥大文本,不要求保持原始顺序的话直接 `sort -u` 就行了。
skypyb
2020-11-10 14:57:05 +08:00
可以接受一点点误差的话
布隆过滤器
loliordie
2020-11-10 14:59:51 +08:00
随便挑个语言 load 到内存里 o(n)复杂度迭代一次就完事了

会用 pandas 用 pandas 不会就用 python 的 set 来实现 处理速度基本等同于 io 的速度
liangfengmark
2020-11-10 15:00:41 +08:00
python set
sl19981007
2020-11-10 15:04:21 +08:00
@loliordie 好吧,我没说清楚,我们同时间可能会有多个这种去重的任务。
way2explore2
2020-11-10 15:05:31 +08:00
@loliordie 正解,2g 直接内存
GM
2020-11-10 15:06:15 +08:00
直接 sort -u,磁盘速度够的话,一分钟完事
icyalala
2020-11-10 15:06:30 +08:00
2G 直接哈希表都能搞定,甚至直接 awk 一行命令:
awk '!a[$0]++' input.txt > output.txt
t6attack
2020-11-10 15:12:34 +08:00
<?php
ini_set('memory_limit',-1);
$array = file('源文件.txt');
$array = array_unique($array);
file_put_contents('输出文件.txt',implode($array,""));
?>
我一直用的方法。也就上面有人说的,直接内存处理。
loliordie
2020-11-10 15:13:18 +08:00
@sl19981007 取决于你的 tradeoff 是空间复杂度优先还是时间复杂度优先

如果是要多个任务同时处理时间复杂度优先 内存够大直接搞个 celery 之类的多线程库就行了 内存不够大就锁队列 只允许 n 个任务同时运行

更简单一点可以输入多个路径 挨个处理 连多线程库都不用上 就是同时只能有一个任务正在运行 但你这个需求 最大瓶颈在于硬盘 io 所以多个并行或者串行影响都不大
mengzhuo
2020-11-10 15:14:04 +08:00
才 2G,直接上哈希表干就完了

一堆超大文件倒是可以试试我的 nabhash
http://nabhash.org/
aladdindingding
2020-11-10 15:54:01 +08:00
linux 命令就行 sort | unique
MOONLIGHTT
2020-11-10 16:44:18 +08:00
别自己写,用 linux 的内建命令
knightdf
2020-11-10 17:14:29 +08:00
2G 而已,sort 都挺快的
hotpot6147
2020-11-10 17:33:26 +08:00
2g 的文本直接 load 进内存,然后 hash 去重就可以了。

如果 pc 机内存不够可以对每行数据进行 hash 后取模分布在 n 个文件中,然后再将这 n 个文件分别 load 进内存去重
BBCCBB
2020-11-10 17:35:11 +08:00
我感觉这种都是先遍历, 按文本 hash 拆分成足够小的文件, 然后在内存足够的情况下去处理每个小文件, 最后 merge 起来就完成了你说的需求了..


一般都是按 hash 拆分, 然后处理每个小文件, 最后再合并.
BBCCBB
2020-11-10 17:35:44 +08:00
不过这是针对超大文件的, 你这个 2G 真的可以试试直接 load 到内存.
Xusually
2020-11-10 17:37:15 +08:00
我开个脑洞,存数据库里。单行内容做主键,不停按行 insert,emmm......
gainsurier
2020-11-10 17:38:02 +08:00
emeditor,十几秒搞定
aec4d
2020-11-10 18:11:08 +08:00
瓶颈是磁盘 IO, 针对选一个 hash https://github.com/rust-lang/hashbrown,按行读取,如果 hash 值已存在则跳过,猜测十秒能完成吧

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/723598

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX