码迷,mamicode.com
首页 > 其他好文 > 详细

关于无符号整型数中1的个数与0的个数的改变与计算引发的思考

时间:2015-07-04 09:40:26      阅读:155      评论:0      收藏:0      [点我收藏+]

标签:

首先可以把unsigned int数中的1的个数与0的个数改变与计算的实现:

</pre><pre name="code" class="cpp">/**********************************************************************     
* *   Copyright (c)2015,WK Studios   
* *   Filename:  A.h 
* *   Compiler: GCC  vc 6.0    
* *   Author:WK     
* *   Time: 2015 2 7 
* **********************************************************************/
#include<iostream>
using namespace std;
#include <assert.h>
void Set_Bit(size_t * Int_Dat,size_t Posi,bool ch )
{
	if(ch)
	{
		*Int_Dat |= (0x01<<(Posi-1));
	}
	else
	{
		*Int_Dat &= ~(0x01<<(Posi-1));
	}
}

size_t Cal_Bit1(size_t d)
{
	size_t n=0;
	while(d )
	{
		if(d & 0x01)
		{
			++n;
		}
		d/=2;
	}
	return n;
}
size_t Cal_Bit0(size_t d)
{
	size_t n=0;
	while(d)
	{
		if(!(d%2)) 
		{
			++n;
		}
		d/=2;
	}
	return n;
	
}

size_t Cal_B1(size_t d)
{
	size_t n=0;
	while(d)
	{
		++n;
		d&=(d-1);//末尾一位置0
	}
	return n;
}

size_t Cal_B0(size_t d)
{
	size_t n=0;
	while((d+1))
	{
		++n;
		d |= (d+1);//末尾一位置1
	}
	return n;
}

void main()
{
	cout<<"-----计算无符号整型中0或者1的个数-----\n";
	unsigned int m=15;
	cout<<"原数据:"<<m<<endl;
	cout<<"0个数:"<<Cal_Bit0(m)<<endl;//这种计算忽略了前边的零
	cout<<"1个数:"<<Cal_Bit1(m)<<endl;
	cout<<"0个数:"<< Cal_B0(m)<<endl;//计算在32位中的零
	cout<<"1个数:"<< Cal_B1( m)<<endl;
	cout<<"-----无符号整型指定位置0或者置1-----\n";
	unsigned int d=4;
	cout<<"原数据:"<<d<<endl;
	Set_Bit( &d, 2,1 );
	cout<<"指定位置置1后:"<<d<<endl;
	Set_Bit( &d, 2,0 );
	cout<<"指定位置置0后:"<<d<<endl;
}


技术分享

用类实现在无符号整型指定的位置赋1:

#include<iostream>
using namespace std;
#include <assert.h>

#define FSIZE 32
#define TRUE 1
#define FALSE 0


class flags
{
	unsigned char f[FSIZE];
public:
	flags();
	void set(int i);
	void clear(int i );
	int read(int i);
	int size();
};

flags::flags()
{
	memset(f,FALSE,FSIZE);//初始化为FSIZE位全是0
}
void flags::set(int i)
{
	assert(i>=0 && i<FSIZE);
	f[i]=TRUE;
}

void flags::clear(int i)
{
    assert(i>=0 && i<FSIZE);
	f[i]=FALSE;
}

int flags::read(int i)
{
	assert(i>=0 && i<FSIZE);
	return f[i];
}

int flags::size()
{
	return FSIZE;
}

void main()
{
	flags f1;
for(int i=0;i<f1.size();++i)
	{
	if(i%3==0)//在可以被三整除的位置赋为1
	f1.set(i);
	}
				
	for(int j=0;j<f1.size();++j)
	{
	cout<<f1.read(j)<<" ";
	}
	cout<<endl;
}

技术分享

更加复杂的实现对无符号整型中二进制位的修改

/**********************************************************************     
* *   Copyright (c)2015,WK Studios   
* *   Filename:  A.h 
* *   Compiler: GCC  vc 6.0    
* *   Author:WK     
* *   Time: 2015 2 7 
* **********************************************************************/
#include<iostream>
using namespace std;
#include<assert.h>
#include<limits.h>


const unsigned char highbit=1 << (CHAR_BIT-1);

class BitVector
{  
public:
	BitVector();
	BitVector(unsigned char* init,int size=8);
	BitVector(char* Binary);//可以使用"000101010"字符串来初始化
	~BitVector();
	void set(int init);
	void clear(int bit);
	int read(int bit);
	void bits(int sz);
	int bits();
	void print(const char* msg="");//缺省的常量字符串仍然在常量区里保存
private:
	unsigned char* Bytes;
	int Bits,NumBytes;//比特位和字节数
};

