Bash 逐行读取文件并删除字符shell脚本
该程序的目的是删除文本中的标点符号,并可以处理选项Bash 逐行读取文件并删除字符shell脚本,bash,Bash,该程序的目的是删除文本中的标点符号,并可以处理选项-c,以删除所需的字符 #!/bin/bash old_IFS=$IFS IFS=$’\n’ if [ “$1” == “-c” ];then if [ -f $2 ];then for line in $(<$2) do echo $line | tr -d $3 done IFS=$old_IFS else echo $2 | tr -d $3 fi else if [ -f $1 ];then f
-c
,以删除所需的字符
#!/bin/bash
old_IFS=$IFS
IFS=$’\n’
if [ “$1” == “-c” ];then
if [ -f $2 ];then
for line in $(<$2)
do
echo $line | tr -d $3
done
IFS=$old_IFS
else
echo $2 | tr -d $3
fi
else
if [ -f $1 ];then
for line in $(cat $1)
do
echo $line | tr -d '[:punct:]'
done
IFS=$old_IFS
else
echo $1 | tr -d '[:punct:]'
fi
fi
如果我只想删除标点符号,结果是:
Twaddle you say Ill have you k
iheres a deep truth
what I said
其他字符丢失,如
now
的know
。有人能找到问题所在吗?您遇到的困难是由于使用了非ASCII字符。尤其要注意:
IFS=$’\n’
该行不能按预期工作,因为它们不是普通的ASCII单引号。结果是字符n
,以及其他字符,最终出现在变量IFS中。这会导致n
上出现分词,这就是n
在know
中消失的原因
改用:
IFS=$'\n'
双引号也是非标准的,应该用ASCII双引号代替。特别是,这一行:
if [ “$1” == “-c” ];then
应替换为:
if [ "$1" == "-c" ];then
替代脚本
脚本的逻辑可以重新排列和简化:
#!/bin/bash
remove='[:punct:]'
if [ “$1” == “-c” ]
then
remove=$3
shift
fi
if [ -f $1 ]
then
tr -d "$remove" <"$1"
else
echo "$1" | tr -d "$remove"
fi
#/bin/bash
删除='[:点:'
如果[“$1”==“-c”]
然后
删除=3美元
转移
fi
如果[-f$1]
然后
tr-d“$remove”
在脚本上的“reduce”regex面板中使用sed,但对特殊字符的安全性要求不高此脚本非常愚蠢tr
可以过滤整个流/文件并删除或替换多个字符。执行此类任务的更好工具是使用文本编辑器,我认为像sed
和awk
twadle,你说我会让你知道我说的话(更改后的结果,丢失一行)@user3606466您可能还有其他我没有捕捉到的特殊字符。您报告说,您的脚本现在正在将单词truth
从句中移动到句末?我无法复制那个。在文本文件中,应该将文本分隔为三行。第一句话是:“胡扯!”,你说?我会让你知道,第二句话是:有一个{深刻的}真相,第三句话是:在我说的话里。但是在尝试了你的方法之后,结果只显示了两行,并且“真理”移到了结尾,这是不对的。@JAC我只是用(1)你的代码和我的修改,以及(2)我的替代代码再次尝试了它。两者都为我工作。但是,如果文件在第二行末尾有一个回车字符代替换行符,则可能导致第三行部分覆盖第二行。那将符合你的结果。您使用什么程序创建这些文件?
#!/bin/bash
remove='[:punct:]'
if [ “$1” == “-c” ]
then
remove=$3
shift
fi
if [ -f $1 ]
then
tr -d "$remove" <"$1"
else
echo "$1" | tr -d "$remove"
fi
#!/bin/bash
if [ "$1" = '-c' ]
then
Pattern="$( echo "$3" | sed 's/[]\[&\\{}()"]/\\&/g' )"
File="$2"
else
Pattern="[[:punct:]]"
File="$1"
fi
sed -i "s/${Pattern}//g" ${File}