Je voudrais filtrer une liste de chaînes dans python en utilisant regex. Dans le cas suivant, ne gardez que les fichiers avec une extension '.npy'.
Le code qui ne fonctionne pas:
import re
files = [ '/a/b/c/la_seg_x005_y003.png',
'/a/b/c/la_seg_x005_y003.npy',
'/a/b/c/la_seg_x004_y003.png',
'/a/b/c/la_seg_x004_y003.npy',
'/a/b/c/la_seg_x003_y003.png',
'/a/b/c/la_seg_x003_y003.npy', ]
regex = re.compile(r'_x\d+_y\d+\.npy')
selected_files = filter(regex.match, files)
print(selected_files)
La même expression rationnelle fonctionne pour moi dans Ruby:
selected = files.select { |f| f =~ /_x\d+_y\d+\.npy/ }
Quel est le problème avec le code Python?
selected_files = filter(regex.match, files)
re.match('regex')
est égal à re.search('^regex')
ou text.startswith('regex')
mais en version regex. Il vérifie uniquement si la chaîne commence par l'expression régulière .
Donc, utilisez re.search()
à la place:
import re
files = [ '/a/b/c/la_seg_x005_y003.png',
'/a/b/c/la_seg_x005_y003.npy',
'/a/b/c/la_seg_x004_y003.png',
'/a/b/c/la_seg_x004_y003.npy',
'/a/b/c/la_seg_x003_y003.png',
'/a/b/c/la_seg_x003_y003.npy', ]
regex = re.compile(r'_x\d+_y\d+\.npy')
selected_files = list(filter(regex.search, files))
# The list call is only required in Python 3, since filter was changed to return a generator
print(selected_files)
Sortie:
['/a/b/c/la_seg_x005_y003.npy',
'/a/b/c/la_seg_x004_y003.npy',
'/a/b/c/la_seg_x003_y003.npy']
Et si vous voulez juste obtenir tous les fichiers .npy
, Utilisez simplement str.endswith()
:
files = [ '/a/b/c/la_seg_x005_y003.png',
'/a/b/c/la_seg_x005_y003.npy',
'/a/b/c/la_seg_x004_y003.png',
'/a/b/c/la_seg_x004_y003.npy',
'/a/b/c/la_seg_x003_y003.png',
'/a/b/c/la_seg_x003_y003.npy', ]
selected_files = list(filter(lambda x: x.endswith('.npy'), files))
print(selected_files)
Il suffit d’utiliser search
- car la correspondance commence à correspondre du début à la fin (c’est-à-dire la totalité) de la chaîne et la recherche correspond à n’importe où dans la chaîne.
import re
files = [ '/a/b/c/la_seg_x005_y003.png',
'/a/b/c/la_seg_x005_y003.npy',
'/a/b/c/la_seg_x004_y003.png',
'/a/b/c/la_seg_x004_y003.npy',
'/a/b/c/la_seg_x003_y003.png',
'/a/b/c/la_seg_x003_y003.npy', ]
regex = re.compile(r'_x\d+_y\d+\.npy')
selected_files = filter(regex.search, files)
print(selected_files)
Sortie-
['/a/b/c/la_seg_x005_y003.npy', '/a/b/c/la_seg_x004_y003.npy', '/a/b/c/la_seg_x003_y003.npy']
re.match()
recherche une correspondance au début de la chaîne. Vous pouvez utiliser re.search()
à la place.
Si vous correspondez , le motif doit couvrir l’entrée entière . Soit vous prolongez l'expression régulière:
regex = re.compile(r'.*_x\d+_y\d+\.npy')
Ce qui correspondrait à:
['/a/b/c/la_seg_x005_y003.npy',
'/a/b/c/la_seg_x004_y003.npy',
'/a/b/c/la_seg_x003_y003.npy']
Ou utilisez re.search , qui
balaye la chaîne à la recherche du premier emplacement où le modèle d'expression régulière produit une correspondance [...]