2

i am a newbie to python 2.7 , trying to create a simple program, which takes an input string from the user, converts all the characters into their ascii values, adds 2 to all the ascii values and then converts the new values into text. So for example, if the user input is "test" , the output should be "vguv".

This is the code i have written so far :

message = input("enter message to encode")

for ch in message:
     message2 = ord(ch) + 2
     print "\n\n"
     encodedmessage = ""
     for item in message2.split():
            encodedmessage += chr(int(item))

print ("encoded msg in text : "), encodedmessage

It doesnt seem to be working properly, any help would be appreciated. Thanks.

Alex Martelli
  • 854,459
  • 170
  • 1,222
  • 1,395
user417947
  • 21
  • 1
  • 2
  • 3
    Always spend a little time trying to digest errors the interpreter throws at you. This code would return `AttributeError: 'int' object has no attribute 'split'`, and show you the line that didn't work. It fairly directly says that `message2` is an `'int' object` which you probably weren't expecting. If you can't figure it out (some errors can be fairly obscure), *post the error* instead of just saying "it doesn't work". – Nick T Aug 17 '10 at 19:07
  • By the way: Nick T's advice is very sound: take the error from the interpreter and look at what it means. It should also give you a line number and some context, so you know where to look. Make sure each variable is holding that you think it's holding. – rbp Aug 18 '10 at 13:49

3 Answers3

2

message2 = ord(ch) + 2 makes message2 an integer, and so of course you cannot then call split on it -- it's a single int representing a single character, why ever would you want to split it?! Plus, you're resetting encodedmessage to the empty string each time through the loop, so once you've fixed the split weirdness (by simply removing it!) you'll only see the last characted of course; move the encodedmessage = '' to before the loop instead.

Alex Martelli
  • 854,459
  • 170
  • 1,222
  • 1,395
  • It's bad practice to use the += operator on strings in general, isn't it? You're creating a new string each time it's called. Perhaps it would be better to keep a list of characters and then do `''.join(whateverlist)`? – Alex Bliskovsky Aug 17 '10 at 18:21
  • Alex: it is, and I considered this as well. But I think it would confuse the OP, so it's forgiveable on this case. – rbp Aug 17 '10 at 18:23
  • @Alex Bliskovsky: Although its often repeated that `''.join()` is faster than string concatenation, I think with modern releases of Python, that is not necessarily true. In fact, in this microtest, http://paste.ubuntu.com/479529/, `python -mtimeit -s'import test' 'test.add_strings(1000)` takes 201us, while `python -mtimeit -s'import test' 'test.join_strings(1000)` takes 250us per loop. I'd be interested to hear if @Alex Martelli would weigh in on this. – unutbu Aug 17 '10 at 18:34
  • Ah, it looks like @Alex Martelli has already answered this here: http://stackoverflow.com/questions/1349311/python-string-join-is-faster-than-but-whats-wrong-here/1350289#1350289 – unutbu Aug 17 '10 at 18:50
  • @Alex, yep, but I agree with @rbp -- there are clearly deeper problems here, tackling them first seems preferable. – Alex Martelli Aug 17 '10 at 23:37
1

You are mixing up characters and strings. When you loop throught a string (such as "message"), on each iteration you'll get a single character. Also, ord(ch) is an integer, a number, so you can't "split" it.

Also, don't use "input", use "raw_input" instead.

What you want is probably something similar to this:

message = raw_input("enter message to encode: ")
encoded_message = ""
for ch in message:
     encoded_ord = ord(ch) + 2

Here you don't have a new message yet, as the loop gies you one character at a time, so I'm renaming the variable to "encoded_ord", which better describes what it holds.

Now, you can turn this "encoded ord" into an encoded character, and add it to the encoded message:

     encoded_ch = chr(encoded_ord)
     encoded_message += chr(encoded_ch)

print "encoded msg in text:", encodedmessage
rbp
  • 43,594
  • 3
  • 38
  • 31
1

Are you trying to do a rot-13 (or generalized "rot-x") type function?

from string import ascii_uppercase, ascii_lowercase

def rotx(data,rotby):
    total = []
    for char in data:
        if char in ascii_uppercase:
            index = (ascii_uppercase.find(char) + rotby) % 26
            total.append(ascii_uppercase[index])
        elif char in ascii_lowercase:
            index = (ascii_lowercase.find(char) + rotby) % 26
            total.append(ascii_lowercase[index])
        else:
            total.append(char)
    return "".join(total)

Running:

>>> import rotx
>>> rotx.rotx("test",2)
'vguv'
>>> rotx.rotx("IBM-9000",-1)
'HAL-9000'

If you blanket add 2 to ASCII characters, } becomes non-printable, ~ turns into something depending on your character encoding

Nick T
  • 25,754
  • 12
  • 83
  • 121