日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

【IOS网络通信】socket第三方库 AsyncSocket(GCDAsyncSocket)

發(fā)布時間:2023/12/20 编程问答 29 豆豆
生活随笔 收集整理的這篇文章主要介紹了 【IOS网络通信】socket第三方库 AsyncSocket(GCDAsyncSocket) 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

【IOS網(wǎng)絡(luò)通信】socket第三方庫 AsyncSocket(GCDAsyncSocket)

分類: 【MAC/IOS下開發(fā)】 【網(wǎng)絡(luò)編程】 11510人閱讀 評論(4) 收藏 舉報 IOSsocketAsyncSocketGCDAsyncSocket

?? Socket描述了一個IP、端口對。它簡化了程序員的操作,知道對方的IP以及PORT就可以給對方發(fā)送消息,再由服務(wù)器端來處理發(fā)送的這些消息。所以,Socket一定包含了通信的雙發(fā),即客戶端(Client)與服務(wù)端(server)。


1)服務(wù)端利用Socket監(jiān)聽端口;

2)客戶端發(fā)起連接;

3)服務(wù)端返回信息,建立連接,開始通信;

4)客戶端,服務(wù)端斷開連接。


1套接字(socket)概念


? ?? ? 套接字(socket)是通信的基石,是支持TCP/IP協(xié)議的網(wǎng)絡(luò)通信的基本操作單元。


? ?? ? 應(yīng)用層通過傳輸層進行數(shù)據(jù)通信時,TCP會遇到同時為多個應(yīng)用程序進程提供并發(fā)服務(wù)的問題。多個TCP連接或多個應(yīng)用程序進程可能需要通過同一個 TCP協(xié)議端口傳輸數(shù)據(jù)。為了區(qū)別不同的應(yīng)用程序進程和連接,許多計算機操作系統(tǒng)為應(yīng)用程序與TCP/IP協(xié)議交互提供了套接字(Socket)接口。應(yīng) 用層可以和傳輸層通過Socket接口,區(qū)分來自不同應(yīng)用程序進程或網(wǎng)絡(luò)連接的通信,實現(xiàn)數(shù)據(jù)傳輸?shù)牟l(fā)服務(wù)。


2 建立socket連接


? ?? ? 建立Socket連接至少需要一對套接字,其中一個運行于客戶端,稱為ClientSocket,另一個運行于服務(wù)器端,稱為ServerSocket。


? ?? ? 套接字之間的連接過程分為三個步驟:服務(wù)器監(jiān)聽,客戶端請求,連接確認。


? ?? ? 服務(wù)器監(jiān)聽:服務(wù)器端套接字并不定位具體的客戶端套接字,而是處于等待連接的狀態(tài),實時監(jiān)控網(wǎng)絡(luò)狀態(tài),等待客戶端的連接請求。


? ?? ? 客戶端請求:指客戶端的套接字提出連接請求,要連接的目標是服務(wù)器端的套接字。為此,客戶端的套接字必須首先描述它要連接的服務(wù)器的套接字,指出服務(wù)器端套接字的地址和端口號,然后就向服務(wù)器端套接字提出連接請求。


? ?? ? 連接確認:當服務(wù)器端套接字監(jiān)聽到或者說接收到客戶端套接字的連接請求時,就響應(yīng)客戶端套接字的請求,建立一個新的線程,把服務(wù)器端套接字的描述發(fā) 給客戶端,一旦客戶端確認了此描述,雙方就正式建立連接。而服務(wù)器端套接字繼續(xù)處于監(jiān)聽狀態(tài),繼續(xù)接收其他客戶端套接字的連接請求。


4、SOCKET連接與TCP連接


? ?? ? 創(chuàng)建Socket連接時,可以指定使用的傳輸層協(xié)議,Socket可以支持不同的傳輸層協(xié)議(TCP或UDP),當使用TCP協(xié)議進行連接時,該Socket連接就是一個TCP連接。


5、Socket連接與HTTP連接


