Дополнительная буква добавляется во время расшифровки
Я строю шифр Vignere в C++, и по какой-то причине после первой команды encrypt/decrypt вводится дополнительный символ, и я озадачен, почему. Вот пример
AAAA, BBBB,1
В качестве вывода мы получаем,
BBBB
После этого мы повторяем операции
AAAA, BBBB,1
Теперь мы получаем это:
? BBBB
То же самое происходит с расшифровкой. Я законно озадачен тем, почему это добавляется, учитывая, что начальное шифрование / дешифрование работает просто отлично
Вот vignere.cpp
#include <iostream>
#include <cstdlib>
#include<algorithm>
std::string encrypt(std::string plaintext, std::string key, int encryptordecrypt){
std::string ciphertext="";
std::string dekey="";
if(key[0]==' '){
key.erase(std::remove(key.begin(),key.end(),' '),key.end()); }
unsigned int keylength=key.length(); /* Gets rid of leading spaces */
for( unsigned int i=0; i<plaintext.length();i++){
if(islower(plaintext[i])){
plaintext[i]=toupper(plaintext[i]);
};
if(islower(key[i%keylength])){
key[i]=toupper(key[i%keylength]);
};
if(encryptordecrypt>0){
if(plaintext[i]==' '){
ciphertext+=' ';
}
else{
div_t ptxtdiv= div(plaintext[i]+key[i%keylength]-65*2,26);
int rem= ptxtdiv.rem;
ciphertext+= char (rem+65);
};
}
else if(encryptordecrypt<0){
if(plaintext[i]==' '){
ciphertext+=' ';
}
else{
dekey+=26-key[i]+65*2;
std::cout<< dekey[i]<<std::endl;
div_t ptxtdiv= div(plaintext[i]+dekey[i%keylength]-65*2,26);
int rem= ptxtdiv.rem;
ciphertext+= char (rem+65);
};
}
};
return ciphertext;
}
А вот и main.cpp
#include <iostream>
#include <cstdlib>
std::string encrypt(std::string plaintext, std::string key,int encryptordecrypt);
int main(){
std::cout << "Please input the message, then the key, separated by a comma, and then after another comma, either 1=encrypt or -1=decrypt" << std::endl;
std::string plaintext,key;
int enorde;
while(std::getline(std::cin,plaintext, ',') && std::getline(std::cin,key,',') && std::cin>>enorde){
std::cout << encrypt(plaintext,key,enorde) << std::endl;
}
return 0;
}
Может ли это быть потому, что
std::string Ciphertext="";
не в цикле?
1 ответ
Это не добавляется - есть больше, чем вы думаете на входе.
Если вы сразу напечатаете то, что прочитали:
while(std::getline(std::cin,plaintext, ',') && std::getline(std::cin,key,',') && std::cin>>enorde){
std::cout << "Plaintext: " << plaintext << std::endl
<< "key: " << key << std::endl
<< "direction: " << enorde << std::endl;
std::cout << encrypt(plaintext,key,enorde) << std::endl;
}
ты увидишь
Plaintext: aaaa
key: bbbb
direction: 1
BBBB
Plaintext:
aaaa
key: bbbb
direction: 1
?BBBB
Обратите внимание, что во втором plaintext
,
Это потому что std::cin>>enorde
оставил разрыв строки во входном буфере, и он поднялся, когда вы читаете следующую запятую в следующей итерации.
Простое исправление заключается в добавлении std::cin.ignore(some_big_number, '\n')
в петле.
Мораль: когда результат удивителен, убедитесь, что он соответствует тому, что вы предполагаете.