JAVA 中字符串的截取,要求不能截取半个汉字
http://www.360doc.com/content/12/1126/16/1542811_250345184.shtml
編寫一個截取字符串的函數,輸入為一個字符串和字節數,輸出為按字節截取的字符串。?
?但是要保證漢字不被截半個,如"我ABC"4,應該截為"我AB",輸入"我ABC漢DEF",6,?
?
? 應該輸出為"我ABC"而不是"我ABC+漢的半個"。?
?
import java.io.UnsupportedEncodingException;
?
/**
?* 截取的要點:
?* 1.首先將字符串轉換成字節數組,再將字節數組的每個元素拿出來,判斷有無負數(一個漢字為兩個負數),即有漢字
?* 2.len:這個len是將字符串轉換成字節數組的要截取的長度,
?*?? 如"我ABC你"的字節數組長度為7(-50,-46,65,66,67,-60,-29),而截取的是6(-50,-46,65,66,67,-60),
?* 3.對截取的字節數組(-50,-46,65,66,67,-60)統計負數的個數
?* 4.String里的方法substring方法將雙字節的漢字當成一個字節的字符(UCS2字符)處理了,而我們的字節數組一個函數
?*?? 就是兩個字節,所以要想用substring方法,還需要將負數的個數count除以二才可以
?* @author Administrator
?*
?*/
public class TestJq {
?public static String subString(String str, int len) {
? if (str == null && "".equals(str)) {
?? return null;
? }
? // 將字符串中的char數組轉換成指定編碼方式的byte數組的函數
? byte[] strBytes = null;
? try {
?? strBytes = str.getBytes("GBK");
? } catch (UnsupportedEncodingException e) {
?? e.printStackTrace();
? }
? // 得到字符串的長度,判斷截取字符串的長度是否在判斷的范圍內,否則返回原串
? int strLen = strBytes.length;
? if (len >= strLen || len < 1) {
?? return str;
? }
?? System.out.println("strBytes.length="+strBytes.length);
?? System.out.println("len="+len);
? int count = 0;
? for (int i = 0; i < len; i++) {
?? // 將每個字節數組轉換為整型數,以為后面根據值的正負來判斷是否為漢字
?? int value = strBytes[i];
?? System.out.print(value+",");? //我ABC你? -50,-46,65,66,67,-60,-29
?? //對于第一種情況:
?? //注,一個函數轉換成整型數就為兩個負整數,上面的”我ABC你“,
?? //轉換成整型數就為-50,-46,65,66,67,-60,-29,但是len=6,所以截取下來的就是-50,-46,65,66,67,-60,count就為3
?? // 如果是漢字(負),則統計截取字符串中的漢字所占字節數
?? if (value < 0) {
??? count++;
?? }
?? System.out.println("zh count="+count);
? }
? // 依據判斷給定的字符串是否含有漢字,利用String類的substring()方法來截取不同的長度
?
? // 根據所統計的字節數,判斷截取到字符是否為半個漢字,奇數為半個漢字
? if (count % 2 != 0) {
?? // 如果在截取長度為1時,則將該漢字取出,
?? // 其他情況則不截取這里的截取長度則按字符長度截取(截取字節長度數-截取漢字字節數/2-截取到的半個漢字的字節數)
?? len = (len == 1) ? len : len - count / 2 - 1; //len=6-3/2-1=4? 我ABC
?? // System.out.println("處理后的len="+len);
?
? } else {
?? // 截取字符長度為字節長度-漢字所占字節長度/2(漢字占兩個字節)
?? len = len - (count / 2);
? }
? return str.substring(0, len);
?
?}
?
?public static void main(String[] args) {
?
//? String inStrTest = "我ABC你EFG";
//? String strTest = inStrTest.substring(0, 2);
//? System.out.println(strTest);
?
? System.out.println("--------- 情況一-----------");
? // 情況一:
? String inStr = "我ABC你";
? String str = subString(inStr, 6);
? System.out.println(str); // 我ABC www.2cto.com
?
? System.out.println("---------- 情況二----------");
? // 情況二:首字符為漢字
? inStr = "我ABC漢DEF";
? str = subString(inStr, 1);
? System.out.println(str); // 我
?
? System.out.println("-----------情況三---------");
?
? // 情況三:中間有連續漢字
? inStr = "我AB愛孩子CDEF";
? str = subString(inStr, 9);
? System.out.println(str); // 我AB愛孩
?
? System.out.println("-----------情況四---------");
? // 情況四:沒有漢字
? inStr = "ABCDEF";
? str = subString(inStr, 4);
? System.out.println(str); // ABCD
?}
?
}
Web應用程序在瀏覽器中顯示字符串時,由于顯示長度的限制,常常需要將字符串截取后再進行顯示。但目前很多流行的語言,如C#、Java內部采用的都是Unicode 16(UCS2)編碼,在這種編碼中所有的字符都是兩個字符,因此,如果要截取的字符串是中、英文、數字混合的,就會產生問題,如下面的字符串:
?
?
?
String s = "a加b等于c,如果a等1、b等于2,那么c等3";
?
?
?
上面的字符串既有漢字,又有英文字符和數字。如果要截取前6個字節的字符,應該是”a加b等",但如果用substring方法截取前6個字符就成了"a 加b等于c"。產生這個問題的原因是將substring方法將雙字節的漢字當成一個字節的字符(UCS2字符)處理了。要解決這個問題的方法是首先得到該字符串的UCS2編碼的字節數組,如下面的代碼如下:
?
?
?
byte[] bytes = s.getBytes("Unicode");
?
?
?
由于上面生成的字節數組中前兩個字節是標志位,bytes[0] = -2,bytes[1] = -1,因此,要從第三個字節開始掃描,對于一個英文或數字字符,UCS2編碼的第二個字節是相應的ASCII,第一個字節是0,如a的UCS2編碼是0? 97,而漢字兩個字節都不為0,因此,可以利于UCS2編碼的這個規則來計算實際的字節數
總結
以上是生活随笔為你收集整理的JAVA 中字符串的截取,要求不能截取半个汉字的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 异常与锁的释放(synchronized
- 下一篇: 程序员必知的8大排序(三)-------