php获取汉字首字母的函数


Posted in PHP onNovember 07, 2013

网上的方法有不少,都是一样的原理,按照需求,做了一下版本的class类文件,主要功能是:功能明确,易于修改维护和扩展; 英文的字串:不变返回(包括数字);中文字符串:返回拼音首字符; 中英混合串: 返回拼音首字符和英文。该算法采用了二分法查找,修复了之前字母Z读取成Y的错误。好东西要收藏,故在此留下印记,以供后人考证!

<?php 
 /**
* Modified by http://iulog.com @ 2013-05-07
* 修复二分法查找方法
* 汉字拼音首字母工具类
*  注: 英文的字串:不变返回(包括数字)    eg .abc123 => abc123
*      中文字符串:返回拼音首字符        eg. 测试字符串 => CSZFC
*      中英混合串: 返回拼音首字符和英文   eg. 我i我j => WIWJ
*  eg.
*  $py = new str2PY();
*  $result = $py->getInitials('啊吧才的饿飞就好i就看了吗你哦平去人是他uv我想一在');
*/
class str2PY
{
    private $_pinyins = array(
        176161 => 'A',
        176197 => 'B',
        178193 => 'C',
        180238 => 'D',
        182234 => 'E',
        183162 => 'F',
        184193 => 'G',
        185254 => 'H',
        187247 => 'J',
        191166 => 'K',
        192172 => 'L',
        194232 => 'M',
        196195 => 'N',
        197182 => 'O',
        197190 => 'P',
        198218 => 'Q',
        200187 => 'R',
        200246 => 'S',
        203250 => 'T',
        205218 => 'W',
        206244 => 'X',
        209185 => 'Y',
        212209 => 'Z',
    );
    private $_charset = null;
    /**
     * 构造函数, 指定需要的编码 default: utf-8
     * 支持utf-8, gb2312
     *
     * @param unknown_type $charset
     */
    public function __construct( $charset = 'utf-8' )
    {
        $this->_charset    = $charset;
    }
    /**
     * 中文字符串 substr
     *
     * @param string $str
     * @param int    $start
     * @param int    $len
     * @return string
     */
    private function _msubstr ($str, $start, $len)
    {
        $start  = $start * 2;
        $len    = $len * 2;
        $strlen = strlen($str);
        $result = '';
        for ( $i = 0; $i < $strlen; $i++ ) {
            if ( $i >= $start && $i < ($start + $len) ) {
                if ( ord(substr($str, $i, 1)) > 129 ) $result .= substr($str, $i, 2);
                else $result .= substr($str, $i, 1);
            }
            if ( ord(substr($str, $i, 1)) > 129 ) $i++;
        }
        return $result;
    }
    /**
     * 字符串切分为数组 (汉字或者一个字符为单位)
     *
     * @param string $str
     * @return array
     */
    private function _cutWord( $str )
    {
        $words = array();
         while ( $str != "" )
         {
            if ( $this->_isAscii($str) ) {/*非中文*/
                $words[] = $str[0];
                $str = substr( $str, strlen($str[0]) );
            }else{
                $word = $this->_msubstr( $str, 0, 1 );
                $words[] = $word;
                $str = substr( $str, strlen($word) );
            }
         }
         return $words;
    }
    /**
     * 判断字符是否是ascii字符
     *
     * @param string $char
     * @return bool
     */
    private function _isAscii( $char )
    {
        return ( ord( substr($char,0,1) ) < 160 );
    }
    /**
     * 判断字符串前3个字符是否是ascii字符
     *
     * @param string $str
     * @return bool
     */
    private function _isAsciis( $str )
    {
        $len = strlen($str) >= 3 ? 3: 2;
        $chars = array();
        for( $i = 1; $i < $len -1; $i++ ){
            $chars[] = $this->_isAscii( $str[$i] ) ? 'yes':'no';
        }
        $result = array_count_values( $chars );
        if ( empty($result['no']) ){
            return true;
        }
        return false;
    }
    /**
     * 获取中文字串的拼音首字符
     *
     * @param string $str
     * @return string
     */
    public function getInitials( $str )
    {
        if ( empty($str) ) return '';
        if ( $this->_isAscii($str[0]) && $this->_isAsciis( $str )){
            return $str;
        }
        $result = array();
        if ( $this->_charset == 'utf-8' ){
            $str = iconv( 'utf-8', 'gb2312', $str );
        }
        $words = $this->_cutWord( $str );
        foreach ( $words as $word )
        {
            if ( $this->_isAscii($word) ) {/*非中文*/
                $result[] = $word;
                continue;
            }
            $code = ord( substr($word,0,1) ) * 1000 + ord( substr($word,1,1) );
            /*获取拼音首字母A--Z*/
            if ( ($i = $this->_search($code)) != -1 ){
                $result[] = $this->_pinyins[$i];
            }
        }
        return strtoupper(implode('',$result));
    }
    private function _getChar( $ascii )
    {
        if ( $ascii >= 48 && $ascii <= 57){
            return chr($ascii);  /*数字*/
        }elseif ( $ascii>=65 && $ascii<=90 ){
            return chr($ascii);   /* A--Z*/
        }elseif ($ascii>=97 && $ascii<=122){
            return chr($ascii-32); /* a--z*/
        }else{
            return '-'; /*其他*/
        }
    }
    /**
     * 查找需要的汉字内码(gb2312) 对应的拼音字符( 二分法 )
     *
     * @param int $code
     * @return int
     */
    private function _search( $code )
    {
        $data = array_keys($this->_pinyins);
        $lower = 0;
        $upper = sizeof($data)-1;
  $middle = (int) round(($lower + $upper) / 2);
        if ( $code < $data[0] ) return -1;
        for (;;) {
            if ( $lower > $upper ){
                return $data[$lower-1];
            }
            $tmp = (int) round(($lower + $upper) / 2);
            if ( !isset($data[$tmp]) ){
    return $data[$middle];
            }else{ 
    $middle = $tmp;
   }
            if ( $data[$middle] < $code ){
                $lower = (int)$middle + 1;
            }else if ( $data[$middle] == $code ) {
                return $data[$middle];
            }else{
                $upper = (int)$middle - 1;
            }
        }
    }
}
?>
PHP 相关文章推荐
同一空间绑定多个域名而实现访问不同页面的PHP代码
Dec 06 PHP
供参考的 php 学习提高路线分享
Oct 23 PHP
Zend的Registry机制的使用说明
May 02 PHP
利用yahoo汇率接口实现实时汇率转换示例 汇率转换器
Jan 14 PHP
PHP之autoload运行机制实例分析
Aug 28 PHP
PHP扩展开发教程(总结)
Nov 04 PHP
Thinkphp单字母函数使用指南
May 08 PHP
PHP实现的自定义数组排序函数与排序类示例
Nov 18 PHP
利用Homestead快速运行一个Laravel项目的方法详解
Nov 14 PHP
TP(thinkPHP)框架多层控制器和多级控制器的使用示例
Jun 13 PHP
tp5(thinkPHP5框架)使用DB实现批量删除功能示例
May 28 PHP
php7连接MySQL实现简易查询程序的方法
Oct 13 PHP
PHP输出当前进程所有变量/常量/模块/函数/类的示例
Nov 07 #PHP
php cookie使用方法学习笔记分享
Nov 07 #PHP
PHP 5.5 创建和验证哈希最简单的方法详解
Nov 07 #PHP
php使用mb_check_encoding检查字符串在指定的编码里是否有效
Nov 07 #PHP
PHP中spl_autoload_register函数的用法总结
Nov 07 #PHP
php去除HTML标签实例
Nov 06 #PHP
php实现监听事件
Nov 06 #PHP
You might like
PHP一些有意思的小区别
2006/12/06 PHP
PHP nl2br函数 将换行字符转成 &amp;lt;br&amp;gt;
2009/08/21 PHP
允许phpmyadmin空密码登录的配置方法
2011/05/29 PHP
编辑浪子版表单验证类
2007/05/12 Javascript
Ext面向对象开发实践(续)
2008/11/18 Javascript
js 编程笔记 无名函数
2011/06/28 Javascript
Javascript 键盘事件的组合使用实现代码
2012/05/04 Javascript
jQuery中serializeArray()与serialize()的区别实例分析
2015/12/09 Javascript
javascript计时器编写过程与实现方法
2016/02/29 Javascript
js小数计算小数点后显示多位小数的实现方法
2016/05/30 Javascript
JavaScript对Json的增删改属性详解
2016/06/02 Javascript
jQuery实现对无序列表的排序功能(附demo源码下载)
2016/06/25 Javascript
jQuery实现div跟随鼠标移动
2020/08/20 jQuery
利用Vue.js实现求职在线之职位查询功能
2017/07/03 Javascript
JavaScript中一些特殊的字符运算
2017/08/17 Javascript
详解Vue Elementui中的Tag与页面其它元素相互交互的两三事
2018/09/25 Javascript
BootStrap table实现表格行拖拽效果
2018/12/01 Javascript
微信小程序版本自动更新的方法
2019/06/14 Javascript
vue+elementUI(el-upload)图片压缩,默认同比例压缩操作
2020/08/10 Javascript
微信小程序实现打卡签到页面
2020/09/21 Javascript
[01:06:54]DOTA2-DPC中国联赛 正赛 SAG vs DLG BO3 第二场 2月28日
2021/03/11 DOTA
Python对文件操作知识汇总
2016/05/15 Python
基于DATAFRAME中元素的读取与修改方法
2018/06/08 Python
python执行CMD指令,并获取返回的方法
2018/12/19 Python
Flask框架中request、请求钩子、上下文用法分析
2019/07/23 Python
Python autoescape标签用法解析
2020/01/17 Python
利用python查看数组中的所有元素是否相同
2021/01/08 Python
如何用python爬取微博热搜数据并保存
2021/02/20 Python
html5实现图片转圈的动画效果——让页面动起来
2017/10/16 HTML / CSS
美国大城市最热门旅游景点门票:CityPASS
2016/12/16 全球购物
Hertz荷兰:荷兰和全球租车
2018/01/07 全球购物
美国香薰蜡烛品牌:PADDYWAX
2018/10/06 全球购物
员工教育培训协议书
2014/09/27 职场文书
中职毕业生自我鉴定范文(3篇)
2014/09/28 职场文书
JavaWeb Servlet开发注册页面实例
2022/04/11 Java/Android
create-react-app开发常用配置教程
2022/06/25 Javascript