一个高效过滤非UTF8字符的C函数(也可用来判断是否utf8)
/*
UTF-8 valid format list:
0xxxxxxx
110xxxxx 10xxxxxx
1110xxxx 10xxxxxx 10xxxxxx
11110xxx 10xxxxxx 10xxxxxx 10xxxxxx
111110xx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
1111110x 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
*/
char *filter_none_utf8_chars(char *src, int *len)
{
unsigned char *p;
unsigned char *pSub;
unsigned char *pStrEnd;
unsigned char *pCharEnd;
int bytes;
unsigned char *filtered;
unsigned char *pDest;
unsigned char *pInvalidCharStart; pStrEnd = (unsigned char *)src + (*len);
p = (unsigned char *)src;
pInvalidCharStart = NULL;
while (p < pStrEnd)
{
if (*p < 0x80)
{
p++;
continue;
} if ((*p & 0xE0) == 0xC0) //110xxxxx
{
bytes = ;
}
else if ((*p & 0xF0) == 0xE0) //1110xxxx
{
bytes = ;
}
else if ((*p & 0xF8) == 0xF0) //11110xxx
{
bytes = ;
}
else if ((*p & 0xFC) == 0xF8) //111110xx {
bytes = ;
}
else if ((*p & 0xFE) == 0xFC) //1111110x
{
bytes = ;
}
else
{
pInvalidCharStart = p;
break;
} p++;
pCharEnd = p + bytes;
if (pCharEnd > pStrEnd)
{
pInvalidCharStart = p - ;
break;
} for (; p<pCharEnd; p++)
{
if ((*p & 0xC0) != 0x80)
{
break;
}
} if (p != pCharEnd)
{
pInvalidCharStart = pCharEnd - (bytes + );
break;
}
} if (pInvalidCharStart == NULL) //all chars are valid
{
return src;
} filtered = (unsigned char *)malloc(sizeof(char) * (*len));
if (filtered == NULL)
{
*len = ;
*src = '\0';
return src;
} pDest = filtered;
bytes = (char *)pInvalidCharStart - src;
if (bytes > )
{
memcpy(pDest, src, bytes);
pDest += bytes;
} p = pInvalidCharStart + ; //skip this invalid char
while (p < pStrEnd)
{
if (*p < 0x80)
{
*pDest++ = *p++;
continue;
} if ((*p & 0xE0) == 0xC0) //110xxxxx
{
bytes = ;
}
else if ((*p & 0xF0) == 0xE0) //1110xxxx
{
bytes = ;
}
else if ((*p & 0xF8) == 0xF0) //11110xxx
{
bytes = ;
}
else if ((*p & 0xFC) == 0xF8) //111110xx
{
bytes = ;
}
else if ((*p & 0xFE) == 0xFC) //1111110x
{
bytes = ;
} else //invalid char
{
p++;
continue;
} pSub = p + ;
pCharEnd = pSub + bytes;
if (pCharEnd > pStrEnd)
{
p++;
continue;
} for (; pSub<pCharEnd; pSub++)
{
if ((*pSub & 0xC0) != 0x80)
{
break;
}
} if (pSub != pCharEnd)
{
p++;
continue;
} bytes += ;
memcpy(pDest, pSub-bytes, bytes);
pDest += bytes;
p += bytes;
} *len = pDest - filtered;
memcpy(src, filtered, *len);
* (src + (*len)) = '\0'; free(filtered); return src;
}
http://bbs.chinaunix.net/forum.php?mod=viewthread&tid=1230313
一个高效过滤非UTF8字符的C函数(也可用来判断是否utf8)的更多相关文章
- 过滤3个字节以上的utf-8字符
/** * 过滤掉超过3个字节的UTF8字符 * @param text * @return * @throws UnsupportedEncodingException */ public stat ...
- Unicode其实是Latin1的扩展。只有一个低字节的Uncode字符其实就是Latin1字符——附各种字符编码表及转换表
一.概念 1,ASCII ASCII(American Standard Code for Information Interchange),中文名称为美国信息交换标准代码.是 ...
- 字符编码笔记:ASCII,Unicode和UTF-8
很久很久以前,有一群人,他们决定用8个可以开合的晶体管来组合成不同的状态,以表示世界上的万物.他们看到8个开关状态是好的,于是他们把这称为"字节". 再后来,他们又做了一些可以处理 ...
- 字符编码笔记:ASCII,Unicode和UTF-8 转
本文出处 http://www.ruanyifeng.com/blog/2007/10/ascii_unicode_and_utf-8.html 只是为了记录一下省得要去搜. 今天中午,我突然想搞清楚 ...
- [转]字符编码笔记:ASCII,Unicode和UTF-8
转自:http://www.ruanyifeng.com/blog/2007/10/ascii_unicode_and_utf-8.html 作者: 阮一峰 日期: 2007年10月28日 今天中午, ...
- 字符编码笔记:ASCII,Unicode和UTF-8(转载)
作者: 阮一峰 日期: 2007年10月28日 今天中午,我突然想搞清楚Unicode和UTF-8之间的关系,于是就开始在网上查资料. 结果,这个问题比我想象的复杂,从午饭后一直看到晚上9点,才算初步 ...
- ASCII 非打印字符
项目出了问题,因为AscII非打印字符的原因,后来找了一下啊ASCII的非打印字符,总共有31个,然后我们直接全部替换成问号了. 解决方式为先找到非打印字符,这是我从网上找的非打印字符表: 进制 十六 ...
- 字符编码笔记:ASCII,Unicode和UTF-8【转载】
作者: 阮一峰 日期: 2007年10月28日 今天中午,我突然想搞清楚Unicode和UTF-8之间的关系,于是就开始在网上查资料. 结果,这个问题比我想象的复杂,从午饭后一直看到晚上9点,才算初步 ...
- 【转】字符编码笔记:ASCII,Unicode和UTF-8
今天整理笔记,关于NSString转NSData时,什么时候使用NSUTF8StringEncoding,或者NSASCIIStringEncoding,或者 NSUnicodeStringEncod ...
随机推荐
- jquery 点击按钮实现listbox的显示与隐藏,点击其他地方按钮外的地方,隐藏listbox
本来不知道如何获取服务器的控件的,这下知道可以这么做了,所以记录下来.... <asp:ImageButton ID="alltime" ImageUrl="ima ...
- IE 调试JS加断点不管用 增加debugger
ie按F12添加断点调试js不管用 有个方法在你想加断点前面加debugger,再调试就管用了
- 桦仔 笔记4-徐 模仿灾难发生时还原adventurework数据库 示例 stopat
1 --模仿灾难发生时还原adventurework数据库 示例 stopat 2 3 BACKUP DATABASE AdventureWorks 4 TO DISK= 'D:\MSSQL\Data ...
- GCD的使用和面试题集锦
GCD 分为异步和同步 异步: dispatch_async ( 参数1 , { } 同步: dispatch_sync( 参数1 , { } 参数1 :队列 队列分为两种: dispatch_get ...
- js判断微信内置浏览器
做了一个h5页面来下载app,但如果页面是用微信扫一扫打开的,点击下载按钮下载不了app,原因是微信内置浏览器屏蔽了下载链接.所以增加了检测,如果用户是用微信浏览器打开的,则提示用户使用浏览器打开.那 ...
- hadoop搭建杂记:Linux下不同linux主机之间文件copy的scp命令
不同的Linux之间copy文件常用有3种方法: 不同的Linux之间copy文件常用有3种方法: ①ftp 就是其中一台Linux安装ftp Server,这样可以另外一台使用ftp的程序来进行文件 ...
- 常用Json
一般Json是页面与页面之间传递使用. Json用途 1 后台与前台数据交互,并且数据较复杂,如果数据单一,直接传递字符串,然后在前台用js分割就行. 2 webservice和html ...
- android netty5.0 编译时 java.lang.NoClassDefFoundError: io.netty.channel.nio.NioEventLoopGroup
android netty5.0 编译时 java.lang.NoClassDefFoundError: io.netty.channel.nio.NioEventLoopGroup 复制netty包 ...
- return和break的区别
/* Name:return和break的区别 Copyright: By.不懂网络 Author: Yangbin Date:2014年2月25日 02:13:22 Description:以下代码 ...
- 什么是LED锡膏?
LED锡膏熔点172℃,俗称中温锡膏,其合金为Sn64Bi35Ag1,此类产品是含Bi类的低熔点无铅锡膏,加入Ag改变了SnBi合金的焊点的机械强度.大幅度提高焊点可靠性,适用于高频调谐器系列产品的贴 ...