Grep和Python


78

我需要一种通过Unix命令行中的正则表达式使用grep搜索文件的方法。例如,当我在命令行中键入时:

python pythonfile.py 'RE' 'file-to-be-searched'

我需要'RE'在文件中搜索正则表达式并打印出匹配的行。

这是我的代码:

import re
import sys

search_term = sys.argv[1]
f = sys.argv[2]

for line in open(f, 'r'):
    if re.search(search_term, line):
        print line,
        if line == None:
            print 'no matches found'

但是当我输入一个不存在的单词时,no matches found不会打印


1
如果您真的想在grep中使用python样式的正则表达式,则grep的--perl-regex选项确实非常接近。它为您提供了perl样式的正则表达式支持。(此外,我最喜欢的grep未使用的选项是--color = always)
Ross Rogers 2009年

Answers:


82

自然的问题是为什么不只使用grep?但是假设你不能...

import re
import sys

file = open(sys.argv[2], "r")

for line in file:
     if re.search(sys.argv[1], line):
         print line,

注意事项:

  • search而不是match在字符串中找到任何地方
  • 删除回车符,后的逗号()print(行将有一个)
  • argv 包含python文件名,因此变量需要从1开始

这不能处理多个参数(如grep一样)或扩展通配符(如Unix shell一样)。如果您需要此功能,可以使用以下方法获得它:

import re
import sys
import glob

for arg in sys.argv[2:]:
    for file in glob.iglob(arg):
        for line in open(file, 'r'):
            if re.search(sys.argv[1], line):
                print line,

7
您应该在使用循环之前编译正则表达式。
ghostdog74

5
这有两次否决,我不知道为什么。投票否的人想发表评论吗?我知道您可以添加正则表达式编译等,但是我认为这样做会降低答案的清晰度。我不认为有任何不正确的地方,而且我已经运行了代码,与其他一些答案不同
Nick Fortescue 2009年

这个答案非常适合我,谢谢。另一个快速的问题是,如果找不到匹配项,我将如何打印?
大卫,

6
“您应该在使用循环之前先编译正则表达式。”不,Python会自行编译并缓存它,这是一个普遍的神话,出于可读性原因,这是一件好事。
bartekbrak '16

4
对于自然问题的合理答案是:“因为代码是更大的Python脚本的一部分,并且在这种情况下谁想调用grep?” 简而言之,我很高兴这个问题出现在这里,因为我正在用Python脚本替换bash脚本,希望该脚本在系统上更容易。
Mike S

13

简洁而高效的存储:

#!/usr/bin/env python
# file: grep.py
import re, sys

map(sys.stdout.write,(l for l in sys.stdin if re.search(sys.argv[1],l)))

它的工作方式类似于egrep(没有太多错误处理),例如:

cat input-file | grep.py "RE"

这是单线:

cat input-file | python -c "import re,sys;map(sys.stdout.write,(l for l in sys.stdin if re.search(sys.argv[1],l)))" "RE"

7

改编自python中grep

通过接受文件名列表[2:],不进行异常处理:

#!/usr/bin/env python
import re, sys, os

for f in filter(os.path.isfile, sys.argv[2:]):
    for line in open(f).readlines():
        if re.match(sys.argv[1], line):
            print line

sys.argv[1]respsys.argv[2:]可以工作,如果您将其作为独立的可执行文件运行,则意味着

chmod +x

第一


re.match 和 之间有什么区别re.search
OscarRyz

2
@OscarRyz看到Nick Fortescue的最高答案:“search而不是match在字符串中找到任何地方”
icc97


3

您可能对pyp感兴趣。引用我的其他答案

“ Pyed Piper”或pyp是类似于awk或sed的linux命令行文本操作工具,但是它使用标准的python字符串和列表方法以及自定义函数,这些函数在激烈的生产环境中发展为可以快速生成结果。


1

您可以使用python-textops3:

from textops import *

print('\n'.join(cat(f) | grep(search_term)))

与python-textops3一起使用时,可以在管道中使用类unix的命令


0

真正的问题是可变线始终具有一个值。测试“找不到匹配项”是是否存在匹配项,因此应将代码“ if line == None:”替换为“ else:”

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.