ett*_*ore 6 awk text-processing unicode
我正在处理用意大利语和中文编写的文本,我只需要使用AWK
. 我怎样才能做到这一点?
我试过:
[中文Unicode字符的范围是4E00 thru 9FFF (344 270 200 thru 351 277 277)
这样测试应该是>"\343" and <"\352"
(为了避免拿起任何4个字符的UTF-8代码)]:
{
f=0;
for ( i=1; i<=length; i++)
if(substr($0, i, 1)>"\343" &&substr($0, i, 1)<"\352")
f = 1
print $f
}
Run Code Online (Sandbox Code Playgroud)
但是有一个错误或更多错误。我找不到它/他们
Wou*_*lst 13
您的问题是,通过过滤 UTF-8 字符流中的原始字节,您会吃掉 UTF-8 文件中 unicode 序列的一部分,从而导致字节序列无效。那行不通。相反,您需要使用能够理解 UTF-8 的工具,并对 unicode 数据而不是原始字节应用过滤器。
由于我不知道awk
您使用的是哪种实现,因此我无法判断它是否支持 unicode。但是,我知道 perl 是完全 unicode 安全的,所以下面的 perl one-liner 应该可以工作:
perl -CS -p -e 's/[^\s\p{Han}]//g'
Run Code Online (Sandbox Code Playgroud)
该\s
是空白,这我假设你希望看到的。该\p{Han}
位告诉 perl 我们要匹配在 Unicode 中声明为在汉字中使用的字符(即中文字符)。我不知道您是否需要该范围内未包含的任何标点符号;如果这样做,您可能还需要添加它。
然后我们用^
开头否定范围,最后在全局替换命令 ( s///g
) 中对其进行编码,我们告诉 perl 替换第一个斜杠后面部分的实例(我们的否定范围,或“不在此范围内的所有内容”) ) 与第二个之后第三个之前的部分(即,没有)。
如果您不需要包含多个范围,您可以放弃[^]
构造,并切换到 using\P
而不是\p
,它执行相同的匹配反转。
剩下的是我们输入的字符范围——汉字中的 unicode 字符,加上空格。
有关详细信息,请参阅perldoc perlre
有关 perl 如何处理正则表达式的说明,以及perldoc perluniprops
可能的 unicode 属性列表(您可以放置在 a\p{}
或\P{}
构造中的位)。
小智 1
使用awk
你可以这样做:
awk '{for(i=1; i<=length;i++) if(substr($0,i,1)>="\xS_INDEX" && substr($0,i,1)<="\xE_INDEX"){printf substr($0,i,1);f=1;} if(f)printf "\n"; f=0}' filename
Run Code Online (Sandbox Code Playgroud)
这里S_INDEX
和E_INDEX
是 .ascii 中的起始和结束索引hex
。
对于输入:
1243
135
dgfsdaa
125
sdg124
sdf34
Run Code Online (Sandbox Code Playgroud)
仅选择数字:S_INDEX = 30 和 E_INDEX = 39
输出:
1243
135
125
124
34
Run Code Online (Sandbox Code Playgroud)