2017-03-17 4 views
1

私はVigenere暗号を作ろうとしています。メッセージを暗号化しようとすると、次のエラーが発生します。Python Vigenereタプルエラー

cipherCharIndexValue = baseAlphabet.index(keyList[keyIncrement]) + baseAlphabet.index(plainTextChar) 
ValueError: tuple.index(x): x not in tuple 

どのようなエラーが発生しているのかわかりません。

baseAlphabet = ('a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 
'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z') 

plainText = input("Please enter the plain text") 
key = input("Please enter the key word") 
keyList = [] 
keyLength = 0 
while keyLength < len(plainText): 
    #Adds the users entered key into a list character by character. 
    #Also makes the key the same length as plainText 
    for char in key: 
     if keyLength < len(plainText): 
      keyList.append(str(char)) 
      keyLength = keyLength + 1 

#The variable each processed letter is appended to 
completeCipherText = [] 
#This is the value used to temporaily store the ciphertext character during the iteration 
cipherCharIndexValue = 0 
keyIncrement = 0 

#iterates through the plain text 
for plainTextChar in plainText: 
     #Adds the base alphabets index value of the key and the plain text char 
     cipherCharIndexValue = baseAlphabet.index(keyList[keyIncrement]) + baseAlphabet.index(plainTextChar) 
     while cipherCharIndexValue > 25: 
      #makes the addition value under 26 as to not go out of range of base alphabet tuple 
      cipherCharIndexValue = cipherCharIndexValue - 26 
     #appends the ciphertext character to the completeCipherText variable. 
     #The character is the index of the key + index of the  plainTextChar from baseAlphabet 
     completeCipherText.append(baseAlphabet[cipherCharIndexValue]) 
     #Moves onto the next key 
     keyIncrement = keyIncrement + 1 
print ('').join(completeCipherText)#Makes the result a strings for printing to the console. 
+1

その行を一つのスペースでインデントした後、 'NameError:name 'baseAlphabet' not defined'を取得しました。あなたの問題を実際に示す[mcve]を投稿してください。 – Kevin

+0

'keyList [keyIncrement]または' plainTextChar'は 'baseAlphabet'にありません。どの値が正確に機能していないかを調べるには、トラブルシューティングを行う必要があります。 – glibdud

+1

コードを編集していただきありがとうございます。それは今私のために走る。 Python 2を使って実行し、最初のプロンプトに '' foo "'を、2番目のプロンプトに '' bar "'を入力すると、クラッシュせずに実行され、 'gof'が出力されます。あなたのプログラムをクラッシュさせるために入力した入力内容を記述してください。 – Kevin

答えて

0

baseAlphabetにない文字のインデックスを取得しようとすると、エラーValueError: tuple.index(x): x not in tupleが返されます。したがって、keyにはそのような文字のみが含まれている必要があります。plainTextのエンコードでは、「不良」文字のエンコードを避け、completeCipherTextリストにそのままコピーするか、有効なbaseAlphabet文字に変換してください。

伝統的な暗号化では、すべてのスペースと句読点を別の文字に変換するのが一般的でした(例:'x'または'.')。私は'.'baseAlphabetに追加し、小さな機能fix_stringを書いてその操作を実行することにしました。 fix_stringは、すべての文字が小文字であることも保証します。

私はまた、あなたのコードを少し簡略化しました。

baseAlphabetはタプルである必要はありません。文字列を使うことができます。あなたが場合でも、あなただけの、tupleコンストラクタに文字列を渡すことができ、フルでそれを書く必要はありません、単一の文字の組を使用するなど

tuple("some string") 
我々は、一般的には必要ありません

リストや文字列などのコレクションの長さを追跡します。組み込みのコレクションはすべて独自の長さを追跡し、len()関数で効率的にその長さにアクセスできます。

keyIncrementは必要ありません。代わりに、zip関数を使用して、keyListplainTextの文字を並列にループすることができます。

ループを使用してkeyとplainTextインデックスの合計が適切な範囲になるようにする代わりに、%モジュラス演算子を使用できます。

from __future__ import print_function 

baseAlphabet = 'abcdefghijklmnopqrstuvwxyz.' 

# Process s so that it only contains chars in baseAlphabet 
def fix_string(s): 
    # Convert to lower case 
    s = s.lower() 
    # Convert "other" chars to dot 
    a = [ch if ch in baseAlphabet else '.' for ch in s] 
    return ''.join(a) 

# Vignere cipher 
# mode = 1 to encode, -1 to decode 
def vignere(plainText, key, mode): 
    keyList = [] 
    while len(keyList) < len(plainText): 
     # Adds the key into a list character by character. 
     # Also makes the key the same length as plainText 
     for char in key: 
      if len(keyList) < len(plainText): 
       keyList.append(str(char)) 

    # The variable each processed letter is appended to 
    completeCipherText = [] 

    # iterates through the plain text 
    for keyChar, plainTextChar in zip(keyList, plainText): 
     # Adds the base alphabet's index value of the plain text char and the key char 
     cipherCharIndexValue = baseAlphabet.index(plainTextChar) 
     cipherCharIndexValue += mode * baseAlphabet.index(keyChar) 
     # makes the addition value in range(len(baseAlphabet)) 
     cipherCharIndexValue = cipherCharIndexValue % len(baseAlphabet) 

     # appends the ciphertext character to the completeCipherText variable. 
     # The character is the index of the key + index of the plainTextChar from baseAlphabet 
     completeCipherText.append(baseAlphabet[cipherCharIndexValue]) 

    # Makes the result a string 
    return ''.join(completeCipherText) 

# Test 

# plainText = raw_input("Please enter the plain text") 
# key = raw_input("Please enter the key word") 

plainText = 'This, is a test string!' 
key = 'the key' 

# Process plainText and key so that they only contain chars in baseAlphabet 
plainText = fix_string(plainText) 
key = fix_string(key) 

ciphertext = vignere(plainText, key, 1) 
print(ciphertext) 

decoded = vignere(ciphertext, key, -1) 
print(decoded) 

ループ、私はライン28上IndentationErrorを得ながら、私はあなたのコードを実行しようとしたとする非インデントすべてをバックアップした後、2行目にIndentationErrorを持って、最初を含む出力

lomrjdfkgezciplgwsamkzg 
this..is.a.test.string. 
1

あなたがpython2.xを使用している、あなたはむしろinputよりraw_input使用すべきであると思われます。

あなたの入力文字列にそこにいる空白や句読点場合は、あなたのコードがクラッシュしますので、私はあなたがindexメソッドを使用する前にkeyList[keyIncrement]が、それはこのタプルではない場合、あなたはこれを取得します、baseAlphabetであることを確認してください示唆エラー:

ValueError: tuple.index(x): x not in tuple 

if keyList[keyIncrement] in keyList: 
    cipherCharIndexValue = baseAlphabet.index(keyList[keyIncrement]) + baseAlphabet.index(plainTextChar) 

try/catchを使用して、コードをデバッグするために例外をキャッチすることができます。

これが役に立ちます。

関連する問題