⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 convertcode.cpp

📁 对于通用的嵌入式系统字处理单元,本模块化程序可以快速实现常用汉字编码(GB2312,GB18030,BIG5码,Unicode码)的相互转换,无需库函数.从而实现使用单汉字字库显现多内码.具体参见re
💻 CPP
📖 第 1 页 / 共 3 页
字号:
				/* 默认按照Little Endian */
				fseek( pfIn, 0, SEEK_SET); /* 文件指针回到文件头 */
			 }
		 }
		 
		 /* 从输入文件读入UTF16数据,转换为BIG5格式后写入输出文件 */
		 while (!feof(pfIn))
		 {/* 输入文件未结束 */
		  /* 从输入文件读入UTF16数据 */
		  inputCode[0] = fgetc(pfIn);
		  inputCode[1] = fgetc(pfIn);
		  u16Indata =inputCode[0] + (inputCode[1]<<8);
		  if( ferror( pfIn ) )
		  {
			printf( "\nRead error" );
			break;
		  }
		  /* 转换为BIG5格式后写入输出文件 */
		  Utf16TOBig5(&u16Indata, outputCode, &u8OutputLen);
		  for (i = 0; i < u8OutputLen; i++)
		  {
			fputc(outputCode[i],pfOut);
		  }
		 }
		fclose(pfIn);
		fclose(pfOut);
		return 0;

		}
	  else
	  {
		printf("输入%s(%X)或输出文件%s(%X)不存在\n",argv[2],(S32)pfIn,argv[3],(S32)pfOut);
		return 3;
	  }
	} 
#endif	

#if (_UTF16BE_BIG5)
	if(strcmp(argv[1],"UTF16BE_BIG5") == 0)
	{
	  if (((pfIn = fopen(argv[2],"rb"))!= NULL)&& ((pfOut = fopen(argv[3],"wb"))!=NULL))
 	  {
		 inputCode[0] = fgetc(pfIn);
		 inputCode[1] = fgetc(pfIn);
		 if ((inputCode[0] != 0xfe)||(inputCode[1] != 0xff))
		 {
	 		 if ((inputCode[0] == 0xff)&&(inputCode[1] == 0xfe))
			 {
				 printf("输入文件为LittleEndian格式,请使用UTF16_BIG5标识转换\n");
				 return 4;
			 }
			 else
			 {
				printf("警告:输入文件没有BOM标识\n");
				/* 默认按照BIG Endian */
				fseek( pfIn, 0, SEEK_SET); /* 指针回到文件头 */
			 }
		 }
		 
		 /* 从输入文件读入UTF16数据,转换为BIG5格式后写入输出文件 */
		 while (!feof(pfIn))
		 {/* 输入文件未结束 */
		  /* 从输入文件读入UTF16数据 */
		  inputCode[0] = fgetc(pfIn);
		  inputCode[1] = fgetc(pfIn);
		  u16Indata =inputCode[1] + (inputCode[0]<<8);
		  if( ferror( pfIn ) )
		  {
			printf( "\nRead error" );
			break;
		  }
		  /* 转换为BIG5格式后写入输出文件 */
		  Utf16TOBig5(&u16Indata, outputCode, &u8OutputLen);
		  for (i = 0; i < u8OutputLen; i++)
		  {
			fputc(outputCode[i],pfOut);
		  }
		 }
		fclose(pfIn);
		fclose(pfOut);
		return 0;

		}
	  else
	  {
		printf("输入%s(%X)或输出文件%s(%X)不存在\n",argv[2],(S32)pfIn,argv[3],(S32)pfOut);
		return 5;
	  }
		
	}		
#endif

#if (_UTF8_BIG5)
	if(strcmp(argv[1],"UTF8_BIG5") == 0)
	{
	  if (((pfIn = fopen(argv[2],"rb"))!= NULL)&& ((pfOut = fopen(argv[3],"wb"))!=NULL))
 	  {
		 inputCode[0] = fgetc(pfIn);
		 inputCode[1] = fgetc(pfIn);
		 inputCode[2] = fgetc(pfIn);

		 if ((inputCode[0] != 0xef)||(inputCode[1] != 0xbb)||(inputCode[2] != 0xbf))
		 {
			printf("警告:输入文件没有BOM标识\n");
				/* 默认按照UTF8 */
			fseek( pfIn, 0, SEEK_SET); /* 指针回到文件头 */
		 }
		 
		 /* 从输入文件读入UTF8数据,转换为BIG5格式后写入输出文件 */
		 while (!feof(pfIn))
		 {/* 输入文件未结束 */
		  /* 从输入文件读入UTF8数据 */
		  inputCode[0] = fgetc(pfIn);
		  u8InputLen  = 1 ;

		  if (inputCode[0] > 0x80 )
		  {
			i = 0x40;
			while (i & inputCode[0])
			{
				u8InputLen++;
				i = (i >> 1);
			}
		  } 
		  
		  if( u8InputLen > 3 )
		  {
			if (!feof(pfIn))
			{
				printf( "\n不支持格式的输入文件" );
			}
			break;
		  }
		  
		  for( i = 1; i < u8InputLen ; i++)
		  { /* 读入此UTF8代码剩余几个有效字节 */
		  	inputCode[i] =  fgetc(pfIn);
		  }	

		  if( ferror( pfIn ) )
		  {
			printf( "\n输入文件未知错误" );
			break;
		  }
		  /* 转换为BIG5格式后写入输出文件 */
		  Utf8TOBig5(inputCode, u8InputLen, outputCode, &u8OutputLen);
		  for (i = 0; i < u8OutputLen; i++)
		  {
			fputc(outputCode[i],pfOut);
		  }
		 }
		fclose(pfIn);
		fclose(pfOut);
		return 0;

		}
	  else
	  {
		printf("输入%s(%X)或输出文件%s(%X)不存在\n",argv[2],(S32)pfIn,argv[3],(S32)pfOut);
		return 5;
	  }
		
	}		
