2014-10-27 86 views
1

我想从文件中删除特定的字符串。 我尝试使用:使用bash脚本从文件中删除字符串

for line3 in $(cat 2.txt) 
do 
    if grep -Fxq $line3 4.txt 
     then 
     sed -i /$line3/d 4.txt 
    fi 
done 

我想这个代码删除4.txt行,如果他们也是2.txt,但这个循环将删除所有4.txt线,我不知道为什么。有人能说出这段代码有什么问题吗?

2.txt:

a 
ab 
abc 

4.txt:

a 
abc 
abcdef 
+0

您能否显示一些来自'2.txt'和'4.txt'的示例数据? – anubhava 2014-10-27 20:10:51

+0

已添加示例数据。 – Bouncer00 2014-10-27 20:15:41

+0

只有sed! 'sed $(sed's,^,-e/^ ,; s,$,$/d,'2.txt)4。txt' – gboffi 2014-10-27 20:48:05

回答

1

您可以通过单一awk command做到这一点:

awk 'ARGV[1] == FILENAME && FNR==NR {a[$1];next} !($1 in a)' 2.txt 4.txt 
abcdef 

要存储输出回4.txt使用:

awk 'ARGV[1] == FILENAME && FNR==NR {a[$1];next} !($1 in a)' 2.txt 4.txt > _tmp && mv _tmp 4.txt 

PS:添加ARGV[1] == FILENAME &&负责处理空文件大小写,如@pjh所示。

+1

如果第一个文件为空,则不起作用:它不会生成输出,但应该复制第二个文件中的所有行。有关该问题的详细信息,请参阅[10 Awk提示,技巧和陷阱](http://www.catonmat.net/blog/ten-awk-tips-tricks-and-pitfalls/)中的'警告',以及如何修理它。 – pjh 2014-10-29 12:55:30

+0

谢谢@pjh:现在编辑好了。 – anubhava 2014-10-29 21:01:22

0

妈妈快看”,只用sed ...

sed $(sed 's,^, -e /^,;s,$,$/d,' 2.txt) 4.txt 
  1. 变换每一行2.txt在sed命令,例如,abc - >-e /^abc$/d
  2. 给sed命令的列表,以一个实例对4.txt sed的操作

要存储输出回4.txt使用:

sed -i $(sed 's,^, -e /^,;s,$,$/d,' 2.txt) 4.txt 

编辑:虽然我很喜欢的美学基础我的回答,请不要尝试 这个家!看到PJH评论下面的 许多方面的详细理由在我microscript可能会失败

+0

该解决方案有许多问题。如果第一个文件为空,或者包含空格或包含斜杠,则失败。如果第一个文件包含正则表达式元字符,它可能会生成错误的输出。如果第一个文件非常大,则可能会导致命令由于时间太长而失败。另外,如果第一个文件非常大,它可能会非常低效。 – pjh 2014-10-29 13:50:56

+1

@pjh我编辑了我的答案,以证明你的评论。我承认,我发布了这个特殊的答案,因为它的美丽(像往常一样,美丽在旁观者的眼中!),而不是它的用处...... – gboffi 2014-10-29 17:44:08

1
grep -F -v -x -f 2.txt 4.txt 

grep -Fvxf 2.txt 4.txt 

fgrep -vxf 2.txt 4.txt 
0

只需使用击(4 )builtins:

declare -A found 
while IFS= read -r line || [[ $line ]] ; do found[$line]=1 ; done <2.txt 
while IFS= read -r line || [[ $line ]] ; do 
    ((${found[$line]-0})) || printf '%s\n' "$line" 
done <4.txt 

'[[$ line]]'测试用于处理未终止行的文件。

如果任何输出行以'echo'选项开头,则使用'printf'而不是'echo'。

相关问题