web-dev-qa-db-fra.com

Insensible à la casse remplacer

Quelle est la façon la plus simple de remplacer des chaînes en Python sans tenir compte de la casse?

130
Adam Ernst

Le type string ne supporte pas cela. Vous feriez probablement mieux d'utiliser la sous-méthode d'expression régulière avec l'option re.IGNORECASE .

>>> import re
>>> insensitive_hippo = re.compile(re.escape('hippo'), re.IGNORECASE)
>>> insensitive_hippo.sub('giraffe', 'I want a hIPpo for my birthday')
'I want a giraffe for my birthday'
180
Blair Conrad
import re
pattern = re.compile("hello", re.IGNORECASE)
pattern.sub("bye", "hello HeLLo HELLO")
# 'bye bye bye'
69
Unknown

En une seule ligne:

import re
re.sub("(?i)hello","bye", "hello HeLLo HELLO") #'bye bye bye'
re.sub("(?i)he\.llo","bye", "he.llo He.LLo HE.LLO") #'bye bye bye'

Ou utilisez l’argument optionnel "flags":

import re
re.sub("hello", "bye", "hello HeLLo HELLO", flags=re.I) #'bye bye bye'
re.sub("he\.llo", "bye", "he.llo He.LLo HE.LLO", flags=re.I) #'bye bye bye'
35
viebel

En continuant sur la réponse de bFloch, cette fonction ne changera pas une, mais toutes les occurrences d'ancien à nouveau - de manière insensible à la casse. 

def ireplace(old, new, text):
    idx = 0
    while idx < len(text):
        index_l = text.lower().find(old.lower(), idx)
        if index_l == -1:
            return text
        text = text[:index_l] + new + text[index_l + len(old):]
        idx = index_l + len(new) 
    return text
9
rsmoorthy

Comme Blair Conrad dit que string.replace ne supporte pas cela.

Utilisez la regex re.sub, mais souvenez-vous d’échapper d’abord à la chaîne de remplacement. Notez qu'il n'y a pas d'option flags dans 2.6 pour re.sub, vous devrez donc utiliser le modificateur intégré '(?i)' (ou un objet RE, voir la réponse de Blair Conrad). En outre, un autre piège est que le sous-traitant traitera les échappements de barre oblique inversée dans le texte de remplacement, si une chaîne est donnée. Pour éviter cela, on peut plutôt passer dans un lambda.

Voici une fonction:

import re
def ireplace(old, repl, text):
    return re.sub('(?i)'+re.escape(old), lambda m: repl, text)

>>> ireplace('hippo?', 'giraffe!?', 'You want a hiPPO?')
'You want a giraffe!?'
>>> ireplace(r'[binfolder]', r'C:\Temp\bin', r'[BinFolder]\test.exe')
'C:\\Temp\\bin\\test.exe'
2
johv

Cela ne nécessite pas RegularExp

def ireplace(old, new, text):
    """ 
    Replace case insensitive
    Raises ValueError if string not found
    """
    index_l = text.lower().index(old.lower())
    return text[:index_l] + new + text[index_l + len(old):] 
2
bFloch

Cette fonction utilise à la fois les fonctions str.replace() et re.findall(). Il remplacera toutes les occurrences de pattern dans string par repl sans tenir compte de la casse.

def replace_all(pattern, repl, string) -> str:
   occurences = re.findall(pattern, string, re.IGNORECASE)
   for occurence in occurences:
       string = string.replace(occurence, repl)
       return string
1
Nico Bako

je n'avais jamais posté de réponse auparavant et ce fil est vraiment vieux, mais je suis venu avec une autre solution et j'ai pensé que je pourrais obtenir votre réponse, je ne suis pas expérimenté dans la programmation Python, donc s'il y a des inconvénients apparents, veuillez le signaler, car il a bien appris: )

i='I want a hIPpo for my birthday'
key='hippo'
swp='giraffe'

o=(i.lower().split(key))
c=0
p=0
for w in o:
    o[c]=i[p:p+len(w)]
    p=p+len(key+w)
    c+=1
print(swp.join(o))
0
anddan

J'étais en train d'être converti en séquences d'échappement (défilement un peu plus bas), donc j'ai remarqué que re.sub convertit les caractères d'échappement en caractères obliques inversés en séquences d'échappement.

Pour empêcher que j'ai écrit ce qui suit:

Remplacer insensible à la casse.

import re
    def ireplace(findtxt, replacetxt, data):
        return replacetxt.join(  re.compile(findtxt, flags=re.I).split(data)  )

En outre, si vous souhaitez le remplacer par les caractères d'échappement, comme pour les autres réponses ici qui convertissent les caractères spéciaux bashslash en séquences d'échappement, il suffit de décoder votre recherche et/ou de remplacer la chaîne. En Python 3, vous pourriez avoir à faire quelque chose comme .decode ("unicode_escape") # python3

findtxt = findtxt.decode('string_escape') # python2
replacetxt = replacetxt.decode('string_escape') # python2
data = ireplace(findtxt, replacetxt, data)

Testé en Python 2.7.8

J'espère que cela pourra aider.

0
Stan S. - Lee