swift utf16 数据流 - 分成块的问题
swift utf16 data stream - issue dividing into chunks
我可以请求帮助将 UTF-16 数据流拆分成块吗?
不幸的是,很难找到字母边界。
任何帮助表示感谢,已经花了几个晚上在这上面,很想了解这个问题。
Java 版本工作正常(是否有任何自动更正,即使在拆分前两个字节时输出也会给出正确的字符串作为第 2 部分?):
public static void main(String[] args) throws Exception {
String encoding = "UTF-16";
byte[] data = "ČŘŠŤĎŽŇčřšťďňě".getBytes(encoding);
System.out.println("Data size: "+data.length);
for(int index=2; index<= data.length / 2; index+=2)
{
byte[] part1 = java.util.Arrays.copyOfRange(data, 0, index);
byte[] part2 = java.util.Arrays.copyOfRange(data, index, data.length);
assert(part1.length + part2.length == data.length);
System.out.println("--------------------- "+index);
System.out.println(new String(part1, encoding));
System.out.println(new String(part2, encoding));
}
}
Java 输出:
Data size: 30
--------------------- 2
ČŘŠŤĎŽŇčřšťďňě
--------------------- 4
Č
ŘŠŤĎŽŇčřšťďňě
--------------------- 6
ČŘ
ŠŤĎŽŇčřšťďňě
--------------------- 8
....
Swift(Xcode 8 beta 6,Swift 3)操场代码:
import Foundation
let encoding = String.Encoding.utf16
let data = "ČŘŠŤĎŽŇčřšťďňě".data(using: encoding)!
print("Data size: \(data.count)")
for index in stride(from: 2, to: data.count/2, by: 2)
{
let part1 = data.subdata(in: 0..<index)
let part2 = data.subdata(in: index..<data.count)
assert(part1.count + part2.count == data.count)
print("--------------------- \(index)")
print(String(data: part1, encoding: encoding))
print(String(data: part2, encoding: encoding))
}
Swift 输出:
Data size: 30
--------------------- 2
Optional("")
Optional("ఁ堁态搁ก紁䜁ഁ夁愁攁༁䠁ᬁ")
--------------------- 4
Optional("Č")
Optional("堁态搁ก紁䜁ഁ夁愁攁༁䠁ᬁ")
--------------------- 6
Optional("ČŘ")
Optional("态搁ก紁䜁ഁ夁愁攁༁䠁ᬁ")
--------------------- 8
Optional("ČŘŠ")
Optional("搁ก紁䜁ഁ夁愁攁༁䠁ᬁ")
--------------------- 10
Optional("ČŘŠŤ")
Optional("ก紁䜁ഁ夁愁攁༁䠁ᬁ")
--------------------- 12
Optional("ČŘŠŤĎ")
Optional("紁䜁ഁ夁愁攁༁䠁ᬁ")
如果我将 swift 编码更改为 String.Encoding.utf8,输出符合预期,但对于 utf16 和 utf32,我不明白发生了什么。
谢谢。
简答:使用utf16LittleEndian
或utf16BigEndian
编码
获得预期结果:
Data size: 28
--------------------- 2
Optional("Č")
Optional("ŘŠŤĎŽŇčřšťďňě")
--------------------- 4
Optional("ČŘ")
Optional("ŠŤĎŽŇčřšťďňě")
--------------------- 6
Optional("ČŘŠ")
Optional("ŤĎŽŇčřšťďňě")
...
更长的答案: utf16
编码将字符串转换为小端
UTF-16 数据,以字节顺序标记为前缀:
let data = "abc".data(using: .utf16)!
print(data as NSData) // <fffe6100 62006300>
当数据被拆分成两部分时,第二部分还没有
不再是前导字节顺序标记:
let part1 = data.subdata(in: 0..<4)
let part2 = data.subdata(in: 4..<8)
print(part1 as NSData, part2 as NSData) // <fffe6100> <62006300>
没有字节序标记的部分显然是转换错了
它是一个 big-endian 现在假定的字节顺序:
print(String(data: part1, encoding: .utf16)) // Optional("a")
print(String(data: part2, encoding: .utf16)) // Optional("戀挀")
print(String(data: part2, encoding: .utf16LittleEndian)) // Optional("bc")
我可以请求帮助将 UTF-16 数据流拆分成块吗?
不幸的是,很难找到字母边界。
任何帮助表示感谢,已经花了几个晚上在这上面,很想了解这个问题。
Java 版本工作正常(是否有任何自动更正,即使在拆分前两个字节时输出也会给出正确的字符串作为第 2 部分?):
public static void main(String[] args) throws Exception {
String encoding = "UTF-16";
byte[] data = "ČŘŠŤĎŽŇčřšťďňě".getBytes(encoding);
System.out.println("Data size: "+data.length);
for(int index=2; index<= data.length / 2; index+=2)
{
byte[] part1 = java.util.Arrays.copyOfRange(data, 0, index);
byte[] part2 = java.util.Arrays.copyOfRange(data, index, data.length);
assert(part1.length + part2.length == data.length);
System.out.println("--------------------- "+index);
System.out.println(new String(part1, encoding));
System.out.println(new String(part2, encoding));
}
}
Java 输出:
Data size: 30
--------------------- 2
ČŘŠŤĎŽŇčřšťďňě
--------------------- 4
Č
ŘŠŤĎŽŇčřšťďňě
--------------------- 6
ČŘ
ŠŤĎŽŇčřšťďňě
--------------------- 8
....
Swift(Xcode 8 beta 6,Swift 3)操场代码:
import Foundation
let encoding = String.Encoding.utf16
let data = "ČŘŠŤĎŽŇčřšťďňě".data(using: encoding)!
print("Data size: \(data.count)")
for index in stride(from: 2, to: data.count/2, by: 2)
{
let part1 = data.subdata(in: 0..<index)
let part2 = data.subdata(in: index..<data.count)
assert(part1.count + part2.count == data.count)
print("--------------------- \(index)")
print(String(data: part1, encoding: encoding))
print(String(data: part2, encoding: encoding))
}
Swift 输出:
Data size: 30
--------------------- 2
Optional("")
Optional("ఁ堁态搁ก紁䜁ഁ夁愁攁༁䠁ᬁ")
--------------------- 4
Optional("Č")
Optional("堁态搁ก紁䜁ഁ夁愁攁༁䠁ᬁ")
--------------------- 6
Optional("ČŘ")
Optional("态搁ก紁䜁ഁ夁愁攁༁䠁ᬁ")
--------------------- 8
Optional("ČŘŠ")
Optional("搁ก紁䜁ഁ夁愁攁༁䠁ᬁ")
--------------------- 10
Optional("ČŘŠŤ")
Optional("ก紁䜁ഁ夁愁攁༁䠁ᬁ")
--------------------- 12
Optional("ČŘŠŤĎ")
Optional("紁䜁ഁ夁愁攁༁䠁ᬁ")
如果我将 swift 编码更改为 String.Encoding.utf8,输出符合预期,但对于 utf16 和 utf32,我不明白发生了什么。
谢谢。
简答:使用utf16LittleEndian
或utf16BigEndian
编码
获得预期结果:
Data size: 28 --------------------- 2 Optional("Č") Optional("ŘŠŤĎŽŇčřšťďňě") --------------------- 4 Optional("ČŘ") Optional("ŠŤĎŽŇčřšťďňě") --------------------- 6 Optional("ČŘŠ") Optional("ŤĎŽŇčřšťďňě") ...
更长的答案: utf16
编码将字符串转换为小端
UTF-16 数据,以字节顺序标记为前缀:
let data = "abc".data(using: .utf16)!
print(data as NSData) // <fffe6100 62006300>
当数据被拆分成两部分时,第二部分还没有 不再是前导字节顺序标记:
let part1 = data.subdata(in: 0..<4)
let part2 = data.subdata(in: 4..<8)
print(part1 as NSData, part2 as NSData) // <fffe6100> <62006300>
没有字节序标记的部分显然是转换错了 它是一个 big-endian 现在假定的字节顺序:
print(String(data: part1, encoding: .utf16)) // Optional("a")
print(String(data: part2, encoding: .utf16)) // Optional("戀挀")
print(String(data: part2, encoding: .utf16LittleEndian)) // Optional("bc")