Фон
Одноразовый блокнот - это форма шифрования, которую при правильном использовании оказалось невозможно взломать.
Шифрование выполняется путем взятия открытого текста (состоящего только из букв AZ) и генерирования случайной строки одинаковой длины (также только буквы). Эта строка действует как ключ. Каждый символ в текстовом виде затем соединяется с соответствующим символом в ключе. Зашифрованный текст вычисляется следующим образом: для каждой пары оба символа преобразуются в числа (A = 0, B = 1, ... Z = 25). Два числа добавляются по модулю 26. Это число превращается обратно в символ.
Расшифровка с точностью до наоборот. Символы в зашифрованном тексте и ключе соединены в пары и преобразованы в числа. Затем ключ вычитается из зашифрованного текста по модулю 26, и результат преобразуется обратно в символ AZ.
Соревнование
Ваша задача - написать самую короткую из возможных программ, которая может как зашифровать, так и расшифровать одноразовый блокнот.
В первой строке ввода (в STDIN) будет либо слово «ENCRYPT», либо слово «DECRYPT».
Если слово зашифровано, то следующая строка будет открытым текстом. Ваша программа должна вывести две строки (в STDOUT), первая - это ключ, а вторая - зашифрованный текст.
Если слово расшифровано, ваша программа получит еще две строки ввода. Первая строка будет ключом, а вторая строка будет зашифрованным текстом. Ваша программа должна вывести одну строку, которая будет открытым текстом, который был расшифрован.
Открытый текст, зашифрованный текст и ключ всегда должны состоять из заглавных букв AZ. Они всегда будут одной строкой и не будут содержать пробелов.
Ключ всегда должен быть случайным. Никакие его большие части не должны повторяться между прогонами, и не должно быть никаких шаблонов, которые можно найти в тексте.
Два простых примера:
ENCRYPT
HAPPYBIRTHDAY
>ABKJAQLRJESMG
>HBZYYRTICLVME
DECRYPT
ABKJAQLRJESMG
HBZYYRTICLVME
>HAPPYBIRTHDAY
>
Представляет , какие линии вывода, так что вы не должны печатать этот символ в качестве вывода.
источник
/dev/random
,haveged
), зашифруйте, записав ордера в байтах, и расшифруйте, записав их в ключе. gist.github.com/5078264 ключ или случайность могут быть прочитаны из стандартного ввода, сообщение или зашифрованный текст может быть аргумент имени файла./dev/hwrng
, вместо использования псевдослучайного (что технически делает егоОтветы:
GolfScript, 53 символа
Это задача, для которой GolfScript кажется идеально подходящим.
Для краткости кода я использую один и тот же код как для шифрования, так и для дешифрования: для дешифрования я вычитаю ключ из зашифрованного текста, а для шифрования сначала генерирую случайный зашифрованный текст, а затем вычитаю из него открытый текст. Несмотря на это, дополнительный код для реализации режима шифрования занимает чуть более половины длины программы.
Де-гольф версия с комментариями:
источник
Рубин (
200185)образец работает + туалет:
источник
s[k=(p=f).map{rand 26}],r[k,p,:-]
должно быть написаноs[k=f.map{rand 26}],r[k,$_,:-]
$_
и последняя прочитанная строкаgets
.f
также делает.scan(/./).map{|b|b.ord-65}
после прочтения строки.Хаскель, 203 персонажа
Пример:
источник
Perl,
220171 символовПробный прогон:
Примечание: по крайней мере, когда я запускаю его, «Нажмите любую клавишу для продолжения ...» добавляется в конец последнего вывода. Я надеюсь, что это нормально, потому что это не часть программы. Если нет, я могу сделать так, чтобы он появился на следующей строке.
Это моя первая настоящая программа на Perl и мой первый в мире гольф, поэтому я буду очень признателен за советы. Кроме того, я нашел
/(.)/g
в Интернете, но я понятия не имею, как это работает (это регулярное выражение? Я еще не изучил их). Может кто-нибудь объяснить это мне?РЕДАКТИРОВАТЬ: Спасибо Ilmari Karonen за помощь в регулярных выражениях, я использовал мои новые знания, чтобы сохранить 7 символов!
Расширенная, слегка читаемая версия:
источник
/(.)/g
это регулярное выражение. Вы определенно захотите узнать их, если собираетесь играть в гольф Perl. perldoc.perl.org/perlre.html неплохая отправная точка .Питон -
304295Я считаю, что это точно соответствует спецификациям
(в том числе иОн не проверяет ввод, поэтому я думаю, что он будет просто выводить мусор, если вы дадите ему символы вне'>'
в начале входных приглашений).[A-Z]
. Он также проверяет только первую букву команды ввода. Все, что начинается с,D
приведет к расшифровке, а все остальное приведет к шифрованию.источник
>
, я просто использовал его, чтобы продемонстрировать, какие строки были выведены. Вам не нужно реализовывать это.C ++ -
220241 символов, 4 строкиРедактировать 1 - Стандартная библиотека MSVS, кажется, включает в себя много ненужных файлов, что означало, что в ios были все необходимые мне включения, но это не работало с другими компиляторами. Изменены ios для фактических файлов, которые необходимые функции появляются в cstdlib и cstdio. Спасибо Ильмари Каронен за то, что указал на это.
источник
g++ otp.cpp
говоритotp.cpp: In function ‘int main()’: otp.cpp:3: error: ‘scanf’ was not declared in this scope otp.cpp:3: error: ‘rand’ was not declared in this scope otp.cpp:3: error: ‘puts’ was not declared in this scope otp.cpp:3: error: ‘puts’ was not declared in this scope
Python - 270
Пример вывода:
Количество символов:
источник
J: 94 байта
Весь необходимый пробел засчитан.
Комментируемая версия:
источник
C # (
445416)Забыли про агрегат. Отрежь немного.
Несколько в гольф:
}
Golfed:
источник
C (159 + 11 для флагов компилятора)
Golfed:
Ungolfed:
Компилировать с
-Dg=gets(s)
.Пример:
источник
JavaScript 239
Использование:
источник
Рубин -
184179177 символовЗапустите это так:
$ ruby pad-lock.rb
Вот незагрязненная версия, если кому-то интересно (хотя она не совсем в курсе игры в гольф)
источник