经验首页 前端设计 程序设计 Java相关 移动开发 数据库/运维 软件/图像 大数据/云计算 其他经验
当前位置:技术经验 » 程序设计 » C++ » 查看文章
计算机网络中的检验和(checksum)(包括计算文件的检验和附有c++代码) - Lxx-123
来源:cnblogs  作者:Lxx-123  时间:2024/7/22 10:22:40  对本文有异议

介绍:
检验和(checksum),在数据处理和数据通信领域中,用于校验目的地一组数据项的和。它通常是以十六进制为数制表示的形式。如果校验和的数值超过十六进制的FF,也就是255. 就要求其补码作为校验和。通常用来在通信中,尤其是远距离通信中保证数据的完整性和准确性。(此引用了检验和的百度百科)

用处:
在计算机网络中的网络层、运输层的IP协议、TCP协议、UDP协议等高层协议,在报文中存在一个校验和的字段,这个字段的作用是:验证报文在传输过程中是否被改动,如果接收方检测到检验和有差错,则TCP段会被直接丢弃。如下图在IP报文中占4字节。

原理:
把要发送的数据看成 16 比特的二进制整数序列,并计算他们的和。若数据字节长度为奇数,则在数据尾部补一个字节的 0 以凑成偶数。

例子:
16 位效验和计算,下图表明一个小的字符串的 16 位效验和的计算。为了计算效验和,发送计算机把每对字符当成 16 位整数处理并计算效验和。如果效验和大于 16 位,那么把进位一起加到最后的效验和中。

主要思想为:
1.打开文件,用一个字符串存下里面内容
2.首先判断字符串长度是否为奇数,若为奇数,后面补一个“0”
3.将字符串里面的字符进行读取,并转化成ASCII码对应。每次读取两个字符,也就是每两个为一组。
4.由于字符要化为十六进制后拼接,那么两位里面的前一位将乘于16的平方(256)
5.每一组的十进制数相加
6.先将相加得到的化为2进制存放在int里面,再进行处理,int型里面有32位,我们分为前16位和后16位,对于溢出的在进行处理

而这是现在网上大多数的做法,我现在只是为了更直观,在4、5、6步进行修改
4.由于字符要化为十六进制后拼接,那么两位里面的前一位将乘于16的平方(256),转化成16进制
5.每一组的16进制数相加
6.相加时,超过了0xFFFF(16位最大值),则进行溢出处理。

c++代码

  1. #include <vector>
  2. #include <sstream>
  3. #include <iomanip>
  4. #include <fstream>
  5. using namespace std;
  6. string to_hex(int value) {
  7. stringstream ss;
  8. ss << hex << value;
  9. return ss.str();
  10. }
  11. string add_hex(string hex1, string hex2) {
  12. int num1, num2;
  13. stringstream ss;
  14. ss << hex << hex1;
  15. ss >> num1;
  16. ss.clear();
  17. ss << hex << hex2;
  18. ss >> num2;
  19. int sum = num1 + num2;
  20. if (sum > 0xFFFF) {
  21. sum = (sum & 0xFFFF) + 1; // Add carry to the sum
  22. }
  23. stringstream result;
  24. result << hex << setw(4) << setfill('0') << sum;
  25. return result.str();
  26. }
  27. string check(string filename) {
  28. ifstream file(filename);
  29. if (!file.is_open()) {
  30. cout << "无法打开文件" << endl;
  31. exit(0);
  32. }
  33. string chuang;
  34. getline(file, chuang);
  35. if (chuang.size() % 2 == 1) {
  36. chuang += "0";
  37. }
  38. cout << "得到字符串为 " << chuang << endl;
  39. vector<int> num;
  40. for (int i = 0; i < chuang.size(); i += 2) {
  41. int value = 0;
  42. value = (int(chuang[i]) * 256) + int(chuang[i + 1]); // Convert 2 characters to int
  43. num.push_back(value);
  44. }
  45. string hexchuang;
  46. string sum = "0000"; // Initialize sum as "0000"
  47. for (int i = 0; i < num.size(); i++) {
  48. int value = num[i];
  49. sum = add_hex(sum, to_hex(value));
  50. hexchuang += to_hex(value);
  51. cout << "转化为16进制后为 " << to_hex(value) << endl;
  52. }
  53. cout << "转化为16进制后为 " << hexchuang << endl;
  54. return sum;
  55. }
  56. int main() {
  57. string command; // 从命令行输入的命令
  58. string filename; // 输入的文件名
  59. cout << "请输入要执行的命令和处理的文件名" << endl;
  60. cin >> command >> filename;
  61. //这样运行check_sum D:/infile.txt
  62. while (true) {
  63. if (command.compare("check_sum") != 0) {
  64. cout << "输入命令无效,请重新输入" << endl;
  65. }
  66. else {
  67. cout << "最终的16位校验和: " << check(filename) << endl;
  68. break;
  69. }
  70. }
  71. return 0;
  72. }

原文链接:https://www.cnblogs.com/l-xx123/p/18237938

 友情链接:直通硅谷  点职佳  北美留学生论坛

本站QQ群:前端 618073944 | Java 606181507 | Python 626812652 | C/C++ 612253063 | 微信 634508462 | 苹果 692586424 | C#/.net 182808419 | PHP 305140648 | 运维 608723728

W3xue 的所有内容仅供测试,对任何法律问题及风险不承担任何责任。通过使用本站内容随之而来的风险与本站无关。
关于我们  |  意见建议  |  捐助我们  |  报错有奖  |  广告合作、友情链接(目前9元/月)请联系QQ:27243702 沸活量
皖ICP备17017327号-2 皖公网安备34020702000426号