65.9K
CodeProject 正在变化。 阅读更多。
Home

在不同基数之间转换

starIconstarIcon
emptyStarIcon
starIcon
emptyStarIconemptyStarIcon

2.93/5 (8投票s)

2002年2月6日

viewsIcon

195969

一篇关于将数字和字符串转换为不同进制的文章,例如二进制、八进制、十进制和十六进制。

引言

最近我正在做一个项目,需要将二进制数据存储到文本文件中,然后再读取出来。我认为一个简单快速的解决方案是将每个字节转换为十六进制格式,然后再转换回二进制格式。还有其他方法,例如Base64编码,但我时间有限。因此,我创建了两个完全兼容UNICODE的函数。

以下函数可以将任何数字转换为任何进制,例如二进制、八进制、十进制、十六进制,范围在2到36之间。

int StrToNum(const TCHAR *udata, int datalen, int base) :  将任何字符串转换为相应的数值进制。

TCHAR* __fastcall NumToStr(TCHAR *RetData, long number, int base)  : 将任何数字转换为所需进制的字符串。

这是包含示例的完整代码

#include <windows.h>
#include <iostream.h>
#include <tchar.h>
//convert the string to number
//udata is string
//udatalen is length of string
//base is numerical base eg. for decimal it is 10
// for hex it is 16
//largest base supported here is upto 36

int __fastcall StrToNum(const TCHAR *udata, int udatalen, int base)
{
	long index;
	const TCHAR numdigits[] = TEXT("0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ");
	long digitValue = 0;
	long RetVal = 0;
	TCHAR digits[sizeof(numdigits)+1];
	TCHAR *dataVal;
	TCHAR data[512] ;
	//copy the data to our variable
	_tcscpy(data, udata);
	//convert it to upper case
	_tcsupr(data);
	ZeroMemory(digits, sizeof(digits));
	//copy the number of digits supported by base in digits
	_tcsncpy(digits, numdigits, base);
	for(index = 0; index < udatalen; index++)
	{
		//is the number there
		dataVal = _tcschr(digits, data[index] );
		if(dataVal != 0 )
		{
			//if it is subtract where to start point
			digitValue = long(dataVal - digits);
			//increment Retval with digitvalue
			RetVal = RetVal * base + digitValue;
		}
	}
	//return the result
	return RetVal;
}

TCHAR* __fastcall NumToStr(TCHAR *RetData, long number, int base)
{
	long index = 0;
	const TCHAR numdigits[] = TEXT("0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ");
	long digitValue = 0;
	TCHAR digits[sizeof(numdigits) + 1];
	TCHAR RetVal[512];
	TCHAR CurVal = 0;	
	ZeroMemory(RetVal, sizeof(RetVal));
	// only base supported are from 2 to 36
	if(base < 2 || base > 36 ) return NULL;
	ZeroMemory(digits, sizeof(digits));
	_tcsncpy(digits, numdigits, base);
	while(number)
	{
		digitValue = number % base;
		number = number base;
		RetVal[index++] = digits[digitValue];
	}
	//since string we have got is in reversed format
	//eg 100 will be 001 so we have to reverse it
	//and put the value in our variable
	ZeroMemory(RetData, _tcslen(RetVal)+1);
	int i = 0;
	for(index = _tcslen(RetVal) - 1; index > -1; index--)
	{
		//start reversing
		RetData[i++] = RetVal[index];
	}
	//return the result
	return RetData;
}

//our main function
int _tmain(int argc, TCHAR* argv[], TCHAR* envp[])
{
	TCHAR Data[128];
	ZeroMemory(Data, sizeof(Data));
	//convert a number to string
	NumToStr(Data, 1123, 10);
	//now again convert string to number and see the result
	cout << StrToNum(Data, _tcslen(Data), 10) << endl;
	return 0;
}

注意:这段代码也可以用作一种简单的加密形式。这里有一个简单的例子:-

//convert string "1024" to a number of base 10;
_tcscpy(Data, TEXT("1024") );
int Number = StrToNum(Data, _tcslen(Data), 10);
//convert the number to a different base 27;
NumToStr(Data, Number, 27);
//now check the number
cout << TEXT("Modified String is ") << Data << endl;
//now again get back our original number
Number = StrToNum(Data, _tcslen(Data), 27);
NumToStr(Data, Number, 10);
cout << TEXT("Original Number is ") << Data << endl;

© . All rights reserved.