Взломать шифр Виженера методом частотного анализа - C#
Формулировка задачи:
Добрый вечер, сообщество. Возникла трудная задача, необходимо взломать шифр Виженера.
Основная проблема в том, что я не могу найти внятную информацию о том как это сделать и хотя бы один законченный пример. Я приведу пример своего кода, здесь я шифрую текст, расшифровываю его для проверки работы алгоритма шифрования, потом получаю длину ключевого слово методом Касиски, но дальше ничего. Может хоть кто-нибудь знает как это сделать?
Листинг программы
- using System;
- using System.Collections.Generic;
- using System.Linq;
- namespace Lab1IT
- {
- public class Lab1Task1
- {
- public List<char> abc = new List<char>();
- public int GetIndex(char c)
- {
- for (int i = 0; i < abc.Count; i++)
- {
- if (abc[i] == c)
- return i;
- }
- return 0;
- }
- public int GetOffeset(char c)
- {
- return GetIndex (c) - GetIndex ('a');
- }
- public void InitABC()
- {
- for (int i = 97; i < 123; i++)
- abc.Add ((char)i);
- // for (int i = 1072; i < 1104; i++)
- // abc.Add ((char)i);
- }
- public void Encrypt (string file, string resultFile, string key)
- {
- string result = "";
- string message = System.IO.File.ReadAllText(file);
- key = PreapareKey (key, message);
- for (int i = 0; i < message.Length; i++)
- {
- if (message [i] != ' ')
- {
- int index = GetIndex (message [i]);
- int res = (index + GetIndex (key [i])) % abc.Count;
- result += abc [res];
- }
- else
- result += ' ';
- }
- System.IO.File.WriteAllText (resultFile,result,System.Text.Encoding.UTF8);
- Console.WriteLine (result);
- }
- public void Decrypt (string file, string resultFile, string key)
- {
- string result = "";
- string message = System.IO.File.ReadAllText(file);
- key = PreapareKey (key, message);
- for (int i = 0; i < message.Length; i++)
- {
- if (message [i] != ' ')
- {
- int index = GetIndex(message[i]);
- int res = (index - GetIndex(key[i]) + abc.Count) % abc.Count;
- result += abc[res];
- }
- else
- result += ' ';
- }
- System.IO.File.WriteAllText (resultFile,result,System.Text.Encoding.UTF8);
- Console.WriteLine (result);
- }
- public string PreapareKey(string key, string message)
- {
- string newKey = "";
- while (newKey.Length < message.Length)
- newKey = newKey + key;
- if (newKey.Length < message.Length)
- newKey.Remove (message.Length);
- return newKey;
- }
- public Lab1Task1()
- {
- InitABC ();
- }
- }
- public class Lab1Task2
- {
- public int lgramsLength = 3;
- public Dictionary <char,double> values = new Dictionary<char, double> ();
- public Lab1Task2()
- {
- values.Add ('a', 0.08167f);
- values.Add ('b', 0.01492f);
- values.Add ('c', 0.02782f);
- values.Add ('d', 0.04253f);
- values.Add ('e', 0.12702f);
- values.Add ('f', 0.02228f);
- values.Add ('g', 0.02015f);
- values.Add ('h', 0.06094f);
- values.Add ('i', 0.06966f);
- values.Add ('j', 0.00153f);
- values.Add ('k', 0.00772f);
- values.Add ('l', 0.04025f);
- values.Add ('m', 0.02406f);
- values.Add ('n', 0.06749f);
- values.Add ('o', 0.07507f);
- values.Add ('p', 0.01929f);
- values.Add ('q', 0.00095f);
- values.Add ('r', 0.05987f);
- values.Add ('s', 0.06327f);
- values.Add ('t', 0.09056f);
- values.Add ('u', 0.02758f);
- values.Add ('v', 0.00978f);
- values.Add ('w', 0.02360f);
- values.Add ('x', 0.00150f);
- values.Add ('y', 0.01974f);
- values.Add ('z', 0.00074f);
- // values.Add ('а', );
- // values.Add ('б', );
- // values.Add ('в', );
- // values.Add ('г', );
- // values.Add ('д', );
- // values.Add ('е', );
- // values.Add ('ж', );
- // values.Add ('з', );
- // values.Add ('и', );
- // values.Add ('к', );
- // values.Add ('л', );
- // values.Add ('м', );
- // values.Add ('н', );
- // values.Add ('о', );
- // values.Add ('п', );
- // values.Add ('р', );
- // values.Add ('с', );
- // values.Add ('т', );
- // values.Add ('у', );
- // values.Add ('ф', );
- // values.Add ('х', );
- // values.Add ('ц', );
- // values.Add ('ч', );
- // values.Add ('ш', );
- // values.Add ('щ', );
- // values.Add ('ъ', );
- // values.Add ('ы', );
- // values.Add ('ь', );
- // values.Add ('э', );
- // values.Add ('ю', );
- // values.Add ('я', );
- }
- int GCD(int a, int b)
- {
- return b == 0 ? a : GCD(b, a % b);
- }
- void GCD(List<int> repeatCount)
- {
- Dictionary<int,int> pairs = new Dictionary<int, int> ();
- Console.WriteLine (repeatCount.Count);
- for (int i = 0; i < repeatCount.Count; i++)
- {
- for (int j = i + 1; j < repeatCount.Count; j++)
- {
- int gc = GCD (repeatCount [i], repeatCount [j]);
- if (gc > 1)
- {
- if (pairs.ContainsKey (gc))
- pairs [gc]++;
- else
- pairs.Add (gc, 1);
- }
- }
- }
- var sortDict = pairs.OrderByDescending (x => x.Value).Take(5);
- foreach (var s in sortDict)
- {
- if(s.Value>0)
- {
- Console.Write (s.Key + " ");
- }
- }
- Console.WriteLine ();
- }
- public void SearchLGrams(string file)
- {
- string message = System.IO.File.ReadAllText(file);
- List<int> repeats = new List<int>();
- for (int i = 0; i < message.Length - lgramsLength; i++)
- {
- string lgram1 = message.Substring(i,lgramsLength);
- for (int j = i+1; j < message.Length - lgramsLength; j++)
- {
- string lgram2 = message.Substring(j,lgramsLength);
- if (lgram1.Equals(lgram2))
- {
- repeats.Add (j - i);
- }
- }
- }
- GCD (repeats);
- string text = message.Replace(" ", string.Empty).ToLower();
- double symbolsCount = text.Length;
- SortedDictionary< char, int > dict = new SortedDictionary<char, int>();
- for (int i = 0; i < text.Length; i++)
- if (dict.ContainsKey(text[i]))
- dict[text[i]]++;
- else
- dict.Add(text[i], 1);
- var sortDict = dict.OrderByDescending(x => x.Value);
- Dictionary<char,double> resultedValues = new Dictionary<char, double> ();
- foreach (KeyValuePair< char, int > kvp in sortDict)
- {
- double val = System.Math.Round((double)kvp.Value/symbolsCount,5);
- resultedValues.Add(kvp.Key,val);
- Console.WriteLine ("Символ: {0}, встречается {1} раз. Частота {2}. Дано {3}", kvp.Key,
- kvp.Value,val,System.Math.Round((double)values[kvp.Key],5));
- }
- }
- }
- class MainClass
- {
- public static void Main (string[] args)
- {
- Lab1Task1 lab1Task1 = new Lab1Task1 ();
- lab1Task1.Encrypt ("/Users/Alexander/Projects/Lab1IT/Lab1IT/files/code.txt", "/Users/Alexander/Projects/Lab1IT/Lab1IT/files/encoded.txt", "abcdefg");
- lab1Task1.Decrypt ("/Users/Alexander/Projects/Lab1IT/Lab1IT/files/encoded.txt", "/Users/Alexander/Projects/Lab1IT/Lab1IT/files/decoded.txt", "abcdefg");
- Lab1Task2 lab1Task2 = new Lab1Task2 ();
- lab1Task2.SearchLGrams ("/Users/Alexander/Projects/Lab1IT/Lab1IT/files/encoded.txt");
- }
- }
- }
Решение задачи: «Взломать шифр Виженера методом частотного анализа»
textual
Листинг программы
- for (int j = 0; j < (message.Length / keyLength)+1; j++)
- if (dict.ContainsKey(strings[j,i]))
- dict[strings[j,i]]++;
- else
- dict.Add(strings[j,i], 1);
ИИ поможет Вам:
- решить любую задачу по программированию
- объяснить код
- расставить комментарии в коде
- и т.д