列表过滤和转换
我有一个库文件名列表,需要根据正则表达式进行过滤,然后从匹配的文件名中提取版本号。这是执行此操作的明显方法:
libs = ['libIce.so.33', 'libIce.so.3.3.1', 'libIce.so.32', 'libIce.so.3.2.0']
versions = []
regex = re.compile('libIce.so\.([0-9]+\.[0-9]+\.[0-9]+)')
for l in libs:
m = regex.match(l)
if m:
versions.append(m.group(1))
这会产生以下列表:
['3.3.1', '3.2.0']
但我觉得循环不是很“Python 风格”,并且觉得应该可以用一些智能单行代码替换上面的“for”循环。 建议?
I have a list of library filenames that I need to filter against regular expression and then extract version number from those that match. This is the obvious way to do that:
libs = ['libIce.so.33', 'libIce.so.3.3.1', 'libIce.so.32', 'libIce.so.3.2.0']
versions = []
regex = re.compile('libIce.so\.([0-9]+\.[0-9]+\.[0-9]+)')
for l in libs:
m = regex.match(l)
if m:
versions.append(m.group(1))
That produces the following list:
['3.3.1', '3.2.0']
Yet I feel that loop is not very 'Python style' and feel it should be possible to replace 'for' loop above with some smart one-liner.
Suggestions?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(8)
列表理解怎么样?
How about a list comprehension?
再一句只是为了展示其他方式(我还清理了一点正则表达式):
但请注意,您的原始版本比所有建议更具可读性。值得改变吗?
One more one-liner just to show other ways (I've also cleaned regexp a bit):
But note, that your original version is more readable than all suggestions. Is it worth to change?
你可以这样做:
不过,我认为它的可读性不是很好......
也许分两步完成会更清楚:
You could do this:
I don't think it's very readable, though...
Maybe it's clearer done in two steps:
使用标准 for 循环没有什么不是 Pythonic 的。但是,您可以使用 map() 函数生成新的基于针对列表中的每个项目运行的函数的结果的列表。
There's nothing that isn't pythonic about using a standard for loop. However, you can use the map() function to generate a new list based on the results from a function run against each item in the list.
对于简单的情况,您真的不需要费心使用正则表达式
进行进一步检查以获取带有“点”的内容。
you don't really need to bother with regex for your simple case
Do further checking to get those with "dots".
这个怎么样:
How about this one:
我能想到的一种方法是将“地图”和列表理解结合起来。
解决方案如下所示:
One way I could think of was to combine 'map' and list comprehension.
The solution looks as below:
从
Python 3.8
开始,并引入赋值表达式 (PEP 572) (:=
运算符),可以在列表理解中使用局部变量,以避免调用正则表达式匹配结果的两次:此:
match
(可以是None
或re.Match
对象)match
命名表达式(None
或Match
)过滤掉不匹配的元素match 通过提取第一个组 (
match.group(1)
) 来添加到映射值中。Starting
Python 3.8
, and the introduction of assignment expressions (PEP 572) (:=
operator), it's possible to use a local variable within a list comprehension in order to avoid calling twice the result of the regex matching:This:
pattern.match(lib)
as a variablematch
(which is eitherNone
or are.Match
object)match
named expression in place (eitherNone
or aMatch
) to filter out non matching elementsmatch
in the mapped value by extracting the first group (match.group(1)
).