我目前正在使用grep尝试从文件的每一行提取特定文本。它已成功提取出匹配项,但是,我希望它保留所有没有匹配项的行(将它们保留为空白行)。
这是我到目前为止尝试过的方法(在每一行上获取城市名称):
grep -o -P '(?<="city":").*?(?=")' input.txt
示例输入:
email":"addictedtotlick7@gmail.com","last_name":"THOMPSON","first_name":"ERIN",,"__v":0,,,,"state":"NY","city":"north tonawanda"}
first_name":"chris","last_name":"caul",,"email":"dawgzn@mail.com",,,,"__v":0}
email":"lesliebo993@hotmail.com",,"first_name":"LESLIE","last_name":"RAMBO",,"city":"DOTHAN","state":"AL",,,"__v":0,
email":"malala@yahoo.com",,,"state":"GA","city":"NORCROSS",,"last_name":"KEO","first_name":"CATHY",,"__v":0,
email":"kdela@gmail.com",,"state":"FL","city":"HOLLYWOOD",,"last_name":"DE LA CRUZ","first_name":"KIDA",,"__v":0,
所需的输出:
north tonawanda
DOTHAN
NORCROSS
HOLLYWOOD
如果更容易的话,也很乐意在SED中尝试某些操作,但是由于我必须处理大文件,并且不确定我是否有足够的RAM,所以宁愿避免使用AWK。
答案 0 :(得分:0)
您可以使用GNU awk
:
gawk '{print index($0, "\"city\":\"") == 0 ? "" : gensub(/.*\"city\":\"([^\"]*).*/, "\\1", 1);}' file > newfile
这意味着:如果行中包含"city":"
(index($0, "\"city\":\"") == 0
),则(?
)打印空白行(""
)或(:
)打印gensub(/.*\"city\":\"([^\"]*).*/, "\\1", 1)
正则表达式替换的结果:
.*
-任意0个以上的字符\"city\":\"
-一个"city":"
子字符串([^\"]*)
-捕获组1(\1
):除"
以外的任何0+个字符.*
-任意0个以上的字符。其结果是组1的值。我们需要gensub
,因此需要GNU awk,因为我们需要访问捕获组的值。
答案 1 :(得分:0)
Sed:
sed 's/.*city":"\([^"]*\).*/|\1/; /^[^|]/s/.*//; s/^|//'
答案 2 :(得分:0)
您可以尝试Perl
$ perl -nle ' if(/"city":"(.*?)"/) { print $1 } else { print "" } ' input.txt
north tonawanda
DOTHAN
NORCROSS
HOLLYWOOD
$
答案 3 :(得分:-1)
我建议另一个awk脚本
awk 'match($0,/(?<=\"city\":\").*?(?=\")/,m){$0=m[0]}1' input.txt
RAM和AWK没问题。
此脚本处理每一行。
如果当前行与RegExp (?<="city":").*?(?=")
相匹配,则使用匹配项覆盖当前行。打印当前行。