我有一个1,00,000行的JSON文本文件.手动提取不公平.我编写了一个Perl程序来读取文件的每一行,满足我的需求.
这是一个示例文本文件
"key": "Programming",
"doc_count": 1
"key": "Base",
"doc_count": 1,
"key": "Experience",
"doc_count": 1
"key": "Electrophoresis",
"doc_count": 1
Run Code Online (Sandbox Code Playgroud)
我想把键值单独用双括号分隔,比如编程,基础,经验和电泳.
这是我尝试过的Perl代码:
use strict;
use warnings;
my $file = $ARGV[0];
open my $info, $file or die "Could not open $file: $!";
while ( my $line = <$info> ) {
if ( $line =~ /"key(.*)",/ ) {
print $1;
print "\n";
}
}
close $info;
Run Code Online (Sandbox Code Playgroud)
通过使用它,我得到这个输出
": "Programming
": "Base
": "Experience
": "Electrophoresis
Run Code Online (Sandbox Code Playgroud)
我不想要领先的冒号和空间.
我试过了$line =~ /"key: "(.*)",/
.但它没有用.该命令执行但没有输出,也没有错误症状.
G:\ExtractKeyValue_Regex>perl ExtractKeyValue.pl Sample.txt > Output_Sample.txt
G:\ExtractKeyValue_Regex>
Run Code Online (Sandbox Code Playgroud)
输出应该是,像,
Programming
Base
Experience
Electrophoresis
Run Code Online (Sandbox Code Playgroud)
我无法弄清楚为什么冒号:
,空格和双引号"
没有被模式跟踪.
你展示的所有线条都是你需要的
my $key_assoc = $line =~ /: "([^"]+)/;
print "$key_assoc\n" if $key_assoc;
Run Code Online (Sandbox Code Playgroud)
或者你可以输入"key"
字符串,",
以获得额外的保证和格式检查
if ($line =~ /"key": "([^"]+)",/) {
# ...
}
Run Code Online (Sandbox Code Playgroud)
请注意,如果存在空引号(),+
则不会捕获任何内容,"key": "",
而.*
在这种情况下会获得空字符串.一个细节可能无关紧要,但它们是不同的.
请注意, 在正则表达式中使用单个文字空间很容易被忽略(或加倍),如果/x
稍后添加,也会被吞下,如果没有测试则会引入错误.
指定单个简单空间的更好方法是什么?我们可以通过pragma 使用\x20
或者使用Unicode .感谢Borodin提出这个并指定这两个.\N{SPACE}
charnames
来自SinanÜnür的一个很好的解决方法是使用仅有空格的角色类/a [ ] b/x
.这两者都强调文字空间是有意的(没有/x
),并允许它在下面/x
.
另一个解决方法是明确地逃避它,/\ /
它会引起对它的注意并保护它/x
.