From fe670f3297461e35af294da8ce9432a52b792d84 Mon Sep 17 00:00:00 2001 From: Andras Nagy Date: Mon, 19 Jun 2023 14:52:39 -0700 Subject: [PATCH 1/2] Initial implementation --- config.json | 8 +++ .../rotational-cipher/.docs/instructions.md | 29 ++++++++++ .../rotational-cipher/.meta/config.json | 19 +++++++ .../rotational-cipher/.meta/example.rkt | 18 +++++++ .../rotational-cipher/.meta/tests.toml | 40 ++++++++++++++ .../rotational-cipher-tests.rkt | 53 +++++++++++++++++++ .../rotational-cipher/rotational-cipher.rkt | 6 +++ 7 files changed, 173 insertions(+) create mode 100644 exercises/practice/rotational-cipher/.docs/instructions.md create mode 100644 exercises/practice/rotational-cipher/.meta/config.json create mode 100644 exercises/practice/rotational-cipher/.meta/example.rkt create mode 100644 exercises/practice/rotational-cipher/.meta/tests.toml create mode 100644 exercises/practice/rotational-cipher/rotational-cipher-tests.rkt create mode 100644 exercises/practice/rotational-cipher/rotational-cipher.rkt diff --git a/config.json b/config.json index 22926402..48e2f8eb 100644 --- a/config.json +++ b/config.json @@ -472,6 +472,14 @@ "strings" ] }, + { + "slug": "rotational-cipher", + "name": "Rotational Cipher", + "uuid": "2bdb8cb6-10dc-48aa-b547-7b9f569c0164", + "practices": [], + "prerequisites": [], + "difficulty": 1 + }, { "slug": "darts", "name": "Darts", diff --git a/exercises/practice/rotational-cipher/.docs/instructions.md b/exercises/practice/rotational-cipher/.docs/instructions.md new file mode 100644 index 00000000..4dee51b3 --- /dev/null +++ b/exercises/practice/rotational-cipher/.docs/instructions.md @@ -0,0 +1,29 @@ +# Instructions + +Create an implementation of the rotational cipher, also sometimes called the Caesar cipher. + +The Caesar cipher is a simple shift cipher that relies on transposing all the letters in the alphabet using an integer key between `0` and `26`. +Using a key of `0` or `26` will always yield the same output due to modular arithmetic. +The letter is shifted for as many values as the value of the key. + +The general notation for rotational ciphers is `ROT + `. +The most commonly used rotational cipher is `ROT13`. + +A `ROT13` on the Latin alphabet would be as follows: + +```text +Plain: abcdefghijklmnopqrstuvwxyz +Cipher: nopqrstuvwxyzabcdefghijklm +``` + +It is stronger than the Atbash cipher because it has 27 possible keys, and 25 usable keys. + +Ciphertext is written out in the same formatting as the input including spaces and punctuation. + +## Examples + +- ROT5 `omg` gives `trl` +- ROT0 `c` gives `c` +- ROT26 `Cool` gives `Cool` +- ROT13 `The quick brown fox jumps over the lazy dog.` gives `Gur dhvpx oebja sbk whzcf bire gur ynml qbt.` +- ROT13 `Gur dhvpx oebja sbk whzcf bire gur ynml qbt.` gives `The quick brown fox jumps over the lazy dog.` diff --git a/exercises/practice/rotational-cipher/.meta/config.json b/exercises/practice/rotational-cipher/.meta/config.json new file mode 100644 index 00000000..69ace641 --- /dev/null +++ b/exercises/practice/rotational-cipher/.meta/config.json @@ -0,0 +1,19 @@ +{ + "authors": [ + "BNAndras" + ], + "files": { + "solution": [ + "rotational-cipher.rkt" + ], + "test": [ + "rotational-cipher-test.rkt" + ], + "example": [ + ".meta/example.rkt" + ] + }, + "blurb": "Create an implementation of the rotational cipher, also sometimes called the Caesar cipher.", + "source": "Wikipedia", + "source_url": "https://en.wikipedia.org/wiki/Caesar_cipher" +} diff --git a/exercises/practice/rotational-cipher/.meta/example.rkt b/exercises/practice/rotational-cipher/.meta/example.rkt new file mode 100644 index 00000000..5cb07c4a --- /dev/null +++ b/exercises/practice/rotational-cipher/.meta/example.rkt @@ -0,0 +1,18 @@ +#lang racket + +(provide rotate) + +(define (rotate text key) + (list->string + (map (lambda (char) (rotate-char char key)) + (string->list text)))) + +(define (rotate-char char key) + (cond + [(char-alphabetic? char) + (let* ([alphabet-length 26] + [offset (if (char-upper-case? char) (char->integer #\A) (char->integer #\a))] + [calc-rel-position (lambda () (modulo (+ (- (char->integer char) offset) key) alphabet-length))] + [calc-new-position (lambda () (+ offset (calc-rel-position)))]) + (integer->char (calc-new-position)))] + [else char])) diff --git a/exercises/practice/rotational-cipher/.meta/tests.toml b/exercises/practice/rotational-cipher/.meta/tests.toml new file mode 100644 index 00000000..53441ed2 --- /dev/null +++ b/exercises/practice/rotational-cipher/.meta/tests.toml @@ -0,0 +1,40 @@ +# This is an auto-generated file. +# +# Regenerating this file via `configlet sync` will: +# - Recreate every `description` key/value pair +# - Recreate every `reimplements` key/value pair, where they exist in problem-specifications +# - Remove any `include = true` key/value pair (an omitted `include` key implies inclusion) +# - Preserve any other key/value pair +# +# As user-added comments (using the # character) will be removed when this file +# is regenerated, comments can be added via a `comment` key. + +[74e58a38-e484-43f1-9466-877a7515e10f] +description = "rotate a by 0, same output as input" + +[7ee352c6-e6b0-4930-b903-d09943ecb8f5] +description = "rotate a by 1" + +[edf0a733-4231-4594-a5ee-46a4009ad764] +description = "rotate a by 26, same output as input" + +[e3e82cb9-2a5b-403f-9931-e43213879300] +description = "rotate m by 13" + +[19f9eb78-e2ad-4da4-8fe3-9291d47c1709] +description = "rotate n by 13 with wrap around alphabet" + +[a116aef4-225b-4da9-884f-e8023ca6408a] +description = "rotate capital letters" + +[71b541bb-819c-4dc6-a9c3-132ef9bb737b] +description = "rotate spaces" + +[ef32601d-e9ef-4b29-b2b5-8971392282e6] +description = "rotate numbers" + +[32dd74f6-db2b-41a6-b02c-82eb4f93e549] +description = "rotate punctuation" + +[9fb93fe6-42b0-46e6-9ec1-0bf0a062d8c9] +description = "rotate all letters" diff --git a/exercises/practice/rotational-cipher/rotational-cipher-tests.rkt b/exercises/practice/rotational-cipher/rotational-cipher-tests.rkt new file mode 100644 index 00000000..a973c150 --- /dev/null +++ b/exercises/practice/rotational-cipher/rotational-cipher-tests.rkt @@ -0,0 +1,53 @@ +#lang racket + +(require "rotational-cipher.rkt") + +(module+ test + (require rackunit rackunit/text-ui) + + (define suite + (test-suite + "Rotational cipher tests" + + (test-equal? "rotate a by 0, same output as input" + (rotate "a" 0) + "a") + + (test-equal? "rotate a by 1" + (rotate "a" 1) + "b") + + (test-equal? "rotate a by 26, same output as input" + (rotate "a" 26) + "a") + + + (test-equal? "rotate m by 13" + (rotate "m" 13) + "z") + + (test-equal? "rotate n by 13 with wrap around alphabet" + (rotate "n" 13) + "a") + + (test-equal? "rotate capital letters" + (rotate "OMG" 5) + "TRL") + + (test-equal? "rotate spaces" + (rotate "O M G" 5) + "T R L") + + (test-equal? "rotate numbers" + (rotate "Testing 1 2 3 testing" 4) + "Xiwxmrk 1 2 3 xiwxmrk") + + (test-equal? "rotate punctuation" + (rotate "Let's eat, Grandma!" 21) + "Gzo'n zvo, Bmviyhv!") + + (test-equal? "rotate all letters" + (rotate "The quick brown fox jumps over the lazy dog." 13) + "Gur dhvpx oebja sbk whzcf bire gur ynml qbt."))) + + (run-tests suite)) diff --git a/exercises/practice/rotational-cipher/rotational-cipher.rkt b/exercises/practice/rotational-cipher/rotational-cipher.rkt new file mode 100644 index 00000000..a86b9205 --- /dev/null +++ b/exercises/practice/rotational-cipher/rotational-cipher.rkt @@ -0,0 +1,6 @@ +#lang racket + +(provide rotate) + +(define (rotate text key) + (error "Not implemented yet")) From db37f5c44c52bfed6598a6873a0202c3961916f4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Andr=C3=A1s=20B=20Nagy?= <20251272+BNAndras@users.noreply.github.com> Date: Wed, 30 Aug 2023 11:11:16 -0700 Subject: [PATCH 2/2] Change test name --- .../{rotational-cipher-tests.rkt => rotational-cipher-test.rkt} | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename exercises/practice/rotational-cipher/{rotational-cipher-tests.rkt => rotational-cipher-test.rkt} (100%) diff --git a/exercises/practice/rotational-cipher/rotational-cipher-tests.rkt b/exercises/practice/rotational-cipher/rotational-cipher-test.rkt similarity index 100% rename from exercises/practice/rotational-cipher/rotational-cipher-tests.rkt rename to exercises/practice/rotational-cipher/rotational-cipher-test.rkt