题目:编写一个截取字符串的函数,输入为一个字符串和字节数, 输出为按字节截取的字符串,但要保证汉字不被截取半个,如"我ABC",4,应该截取"我AB",输入"我ABC汉DEF",6, 应该输出"我ABC",而不是"我ABC+汉的半个"。
我们都知道在计算机中,存储一个汉字需要至少两个字节。例如:gbk和gb2312都是用两个字节存储一个汉字,而UTF-8是用三个字节存储一个汉字。关于字符编码请看:汉字与字符编码。下面使用两种方法对字符串进行截取。
第一种方法
适用字符集:UTF-8,gb2312,gbk
思路:依次截取字符串的每个字符,根据字符编码获取其字节数temp_len,total用以记录每次截取字符后及之前截取字符字节数之和,然后判断total是否小于等于所需要截取字节长度(length),如果小于说明还没超过所需要截取字节长度,那么截取字符的长度(len)+1,如果total>length说明已经超出所需要截取的字节长度,此时的len就是所需要截取原字符串的长度
第二种方法
适用字符集:gb2312,gbk
gbk汉字编码是两个字节为一个字符,高字节是小于0的(原因我也不清楚),设置一标志变量bChineseFirstHalf为false,如果获取到的字节小于0且bChineseFirstHalf为false,说明这是汉字的前半个字节,则bChineseFirstHalf设置为true,否则,num(最终需要截取字符串长度)加1。一直循环到字节数i等于需要截取的字节数length
具体代码
package com.zyh.interview;执行结果:
import java.io.UnsupportedEncodingException;
/**
* 编写一个截取字符串的函数,输入为一个字符串和字节数, 输出为按字节截取的字符串,但要保证汉字不被截取半个,
* 如"我ABC",4,应该截取"我AB",输入"我ABC汉DEF",6, 应该输出"我ABC",而不是"我ABC+汉的半个"。
* @author zyh
*/
public class SubChinese_Q113 {
/**
* @param input 需要截取的字符串
* @param length 需要截取的字节数
* @param encoding 字符的编码格式
* @return 截取后的字符串
* @throws UnsupportedEncodingException
*/
public static String subString(String input, int length, String encoding) throws UnsupportedEncodingException {
byte[] buf = input.getBytes(encoding);
int characterNum = input.length();
System.out.println("字符编码:" + encoding +",字符串的字符个数:" + characterNum + ", 字节长度为:" + buf.length);
//截取到当前字符时的字节数
int total = 0;
//应当截取到的字符的长度
int len = 0;
for(int i=0; i<characterNum; i++) {
String temp = input.substring(i, i+1);
int temp_len = temp.getBytes(encoding).length;
total += temp_len;
if(total<=length){
len++;
}
}
return input.substring(0, len);
}
/**
* 参数意义同上
*/
public static String subStr(String input, int length, String encoding) throws UnsupportedEncodingException {
int num = 0;
byte[] buf = input.getBytes(encoding);
System.out.println("字符编码:" + encoding +",字符串的字符个数:" + input.length() + ", 字节长度为:" + buf.length);
boolean bChineseFirstHalf = false;
for (int i = 0; i < length; i++) {
if (buf[i] < 0 && !bChineseFirstHalf) {
bChineseFirstHalf = true;
} else {
num++;
bChineseFirstHalf = false;
}
}
return input.substring(0, num);
}
public static void main(String[] args) throws UnsupportedEncodingException {
String str = "我ABC,中<汉DEF";
System.out.println(subString(str, 7, "UTF-8"));
System.out.println(subStr(str, 10, "GBK"));
}
}