utf8截取无乱码

来源:互联网 发布:手机淘宝 尺码助手 编辑:程序博客网 时间:2024/05/16 07:49
要知道怎么截取UTF8无乱码,我们首先要知道UTF8是怎么编码的,百度了一下,得出以下码表
Unicode/UCS-4
bit数
UTF-8
byte数
备注
0000 ~
007F
0~7
0XXX XXXX
1
 
0080 ~
07FF
8~11
110X XXXX
2
 
0800 ~
FFFF
12~16
1110XXXX
3
基本定义范围:0~FFFF
1 0000 ~
1F FFFF
17~21
1111 0XXX
4
Unicode6.1定义范围:0~10 FFFF
20 0000 ~
3FF FFFF
22~26
1111 10XX
5
说明:此非unicode编码范围,属于UCS-4 编码
早期的规范UTF-8可以到达6字节序列,可以覆盖到31位元(通用字符集原来的极限)。尽管如此,2003年11 月UTF-8 被 RFC3629 重新规范,只能使用原来Unicode定义的区域, U+0000到U+10FFFF。根据规范,这些字节值将无法出现在合法UTF-8序列中
400 0000 ~
7FFF FFFF
27~31
1111 110X
6

看起来很复杂,其实就很简单,utf8编码究竟是多少个字节组成一个字符,主要是看字符的第一个字节,至于第一个字节是什么样对应截取多少个就参照上表了,但是还有一个问题,就是究竟要怎么判断,其实只要截取第一个字节出来,位运算一次就可以了,具体代码如下

function getUTF8($str,$len){    if($len <= 0){        return '';    }    $temp = '';    for($i=0,$j=0;$i<$len;$i++){        $str1 = ord(substr($str,$j,1));        if(($str1 & bindec('11111110')) == bindec('11111100')){            //截取6            $temp .= substr($str,$j,6);            $j = $j + 6;        }elseif(($str1 & bindec('11111100')) == bindec('11111000')){            //截取5            $temp .= substr($str,$j,5);            $j = $j + 5;        }elseif(($str1 & bindec('11111000')) == bindec('11110000')){            //截取4            $temp .= substr($str,$j,4);            $j = $j + 4;        }elseif(($str1 & bindec('11110000')) == bindec('11100000')){            //截取3            $temp .= substr($str,$j,3);            $j = $j + 3;        }elseif(($str1 & bindec('11100000')) == bindec('11000000')){            //截取2            $temp .= substr($str,$j,2);            $j = $j + 2;        }else{            //截取1            $temp .= substr($str,$j,1);            $j = $j + 1;        }    }    return $temp;}


0 0