#endif

#if (_GB_BIG5)
	if(strcmp(argv[1],"GB_BIG5") == 0)
	{
	  if (((pfIn = fopen(argv[2],"rb"))!= NULL)&& ((pfOut = fopen(argv[3],"wb"))!=NULL))
 	  {
		 /* 从输入文件读入GB数据,转换为BIG5格式后写入输出文件 */
		 while (!feof(pfIn))
		 {/* 输入文件未结束 */
		  /* 从输入文件读入GB数据 */
		  u8InputLen = 1;
		  inputCode[0] = fgetc(pfIn);
		  if ((inputCode[0] >= 0x81)&& (inputCode[0] != 0xFF ))
		  {	/* 为双字节汉字或4字节编码 */
		  	if ((inputCode[1] = fgetc(pfIn)) >= 0x40)
			{ /* 为双字节汉字 */
		  		u8InputLen = 2;
			}	
		  	else if ((inputCode[1] >= 0x30)&&(inputCode[1] <= 0x39))
		  	{ /* 为4字节编码的第2字节,继续读取 */
		  		inputCode[2] = fgetc(pfIn);
		  		inputCode[3] = fgetc(pfIn);
		  		if((inputCode[2] >= 0x81)&&((inputCode[3] >= 0x30)&&(inputCode[3] <= 0x39)))
		  		{ /* 符合4字节编码格式 */
		  			u8InputLen = 4;
		  		}
		  		else
		  		{ /* 不符合4字节编码格式,,忽略此4个字节 */
					u8InputLen = 0;
		  		}				
		  	}		
			else
			{/* 貌似双字节汉字或4字节编码,但第2字节格式错,忽略此两个字节 */
				u8InputLen = 0;
			}		
		  }		

		  /* 转换为GB18030格式后写入输出文件 */
		  if( Gb18030TOBig5(inputCode, u8InputLen, outputCode, &u8OutputLen) == CONVERT_OK )
		  {
		  	for (i = 0; i < u8OutputLen; i++)
		  	{
				fputc(outputCode[i],pfOut);
		  	}
		  }
		  else
		  {
				fputc('?',pfOut);
				if (u8InputLen > 1)
				{
						fputc('?',pfOut);
				}		
		  }			
		 }

		#if 0
		  	for (i = 0; i < u8InputLen; i++)
		  	{
				printf("\nintput[%d]=%x",i,inputCode[i]);
		  	}
		#endif

		fclose(pfIn);
		fclose(pfOut);
		return 0;

		}
	  else
	  {
		printf("输入%s(%X)或输出文件%s(%X)不存在\n",argv[2],(S32)pfIn,argv[3],(S32)pfOut);
		return 5;
	  }
		
	}		
#endif

	{
		printf("命令格式: convertCode UTF16_GB utftxt(文件名) gbtxt(文件名)\n");
		return 1;
	}
	
}


