SCNetworkReachabilityRef
介面可以確定當前主機的網路狀態以及目標主機的可達性, 可達性是指data packet(資料包)可以從當前主機傳送出去, 而不是目標主機可以接收到data packet(資料包).
SCNetworkReachabilityRef
介面有同步和非同步兩種模式.
在同步模式下, 可以通過SCNetworkReachabilityGetFlags
方法獲取網路狀態;
在非同步模式下, 可以排程一個SCNetworkReachability
物件到客戶端的執行迴圈上, 客戶端實現一個回撥函式接收網路狀態變化的通知, 這個回撥函式遵循Core Foundation
命名規範, 只要函式名中包含 "Create" 或 "Copy"的函式返回的引用,都必須呼叫CFRelease來釋放。
SCNetworkReachabilityRef
中幾個主要的方法和屬性:
SCNetworkReachabilityContext結構體
typedef struct {
CFIndex version;
void * __nullable info;
const void * __nonnull (* __nullable retain)(const void *info);
void (* __nullable release)(const void *info);
CFStringRef __nonnull (* __nullable copyDescription)(const void *info);
} SCNetworkReachabilityContext;
複製程式碼
結構體中包含使用者指定的資料資訊和用於SCNetworkReachabilitySetCallback
方法的回撥info
.
version
為版本號, 作為引數傳遞給SCDynamicStore
建立結構體型別的版本號. 這個結構體的版本號為0.
info
是一個C語言的指標物件, 這裡一般傳入當網路狀態發生改變時執行的block
回撥, 個人理解為C語言的指標不在ARC
的管理範圍內, 需要手動管理記憶體, 所以這裡傳入release info
和retain info
用於管理記憶體.
這個結構體需要在SCNetworkReachabilitySetCallback
設定才能起作用.
建立網路連線引用
SCNetworkReachabilityRef SCNetworkReachabilityCreateWithAddress(CFAllocatorRef allocator, const struct sockaddr *address);
複製程式碼
通過傳入需要測試的IP地址建立網路連線引用, allocator
可以設定為NULL
或者kCFAllocatorDefault
.
SCNetworkReachabilityRef SCNetworkReachabilityCreateWithName(CFAllocatorRef allocator, const char *nodename);
複製程式碼
通過傳入需要測試的網址建立網路連線引用, 同上個方法.
獲取網路連線狀態
Boolean SCNetworkReachabilityGetFlags(SCNetworkReachabilityRef target, SCNetworkReachabilityFlags *flags);
複製程式碼
用於獲取網路連線的狀態, 傳入的第一個引數是SCNetworkReachabilityRef
網路連線引用, 第二個引數用來儲存獲取的網路連線狀態, 如果能獲取到連線就返回true
否則返回false
.
網路狀態改變時的通知
Boolean SCNetworkReachabilitySetCallback(SCNetworkReachabilityRef target, SCNetworkReachabilityCallBack callout, SCNetworkReachabilityContext *context);
複製程式碼
當網路狀態發生變化時, 就會呼叫callout
, 第一個引數是網路連線引用, 第二個引數是回撥, 如果為NULL
, 當前的target
就會被移除, SCNetworkReachabilityCallBack
的型別為(typedef void (*SCNetworkReachabilityCallBack)(SCNetworkReachabilityRef target, SCNetworkReachabilityFlags flags, void *info);) callout回撥中的info
引數就是從第三個引數context結構體中取的info
回撥, 這樣就把結構體context
中的資料傳到了SCNetworkReachabilityCallBack
引數中, 第三個引數是與callout
相關聯的上下文, 可能為空. 如果通知客戶端成功就返回true
, 否則返回false
.
Boolean SCNetworkReachabilityScheduleWithRunLoop(SCNetworkReachabilityRef target, CFRunLoopRef runLoop, CFStringRef runLoopMode);
複製程式碼
使用指定的執行迴圈和模式排程指定的網路目標, 第一個引數是網路連線引用, 第二個引數runloop
迴圈, 第三個引數迴圈模式. 如果target
執行成功就返回true
, 否則返回false
.
這裡將target
加入指定的runloop
中, 會一直監測target
的網路狀態, 當網路狀態發生變化時就會執行SCNetworkReachabilitySetCallback
方法中的callout
回撥, 所以我們只需要定義一個SCNetworkReachabilityCallBack
型別的block
, 將其傳入SCNetworkReachabilitySetCallback
方法中即可.