在IOS應用程式開發中,為了減少與服務端的互動次數,加快使用者的響應速度,一般都會在IOS裝置中加一個緩衝的機制。使用緩衝的目的是為了使用的應用程式能更快速的響應使用者輸入,是程式高效的運行。有時候我們需要將遠程web伺服器擷取的資料緩衝起來,減少對同一個url多次請求。下面將介紹如何在IOS裝置中進行緩衝。
記憶體緩衝我們可以使用sdk中的NSURLCache類。NSURLRequest需要一個緩衝參數來說明它請求的url何如快取資料的,我們先看下它的CachePolicy類型。
1、NSURLRequestUseProtocolCachePolicy NSURLRequest預設的cache policy,使用Protocol協議定義。
2、NSURLRequestReloadIgnoringCacheData 忽略緩衝直接從原始地址下載。
3、NSURLRequestReturnCacheDataElseLoad 只有在cache中不存在data時才從原始地址下載。
4、NSURLRequestReturnCacheDataDontLoad 只使用cache資料,如果不存在cache,請求失敗;用於沒有建立網路連接離線模式;
5、NSURLRequestReloadIgnoringLocalAndRemoteCacheData:忽略本地和遠端快取資料,直接從原始地址下載,與NSURLRequestReloadIgnoringCacheData類似。
6、NSURLRequestReloadRevalidatingCacheData:驗證本機資料與遠端資料是否相同,如果不同則下載遠端資料,否則使用本機資料。
一些常用方法與屬性:
//擷取當前應用的緩衝管理對象
+ (NSURLCache *)sharedURLCache;
//設定自訂的NSURLCache作為應用緩衝管理對象
+ (void)setSharedURLCache:(NSURLCache *)cache;
//初始化一個應用緩衝對象
/*
memoryCapacity 設定記憶體緩衝容量
diskCapacity 設定磁碟緩衝容量
path 磁碟緩衝路徑
內容緩衝會在應用程式退出後 清空 磁碟緩衝不會
*/
- (instancetype)initWithMemoryCapacity:(NSUInteger)memoryCapacity diskCapacity:(NSUInteger)diskCapacity diskPath:(nullable NSString *)path;
//擷取某一請求的緩衝
- (nullable NSCachedURLResponse *)cachedResponseForRequest:(NSURLRequest *)request;
//給請求設定指定的緩衝
- (void)storeCachedResponse:(NSCachedURLResponse *)cachedResponse forRequest:(NSURLRequest *)request;
//移除某個請求的緩衝
- (void)removeCachedResponseForRequest:(NSURLRequest *)request;
//移除所有快取資料
- (void)removeAllCachedResponses;
//移除某個時間起的緩衝設定
- (void)removeCachedResponsesSinceDate:(NSDate *)date NS_AVAILABLE(10_10, 8_0);
//記憶體緩衝容量大小
@property NSUInteger memoryCapacity;
//磁碟緩衝容量大小
@property NSUInteger diskCapacity;
//當前已用記憶體容量
@property (readonly) NSUInteger currentMemoryUsage;
//當前已用磁碟容量
@property (readonly) NSUInteger currentDiskUsage;
簡單例子:
#import
@interface ViewController : UIViewController
@property (strong, nonatomic) NSURLConnection *connection;
@property (strong, nonatomic) NSURLCache *urlCache;
@property (strong, nonatomic) NSURL *url;
@property (strong, nonatomic) NSMutableURLRequest *request;
- (IBAction)reloadWebView:(UIButton *)sender;
@end
#import "ViewController.h"
@interface ViewController ()
@end
@implementation ViewController
- (void)viewDidLoad
{
[super viewDidLoad];
NSString *paramURLAsString= @"http://blog.sina.com.cn/u/2526279194";
self.urlCache = [NSURLCache sharedURLCache];
[self.urlCache setMemoryCapacity:1*1024*1024];
//建立一個nsurl
self.url = [NSURL URLWithString:paramURLAsString];
//建立一個請求
self.request=[NSMutableURLRequest requestWithURL:self.url
cachePolicy:NSURLRequestUseProtocolCachePolicy
timeoutInterval:30.0f];
[self.myWebView loadRequest:self.request];
}
這個例子中,我們請求url為http://blog.sina.com.cn/u/2526279194的網站。如果這個url被緩衝了,我們直接從緩衝中擷取資料,否則從http://blog.sina.com.cn/u/2526279194網站上重新擷取資料。我們設定了緩衝大小為1M。
- (IBAction)reloadWebView:(UIButton *)sender {
//從請求中擷取緩衝輸出
NSCachedURLResponse *response =[self.urlCache cachedResponseForRequest:self.request];
//判斷是否有緩衝
if (response != nil){
NSLog(@"如果有緩衝輸出,從緩衝中擷取資料");
[self.request setCachePolicy:NSURLRequestReturnCacheDataDontLoad];
}
[self.myWebView loadRequest:self.request];
self.connection = nil;
NSURLConnection *newConnection = [[NSURLConnection alloc] initWithRequest:self.request
delegate:self
startImmediately:YES];
self.connection = newConnection;
}
使用下面代碼,我將請求的過程列印出來
- (void) connection:(NSURLConnection *)connection
didReceiveResponse:(NSURLResponse *)response{
NSLog(@"將接收輸出");
}
- (NSURLRequest *)connection:(NSURLConnection *)connection
willSendRequest:(NSURLRequest *)request
redirectResponse:(NSURLResponse *)redirectResponse{
NSLog(@"即將發送請求");
return(request);
}
- (void)connection:(NSURLConnection *)connection
didReceiveData:(NSData *)data{
NSLog(@"接受資料");
NSLog(@"資料長度為 = %lu", (unsigned long)[data length]);
}
- (NSCachedURLResponse *)connection:(NSURLConnection *)connection
willCacheResponse:(NSCachedURLResponse *)cachedResponse{
NSLog(@"將緩衝輸出");
return(cachedResponse);
}
- (void)connectionDidFinishLoading:(NSURLConnection *)connection{
NSLog(@"請求完成");
}
- (void)connection:(NSURLConnection *)connection
didFailWithError:(NSError *)error{
NSLog(@"請求失敗");
}
@end
第一次列印結果如下
2013-01-31 15:28:29.923 NSURLCacheDemo[27848:907] 即將發送請求2013-01-31 15:28:30.043 NSURLCacheDemo[27848:907] 將接收輸出2013-01-31 15:28:30.045 NSURLCacheDemo[27848:907] 接受資料2013-01-31 15:28:30.047 NSURLCacheDemo[27848:907] 資料長度為 = 300472013-01-31 15:28:30.095 NSURLCacheDemo[27848:907] 接受資料2013-01-31 15:28:30.098 NSURLCacheDemo[27848:907] 資料長度為 = 35752013-01-31 15:28:30.102 NSURLCacheDemo[27848:907] 接受資料2013-01-31 15:28:30.104 NSURLCacheDemo[27848:907] 資料長度為 = 14822013-01-31 15:28:30.105 NSURLCacheDemo[27848:907] 將緩衝輸出2013-01-31 15:28:30.107 NSURLCacheDemo[27848:907] 請求完成
第二次點擊列印結果如下
2013-01-31 15:28:31.599 NSURLCacheDemo[27848:907] 如果有緩衝輸出,從緩衝中擷取資料2013-01-31 15:28:31.607 NSURLCacheDemo[27848:907] 即將發送請求2013-01-31 15:28:31.840 NSURLCacheDemo[27848:907] 將接收輸出2013-01-31 15:28:31.843 NSURLCacheDemo[27848:907] 接受資料2013-01-31 15:28:31.845 NSURLCacheDemo[27848:907] 資料長度為 = 351042013-01-31 15:28:31.846 NSURLCacheDemo[27848:907] 請求完成
我們看到沒有“將緩衝輸出”一項,請求到的資料是第一次請求的累積,也就是第二次是從記憶體中擷取資料的。