#if (_UTF16LE_GB || _UTF16BE_GB)
/***************************************************************************
*	函数名称:	Utf16TOGb18030
*	作者	:		CZ
*	函数功能	:	将Utf16编码的字符转换为GB18030编码
*	接口描述:
*				
*		输入参数:
*				pu16InputCode - 输入的Utf16编码字符的存储地址
*				pu8OutputCode - 供存放输出的GB18030编码字符的首地址
*				pu8OutputLen  - 供存放输出的GB18030编码字符字节数的地址

*		返回参数:CONVERT_OK - 转换成功  CONVERT_ERROR - 转换失败  
*				 转换成功时,输出的字符存放在pu8OutputCode,长度存放在pu8OutputLen
*
*		影响的参数:无
*						
*
*	补充说明:
*				转换通过查表(即TB_UTF16_GB)得到,但节约空间起见,此表只输出前2字节结果
*				对于有4字节的汉字,再通过SearchCodeTable查表得到后面2字节.
*****************************************************************************/
S8 Utf16TOGb18030(U16* pu16InputCode, U8* pu8OutputCode, U8* pu8OutputLen)
{
	U16 u16InData,u16SeekResult,u16OutData;
	U8	u8DataH,u8DataL;
	
	
	/* 取得输入的UTF16数据,并分成高低位 */
	u16InData = *(pu16InputCode);
	u8DataH	  = u16InData >> 8;
	u8DataL   = u16InData & 0xff;
	
	/* 读出转换表结果 */
	u16OutData = TB_UTF16_GB[u8DataH][u8DataL];
	
	/* 单字节以及无对应结果的情况判断 */
	if (u16OutData <= 0xff)
	{
		if ((u16OutData == 0)&&(u16InData != 0))
		{	/* 无对应结果 */
			* pu8OutputLen = 0;
			return CONVERT_ERROR;
		}
		else
		{	/* 单字节结果 */
			* pu8OutputLen = 1;
			pu8OutputCode[0] = (U8)u16OutData;
			return CONVERT_OK;
		}
	}

	/* 4字节的情况判断 ,在CJK统一汉字扩充A 3400-4DB5 */
	/* 但是,有80个字符,对应GB码位是0xFE50-FEA0。Unicode将其中52字收录到“CJK统一汉字扩充A”
	   所以,这80个字符需排除出 4字节的情况判断      
	*/
	if((u16InData >= 0x3400 )&&(u16InData <= 0x4db5)&&((u16OutData < 0xFE50 )||(u16OutData > 0xFEA0 )) )
	{
		u16SeekResult = SearchCodeTable(u16InData);
		if (u16SeekResult > 0)
		{
			* pu8OutputLen = 4;
			pu8OutputCode[0]  =  u16OutData >> 8;
			pu8OutputCode[1]  =  u16OutData & 0xff;
			pu8OutputCode[2]  =  u16SeekResult >> 8;
			pu8OutputCode[3]  =  u16SeekResult & 0xff;
			return CONVERT_OK;
		} 
		else
		{/* 无对应结果 */
			* pu8OutputLen = 0;
			return CONVERT_ERROR;
		}
	}

	/* 余下的为2字节的情况 */
	* pu8OutputLen = 2;
	pu8OutputCode[0]  =  u16OutData >> 8;
	pu8OutputCode[1]  =  u16OutData & 0xff;
	return CONVERT_OK;


}


/***************************************************************************
*	函数名称:	SearchCodeTable
*	作者	:		CZ
*	函数功能	:	查表返回UTF16字符中对应4字节GB18030部分的后两字节
*	接口描述:
*				
*		输入参数:
*				unicodeKey - 输入的Utf16编码字符
*
*		返回参数:	
*				查表成功时 返回的两字节查询结果以BigEndian格式合成一个非零的U16数
*				 即所查询的GB18030编码第3字节对应返回值的高8位,第4字节对应低8位
*				查表失败时,返回值为0  
*
*		影响的参数:无
*						
*
*	补充说明: 
*****************************************************************************/
U16 SearchCodeTable(U16 unicodeKey)
{
    int first = 0;
    int end = sizeof(TB_UTF16_GB_4B)/sizeof(UTF16_GB_4B) - 1;
    int mid = 0;

    while (first <= end)
    {
        mid = (first + end) / 2;

        if (TB_UTF16_GB_4B[mid].unicode == unicodeKey)
        {
            return TB_UTF16_GB_4B[mid].gb;
        }
        else if (TB_UTF16_GB_4B[mid].unicode > unicodeKey)
        {

			end = mid - 1;
        }
        else 
        {
            first = mid + 1;
        }
    }
    return 0;
}
#endif   

#if (_UTF8_GB)
/***************************************************************************
*	函数名称:	Utf8TOGb18030
*	作者	:		CZ
*	函数功能	:	将Utf8编码的字符转换为GB18030编码
*	接口描述:
*				
*		输入参数:
*				pu8InputCode - 输入的Utf8编码字符的存储地址
*				u8InputLen   - 输入的Utf8编码字符的长度
*				pu8OutputCode - 供存放输出的GB18030编码字符的首地址
*				pu8OutputLen  - 供存放输出的GB18030编码字符字节数的地址

*		返回参数:CONVERT_OK - 转换成功  CONVERT_ERROR - 转换失败  
*				 转换成功时,输出的字符存放在pu8OutputCode,长度存放在pu8OutputLen
*
*		影响的参数:无
*						
*
*	补充说明: 
*				算法是先讲Utf8编码字符转换为Utf16编码,然后类似Utf16TOGb18030()
*****************************************************************************/
S8 Utf8TOGb18030(U8* pu8InputCode, U8 u8InputLen, U8* pu8OutputCode, U8* pu8OutputLen)
{
	U16 u16InData,u16SeekResult,u16OutData;
	U8	u8DataH,u8DataL;
	
	/* 将Utf8编码字符转换为Utf16 */
	switch(u8InputLen)

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -