• libiconv字符集转换库在C#中的使用


    libiconv字符集转换库用法》一文中说到了libiconv能够实现不同字符集的转换。

    比方GBK转BIG5等。在项目中由于须要,找到这个库。但是这个库在C#中没有非常好的支持。只是,想着既然是C++的库。那仅仅要动态载入DLL的接口就好了。但是调用并不顺利。传进去的IntPtr或者byte数组总是拿不到数据。后面回到了C++的方式去调用。几经调试,总算找到了原因。
    是iconv接口在转换完毕后。指针的位置往后移了。而在C#中调用DLL后回来的指针,已经是移动后的,所以拿不到所要的数据。
    经过多种尝试,没有办法将指针移回到原位。


    后来。通过C++的二次封装,在C++中将指针的位置移到了原来的位置,再用C#来调用,总算达到了目的。

    #include <fstream>
    //包函 libiconv库头文件 
    #include "iconv.h"
    
    //导入 libiconv库 
    #pragma comment(lib,"libiconv.lib")
    using namespace std;
    
    #define DLL_EXPORT extern "C" __declspec(dllexport)
    
    DLL_EXPORT int ChangeCode( const char* pFromCode,
    						  const char* pToCode,
    						  const char* pInBuf,
    						  size_t* iInLen,
    						  char* pOutBuf,
    						  size_t* iOutLen )
    {   
    
    	size_t outLenTemp=*iOutLen;
    
    	iconv_t hIconv = iconv_open( pToCode, pFromCode );
    	if ( -1 == (int)hIconv )
    	{
    		return 	-100;//打开失败。可能不支持的字符集 
    	}
    
    	//開始转换 
    	int iRet = iconv( hIconv, (const char**)(&pInBuf), iInLen, (char**)(&pOutBuf), iOutLen );
    	if (iRet>=0)
    	{
    		pOutBuf=pOutBuf-(outLenTemp-*iOutLen);//转换后pOutBuf的指针被移动,必须移回到起始位置
    	}
    	else
    	{
    		iRet=-200;
    	}
    
    	//关闭字符集转换 
    	iconv_close( hIconv );
    	return iRet;
    }

    C#调用的部分

      /// <summary>
            /// 字符器转换.
            /// 每次转换都须要打开转换器、字符集转换、关闭转换器。
            /// </summary>
            /// <param name="pFromCode">源字符集编码</param>
            /// <param name="pToCode">目标字符集编码</param>
            /// <param name="pInBuf">待转换的内容</param>
            /// <param name="iInLen">待转换的长度。转换成功后,将变成0.</param>
            /// <param name="pOutBuf">转换后的内容</param>
            /// <param name="iOutLen">转换长度。转换成功后。将变成原值减去转换后的内容所占空间的长度</param>
            /// <returns></returns>
            [DllImport("CharsetConvert.dll", CallingConvention = CallingConvention.Cdecl)]
            public static extern int ChangeCode(string pFromCode,
                                                string pToCode,
                                                byte[] pInBuf,
                                                ref int iInLen,
                                                byte[] pOutBuf,
                                                ref int iOutLen);

       private void buttonOneConvert_Click(object sender, EventArgs e)
            {
    
                string toCode = "BIG5";
                string fromCode = "GBK";
    
                string inStr = "國k";
                byte[] inBuf = Encoding.Default.GetBytes(inStr);
                byte[] outBuf = new byte[100];
    
                int inLen = inBuf.Length;
                int outLen = outBuf.Length;
    
                int result = CharsetConvter.ChangeCode(fromCode, toCode, inBuf, ref inLen, outBuf, ref outLen);
                if (result < 0)
                {
                    MessageBox.Show("转换失败");
                }
                else
                {
                    String outStr = Encoding.GetEncoding("BIG5").GetString(outBuf);
                    MessageBox.Show(outStr);
                }
    
            }


  • 相关阅读:
    js设计模式 -- 装饰模式
    前端项目开发(持续补充中)
    URL地址解析
    line-height有无单位区别
    HTTP请求Response Headers
    HTTP请求Request headers
    docker快速入门
    关于layui动态生成文件上传按钮后点击无效的解决办法
    未证实的一个BUG
    实现一个简单的概率发奖问题
  • 原文地址:https://www.cnblogs.com/lytwajue/p/6734181.html
Copyright © 2020-2023  润新知