用Linux命令在大文件中替换字符串为另一个字符串

3

我有一个巨大的文件(8GB),我想在前30行中将字符串" LATIN1 "替换为" UTF-8 ",最有效的方法是什么?是否有一种方法可以使用sed,但在解析前30行后退出。

VIM无法在3小时内保存文件。

3个回答

3
问题在于,如果进行替换操作,所有程序都会复制该文件并进行替换,以便最终替换原始文件--他们不想冒失丢失原始文件的风险。
使用perl,你可以用一行代码完成这个操作,但这并不意味着它比vim更短(嗯,与vim相比,perl不会在另一个文件中保留历史记录)。
perl -pi -e 's,\bLATIN1\b,UTF-8,g if $. <= 30' thefile

1
“并非所有程序都会复制文件”这个说法绝对是错误的。事实上,此处提供的解决方案不会创建备份! - William Pursell
@WilliamPursell 给我反驳的证据——比如追踪所有系统调用。我打赌它是这样的。唯一的原因可能是,替换后文件大小不同而已...编辑:我的意思是,它会在某些地方写入一个带替换的新副本。 - fge
当然,你的解决方案确实会写入一个临时文件,然后覆盖原始文件。但它并没有备份,原始文件确实会丢失。 - William Pursell
@WilliamPursell 是的,我的初步评论措辞不当,我已进行了编辑。 - fge
1
@fge,哇,我也试了一下你的解决方案。8GB只用了40秒,太棒了。谢谢! - Nenad
@Nenad 在这个级别上,给你性能的是底层的I/O能力 ;) 在一个十年前的机器上,这条评论肯定不需要40秒 :p - fge

2

使用sed时,您可以使用q退出:

sed -e 's/LATIN1/UTF-8/g' -e 30q

谢谢,这个很好用,但是我怎么把结果写到一个文件里呢?实际上,sed -e 's/LATIN1/UTF-8/g' -e 30q my_old_one > my_new_one 只会写前30行。 - Nenad
1
最简单的方法是跟进:sed -n '31,$p' my_old_one >> my_new_one - William Pursell

0

未经测试,但我认为ed将直接编辑文件而不写入临时文件。

ed yourBigFile << END
1,30s/LATIN1/UTF-8/g
w
q
END

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接