我有以下代码:
def grep(pattern, file_path):
with io.open(file_path, "r", encoding="utf-8") as f:
file_size = os.path.getsize(file_path)
mm = mmap.mmap(f.fileno(), file_size, access=mmap.ACCESS_READ)
return re.search(pattern, mm)
使用Python 2.6.6,我可以使用r'approved="no"'
模式
使用Python 3.5.2,我必须使用b'approved="no"'
模式。否则,我得到TypeError: cannot use a string pattern on a bytes-like object
有没有办法在Python 3.5.2中使用原始字符串模式?我有使用相同的原始字符串模式的代码,我使用mmap传递给此函数,所以我想重用这些模式。
我已经尝试将mmap对象读入字符串,但这会大大降低Windows上的性能(在Linux上没那么多)
data = str(mm.read(file_size))
return re.search(pattern, data)
工作集:405个Xliff文件,共计3,860,117行
用Python (time.time() - start_time)
测量时间
将mmap对象读入字符串:29s
直接在正则表达式中使用二进制模式和mmap对象:3s
答案 0 :(得分:2)
最简单的方法可能就是编码为utf-8:
def grep(pattern, file_path):
pattern = pattern.encode("utf-8")
with io.open(file_path, "r", encoding="utf-8") as f:
file_size = os.path.getsize(file_path)
mm = mmap.mmap(f.fileno(), file_size, access=mmap.ACCESS_READ)
return re.search(pattern, mm)
它会在python3上给你字节,并且我评论说使用python2在str和字节之间没有区别。
答案 1 :(得分:1)
bytes
也可以是原始文字。如果您的模式仅与mmap
(或其他bytes
类似的东西一起使用),您可以使用br'approved="no"'
,这在2.6及更高版本上受支持就好了{{1通常在Py2.x上是冗余的,但它对b
转换器意味着什么,并将撤消2to3
对该特定文字的影响。
可悲的是,在Py2.x(和Py3.2及以下版本)上,前缀顺序很重要,from __future__ import unicode_literals
很好,br'approved="no"'
是语法错误。在Py 3.3及更高版本中,任何一个订单都被接受(我自己更喜欢后者,因为它在我的头脑中自然地读取"原始字节",相对于更笨拙"字节raw",但便携性优先。)
显然,如果您的其他用途是严格文本(Py2 rb'approved="no"'
,Py3 unicode
),Padraic的编码答案(或存储为str
并在其他地方解码places)是避免存储每个模式的两个副本的唯一选择。