using System.Text;
namespace EncryptionAlgos {
public class CaesarCipher {
public string Text { get; set; } = String.Empty;
public long Key;
public CaesarCipher(long key) {
Key = key % 26;
}
public CaesarCipher(string text, long key) {
if (text == null) throw new ArgumentNullException("text");
if (key < 1) throw new ArgumentOutOfRangeException("key should be a positive integer");
Text = text;
Key = key % 26;
}
public string Encrypt() {
var encryptedText = new StringBuilder();
foreach (char t in Text) {
if (!Char.IsAsciiLetter(t)) {
encryptedText.Append(t);
continue;
}
char offset = Char.IsUpper(t) ? 'A' : 'a';
char c = (char)((t - offset + Key) % 26 + offset);
encryptedText.Append(c);
}
return encryptedText.ToString();
}
public static string Encrypt(string text, int key) {
if (text == null) throw new ArgumentNullException("text");
if (key < 1) throw new ArgumentOutOfRangeException("key should be a positive integer");
key %= 26;
var encryptedText = new StringBuilder();
foreach (char t in text) {
if (!Char.IsAsciiLetter(t)) {
encryptedText.Append(t);
continue;
}
char offset = Char.IsUpper(t) ? 'A' : 'a';
char c = (char)((t - offset + key) % 26 + offset);
encryptedText.Append(c);
}
return encryptedText.ToString();
}
public static string Decrypt(string encryptedText, long key) {
if (encryptedText == null) throw new ArgumentNullException("encryptedText");
if (key < 1) throw new ArgumentOutOfRangeException("key should be a positive integer");
key %= 26;
var decryptedText = new StringBuilder();
foreach (char c in encryptedText) {
if (!Char.IsAsciiLetter(c)) {
decryptedText.Append(c);
continue;
}
char offset = Char.IsUpper(c) ? 'A' : 'a';
char t = (char)((c - offset - key + 26) % 26 + offset);
decryptedText.Append(t);
}
return decryptedText.ToString();
}
public static List<string> Decrypt(string encryptedText) {
if (encryptedText == null) throw new ArgumentNullException("encryptedText");
var list = new List<string>();
for (int key = 1; key <= 25; ++key)
list.Add(Decrypt(encryptedText, key));
return list;
}
}
public class MonoAlphabeticCipher {
public string Text { get; set; }
public string Key { get; set; }
public Dictionary<char, char> dict;
public MonoAlphabeticCipher(string text) {
if (text == null) throw new ArgumentNullException("text");
Text = text;
var key = new StringBuilder();
for (char c = 'a'; c <= 'z'; ++c)
key.Append(c);
for (char c = 'A'; c <= 'Z'; ++c)
key.Append(c);
var rnd = new Random();
for (int i = 0; i < key.Length; ++i) {
int j = rnd.Next(0, key.Length);
(key[i], key[j]) = (key[j], key[i]);
}
dict = new Dictionary<char, char>();
int idx = 0;
for (char c = 'a'; c <= 'z'; ++c)
dict.Add(c, key[idx++]);
for (char c = 'A'; c <= 'Z'; ++c)
dict.Add(c, key[idx++]);
Key = key.ToString();
}
public string Encrypt() {
var encryptedText = new StringBuilder();
foreach (char t in Text) {
if (!Char.IsAsciiLetter(t)) {
encryptedText.Append(t);
continue;
}
encryptedText.Append(dict[t]);
}
return encryptedText.ToString();
}
public static string Encrypt(string text, string key) {
if (text == null) throw new ArgumentNullException("text");
if (key == null) throw new ArgumentNullException("key");
if (!ValidKey(key))
throw new Exception("invalid key");
var d = new Dictionary<char, char>();
int idx = 0;
for (char c = 'a'; c <= 'z'; ++c)
d.Add(c, key[idx++]);
for (char c = 'A'; c <= 'Z'; ++c)
d.Add(c, key[idx++]);
var encryptedText = new StringBuilder();
foreach (char t in text) {
if (!Char.IsAsciiLetter(t)) {
encryptedText.Append(t);
continue;
}
encryptedText.Append(d[t]);
}
return encryptedText.ToString();
}
public static string Decrypt(string encryptedText, string key) {
if (encryptedText == null) throw new ArgumentNullException("encryptedText");
if (key == null) throw new ArgumentNullException("key");
if (!ValidKey(key))
throw new Exception("invalid key");
var d = new Dictionary<char, char>();
int idx = 0;
for (char c = 'a'; c <= 'z'; ++c)
d.Add(key[idx++], c);
for (char c = 'A'; c <= 'Z'; ++c)
d.Add(key[idx++], c);
var decryptedText = new StringBuilder();
foreach (char c in encryptedText) {
if (!Char.IsAsciiLetter(c)) {
decryptedText.Append(c);
continue;
}
decryptedText.Append(d[c]);
}
return decryptedText.ToString();
}
static bool ValidKey(string key) {
if (key.Length != 52) return false;
var st = new HashSet<char>();
foreach (char ch in key)
st.Add(ch);
for (char c = 'a'; c <= 'z'; ++c)
if (!st.Contains(c)) return false;
for (char c = 'A'; c <= 'Z'; ++c)
if (!st.Contains(c)) return false;
foreach (char c in key)
if (!Char.IsAsciiLetter(c)) return false;
return true;
}
}
public class PolyAlphabeticCipher {
public string Text { get; set; }
public string Key { get; set; }
public PolyAlphabeticCipher(string text) {
if (text == null) throw new ArgumentNullException("text");
Text = text.ToUpper();
var rnd = new Random();
var key = new StringBuilder();
for (int i = 0; i < text.Length; ++i) {
char c = (char)('A' + rnd.Next(0, 26));
key.Append(c);
}
Key = key.ToString();
}
public PolyAlphabeticCipher(string text, string key) {
if (text == null) throw new ArgumentNullException("text");
if (String.IsNullOrEmpty(key)) throw new ArgumentException("key cannot be empty");
Text = text.ToUpper();
Key = key.ToUpper();
}
static int ToNumber(char c) => c - 'A';
public string Encrypt() {
var encryptedText = new StringBuilder();
int idx = 0;
foreach (char t in Text) {
if (!Char.IsAsciiLetter(t)) {
encryptedText.Append(t);
continue;
}
char c = (char)((ToNumber(t) + ToNumber(Key[idx++])) % 26 + 'A');
idx %= Key.Length;
encryptedText.Append(c);
}
return encryptedText.ToString();
}
public static string Encrypt(string text, string key) {
if (text == null) throw new ArgumentNullException("text");
if (string.IsNullOrEmpty(key)) throw new ArgumentException("key cannot be empty");
var encryptedText = new StringBuilder();
int idx = 0;
foreach (char t in text) {
if (!Char.IsAsciiLetter(t)) {
encryptedText.Append(t);
continue;
}
char c = (char)((ToNumber(t) + ToNumber(key[idx++])) % 26 + 'A');
idx %= key.Length;
encryptedText.Append(c);
}
return encryptedText.ToString();
}
public static string Decrypt(string encryptedText, string key) {
if (encryptedText == null) throw new ArgumentNullException("encryptedText");
if (string.IsNullOrEmpty(key)) throw new ArgumentException("key cannot be empty");
var decryptedText = new StringBuilder();
int idx = 0;
foreach (char c in encryptedText) {
if (!Char.IsAsciiLetter(c)) {
decryptedText.Append(c);
continue;
}
char t = (char)((ToNumber(c) - ToNumber(key[idx++]) + 26) % 26 + 'A');
idx %= key.Length;
decryptedText.Append(t);
}
return decryptedText.ToString();
}
}
internal class Program {
static void Main(string[] args) {
string s = Console.ReadLine()!;
var cipher = new MonoAlphabeticCipher(s);
Console.WriteLine("Key = " + cipher.Key);
string encryption = cipher.Encrypt();
Console.WriteLine("encrypted text = " + encryption);
Console.WriteLine("decrypted text = " + MonoAlphabeticCipher.Decrypt(encryption, cipher.Key));
}
}
}