我有一些配置文件,我需要从中提取一些值。例如,我有这个:
PART
{
title = Some Title
description = Some description here. // this 2 params are needed
tags = qwe rty // don't need this param
...
}
我需要提取某个参数的值,例如description
的值。我如何使用正则表达式在Python3中执行此操作?
答案 0 :(得分:2)
这是正则表达式,假设文件文本位于txt
:
import re
m = re.search(r'^\s*description\s*=\s*(.*?)(?=(//)|$)', txt, re.M)
print(m.group(1))
让我解释一下。
^
在行首处匹配。
然后\s*
表示零个或多个空格(或制表符)
description
是您找到价值部分的锚点。
之后,我们希望通过表示=
之前或之后使用可选空格\s*=\s*
进行签名。
然后我们通过表示=
来捕获(.*?)
和可选空格之后的所有内容。该表达式由括号捕获。在括号内,我们说你可以用非贪婪的方式(问号)匹配任何东西(圆点),也就是说,一旦匹配下面的表达式就停止。
以下表达式是一个先行表达式,以(?=
开头,与(?=
之后的东西匹配。
而那个东西实际上是两个选项,由竖线|
分隔。
条形图左侧的第一个选项是//
(在括号中使其成为垂直条选择操作的原子单位),即注释的开头,我想,你不想捕捉。
第二个选项是$
,表示行的结尾,如果行上没有注释//
,则会到达。
因此,我们会在第一个=
符号后查找所有内容,直到我们遇到//
模式,或者我们遇到行尾。这是(?=(//)|$)
部分的本质。
我们还需要re.M
标志,告诉正则表达式引擎我们希望^
和$
分别匹配行的开头和结尾。没有标志,它们匹配整个字符串的开头和结尾,这不是我们想要的情况。
答案 1 :(得分:0)
更好的方法是使用已建立的配置文件系统。 Python内置了对configparser
模块中类似INI的文件的支持。
但是,如果您只是绝望地需要在description
之后获取该文件中的文本字符串,那么您可以这样做:
def get_value_for_key(key, file):
with open(file) as f:
lines = f.readlines()
for line in lines:
line = line.lstrip()
if line.startswith(key + " ="):
return line.split("=", 1)[1].lstrip()
您可以通过以下呼叫使用它:get_value_for_key("description", "myfile.txt")
。如果找不到任何内容,该方法将返回None
。假设您的文件将被格式化为有空格且密钥名称后面的等号,例如key = value
。
这完全避免了正则表达式,并保留了值右侧的任何空格。 (如果这对您不重要,您可以使用strip
代替lstrip
。)
为什么要避免正则表达式?它们非常昂贵,而且对于这种情况来说并不理想。使用简单的字符串匹配这样可以避免导入模块并简化代码。但我真的要说转换为支持的配置文件格式。
答案 2 :(得分:-1)
这是一个非常简单的正则表达式,你只需要一个积极的lookbehind,并可选择删除注释。 (通过将?(//)?
附加到正则表达式
r"(?<=description = ).*"