USER_8675309
USER_8675309

Reputation: 893

Replacing characters in a string in Python

Working on a simple (very simple, laughably weak) cryptography program for an assignment, and I seem to be running into the same error no matter which way I go about it.

 def cryptofied(text, dic):
    for i, j in dic.items():
            text = text.replace(i, j)
    return text

EDIT: now using def cryptofied(text, dic): ret = "" for p in range(len(text)): ret += dic[text[p]] return ret

And

def encode(codedMsg):
    print(codedMsg, '   Here was your message to be encoded.')
    lock = {'A':'X', 'B':'P', 'C':'M', 'D':'G', 'E':'T', 'F':'D', 'G':'H', 'H':'L', 'I':'Y', 'J':'O', 'K':'N', 'L':'Z', 'M':'B', 'N':'W', 'O':'E', 'P':'A', 'Q':'R', 'R':'K', 'S':'J', 'T':'U', 'U':'F', 'V':'S', 'W':'C', 'X':'I', 'Y':'Q', 'Z':'V'}
    codedMsgTest = cryptofied(codedMsg, lock)
    print(codedMsgTest, 'here is your coded message')

However, when I input, for example, "frank" as the codedMsg, it will spit back at "GKXCC", which is obviously incorrect. From what I can tell, the problem is that it is changing the "K" to an "N", and then changing both instances of "N" into "C". What can I do to eliminate this?

EDIT: So, problem with this code now is that if a character is used that is not in my lock, an error comes back. How can I ignore these characters?

Upvotes: 1

Views: 241

Answers (3)

anirudh
anirudh

Reputation: 4176

You can iterate over the word with indices and then modify them one after the other as shown below:

for i in xrange(len(text)):
    text[i] = dic[text[i]]

but there is a method called maketrans(), which allows you to do exactly this.

import string
s1 = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
s2 = "XPMGTDHLYONZBWEARKJUFSCIQV"
trans = string.maketrans(s1,s2)
strtrans = "THIS IS A SAMPLE PROGRAM FOR MAKETRANS"
outstr = strtrans.translate(trans)
print outstr      # ULYJ YJ X JXBAZT AKEHKXB DEK BXNTUKXWJ

Upvotes: 5

Fabian
Fabian

Reputation: 4348

You can iterate over the string itself:

>>> lock = {'A':'X', 'B':'P', 'C':'M', 'D':'G', 'E':'T', 'F':'D', 'G':'H', 'H':'L', 'I':'Y', 'J':'O', 'K':'N', 'L':'Z', 'M':'B', 'N':'W', 'O':'E', 'P':'A', 'Q':'R', 'R':'K', 'S':'J', 'T':'U', 'U':'F', 'V':'S', 'W':'C', 'X':'I', 'Y':'Q', 'Z':'V'}
>>> text = "FRANK"
>>> encrypted_text = ""
>>> for char in text:
...     encrypted_text += lock.get(char)
... 
>>> encrypted_text
'DKXWN'
>>> 

Upvotes: 0

Pavel
Pavel

Reputation: 7562

this is because text.replace(i, j) operates on all matches of i.

instead of iterating over the dictionary

for i, j in dic.items():
        text = text.replace(i, j)

you need to iterate over the positions in the input word

ret = ""
for p in range(len(text)):
        ret += dic[text[p]]
return ret

Upvotes: 2

Related Questions