场景提出
故事要从微信消息推送说起,因为微信对文本消息的推送限定字节数为2048个,多出来的直接被砍掉。所以就想要对过长的文本消息进行拆分。
起初想的是用字节数据拆分,但是发现用字节数组拆分,会出现消息转化乱码的问题,原因其实也很好理解,因为不同字符占用的字节数不一样,所以简单的拆分又重新转换为String,就会出现将本来一个字符的上半个字节转换为一个字符,下半个字节转换为一个字符,这样就出现了乱码。
因此,我决定按字符去拆分,但是按字符去拆分:(最终pageSize取600)
代码示例
拆分方法(代码片段):
public List splitMessageByChars(String message,int pageSize) {
List messages = Lists.newArrayList();
char[] chars = message.toCharArray();
for (int i = 0;i
int j = i + pageSize;
String m ;
if (j>chars.length){
m = new String(chars,i,chars.length-i);
}else {
m = new String(chars,i,pageSize);
}
if (m.indexOf('\n')==0){
messages.add(m.substring(1));
}else {
messages.add(m);
}
}
return messages;
}
可以看到代码中对\n做了过滤,原因是微信的文本消息推送,如果你首字符为\n的话就会报错,所以就需要对消息首字符为\n的情况做单独处理。
字节数占用的验证(代码片段)
@Test
public void contextLoads() throws UnsupportedEncodingException {
List charsets = Lists.newArrayList();
charsets.add(StandardCharsets.UTF_8.name());
charsets.add(StandardCharsets.UTF_16.name());
charsets.add(StandardCharsets.UTF_16BE.name());
charsets.add(StandardCharsets.UTF_16LE.name());
charsets.add(StandardCharsets.ISO_8859_1.name());
charsets.add(StandardCharsets.US_ASCII.name());
charsets.add("UTF-32");
charsets.add("GBK");
charsets.add("GB2312");
charsets.add("unicode");
List ss = Lists.newArrayList();
ss.add("测");
ss.add("a");
ss.add("aa");
ss.add("aaa");
ss.add("\n");
ss.add("\\");
for (String s : ss){
//字节测试
System.out.println("---------"+"字符:\t"+s+"\t-------");
for (String cs : charsets){
System.out.println("在"+cs+"编码下字节数为:"+s.getBytes(cs).length);
}
}
}
执行结果
Axitrader代理申请https://www.fx61.com/brokerlist/axitrader.html
---------字符: 测 -------
在UTF-8编码下字节数为:3
在UTF-16编码下字节数为:4
在UTF-16BE编码下字节数为:2
在UTF-16LE编码下字节数为:2
在ISO-8859-1编码下字节数为:1
在US-ASCII编码下字节数为:1
在UTF-32编码下字节数为:4
在GBK编码下字节数为:2
在GB2312编码下字节数为:2
在unicode编码下字节数为:4
---------字符: a -------
在UTF-8编码下字节数为:1
在UTF-16编码下字节数为:4
在UTF-16BE编码下字节数为:2
在UTF-16LE编码下字节数为:2
在ISO-8859-1编码下字节数为:1
在US-ASCII编码下字节数为:1
在UTF-32编码下字节数为:4
在GBK编码下字节数为:1
在GB2312编码下字节数为:1
在unicode编码下字节数为:4
---------字符: aa -------
在UTF-8编码下字节数为:2
在UTF-16编码下字节数为:6
在UTF-16BE编码下字节数为:4
在UTF-16LE编码下字节数为:4
在ISO-8859-1编码下字节数为:2
在US-ASCII编码下字节数为:2
在UTF-32编码下字节数为:8
在GBK编码下字节数为:2
在GB2312编码下字节数为:2
在unicode编码下字节数为:6
---------字符: aaa -------
在UTF-8编码下字节数为:3
在UTF-16编码下字节数为:8
在UTF-16BE编码下字节数为:6
在UTF-16LE编码下字节数为:6
在ISO-8859-1编码下字节数为:3
在US-ASCII编码下字节数为:3
在UTF-32编码下字节数为:12
在GBK编码下字节数为:3
在GB2312编码下字节数为:3
在unicode编码下字节数为:8
---------字符:
-------
在UTF-8编码下字节数为:1
在UTF-16编码下字节数为:4
在UTF-16BE编码下字节数为:2
在UTF-16LE编码下字节数为:2
在ISO-8859-1编码下字节数为:1
在US-ASCII编码下字节数为:1
在UTF-32编码下字节数为:4
在GBK编码下字节数为:1
在GB2312编码下字节数为:1
在unicode编码下字节数为:4
---------字符: \ -------
在UTF-8编码下字节数为:1
在UTF-16编码下字节数为:4
在UTF-16BE编码下字节数为:2
在UTF-16LE编码下字节数为:2
在ISO-8859-1编码下字节数为:1
在US-ASCII编码下字节数为:1
在UTF-32编码下字节数为:4
在GBK编码下字节数为:1
在GB2312编码下字节数为:1
在unicode编码下字节数为:4
最后为简单结论
'\n’是一个字符,占1个字节 汉字若是用UTF-8编码,占3个字节,特别的汉字占用4个字节 汉字若是用GBK编码,占2个字节。
汉字若是用UTF-16编码,占2个字节,特别的汉字占用4个字节
字母若是用UTF-8编码,占1个字节。
字母若是用UTF-16编码,占2个字节。(至于下面代码中,a占4个,aa占6个,aaa占8个原因是,java在其中)
字母若是用UTF-32编码,占4个字节。 字母若是用GBK编码,占1个字节。 字母若是用GB2312编码,占1个字节。
|
|