RC4算法的实现
c++ 宽字节版本
RC4Enc.h
#pragma once #include <iostream> #include <fstream> #include <vector> #include <string> #include <array> #include <random> //RC4加密类 class RC4Enc { public: //KeyLen:密钥长度,取值范围1~256,大于该长度则会取余;小于则会取1;256的倍数则取256 RC4Enc(int KeyLen); /* * 由明文产生密文 * plain_text:明文文件路径 * key_stream:密钥流文件路径 * cipher_text:密文文件路径 * 返回值:失败返回-1,成功返回0 */ int encryption(const std::wstring& plain_text, const std::wstring& key_stream, const std::wstring& cipher_text); private: //密钥的最大长度 const unsigned short MAX_KeyLen{ 256 }; //状态向量,共256个字符 std::array<wchar_t, 256>S{ 0 }; //临时向量,共256个字符 std::array<wchar_t, 256>Temp{ 0 }; //密钥长度,取值范围1~256 unsigned short KeyLen; //可变长度密钥 std::vector<wchar_t>Variable_Length_Key; //密钥流 std::vector<wchar_t>Key_Stream; // 非确定性生成器 std::random_device rd; // 将随机数种子传递过去,然后使用gen()生成随机数 std::mt19937 gen{this->rd()}; //设置随机数范围 //std::uniform_int_distribution<> dist(1,256); protected: /* 初始化状态向量S和临时向量T,供keyStream_func方法调用 用连续的值初始化数组 */ void initial_func(); /* * 排列状态向量S,供keyStream_func方法调用 * 把数组的值打乱排序 */ void range_S_func(); /* * 生成密钥流 * Len:明文为的长度 */ void keyStream_func(unsigned Len); };
RC4Enc.cpp
#include "RC4Enc.h" RC4Enc::RC4Enc(int KeyLen) { if (KeyLen > 0) { this->KeyLen = (KeyLen % this->MAX_KeyLen) == 0 ? this->MAX_KeyLen : KeyLen % this->MAX_KeyLen; } else { this->KeyLen = 1; } for (unsigned short i{},temp; i < this->KeyLen; i++) { temp = this->gen()% this->MAX_KeyLen; this->Variable_Length_Key.push_back(static_cast<wchar_t>(temp)); } } void RC4Enc::initial_func() { for (unsigned i{}; i < this->MAX_KeyLen; i++) { this->S[i] = i; this->Temp[i] = this->Variable_Length_Key[i%this->KeyLen]; } } void RC4Enc::range_S_func() { unsigned int j{}; for (unsigned short i{}; i < this->MAX_KeyLen; i++) { j = (j + this->S[i] + this->Temp[i]) % this->MAX_KeyLen; this->S[i] += this->S[j]; this->S[j] = this->S[i] - this->S[j]; this->S[i] -= this->S[j]; } } int RC4Enc::encryption(const std::wstring& plain_text, const std::wstring&key_stream, const std::wstring&cipher_text) { std::wifstream w_in; std::wofstream w_out,w_out_key_stream; w_in.open(plain_text); //以字符模式读取 if (!w_in) { std::wcout << L"没有被创建\n"; return -1; } //获取输入流的长度 w_in.seekg(0, std::ios::end); const int FileLen = static_cast<int>(w_in.tellg()); w_in.seekg(0, std::ios::beg); //生成密钥流 this->keyStream_func(FileLen); //明文内容读取入bits中 wchar_t* bits = new wchar_t[FileLen] {}; w_in.read(bits, FileLen); w_in.close(); w_out.open(cipher_text, std::ios::binary); //以二进制模式写入 //将明文按照字符依次与密钥流亦或输出到密文文件中 wchar_t temp_wchar{}; for (int i{}; i < FileLen; i++) { //std::cout << std::hex << bits[i]; //std::cout << '^'; //std::cout << std::hex << this->Variable_Length_Key[i]; //std::cout << "==>"; //std::cout << std::hex << (bits[i] ^ this->Variable_Length_Key[i]); //std::cout << std::endl; temp_wchar = bits[i] ^ this->Variable_Length_Key[i]; w_out << temp_wchar; } w_out.close(); //秘钥流写入到文件 w_out_key_stream.open(key_stream, std::ios::binary); //以二进制模式写入 for (int i{}; i < FileLen; i++) { temp_wchar = this->Variable_Length_Key[i]; w_out_key_stream << temp_wchar; } w_out_key_stream.close(); return 0; } void RC4Enc::keyStream_func(unsigned Len) { this->initial_func(); //用连续的值初始化数组 this->range_S_func(); //把数组的值打乱排序 unsigned i{}, j{}, t{}; while (Len--) { i = (i + 1) % this->MAX_KeyLen; j = (j + this->S[i]) % this->MAX_KeyLen; this->S[i] += this->S[j]; this->S[j] = this->S[i] - this->S[j]; this->S[i] -= this->S[j]; t = (this->S[i] + this->S[j]) % this->MAX_KeyLen; this->Variable_Length_Key.push_back(this->S[t]); } }
RC4Dec.h
#pragma once #include <iostream> #include <vector> #include <string> #include <array> #include <fstream> #include <random> /*RC4解密类*/ class RC4Dec { public: /* * key_stream:密钥流文件路径 * cipher_text:密文文件路径 */ RC4Dec(const std::wstring& key_stream, const std::wstring& cipher_text); /*解密方法 * res:保存解密后的明文的文件路径 */ void decryption(const std::wstring&res); private: std::wstring cipherText, keyStream; };
RC4Dec.cpp
#include "RC4Dec.h" void RC4Dec::decryption(const std::wstring& res) { std::wifstream w_in_key_stream, w_in_cipher_text; std::wofstream w_out; w_in_key_stream.open(this->keyStream, std::ios::binary); //以二进制模式读取 w_in_cipher_text.open(this->cipherText, std::ios::binary); //以二进制模式读取 //计算密文长度 w_in_cipher_text.seekg(0, std::ios::end); const unsigned FileLen = static_cast<unsigned>(w_in_cipher_text.tellg()); w_in_cipher_text.seekg(0, std::ios::beg); //读入密钥流 wchar_t* bitKey = new wchar_t[FileLen] {0}; w_in_key_stream.read(bitKey, FileLen); w_in_key_stream.close(); //读取密文 wchar_t *bitCip = new wchar_t[FileLen]{0}; w_in_cipher_text.read(bitCip, FileLen); w_in_cipher_text.close(); //解密后结果输出到解密文件中 w_out.open(res); //以字符模式写入 wchar_t temp_char{}; std::wstring Text; for (unsigned i{}; i < FileLen; i++) { temp_char = (bitKey[i] ^ bitCip[i]); //std::cout << std::hex << bitKey[i]; //std::cout << '^'; //std::cout << std::hex << bitCip[i]; //std::cout << "==>"; //std::cout << std::hex << static_cast<unsigned>(temp_char); //std::cout << std::endl; if (temp_char) { //不将\0字符写入到文件中 Text += bitKey[i] ^ bitCip[i]; } } w_out << Text; w_out.close(); } RC4Dec::RC4Dec(const std::wstring& key_stream, const std::wstring& cipher_text) { cipherText = cipher_text; keyStream = key_stream; }
调用
#include <iostream> #include "RC4Dec.h" #include "RC4Enc.h" int main() { RC4Enc rc4enc(16); if (rc4enc.encryption(L"明文.txt", L"秘钥流.txt", L"密文.txt")) { std::cout << "RC4 加密失败!" << std::endl; return -1; } std::cout << "RC4 加密成功!" << std::endl; RC4Dec rc4dec(L"秘钥流.txt", L"密文.txt"); rc4dec.decryption(L"解密文件.txt"); std::cout << "RC4 解密成功!" << std::endl; }
分类:
C++
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· DeepSeek 开源周回顾「GitHub 热点速览」
· 物流快递公司核心技术能力-地址解析分单基础技术分享
· .NET 10首个预览版发布:重大改进与新特性概览!
· AI与.NET技术实操系列(二):开始使用ML.NET
· 单线程的Redis速度为什么快?