помогите пожалуйста понять правильно ли работает код
#include <iostream>
using namespace std;
const int MAX_SIZE = 100; // Максимальный размер массива
// Функция для шифрования/дешифрования массива
void processArray(int arr[], int size, int key, bool encrypt) {
for (int i = 0; i < size; i++) {
// Вычисляем ключ для текущего элемента
int elementKey = (key ^ i) << (i % 3);
// Определяем направление сдвига
bool shiftLeft = (i % 2 == 0);
if (encrypt) {
// Шифрование: XOR -> сдвиг
arr[i] ^= elementKey;
if (shiftLeft) {
arr[i] <<= (i % 3);
} else {
arr[i] >>= (i % 3);
}
} else {
// Дешифрование: обратный сдвиг -> XOR
if (shiftLeft) {
arr[i] >>= (i % 3);
} else {
arr[i] <<= (i % 3);
}
arr[i] ^= elementKey;
}
}
}
// Функция для вывода массива
void printArray(int arr[], int size) {
for (int i = 0; i < size; i++) {
cout << arr[i] << " ";
}
cout << endl;
}
int main() {
setlocale(LC_ALL, "Russian");
int arr[MAX_SIZE];
int size, baseKey;
// Ввод размера массива
cout << "Введите размер массива (не более " << MAX_SIZE << "): ";
cin >> size;
if (size <= 0 || size > MAX_SIZE) {
cout << "Некорректный размер массива!" << endl;
return 1;
}
// Ввод элементов массива
cout << "Введите элементы массива:" << endl;
for (int i = 0; i < size; i++) {
cin >> arr[i];
if (arr[i] < 0 || arr[i] > 1073741823) {
cout << "Ошибка: значение должно быть от 0 до 1073741823" << endl;
return 1;
}
}
// Ввод базового ключа
cout << "Введите базовый ключ: ";
cin >> baseKey;
// Шифрование массива
processArray(arr, size, baseKey, true);
cout << "Зашифрованный массив: ";
printArray(arr, size);
// Дешифрование массива
processArray(arr, size, baseKey, false);
cout << "Расшифрованный массив: ";
printArray(arr, size);
return 0;
}
Ответы (1 шт):
Автор решения: Andrey Tabakov
→ Ссылка
Шифрование некорректно. У вас есть сдвиги битов вправо при шифровании (при shiftLeft == false), возможна потеря битов.
Например число 5 (00000101), если сдвинуть на 1 бит вправо будет числом 00000010, вот этот сдвинутый бит вправо уже не вернуть. Если бы его сдвигали влево было бы 00001010.
Можно либо чуть упростить
void processArray(unsigned int arr[], int size, unsigned int key, bool encrypt) {
for (int i = 0; i < size; ++i) {
// лучше использовать unsigned int, чтобы случайно не словить проблемы с битом знака
unsigned int shift = i % 3;
unsigned int elementKey = (key ^ i) << shift;
if (encrypt) {
// Шифрование: сдвиг влево -> XOR
arr[i] = (arr[i] << shift) ^ elementKey;
} else {
// Дешифрование: XOR -> сдвиг вправо
arr[i] = (arr[i] ^ elementKey) >> shift;
}
}
}
Либо надо поддержать циклические сдвиги. Это когда биты, которые вышли за границы переносятся в начало/конец.
// 0101 >> 1 станет 1010
// Циклический сдвиг вправо на 4 бита:
num = (num >> 4) | (num << (32 - 4));
// Циклический сдвиг влево на 4 бита:
num = (num << 4) | (num >> (32 - 4));