@edzech a demandé comment était-il possible de diviser une chaîne et d'y conserver les séparateurs. Sa question a été marquée comme dupliquée , alors que l'approche ici est différente de la "duplication" .
Nous voulons diviser une chaîne mais en y gardant les délimiteurs, nous ne voulons pas qu'ils soient séparés.
En bref, pour , nous voulons:
['<', 'abc', '>' 'd', '<', 'e', '>', '<', 'f', '>', 'ghi', '<', 'j', '>']
au lieu de: p >
['<abc>', 'd', '<e>', '<f>', 'ghi', '<j>']
Utiliser split n'aide pas car il sera fractionné en fonction du séparateur. Nous voulons le garder attaché à son contenu.
3 Réponses :
Voici la solution.
['<abc>', 'd', '<e>', '<f>', 'ghi', '<j>']
Résultat:
import re content = "<abc>d<e><f>ghi<j>" result = re.findall(r"<.*?>|[^<>]+", content) print(result)
Explications:
<.> signifie tout ce qui correspond à [^ ] + signifie tout le reste En bref, findall trouvera tout ce qui correspond à , sinon, tout le reste. De cette façon, le contenu sera divisé sans perdre les séparateurs.
Je pense que vous pouvez utiliser split avec cette expression régulière
>>> import re >>> rx = re.compile( r"(?<=>)(?=[a-z<])|(?<=[a-z>])(?=<)" ) >>> s = "<abc>d<e><f>ghi<j>test><g>" >>> x = re.split( rx, s ) >>> print ( x ) ['<abc>', 'd', '<e>', '<f>', 'ghi', '<j>', 'test>', '<g>']
https : //regex101.com/r/WNy5n9/1
Ce n'est rien de plus que 2 options avec des assertions lookbehind / ahead appariées.
Développer
>>> import sys >>> print( sys.version ) 3.7.3 (v3.7.3:ef4ec6ed12, Mar 25 2019, 21:26:53) [MSC v.1916 32 bit (Intel)]
Update
Notez que dans les versions de Python antérieures à la version 3.7, la division
sur une correspondance vide n'a pas été gérée correctement.
Vraisemblablement, ils ne pouvaient pas faire la différence entre un vide
string et / ou comment effectuer le déplacement sur des correspondances de largeur nulle.
On dirait qu'ils ont sorti la tête de leur ** maintenant dans la version 3.7,
alors voilà.
Démo
Version 3.7.3
(?<= > ) # Behind a > (?= [a-z<] ) # Ahead either a-z or < | # or, (?<= [a-z>] ) # Behind either a-z or > (?= < ) # Ahead a <
Code p>
(?<=>)(?=[a-z<])|(?<=[a-z>])(?=<)
Dans la solution proposée, une seule ouverture Si vous aussi souhaitez conserver un Explication Par exemple: Résultat ou fermeture > qui ne fait pas partie d'une paire est exclue du résultat. ou > que vous pourriez utiliser: ['<abc>', 'd', '<e>', '<f>', 'ghi', '<j>', 'test>', '<g>']
*> Correspond à l'ouverture , puis plus de 0 fois pas > , puis une fermeture > | Ou (?: (?! ] *>).) + Jeton gourmand tempéré, correspond à n'importe quel caractère si ce qui est directement à droite n'est pas le modèle d'ouverture jusqu'à la fermeture
import re
content = "<abc>d<e><f>ghi<j>test><g>"
result = re.findall(r"<[^<>]*>|(?:(?!<[^<>]*>).)+", content)
print(result)
<[^<>]*>|(?:(?!<[^<>]*>).)+