1、在移動開發中,我們會遇到一個網址在瀏覽器上可以載入,但是在App上就不可以載入的情況或則網址解析不出來等。這類情況大多是由於網址含有特俗的字元,包括漢字而造成的。這種原因的處理也有很多方法,網上到處都是。但是,隨著App等系統的升級和更新,支援的程式設計語言的更替,有的方法就有所不足。今天,我對此總結了一下,不敢說以後能用,但是目前絕對是一流的。
2、我們首先舉出一個URL。如下:
@"https://www.goufree.com/wap/tmpl/product_list.html?keyword=電腦&type=黃花"
上面這個網址。我們也沒有看出它有什麼不妥,對,將它放入瀏覽器中它可以順利載入,但是,在App中它就不可以載入。為什麼會出現這種情況。。,這又怎麼解決。。
3、對上述的問題的處理。
第一:含有漢字的網址。
#pragma mark 漢字轉碼處理-(NSString*)encodeCharactersString:(NSString*)inputString{ //** 擷取系統號 NSInteger versonValue = [UIDevice currentDevice].systemVersion.floatValue; if (versonValue<7.0) { //** 進行編碼 inputString = [inputString stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding]; }else{ //** 我們進行漢文書處理 NSMutableString * outString = [NSMutableString stringWithCapacity:0]; for (unsigned int i=0; i<inputString.length; i++) { int utfCode = 0; void * buffer = &utfCode; NSRange range = NSMakeRange(i, 1); BOOL encode = [inputString getBytes:buffer maxLength:10 usedLength:NULL encoding:NSUTF16LittleEndianStringEncoding options:NSStringEncodingConversionExternalRepresentation range:range remainingRange:NULL]; if (encode && (utfCode>=0x4e00 && utfCode<=0x9fa5)) { [outString appendString:[inputString substringWithRange:range]]; } } //**設定處理 inputString = [inputString stringByAddingPercentEncodingWithAllowedCharacters:[NSCharacterSet characterSetWithCharactersInString:[NSString stringWithFormat:@"%@",outString]].invertedSet]; } return inputString;}我們對上面的方法進行測試:
NSString * loadString = @"https://www.goufree.com/wap/tmpl/product_list.html?keyword=電腦&word=黃花"; NSLog(@"%@", [self encodeCharactersString:loadString]); //** 輸出:2017-01-13 14:09:48.697 URL的編碼處理[2537:513951] https://www.goufree.com/wap/tmpl/product_list.html?keyword=%E7%94%B5%E8%84%91&word=%E9%BB%84%E8%8A%B1
第二種:含有特殊字元的網址編碼。
含有特殊字元的編碼的方法有兩種:
1》第一種:
#pragma mark 特殊轉碼- (NSString *)encodeToPercentEscapeString: (NSString *) inputString{ //** 擷取系統的版本 NSInteger VersonValue = [UIDevice currentDevice].systemVersion.floatValue ; if (VersonValue>=8.0) { //** 我們要做一些處理,處理就是處理後方的參數 if (![inputString containsString:@"?"]) { return inputString; } }else{ //** 系統8,以下的處理方法 if ([inputString componentsSeparatedByString:@"?"].count==1) { return inputString; } } //** 這裡分割處理 NSArray * divisionArray = [inputString componentsSeparatedByString:@"?"]; //** 處理後的半部分網址 NSMutableString * lastUrlString = [NSMutableString stringWithCapacity:0]; if (divisionArray.count>=2) { for (unsigned int i =1; i<divisionArray.count; i++) { [lastUrlString appendFormat:@"%@", [NSString stringWithFormat:@"?%@",divisionArray[i]]]; } } //** 網域名稱 NSString * domainString = divisionArray.firstObject; //** 編碼處理 NSString *encodingString = (NSString *) CFBridgingRelease(CFURLCreateStringByAddingPercentEscapes(kCFAllocatorDefault, (CFStringRef)lastUrlString,NULL,(CFStringRef)@"!@#$^%*+,:;'\"`<>()[]{}/\\|",kCFStringEncodingUTF8)); NSString * outEncodingString =[NSString stringWithFormat:@"%@%@",domainString,encodingString]; //** 釋放記憶體 domainString=nil,encodingString=nil,divisionArray=nil; return outEncodingString;}
2》第二種:
#pragma mark 特殊轉碼-(NSString*)specialEncoding:(NSString*)inputString{ //** 擷取系統的版本 NSInteger VersonValue = [UIDevice currentDevice].systemVersion.floatValue ; if (VersonValue>=8.0) { //** 我們要做一些處理,處理就是處理後方的參數 if (![inputString containsString:@"?"]) { return inputString; } }else{ //** 系統8,以下的處理方法 if ([inputString componentsSeparatedByString:@"?"].count==1) { return inputString; } } //** 這裡分割處理 NSArray * divisionArray = [inputString componentsSeparatedByString:@"?"]; //** 處理後的半部分網址 NSMutableString * lastUrlString = [NSMutableString stringWithCapacity:0]; if (divisionArray.count>=2) { for (unsigned int i =1; i<divisionArray.count; i++) { [lastUrlString appendFormat:@"%@", [NSString stringWithFormat:@"?%@",divisionArray[i]]]; } } //** 網域名稱 NSString * domainString = divisionArray.firstObject; //** 設定編碼條件 NSString * characterSetString = @"!@#$^%*+,:;'\"`<>()[]{}/\\|"; //** 類型轉化,防止警告 NSString * encodingString = [NSString stringWithFormat:@"%@", lastUrlString]; //** 進行編碼 encodingString = [encodingString stringByAddingPercentEncodingWithAllowedCharacters:[NSCharacterSet characterSetWithCharactersInString:characterSetString].invertedSet]; //** 請求網址 inputString = [NSString stringWithFormat:@"%@?%@",domainString,encodingString]; //** 釋放記憶體 divisionArray=nil,domainString = nil,encodingString=nil; return inputString;}
我們對上訴兩種方法進行測試和對比:
//** 含有特殊字元的網址 NSString * specialString = @"https://www.goufree.com/wap/tmpl/product_list.html?keyword={}"; //** 我們觀察specialString,我們發現“{}”,一個特俗字元。如果,我們強行載入是不成功的。 NSLog(@"%@",[self specialEncoding:specialString]); //** 輸出:2017-01-13 14:27:15.899 URL的編碼處理[2817:591189] https://www.goufree.com/wap/tmpl/product_list.html??keyword=%7B%7D
//** 含有特殊字元的網址 NSString * specialString = @"https://www.goufree.com/wap/tmpl/product_list.html?keyword={}"; //** 我們觀察specialString,我們發現“{}”,一個特俗字元。如果,我們強行載入是不成功的。 NSLog(@"%@",[self encodeToPercentEscapeString:specialString]); //** 輸出:2017-01-13 14:27:15.899 URL的編碼處理[2817:591189] https://www.goufree.com/wap/tmpl/product_list.html??keyword=%7B%7D
3、我們編碼完畢的網址進行解碼
#pragma mark 還原網頁編碼-(NSString*)reductionEncoding:(NSString*)inputString{ inputString = [inputString stringByRemovingPercentEncoding]; return inputString;} 對方法的測試:
//** 解碼測試 NSString * test = @"https://www.goufree.com/wap/tmpl/product_list.html??keyword=%7B%7D"; NSLog(@"%@",[self reductionEncoding:test]); //** 輸出:2017-01-13 14:38:07.183 URL的編碼處理[2998:653386] https://www.goufree.com/wap/tmpl/product_list.html??keyword={}4、建議。
網頁上對Url的編碼非常多,但是可用的非常少,建議使用的時候,要進行測試。
5、demo的擷取方法
本部落格附有對應的demo,如果有需要的可以加 QQ:1542100658 或 QQ群:成功QQ吧。回複即可擷取。