La forma más eficiente de reemplazar varios caracteres en una cadena

Digamos que hay una cadena de cualquier longitud, y solo contiene las letras A a D:

s1 = 'ACDCADBCDBABDCBDAACDCADCDAB' 

¿Cuál es la forma más eficiente / rápida de reemplazar cada ‘B’ con una ‘C’ y cada ‘C’ con una ‘B’.

Aquí está lo que estoy haciendo ahora:

 replacedString = '' for i in s1: if i == 'B': replacedString += 'C' elif i == 'C': replacedString += 'B' else: replacedString += i 

Esto funciona pero obviamente no es muy elegante. El problema es que estoy tratando con cadenas que pueden tener miles de millones de caracteres, por lo que necesito una mejor solución.

No puedo pensar en una manera de hacer esto con el método .replace (). Esto sugiere que tal vez una expresión regular es el camino a seguir. ¿Es eso aplicable aquí también? Si es así, ¿cuál es una expresión regular adecuada? ¿Hay una manera aún más rápida?

Gracias.

Aparte del método str.translate , puede simplemente construir un dict de traducción y ejecutarlo usted mismo.

 s1 = 'ACDCADBCDBABDCBDAACDCADCDAB' def str_translate_method(s1): try: translationdict = str.maketrans("BC","CB") except AttributeError: # python2 import string translationdict = string.maketrans("BC","CB") result = s1.translate(translationdict) return result def dict_method(s1): from, to = "BC", "CB" translationdict = dict(zip(from, to)) result = ' '.join([translationdict.get(c, c) for c in s1]) return result 

Quería mostrarte los efectos de una traducción incorrecta. Supongamos que tenemos una secuencia de ADN como la cadena y queremos traducirla a la cadena de ARN. Un método utiliza la sustitución incorrecta, mientras que el otro utiliza la concatenación de cadenas.

 string = 'GGGCCCGCGCCCGGG' # DNA string ready for transcription 

Reemplazo

El problema con el reemplazo es que las letras ya reemplazadas serán reemplazadas en una iteración futura. Por ejemplo, puede ver que una vez que haya terminado, tendrá una cadena de la misma letra en lugar de una inversión completa.

 string = 'GGGCCCGCGCCCGGG' coding = {'A': 'U', 'T': 'A', 'G': 'C', 'C': 'G'} for k, v in coding.items(): string = string.replace(k, v) print string 

Concatenación

En su lugar, utilice la concatenación de cadenas con una cadena diferente. Como resultado, puede conservar la cadena original sin reemplazarla incorrectamente. Por supuesto, puede utilizar una traducción de cadena, pero tiendo a preferir los diccionarios porque, por definición, asignan valores.

 string = 'GGGCCCGCGCCCGGG' coding = {'A': 'U', 'T': 'A', 'G': 'C', 'C': 'G'} answer = '' for char in string: answer += coding[char] print answer 

Usando expresiones regulares, esto maneja la sensibilidad a las mayúsculas y minúsculas, por ejemplo, si el alfabeto que debe reemplazarse en la cadena está en minúsculas, entonces lo reemplazará con un carácter de reemplazo en minúscula y en mayúsculas:

 import re chars_map = {'b': 'c', 'c': 'b'} # build a dictionary of replacement characters in lowercase def rep(match): char = match.group(0) replacement = chars_map[char.lower()] return replacement if char.islower() else replacement.upper() s = 'AbC' print re.sub('(?i)%s' % '|'.join(chars_map.keys()), rep, s) # 'AcB'