caesar.c
Here is the reference solution for Problem Set 2, caesar.c
// Encrypt a message using the Caesar cypher, with a user-provided key.
// This is CS50x pset2 caesar.c
//
// Author: david@newtongwc.org
//
// Usage: caesar <secret>
//
// Reads the (new-line-terminated) clear-text message from stdin, writes the
// crypt-text message to stdout.
#include <stdio.h>
#include <ctype.h>
#include <string.h>
#include <cs50.h>
#define true 1
#define false 0
int ArgsAreValid(int argc, string argv[]) {
if (argc != 2) {
printf("Error: You must supply exactly 1 argument to %s\n", argv[0]);
return false;
}
if (atoi(argv[1]) < 0) {
printf("Error: The ceaser secret must be a non-negative integer\n");
return false;
}
return true;
}
int GetSecret(int argc, string argv[]) {
return atoi(argv[1]);
}
// Encrypt a single character by shifting it some number ("secret") of places
// up the alphabet, wrapping around from 'z' to 'a'. Works for both upper- and
// lower-case letters, staying within the same case. Leaves non-alphabetic
// characters unchanged.
char EncryptChar(char clear, int secret) {
char crypt = 0;
if (isupper(clear)) {
crypt = (clear - 'A' + secret) % 26 + 'A';
} else if (islower(clear)) {
crypt = (clear - 'a' + secret) % 26 + 'a';
} else {
crypt = clear;
}
return crypt;
}
// Encrypts a full message, one character at a time, using the provided
// encryption secret.
string Encrypt(string clear_text, int secret) {
string crypt_text = malloc(strlen(clear_text) * sizeof(char));
int num_chars = strlen(clear_text);
for (int i = 0; i < num_chars; ++i) {
crypt_text[i] = EncryptChar(clear_text[i], secret);
}
return crypt_text;
}
int main(int argc, string argv[]) {
if (!ArgsAreValid(argc, argv)) {
return 1;
}
int secret = GetSecret(argc, argv);
string clear_text = GetString();
string crypt_text = Encrypt(clear_text, secret);
printf("%s\n", crypt_text);
free(clear_text);
free(crypt_text);
return 0;
}