Base64编码逐行更快

时间:2016-08-18 13:51:44

标签: bash shell base64

我有一个大文本文件(大约10GB),它可以毫不费力地存储到内存中。我的目标是将每一行转换为base64字符串。目前我的方法需要永远,似乎没有完成,因为它是单线程的。

while read line; do echo -n -i $line | base64 >> outputfile.txt; done < inputfile.txt

有人可以给我一个如何更快地提示吗?这个解决方案每小时产生大约100MB(因此整理时间为100h)CPU使用率为5%,磁盘使用率也非常低。

似乎我误解了控制角色...... 所以我包含了一个示例文本文件,以及输出应该是什么(chepner在chomp中是正确的):

示例输入:

Банд`Эрос
testè!?£$
``
▒``▒`

示例输出:

user@monster ~ # head -n 5 bash-script-output.txt
0JHQsNC90LRg0K3RgNC+0YE=
dGVzdMOoIT/CoyQ=
YGA=
4paSYGDilpJg

user@monster ~ # head -n 5 perl-without-chomp.txt
0JHQsNC90LRg0K3RgNC+0YEK
dGVzdMOoIT/CoyQK
YGAK
4paSYGDilpJgCg==

user@monster ~ # head -n 5 perl-chomp.txt
0JHQsNC90LRg0K3RgNC+0YE=
dGVzdMOoIT/CoyQ=
YGA=
4paSYGDilpJg

所以样本每次都比人类声明更好; =)

2 个答案:

答案 0 :(得分:3)

仅打开一次输出文件可能会有所帮助:

while IFS= read -r line; do echo -n $line | base64; done < inputfile.txt > outputfile.txt

bash在这里不是一个好选择,但有两个原因:迭代文件的开始很慢,并且您为每一行开始一个新进程。更好的想法是使用具有用于计算base64值的库的语言,以便在一个进程中处理所有内容。使用Perl的示例

perl -MMIME::Base64 -ne 'print encode_base64($_)' inputfile.txt > outputfile.txt

答案 1 :(得分:0)

不要使用perl或任何其他dyn类型的语言来处理10G文本,尤其是在以下情况下:受串行处理的约束,期望源有效载荷随时间增加和/或在处理时间附近具有一些SLA。

如果顺序无关紧要,那么一定要绕过高级语言方法,因为您可以使用shell和posix组件免费并行处理。

$ printf "%s\n" one two three
one
two
three
$ printf "%s\n" one two three \
> | xargs \
>      -P3 `# three parallel processes` \
>      -L1 `# use one line from stdin` \
>     -- sh -c 'echo $@ | base64' _ 
b25lCg==
dHdvCg==
dGhyZWUK

即使顺序(读取,处理,写入)受约束,我仍然会利用可用的多个内核,将工作分散到多个处理程序,然后分散到一些类似reducer的方法,单一过程。

# add line number to each line
$ printf "%s\n" one two three | nl
     1  one
     2  two
     3  three
# base64 encode second column
$ printf "%s\n" one two three \
>     | nl \
>     | xargs -P3 -L1 sh -c \
>       'echo $2 | base64 | xargs printf "%s %s\n" "$1"' _
2 dHdvCg==
1 b25lCg==
3 dGhyZWUK
# sort based on numeric value of first col
$ printf "%s\n" one two three \
>     | nl \
>     | xargs -P3 -L1 sh -c \
>       'echo $2 | base64 | xargs printf "%s %s\n" "$1"' _ \
>     | sort -k1 -n
1 b25lCg==
2 dHdvCg==
3 dGhyZWUK

所有这些方法都将扩展到可用核心的数量,并且所有繁重的工作(在文本处理方面)都是由古老的c二进制文件完成的,它将胜过其他任何事情。

如果您是一个狂想者,请使用C来完成整个工作,但是我可以保证以上内容将胜过用perl,python,ruby等编写的任何内容。内核将管理管道之间的缓冲区,这意味着大部分深奥的工作已经完成。

相关问题