? ?? ? 由于通常情況下Socket連接就是TCP連接,因此Socket連接一旦建立,通信雙方即可開始相互發(fā)送數(shù)據(jù)內(nèi)容,直到雙方連接斷開。但在實際網(wǎng) 絡(luò)應(yīng)用中,客戶端到服務(wù)器之間的通信往往需要穿越多個中間節(jié)點,例如路由器、網(wǎng)關(guān)、防火墻等,大部分防火墻默認會關(guān)閉長時間處于非活躍狀態(tài)的連接而導(dǎo)致 Socket 連接斷連,因此需要通過輪詢告訴網(wǎng)絡(luò),該連接處于活躍狀態(tài)。

而HTTP連接使用的是“請求—響應(yīng)”的方式,不僅在請求時需要先建立連接,而且需要客戶端向服務(wù)器發(fā)出請求后,服務(wù)器端才能回復(fù)數(shù)據(jù)。


? ?? ? 很多情況下,需要服務(wù)器端主動向客戶端推送

? ?? ? iphone的標準推薦CFNetwork C庫編程.但是編程比較煩躁。在其它OS往往用類來封裝的對Socket函數(shù)的處理。比如MFC的CAsysncSocket.在iphone也有類似于 開源項目.cocoa AsyncSocket庫, 官方網(wǎng)站:http://code.google.com/p/cocoaasyncsocket/?它用來簡化 CFnetwork的調(diào)用.


一.在項目引入ASyncSocket庫


??1.下載ASyncSocket庫源碼

??2.把ASyncSocket庫源碼加入項目:只需要增加RunLoop目錄中的AsyncSocket.h、AsyncSocket.m、AsyncUdpSocket.h和AsyncUdpSocket.m四個文件。

??3.在項目增加CFNetwork框架

? ?? ? 在Framework目錄右健,選擇Add-->Existing Files...? ? , 選擇 CFNetwork.framework


二.TCP客戶端


