洛谷P1461 海明码 Hamming Codes

一、算法分析

题目的关键在于,对于所找出的编码,任两两编码之间都至少有 d 个单位的 “Hamming距离”。解决方案即从起始数0开始,进行编码生成(实则就是从0开始枚举十进制数1,2,3,4…并转换为二进制数)。然后将生成的编码和前面的编码一一比较,只要保证当前生成编码和前面任一编码的hamming距离都大于等于d,则最后所有的编码都是满足条件的。这里求算hamming距离的方法,可以联系树状数组的lowbit,具体看代码。

二、代码与分析

#include<iostream>
#include<cstdio>
#include<cstring>
#include<vector>
#include<algorithm>
#include<map>
#include<cmath>
#define ll long long
using namespace std;
int n,b,d;
int hamming(int x1,int x2){
	int k=x1^x2;
	int ans=0;
  while(k>0){
    ans++;
    k-=k&(-k);                      //k&(-k)可以去掉k最右边的1的左边部分,而再用k减去k&(-k)就可以去掉k的最后一个1 
  }
  return ans;
}
vector<int> ans;
int main(){ 

  
  cin>>n>>b>>d;
  
  int x=0;                           //当前编码的十进制数
	int maxx=pow(2,b)-1;               //因为规定了每个编码是b位,就相当于给出了枚举上界了 
  ans.push_back(x);
	while(x<maxx){
		x++;
		int len=ans.size();
		if(len==n) break;
		int ok=1;
		for(int i=0;i<len;i++){
		  if(hamming(ans[i],x)<d){
		  	ok=0;
		  	break;
			}
		}
		if(ok) ans.push_back(x);
	} 
  int len=ans.size(); 
  for(int i=0;i<len;i++){
  	cout<<ans[i];
  	if((i+1)%10==0) cout<<endl;
  	else cout<<' ';
	}
  
	return 0;
}
发布了50 篇原创文章 · 获赞 7 · 访问量 1122

猜你喜欢

转载自blog.csdn.net/numb_ac/article/details/103992423