BitVector::BitVector()//把所有的变量赋零
{
	NumBytes=0;
	Bits=0;
	Bytes=0;
}

BitVector::BitVector(unsigned char* init,int size)//分配内存并且初始化位数
{
	
	NumBytes=size;//字节数        11110000
	Bits=NumBytes*CHAR_BIT;//总共的比特位数
	Bytes=(unsigned char*)calloc(NumBytes,1);//void *calloc(size_t n, size_t size);
	                                      //分配NumBytes个1字节的空间
	assert(Bytes);
	if(init==NULL )
	{
		return;
	}
	for(int index=0;index<NumBytes;++index)
	{
		for(int offset=0;offset<CHAR_BIT;++offset)
		{
			if(init[index] & (highbit>>offset))
				set(index * CHAR_BIT+offset);
		}
            
	}
}

BitVector::BitVector(char* Binary)
{                    //"1111010010"
	assert(Binary);
    Bits=strlen(Binary);
    NumBytes=Bits/CHAR_BIT;//字节数
	//不足8比特位的也分配一个字节
	if(Bits%CHAR_BIT)
		NumBytes++;
	Bytes=(unsigned char*)calloc(NumBytes,1);
	assert(Bytes);
	for(int i=0;i<Bits;++i)
	{
      if(Binary[i]=='1')
		  set(i);

	}
      
}

BitVector::~BitVector()
{
	free(Bytes);
}

void BitVector::set(int bit)
{
   assert(bit>=0 && bit<Bits);
   int index=bit/CHAR_BIT;
   int offset=bit % CHAR_BIT;
   unsigned char mask =(1<<offset);
   Bytes[index]  |= mask; 
}                          

int BitVector::read(int bit)
{
	assert(bit>=0 && bit<Bits);
	int index=bit/CHAR_BIT;
    int offset=bit % CHAR_BIT;
   unsigned char mask =(1<<offset);
   return Bytes[index] & mask;//其实可以只用一句就结局问题,但是程序的可读性太差
}

void BitVector::clear(int bit)
{
	assert(bit>=0 && bit<Bits);
	int index=bit/CHAR_BIT;
    int offset=bit % CHAR_BIT;
    unsigned char mask =~(1<<offset);
    Bytes[index]  &= mask;   
}

int BitVector:: bits()
{
	return Bits;
}
void BitVector::bits(int size)
{
 int oldsize =Bits;
 Bits=size;
 NumBytes=Bits/CHAR_BIT;
 if(Bits%CHAR_BIT)
	 NumBytes++;
 void* V=realloc(Bytes,NumBytes);
 assert(V);
 Bytes=(unsigned char*)V;
 for(int i=oldsize;i<Bits;++i)
 {
	 clear(i);
 }

}
void BitVector::print(const char* msg)
{
	puts(msg);
	for(int i=0;i<Bits;i++)
	{
		if(read(i))
			putchar('1');
		else
			putchar('0');
		if((i+1)%CHAR_BIT == 0)
			putchar(' ');
	}
	putchar('\n');
}

void main()
{
	unsigned char b[]={0x0f,0xff,0xf0,
		              0xAA,0x78,0x11};
//	unsigned char b[]={'a','b','c','d','e','f'};
	BitVector bv1(b,sizeof (b)/sizeof (*b)),
	bv2("10010100111100101010001010010010101");

	bv1.print("bv1 before modification");
	for(int i=36;i<bv1.bits();++i)
	{
           bv1.clear(i);
	}
	bv1.print("bv1 after modification");
	bv2.print("bv2 after modification");
	for(int j=bv2.bits()-10;j<bv2.bits();++j)
	{
        bv2.clear(j);
	}
	bv2.set(30);
	bv2.print("bv2 after modification");
	bv2.bits(bv2.bits()/2);
	bv2.print("bv2 cut in half");
	bv2.bits(bv2.bits()+10);
	bv2.print("bv2 grown by 10");

    BitVector bv3((unsigned char*)0);
}
技术分享


版权声明:本文为博主原创文章,未经博主允许不得转载。

关于无符号整型数中1的个数与0的个数的改变与计算引发的思考

标签:

原文地址:http://blog.csdn.net/kai8wei/article/details/46746647

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!