??1. 在controller頭文件定義AsyncSocket對象


  • #import #import "AsyncSocket.h"
  • @interface HelloiPhoneViewController : UIViewController {? ? UITextField? ? * textField;? ? AsyncSocket * asyncSocket;}@property (retain, nonatomic) IBOutlet UITextField *textField;- (IBAction) buttonPressed: (id)sender;- (IBAction) textFieldDoneEditing: (id)sender;? ? @end
  • 復(fù)制代碼

    ??2.在需要聯(lián)接地方使用connectToHost聯(lián)接服務(wù)器


    ? ?? ? 其中initWithDelegate的參數(shù)中self是必須。這個對象指針中的各個Socket響應(yīng)的函數(shù)將被ASyncSocket所調(diào)用.


    ? ?asyncSocket = [[AsyncSocket alloc] initWithDelegate:self];

  • ? ? NSError *err = nil;? ???if(![asyncSocket connectToHost:host on:port error:&err])? ???{? ?? ?? ?NSLog(@"Error: %@", err);? ???}
  • 復(fù)制代碼

    3.增加Socket響應(yīng)事件


    ? ???因為initWithDelegate把將當前對象傳遞進去,這樣只要在當前對象方法實現(xiàn)相應(yīng)方法.


    4.關(guān)于NSData對象


    ? ? 無論SOCKET收發(fā)都采用NSData對象.


    ? ?NSData主要是帶一個(id)data指向的數(shù)據(jù)空間和長度 length.


    ? ? NSString 轉(zhuǎn)換成NSData 對象

  • ? ?? ?NSData* xmlData = [@"testdata" dataUsingEncoding:NSUTF8StringEncoding];
  • 復(fù)制代碼

    ? ?NSData 轉(zhuǎn)換成NSString對象


    ? ?NSData * data;

  • ? ?NSString *result = [[NSString alloc] initWithData:data??encoding:NSUTF8StringEncoding];
  • 復(fù)制代碼

    4.發(fā)送數(shù)據(jù)

    ? ???AsyncSocket??writeData? ? 方法來發(fā)送數(shù)據(jù),它有如下定義

  • ? ? - (void)writeDataNSData *)data withTimeoutNSTimeInterval)timeout taglong)tag;
  • 復(fù)制代碼

    以下是一個實例語句.


  • ? ???NSData* aData= [@"test data" dataUsingEncoding: NSUTF8StringEncoding];? ???[sock writeData:aData withTimeout:-1 tag:1];
  • 復(fù)制代碼

    ? ?? ? 在onSocket重載函數(shù),有如定義采用是專門用來處理SOCKET的發(fā)送數(shù)據(jù)的:


    ? ?-(void)onSocket(AsyncSocket *)sock didWriteDataWithTag:(long)tag

  • {? ?? ?NSLog(@"thread(%),onSocket:%p didWriteDataWithTag:%d",[[NSThread currentThread] name],? ???sock,tag);}
  • 復(fù)制代碼

    5.接收Socket數(shù)據(jù).


    ? ? 在onSocket重載函數(shù),有如定義采用是專門用來處理SOCKET的接收數(shù)據(jù)的.

  • ? ? -(void) onSocketAsyncSocket *)sock didReadDataNSData *)data withTaglong)tag
  • 復(fù)制代碼

    ? ?? ? 在中間將其轉(zhuǎn)換成NSString進行顯示.


  • ? ? NSString* aStr = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];? ???NSLog(@"===%@",aStr);? ???[aStr release];
  • 復(fù)制代碼

    下面是用開源的庫Asyncsocket的例子:

  • //
  • //??SocketDemoViewController.h
  • //??SocketDemo
  • //
  • //??Created by xiang xiva on 10-7-10.
  • //??Copyright 2010 __MyCompanyName__. All rights reserved.
  • //

  • #import <UIKit/UIKit.h>
  • #import "AsyncSocket.h"
  • #define SRV_CONNECTED 0
  • #define SRV_CONNECT_SUC 1
  • #define SRV_CONNECT_FAIL 2
  • #define HOST_IP @"192.168.110.1"
  • #define HOST_PORT 8080

  • @interface SocketDemoViewController : UIViewController {

  • UITextField *inputMsg;
  • UILabel *outputMsg;
  • AsyncSocket *client;
  • }

  • @property (nonatomic, retain) AsyncSocket *client;
  • @property (nonatomic, retain) IBOutlet UITextField *inputMsg;
  • @property (nonatomic, retain) IBOutlet UILabel *outputMsg;

  • - (int) connectServer: (NSString *) hostIP port:(int) hostPort;
  • - (void) showMessage:(NSString *) msg;
  • - (IBAction) sendMsg;
  • - (IBAction) reConnect;
  • - (IBAction) textFieldDoneEditing:(id)sender;
  • - (IBAction) backgroundTouch:(id)sender;

  • @end



  • //
  • //??SocketDemoViewController.m
  • //??SocketDemo
  • //
  • //??Created by xiang xiva on 10-7-10.
  • //??Copyright 2010 __MyCompanyName__. All rights reserved.
  • //

  • #import "SocketDemoViewController.h"

  • @implementation SocketDemoViewController

  • @synthesize inputMsg, outputMsg;
  • @synthesize client;
  • /*
  • // The designated initializer. Override to perform setup that is required before the view is loaded.
  • - (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil {
  • ? ? self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
  • ? ? if (self) {
  • ? ?? ???// Custom initialization
  • ? ? }
  • ? ? return self;
  • }
  • */

  • /*
  • // Implement loadView to create a view hierarchy programmatically, without using a nib.
  • - (void)loadView {
  • }
  • */



  • // Implement viewDidLoad to do additional setup after loading the view, typically from a nib.
  • - (void)viewDidLoad {
  • ? ? //[super viewDidLoad];
  • [self connectServer:HOST_IP port:HOST_PORT];
  • //監(jiān)聽讀取

  • }



  • // Override to allow orientations other than the default portrait orientation.
  • - (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation {
  • ? ? return YES;
  • }

  • - (void)didReceiveMemoryWarning {
  • // Releases the view if it doesn't have a superview.
  • ? ? [super didReceiveMemoryWarning];

  • // Release any cached data, images, etc that aren't in use.
  • }

  • - (void)viewDidUnload {
  • self.client = nil;
  • // Release any retained subviews of the main view.
  • // e.g. self.myOutlet = nil;
  • }

  • - (int) connectServer: (NSString *) hostIP port:(int) hostPort{

  • if (client == nil) {
  • ??client = [[AsyncSocket alloc] initWithDelegate:self];
  • ??NSError *err = nil;
  • ??//192.168.110.128
  • ??if (![client connectToHost:hostIP onPort:hostPort error:&err]) {
  • ? ?NSLog(@"%@ %@", [err code], [err localizedDescription]);
  • ? ?
  • ? ?UIAlertView *alert = [[UIAlertView alloc] initWithTitle:[@"Connection failed to host "
  • ? ?? ?? ???stringByAppendingString:hostIP]
  • ? ?? ?? ?? ?? ?message:[[[NSString alloc]initWithFormat:@"%@",[err code]] stringByAppendingString:[err localizedDescription]]
  • ? ?? ?? ?? ?? ???delegate:self
  • ? ?? ?? ?? ???cancelButtonTitle:@"OK"
  • ? ?? ?? ?? ???otherButtonTitles:nil];
  • ? ?[alert show];
  • ? ?[alert release];
  • ? ?//client = nil;
  • ? ?return SRV_CONNECT_FAIL;
  • ??} else {
  • ? ?NSLog(@"Conectou!");
  • ? ?return SRV_CONNECT_SUC;
  • ??}
  • }
  • else {
  • ??[client readDataWithTimeout:-1 tag:0];
  • ??return SRV_CONNECTED;
  • }

  • }

  • - (IBAction) reConnect{
  • int stat = [self connectServer:HOST_IP port:HOST_PORT];
  • switch (stat) {
  • ??case SRV_CONNECT_SUC:
  • ? ?[self showMessage:@"connect success"];
  • ? ?break;
  • ??case SRV_CONNECTED:
  • ? ?[self showMessage:@"It's connected,don't agian"];
  • ? ?break;
  • ??default:
  • ? ?break;
  • }
  • }

  • - (IBAction) sendMsg{

  • NSString *inputMsgStr = self.inputMsg.text;
  • NSString * content = [inputMsgStr stringByAppendingString:@"\r\n"];
  • NSLog(@"%a",content);
  • NSData *data = [content dataUsingEncoding:NSISOLatin1StringEncoding];
  • [client writeData:data withTimeout:-1 tag:0];

  • //[data release];
  • //[content release];
  • //[inputMsgStr release];
  • //繼續(xù)監(jiān)聽讀取
  • //[client readDataWithTimeout:-1 tag:0];
  • }

  • #pragma mark -
  • #pragma mark close Keyboard
  • - (IBAction) textFieldDoneEditing:(id)sender{
  • [sender resignFirstResponder];
  • }

  • - (IBAction) backgroundTouch:(id)sender{
  • [inputMsg resignFirstResponder];
  • }

  • #pragma mark socket uitl

  • - (void) showMessage:(NSString *) msg{
  • UIAlertView * alert = [[UIAlertView alloc]initWithTitle:@"Alert!"
  • ? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ? message:msg
  • ? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?delegate:nil
  • ? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?cancelButtonTitle:@"OK"
  • ? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?otherButtonTitles:nil];
  • ? ? [alert show];
  • ? ? [alert release];
  • }


  • #pragma mark socket delegate

  • - (void)onSocket:(AsyncSocket *)sock didConnectToHost:(NSString *)host port:(UInt16)port{
  • [client readDataWithTimeout:-1 tag:0];
  • }

  • - (void)onSocket:(AsyncSocket *)sock willDisconnectWithError:(NSError *)err
  • {
  • ? ? NSLog(@"Error");
  • }

  • - (void)onSocketDidDisconnect:(AsyncSocket *)sock
  • {
  • NSString *msg = @"Sorry this connect is failure";
  • [self showMessage:msg];
  • [msg release];
  • client = nil;
  • }

  • - (void)onSocketDidSecure:(AsyncSocket *)sock{

  • }

  • - (void)onSocket:(AsyncSocket *)sock didReadData:(NSData *)data withTag:(long)tag{

  • NSString* aStr = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
  • NSLog(@"Hava received datas is :%@",aStr);
  • self.outputMsg.text = aStr;
  • [aStr release];
  • [client readDataWithTimeout:-1 tag:0];
  • }

  • #pragma mark dealloc

  • - (void)dealloc {

  • [client release];
  • [inputMsg release];
  • [outputMsg release];
  • ? ? [super dealloc];
  • }

  • @end
  • 復(fù)制代碼


    文章來源:http://my.oschina.net/amoyai/blog/91694

    總結(jié)

    以上是生活随笔為你收集整理的【IOS网络通信】socket第三方库 AsyncSocket(GCDAsyncSocket)的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。