PHP获取中英混合字符串长度的方法


Posted in PHP onJune 07, 2014

今晚在写框架的表单验证类时,需要判断某个字符串长度是否在指定区间内,很自然地,想到了PHP中的strlen函数。

$str = 'Hello world!';
echo strlen($str); // 输出12

然而在PHP自带的函数中,strlen及mb_strlen都是通过计算字符串所占字节数来计算长度的,在不同的编码情况下,中文所占的字节数是不同的。在GBK/GB2312下,中文字符占2个字节,而在UTF-8下,中文字符占3个字节。
$str = '你好,世界!';
echo strlen($str); // GBK或GB2312下输出12,UTF-8下输出18

而我们在判断字符串长度时往往需要判断的是字符的数量,而非字符串所占字节数,如在UTF-8下的这段PHP代码:
$name = '张耕畅';
$len = strlen($name);
// 输出 FALSE,因为在UTF-8下三个中文占9个字节
if($len >= 3 && $len <= 8){
 echo 'TRUE';
}else{
 echo 'FALSE';
}

那么有什么方便而实用的方法可以获得含中文字符串的长度呢?可以用正则计算出中文字符的个数,在GBK/GB2312编码下除以2,UTF-8编码下则除以3,最后再加上非中文字符串的长度,但这样未免太过麻烦。

WordPress这么一段代码,借鉴如下:

$str = 'Hello,世界!';
preg_match_all('/./us', $str, $match);
echo count($match[0]); // 输出9

思想是用正则表达式将字符串分割成单个字符,并直接用count计算出匹配到的字符数,便是我们想要的结果了。

但以上代码在UTF-8编码下并不能处理GBK/GB2312的中文字符串,因为GBK/GB2312的中文字符会被识别为两个字符而计算出来的中文字符数量会翻倍,于是我想到了这么一个办法:

$tmp = @iconv('gbk', 'utf-8', $str);
if(!empty($tmp)){
 $str = $tmp;
}
preg_match_all('/./us', $str, $match);
echo count($match[0]);

可兼容GBK/GB2312及UTF-8编码,经小量数据测试通过,但暂未确定是否完全正确,盼有大牛指点一二。

以上本意是为了框架可以兼容多种编码格式,但一般在日常开发中,一个项目是已经可以确定为何种编码的,因此可以使用以下函数来方便地获取字符串长度:

int iconv_strlen ( string $str [, string $charset = ini_get("iconv.internal_encoding") ] )

PHP 相关文章推荐
PHP中的array数组类型分析说明
Jul 27 PHP
php用数组返回无限分类的列表数据的代码
Aug 08 PHP
php获取post中的json数据的实现方法
Jun 08 PHP
PHP和.net中des加解密的实现方法
Feb 27 PHP
PHP数据类型之布尔型的介绍
Apr 28 PHP
php强制运行广告的方法
Dec 01 PHP
php+mysql实现用户注册登陆的方法
Jan 03 PHP
PHP实现的统计数据功能详解
Dec 06 PHP
php从身份证获取性别和出生年月
Feb 09 PHP
PHP新特性之字节码缓存和内置服务器
Aug 11 PHP
php 字符串中是否包含指定字符串的多种方法
Apr 12 PHP
详解如何实现Laravel的服务容器的方法示例
Apr 15 PHP
使用PHP破解防盗链图片的一个简单方法
Jun 07 #PHP
PHP防止post重复提交数据的简单例子
Jun 07 #PHP
解决PhpMyAdmin中导入2M以上大文件限制的方法分享
Jun 06 #PHP
php 判断网页是否是utf8编码的方法
Jun 06 #PHP
PHP实现的博客欢迎提示功能(很特别哦)
Jun 05 #PHP
php中数字0和空值的区别分析
Jun 05 #PHP
兼容各大浏览器带关闭按钮的漂浮多组图片广告代码
Jun 05 #PHP
You might like
几个php应用技巧
2008/03/27 PHP
php 删除无限级目录与文件代码共享
2008/11/22 PHP
php curl 登录163邮箱并抓取邮箱好友列表的代码(经测试)
2011/04/07 PHP
Linux Apache PHP Oracle 安装配置(具体操作步骤)
2013/06/17 PHP
如何使用PHP获取指定日期所在月的开始日期与结束日期
2013/08/01 PHP
PHP中比较时间大小实例
2014/08/21 PHP
Laravel框架自定义验证过程实例分析
2019/02/01 PHP
javascript 同时在IE和FireFox获取KeyCode的代码
2010/02/07 Javascript
简单实现异步编程promise模式
2015/07/31 Javascript
动态设置form表单的action属性的值的简单方法
2016/05/25 Javascript
JS作为值的函数用法示例
2016/06/20 Javascript
Javascript使用uploadify来实现多文件上传
2016/11/16 Javascript
微信小程序 基础知识css样式media标签
2017/02/15 Javascript
jquery实现tab选项卡切换效果(悬停、下方横线动画位移)
2017/05/05 jQuery
Vue.js获取被选择的option的value和text值方法
2018/08/24 Javascript
vue 项目接口管理的实现
2019/01/17 Javascript
JS使用栈判断给定字符串是否是回文算法示例
2019/03/04 Javascript
layer.open组件获取弹出层页面变量、函数的实例
2019/09/25 Javascript
Webpack中SplitChunksPlugin 配置参数详解
2020/03/24 Javascript
jquery实现加载更多&quot;转圈圈&quot;效果(示例代码)
2020/11/09 jQuery
Node.js文本文件BOM头的去除方法
2020/11/22 Javascript
[03:15]2014DOTA2国际邀请赛 专访国士无双信心满满
2014/07/12 DOTA
Python连接PostgreSQL数据库的方法
2016/11/28 Python
Django自定义manage命令实例代码
2018/02/11 Python
Python过滤txt文件内重复内容的方法
2018/10/21 Python
利用Python实现微信找房机器人实例教程
2019/03/10 Python
PyQt5事件处理之定时在控件上显示信息的代码
2020/03/25 Python
在tensorflow下利用plt画论文中loss,acc等曲线图实例
2020/06/15 Python
python如何调用java类
2020/07/05 Python
详解Canvas 跨域脱坑实践
2018/11/07 HTML / CSS
后勤岗位职责
2013/11/26 职场文书
教师先进个人材料
2014/12/17 职场文书
家庭聚会祝酒词
2015/08/11 职场文书
pytorch中的numel函数用法说明
2021/05/13 Python
Java基础之this关键字的使用
2021/06/30 Java/Android
Android学习之BottomSheetDialog组件的使用
2022/06/21 Java/Android