### Using modulo for a caesar cipher

I'm only a couple of weeks into semester and I have no prior experience so I'm the beginner of the beginners. In fact, the code below represents most of the knowledge I have of C++. Please keep that in mind. I have two problems. First, whenever I input either character 'y' or 'z', the program adds 2 to the ascii assignment instead of the intended 1. I don't know why it occurs only with these characters but works fine for all the others. Second problem is with the non-letter characters between 'Z' and 'a'. The instructor is requiring we use only letters and I don't know how to exclude the ones in between the capitals and non-capitals. Also, I should point out that we are being required to use the modulo operator for this task. I know there's probably other ways to do this. Thanks in advance

 ``1234567891011121314151617181920`` `````` #include #include using namespace std; int main() { const int CRYPT_KEY = 1; char char1; cout << "Enter letter: "; cin >> char1; cout << char1 << endl; int ascii = static_cast(char1) + CRYPT_KEY;; ascii = ((ascii - 65) % 57) + 65; char1 = static_cast(ascii); cout << "Encrypted letter: " << char1; return 0; } ``````
What's up with the mod 57? What does that number come from? I assume it's an attempt to deal with capital lettering?

 whenever I input either character 'y' or 'z', the program adds 2 to the ascii assignment instead of the intended 1. I don't know why it occurs only with these characters but works fine for all the others.

Let's try out the math.

65 == 'a'
120 == 'x' --> 120 - 65 + 1 = 56, 56 % 57 = 56, 56 + 65 = 121 == 'y'
but then...
121 == 'y' --> 121 - 65 + 1 = 57, 57 % 57 = 0, 0 + 65 = 0 == 'A'

The problem is that you incorrectly implementing the modular "wrap-around" logic.
Inputting 'Z' would not work correctly either. 57 isn't going to solve that.

Are you sure you have to make A -> B and a -> b? Usually these types of ciphers just stick with either all caps (or they represent lowercase as the cleartext, and ALL CAPS as the ciphertext). But it's not too big of a deal, you just have to change the offset if it's a capital letter.

Let's just focus on lowercase. That's working in modulo 26.
We want a -> b, but z -> a (wrap back around)

 ``12345678910111213141516171819`` ``````#include #include // islower using namespace std; int main() { const int CRYPT_KEY = 1; char char1; cout << "Enter letter: "; cin >> char1; cout << char1 << endl; int ascii = static_cast(char1) + CRYPT_KEY; ascii = ((ascii - 'a') % 26) + 'a'; char1 = static_cast(ascii); cout << "Encrypted letter: " << char1; return 0; }``````

but now we want to incorporate capital letters as well. Simply change the offset from 'a' to 'A'.

 ``12345678910111213141516171819202122`` ``````#include #include using namespace std; int main() { const int CRYPT_KEY = 1; char char1; cout << "Enter letter: "; cin >> char1; cout << char1 << endl; int ascii = static_cast(char1) + CRYPT_KEY; if (islower(char1)) ascii = ((ascii - 'a') % 26) + 'a'; else ascii = ((ascii - 'A') % 26) + 'A'; char1 = static_cast(ascii); cout << "Encrypted letter: " << char1; return 0; }``````

I'm sure you could do something fancy to eliminate the if statement, but that should do just fine.
Last edited on
The 57 was a typo, not just here on the forum, but that's how it copied over to here. As it turns out that was my problem. Since the first number for character A is 65 and the last number for character z is 122, I subtracted to find the range. It was supposed to be 58. Once I updated it, it worked fine. I wasn't able to spot this because I was doing the math wrong due to my lack of understanding of modulo.

After seeing your math example, it seems like I had the numbers reversed in my head when using modulo. I thought 56 % 57 meant the remainder after dividing 56/57, which yields no remainder. But your example seems to make it 57/56, which makes more sense. Is my thinking correct now?

As for the using only letters part, I got clarification from the instructors. They are fine with using the in between characters. I also would have used if-else statements, but they were adamant about using only knowledge we had at the time of being assigned this work, which was a week ago. I'm pretty sure I could have used if-else in such a way as to avoid modulo altogether.

I would consider this issue resolved. Thanks for you're help.
Topic archived. No new replies allowed.