我想使用linux bash命令从文件中删除所有控制字符。

有一些控制字符,例如EOF(0x1A),尤其是当我在其他软件中加载文件时引起问题。我要删除它。

到目前为止,这是我尝试过的:

这将列出所有控制字符:

cat -v -e -t file.txt | head -n 10

^A+^X$
^A1^X$
^D ^_$
^E-^D$
^E-^S$
^E1^V$
^F%^_$
^F-^D$
^F.^_$
^F/^_$
^F4EZ$
^G%$

这将使用grep列出所有控制字符:
$ cat file.txt | head -n 10 | grep '[[:cntrl:]]'
+
1

-
-
1
%
-
.
/

与cat命令的上述输出匹配。

现在,我运行以下命令以显示所有不包含控制字符的行,但仍显示与上述相同的输出(包含控制字符的行)
$ cat file.txt | head -n 10 | grep '[^[:cntrl:]]'
+
1

-
-
1
%
-
.
/

这是十六进制格式的输出:
$ cat file.txt | head -n 10 | grep '[[:cntrl:]]' | od -t x2
0000000 2b01 0a18 3101 0a18 2004 0a1f 2d05 0a04
0000020 2d05 0a13 3105 0a16 2506 0a1f 2d06 0a04
0000040 2e06 0a1f 2f06 0a1f
0000050

如您所见,十六进制值0x01、0x18是控制字符。

我尝试使用tr命令删除控制字符,但出现错误:
$ cat file.txt | tr -d "\r\n" "[:cntrl:]" >> test.txt
tr: extra operand `[:cntrl:]'
Only one string may be given when deleting without squeezing repeats.
Try `tr --help' for more information.

如果删除所有控制字符,最终将删除换行符和回车符,它们将用作Windows上的换行符。如何删除仅保留诸如“\r\n”之类的控制字符?

谢谢。

最佳答案

无需使用预定义的[:cntrl:]集(如您所观察的那样包括\n\r),而只需列出(以八进制表示)要删除的控制字符:

$ tr -d '\000-\011\013\014\016-\037' < file.txt > newfile.txt

07-24 15:45