在使用initwithdata
等方法將
nsdata轉換成nsstring時,如果nsdata的內容含有非encoding編碼的字元,將會返回nil。
----------sdk文件如下-------------
- (instancetype
)initwithdata:
()data
encoding:
()encoding;
return value
annsstring
object initialized by converting the bytes indata
into unicode characters usingencoding
. the returned object may be different from the original receiver. returnsnil
if the initialization fails for some reason (for example ifdata
does not represent valid data forencoding
).
-----------------------------
這個結果在很多時候可能並不是我們所希望的,比如在獲取網頁原始碼進行分析等方面,如果頁面採用了utf-8編碼,只是含有個別非utf-8字元,我們更希望轉換nsstring成功,拋棄(或替換)那些非法字元。
按照utf8格式標準
unicode/ucs-4
bit數
utf-8
byte數
範圍(16進製制)
0000 ~
007f
0~7
0*** ***x
1
0x - 7x
0080 ~
07ff
8~11
110x ***x
10xx ***x
2
cx 8x - dx bx
0800 ~
ffff
12~16
1110***x
10xx ***x
10xx ***x
3
ex 8x 8x - ex bx bx
1 0000 ~
1f ffff
17~21
1111 0***
10xx ***x
10xx ***x
10xx ***x
4
f8 8x 8x 8x 8x - fb bx bx bx bx
20 0000 ~
3ff ffff
22~26
1111 10xx
10xx ***x
10xx ***x
10xx ***x
10xx ***x
5
fc 8x 8x 8x 8x 8x - fd bx bx bx bx bx
400 0000 ~
7fff ffff
27~31
1111 110x
10xx ***x
10xx ***x
10xx ***x
10xx ***x
10xx ***x
6
如果乙個位元組小於0x80,那麼他就是乙個字元;
如果大於c0小於e0,表示2個位元組組成的utf8字元(第乙個是110開頭的,第二個是10開頭的);
如果大於e0小於f0,表示3個位元組組成的utf8字元(第乙個是1110開頭的,第二個是10開頭的,第三個是10開頭的);
以此類推,如果不符合utf-8規則,則表示乙個非法字元,只要替換這樣的字元即可。
實現方法如下(此實現可用但不夠嚴謹,如用於工程中建議進行優化):
[objc]view plain
copy
//替換非utf8字元
//注意:如果是三位元組utf-8,第二位元組錯誤,則先替換第一位元組內容(認為此位元組誤碼為三位元組utf8的頭),然後判斷剩下的兩個位元組是否非法;
- (nsdata
*)replacenoutf8:(
nsdata
*)data
;
//utf8最多6個字元,當前方法未使用
nsmutabledata
*md = [nsmutabledata
datawithdata
:data];
intloc =
0;
while
(loc
length
])
else
if((buffer & 0xe
0) == 0xc
0)
loc--;
//非法字元,將這個字元(乙個byte)替換為a
[mdreplacebytesinrange
:nsmakerange(loc, 1)
withbytes
:aalength:1
];
loc++;
continue
; }
else
if((buffer & 0xf
0) == 0xe
0)
loc--;
} loc--;
//非法字元,將這個字元(乙個byte)替換為a
[mdreplacebytesinrange
:nsmakerange(loc, 1)
withbytes
:aalength:1
];
loc++;
continue
; }
else
} return
md;
}
轉換後的nsdata就可以正確轉換為nsstring了。
*如果是非utf-8編碼,請自行對對應照編碼協議轉換。
解決NSData轉NSString返回nil的問題
在使用initwithdata 等方法將 nsdata轉換成nsstring時,如果nsdata的內容含有非encoding編碼的字元,將會返回nil。sdk文件如下 instancetype initwithdata dataencoding encoding return value annss...
NSDictionary轉NSData 相互轉換
前言 今天發現一些同學 在nsdictionary轉nsdata竟然抓瞎了,所以就粘出來這個簡單的方法!大家在做網路請求的時間,如nsconnection 把nsdata轉nsdictionary的事了吧!這裡是一樣的foundation庫提供的nsjsonserialization 的乙個方法 d...
NSDictionary轉NSData 相互轉換
前言 今天發現一些同學 在nsdictionary轉nsdata竟然抓瞎了,所以就粘出來這個簡單的方法!大家在做網路請求的時間,如nsconnection 把nsdata轉nsdictionary的事了吧!這裡是一樣的foundation庫提供的nsjsonserialization 的乙個方法 d...