Possibilité de réponse à une activité proposée par NumWorks
message = "LOI SMPJOSMPQUWOI IGZP WZ OZIOSTLO HO AGZZMQIIMZAOI MTIPBMQPOI BOIWLPMZP HO BMQIGZZOSOZPI LGCQUWOI MNNLQUWOI M HOI GTXOPI HQDOBI OLI UWO LOI OZIOSTLOI SMPJOSMPQUWOI, LOI ZGSTBOI, LOI VGBSOI… SOBAQ KQEQNOHQM !" # Codes ASCII de 'A' à 'Z' alphabet = range(65, 91) def decode(txt): # Stats sur les lettres stats = [] for a in alphabet: stats.append(txt.count(chr(a))) # On garde les 2 meilleurs scores # qui devraient correspondre aux lettres 'E' et 'S' best = sorted(enumerate(stats), key=lambda x:x[1], reverse = True)[:2] # Substitutions probables pour 'E' et 'S' # 0 pour 'A', 1 pour 'B'... x,y = best[0][0], best[1][0] # On cherche les transformations affines a*x+b # qui envoient x vers 4 (lettre 'E') et y vers 18 (lettre 'S') for a in range(27): for b in range(27): if (a * x + b) % 26 == 4 and (a * y + b) % 26 == 18: # Si on trouve une transformation # on traduit le texte en effectuant # la même transformation pour les autres lettres s = '' for c in txt: l = chr(65 + (a * (ord(c)-65) + b) % 26) if ord(c) in alphabet else c s += l # Affichage du résultat print('y={}x+{} mod 26\n{}'.format(a,b,s))
message = "LOI SMPJOSMPQUWOI IGZP WZ OZIOSTLO HO AGZZMQIIMZAOI MTIPBMQPOI BOIWLPMZP HO BMQIGZZOSOZPI LGCQUWOI MNNLQUWOI M HOI GTXOPI HQDOBI OLI UWO LOI OZIOSTLOI SMPJOSMPQUWOI, LOI ZGSTBOI, LOI VGBSOI... SOBAQ KQEQNOHQM !" alphabet = range(65, 91) def decode(txt): stats = [] for a in alphabet: stats.append(txt.count(chr(a))) best = sorted(enumerate(stats), key=lambda x:x[1], reverse = True)[:2] x,y = best[0][0], best[1][0] for a in range(27): for b in range(27): if (a * x + b) % 26 == 4 and (a * y + b) % 26 == 18: s = '' for c in txt: l = chr(65 + (a * (ord(c)-65) + b) % 26) if ord(c) in alphabet else c s += l print('y={}x+{} mod 26\n{}'.format(a,b,s)) decode(message)