天天看点

计算机组成原理:用c++实现汉明码

今天学习计组时,学习到了一个新知识海明码,一般用于网络传输中对数据进行校验,如果出差,可以通过海明码这个算法实现查找一个出错位,通过取反的方式纠错,实现原理是在信息位中加入校验位,组成新的二进制串,形成海明码。

#include <algorithm>
#include <iostream>
#include <string>
#include <unordered_map>
#include <vector>

/*汉明码的生产和检测一位错误*/
class HanmingCode {
 public:
  /*构造函数*/
  HanmingCode(std::string& _inforcode) {
    this->inforlen = _inforcode.size();
    for (auto& now : _inforcode) {
      this->inforcode.push_back(now - '0');
    }
  }

  /*生成校验位长度*/
  void Generateveriflen() {
    for (int i = 0;; i++) {
      if ((1 << i) - 1 >= inforlen + i) {
        this->veriflen = i;
        return;
      }
    }
  }

  /*生成汉明码长度*/
  void Generatehanmlen() {
    Generateveriflen();
    this->hanmlen = this->inforlen + this->veriflen;
    return;
  }

  /*生成校验码*/
  void Generateverifcode() {
    for (int i = 0; i < this->veriflen; i++) {
      this->verifcode.push_back(0);
    }

    int k = 0, m = 0;

    /*收集非校验位*/
    for (int i = 1; i <= this->hanmlen; i++) {
      if (i == (1 << k)) {
        k++;
      } else {
        int tmp = i, ks = this->veriflen - 1;
        while (tmp) {
          if (tmp >= (1 << ks)) {
            tmp -= (1 << ks);
            verifcode[ks] ^= inforcode[m];
          }
          ks--;
        }
        m++;
      }
    }
  }

  /*生成海明码*/
  void Generatehanmcode() {
    this->Generatehanmlen();
    this->Generateverifcode();
    for (int i = 1, j = 0, k = 0, s = 0; i <= hanmlen; i++) {
      if (((1 << s)) == i) {
        hanmcode.push_back(verifcode[j++]);
        s++;
      } else {
        hanmcode.push_back(inforcode[k++]);
      }
    }
    for (auto& x : hanmcode) {
      std::cout << x;
    }
    std::cout << std::endl;
  }

 private:
  int inforlen;               /*信息码长度*/
  int veriflen;               /*校验码长度*/
  int hanmlen;                /*汉明码长度*/
  std::vector<int> hanmcode;  /*汉明码*/
  std::vector<int> inforcode; /*信息码*/
  std::vector<int> verifcode; /*校验码*/
};

int main() {
  /*[1][2][3][4]....按照从做往右大小递增顺序编写,最后生成的汉明码是从左往右顺序的答案*/
  std::string ans = "1010";
  HanmingCode test(ans);
  test.Generatehanmcode();
  return 0;
}