IOS的网络通信的方法
来源:互联网 发布:淘宝差评给多了 编辑:程序博客网 时间:2024/06/05 05:24
ios设备的网络通信的方法,有如下两个大类:
1、使用socket的方式进行通信。
2、使用asynsocket类库进行通信。
两种方法当中,我觉得asynsocket更好,因为是别人已经封装好的类库,比较稳定。但是对于直接使用socket的通信方法我倒是觉得很灵活。因为控制都是自己在做的事情。
先列举集中不同的使用方法:
1、直接使用socket的方式。
以 TCP为利,对于TCP来说,是要区分服务端和客户端的。服务端:通常的方法是服务端启动后监听,是否有客户端连接,如果有连接,则建立与客户端的通信。客户端的方法通常是连接服务端,当连接成功之后,就希望发送数据了。
客户端:
CFSocketContext sockContext ;
CFSocketRef cfsock ;
sockContext.info =self;
sockContext.copyDescription =0;
cfsock =CFSocketCreate(kCFAllocatorDefault,
PF_INET,
SOCK_STREAM,
IPPROTO_TCP,
kCFSocketConnectCallBack,
MyCallBack,
&sockContext
);
// 这个地方是个关键的地方,就是建立一个ip地址,然后使的客户端可以向服务端发起连接。
NSString *strAddress = @"192.168.1.1";
if (cfsock !=nil) {
struct sockaddr_in addr4;
memset(&addr4,0,sizeof(addr4));
addr4.sin_len = sizeof(addr4);
addr4.sin_family =AF_INET;
addr4.sin_port = htons(1230);
addr4.sin_addr.s_addr =inet_addr( [strAddress UTF8String] );
CFDataRef address =CFDataCreate(kCFAllocatorDefault, (UInt8*)&addr4,sizeof(addr4));
CFSocketConnectToAddress(cfsock, address, -1);
}
// 发起连接之后,需要将runloop的过程,也就是消息的过程加入到当前线程当中。这样当有事件发生时,会调用对应的方法。
CFRunLoopRef crun =CFRunLoopGetCurrent();//CFRunLoopGetMain();
CFRunLoopSourceRef source =CFSocketCreateRunLoopSource(kCFAllocatorDefault,cfsock, 0);
CFRunLoopAddSource(crun, source,kCFRunLoopCommonModes);
CFRelease(source);
回调函数:当连接成功之后的处理如下:
static void MyCallBack (
CFSocketRef s,
CFSocketCallBackType callbackType,
CFDataRef address,
constvoid *data,
void *info
)
{
if (data!=NULL) {
NSLog(@"传输失败!");
}
SocketTestAppDelegate *client = (SocketTestAppDelegate*)info;
[client performSelectoInBackground:@selector(readstream)withObject:nil];
}
-(void) readstream
{
char buffer[1024];
NSAutoreleasePool *pool = [[NSAutoreleasePoolalloc] init];
while (recv(CFSocketGetNative(cfsock),buffer,sizeof(buffer),0)) {
}
[pool release];
}
// 如果希望直接向服务器写内容的话,采用如下的方法。
-(void) sendstream
{
NSString * stringtosend = @"hello everyone";
const char *data = [stringtosendUTF8String];
send(CFSocketGetNative(cfsock),data,strlen(data)+1,0);
}
服务器端的程序:
CFSocketRef socketserver;
int setupSocket()
{
socketserver =CFSocketCreate(kCFAllocatorDefault,PF_INET,SOCK_STREAM,IPPROTO_TCP,kCFSocketAcceptCallBack,myaccept,NULL);
int optval =1;
setsockopt(CFSocketGetNative(socketserver),SOL_SOCKET, SO_REUSEADDR, (void*)&optval,sizeof(optval));
struct sockaddr_in addr4;
memset(&addr4,0,sizeof(addr4));
addr4.sin_len = sizeof(addr4);
addr4.sin_family = AF_INET;
addr4.sin_port = htons(10);
addr4.sin_addr.s_addr=htonl(INADDR_ANY);
CFDataRef address = CFDataCreate(kCFAllocatorDefault, (UInt8*)&addr4,sizeof(addr4));
CFSocketSetAddress(socketserver, address);
CFRunLoopRef cfRunloop =CFRunLoopGetCurrent();
CFRunLoopSourceRef source =CFSocketCreateRunLoopSource(kCFAllocatorDefault,socketserver, 0);
CFRunLoopAddSource(cfRunloop, source,kCFRunLoopCommonModes);
CFRelease(source);
}
//服务端的socket建立之后,就需要接受client的连接,因此建立连接的回调函数。
static void myaccept (
CFSocketRef s,
CFSocketCallBackType callbackType,
CFDataRef address,
constvoid *data,
void *info
)
{
if (callbackType ==kCFSocketAcceptCallBack) {
// 如果对端连接成功的话,是可以获取对端的名称和socket的。
CFSocketNativeHandle nativesockethandle = *(CFSocketNativeHandle*)data;
uint8_t name[100];
socklen_t namelen =100;
getpeername(nativesockethandle, (struct sockaddr *)name, &namelen);
//除此以外,更重要的是获取输入流 和 输出流,
CFReadStreamRef iStream;
CFWriteStreamRef oStream;
// 创建一个可读写的socket连接
CFStreamCreatePairWithSocket(kCFAllocatorDefault, nativesockethandle, &iStream, &oStream);
CFStreamClientContextstreamcontext={
0,NULL,NULL,NULL
};
// 注册两种事件!
CFReadStreamSetClient(iStream,kCFStreamEventHasBytesAvailable, readStream, &streamcontext);
CFReadStreamSetClient(iStream,kCFStreamEventCanAcceptBytes, writeStream, &streamcontext);
//加入到循环当中!
CFReadStreamScheduleWithRunLoop(iStream,CFRunLoopGetCurrent(),kCFRunLoopCommonModes);
CFWriteStreamScheduleWithRunLoop(oStream,CFRunLoopGetCurrent(),kCFRunLoopCommonModes);
CFReadStreamOpen(iStream);
CFWriteStreamOpen(oStream);
}
}
void readStream(CFReadStreamRef stream,CFStreamEventType eventType,void *clientCallBackInfo) {
UInt8 buff[255];
CFReadStreamRead(stream, buff, 255);
printf("received: %s", buff);
}
void writeStream (CFWriteStreamRef stream,CFStreamEventType eventType, void *clientCallBackInfo) {
// outputStream = stream;
char *str = "nihao";
CFWriteStreamWrite(outputStream, str, strlen(line) + 1);
}
另一种方法是使用NSStream的方式构建客户端,然后发送和接受内容。
-(
void
)startClient
{
host = [
NSHost
hostWithAddress:@
"192.168.201.24"
];
//hostWithName:@"www.apple.com"];
[
NSStream
getStreamsToHost:host port:4242 inputStream:&inStream outputStream:&outStream];
if
((inStream ==
nil
) || (outStream ==
nil
))
{
NSLog
(@
"Error: Failed to create streams!"
) ;
[
self
release];
}
}
- (
void
)stream:(
NSStream
*)aStream handleEvent:(
NSStreamEvent
)eventCode
{
switch
(eventCode) {
case
NSStreamEventHasBytesAvailable
:
{
NSMutableData
*input = [[
NSMutableData
alloc] init];
uint8_t buffer[1024];
int
len;
while([inStream hasBytesAvailable])
{
len = [inStream read:buffer maxLength:
sizeof
(buffer)];
if
(len > 0)
{
[input appendBytes:buffer length:len];
}
}
self
._resultdata = input;
self
._resultstring = [[
NSString
alloc] initWithData:input encoding:
NSUTF8StringEncoding
];
[input release];
break
;
}
case
NSStreamEventEndEncountered
:
[
self
closeStream];
break
;
case
NSStreamEventHasSpaceAvailable
:
case
NSStreamEventErrorOccurred
:
{
NSLog
(@
"Error:%@:%@"
,[[aStream streamError] code], [[aStream streamError] localizedDescription]);
}
case
NSStreamEventOpenCompleted
:
case
NSStreamEventNone
:
default
:
break
;
}
}
-(
void
)closeStream{
[inStream close];
[outStream close];
[inStream removeFromRunLoop:[
NSRunLoop
currentRunLoop] forMode:
NSDefaultRunLoopMode
];
[outStream removeFromRunLoop:[
NSRunLoop
currentRunLoop] forMode:
NSDefaultRunLoopMode
];
[inStream setDelegate:
nil
];
[outStream setDelegate:
nil
];
[inStream release];
[outStream release];
inStream =
nil
;
outStream =
nil
;
}
-(
void
)openStream{
[inStream retain];
[outStream retain];
[inStream setProperty:
NSStreamSocketSecurityLevelSSLv3
forKey:
NSStreamSocketSecurityLevelKey
];
[outStream setProperty:
NSStreamSocketSecurityLevelSSLv3
forKey:
NSStreamSocketSecurityLevelKey
];
NSMutableDictionary
* sslSettings;
sslSettings = [
NSMutableDictionary
dictionaryWithObjectsAndKeys:(
id
)kCFBooleanFalse,kCFStreamSSLValidatesCertificateChain,kCFBooleanFalse,kCFStreamSSLIsServer,
nil
];
CFWriteStreamSetProperty((CFWriteStreamRef)outStream, kCFStreamPropertySSLSettings, sslSettings);
[inStream setDelegate:
self
];
[outStream setDelegate:
self
];
[inStream scheduleInRunLoop:[
NSRunLoop
currentRunLoop] forMode:
NSDefaultRunLoopMode
];
[outStream scheduleInRunLoop:[
NSRunLoop
currentRunLoop] forMode:
NSDefaultRunLoopMode
];
[inStream open];
[outStream open];
}
-(
int
)writeString: (
NSString
*) string
{
NSData
*messageAsData = [string dataUsingEncoding:
NSASCIIStringEncoding
];
return
[outStream write: (c*****t uint8_t *) [messageAsData bytes] maxLength: [messageAsData length]];
}
-(
int
)writeBytes: (
char
*) buffer length: (unsigned
int
) len
{
return
[outStream write: (c*****t uint8_t *) buffer maxLength: len];
}
@end
- iOS 网络通信的方法
- IOS的网络通信的方法
- IOS的网络通信的方法
- IOS的网络通信的方法
- iOS的网络通信
- iOS下的网络通信
- IOS网络篇:HTTP的通信过程
- ios 网络通信过程cookie的使用
- IOS网络通信之ASIHttpRequest的使用(二)
- IOS网络通信之ASIHttpRequest下载/上传进度的追踪
- IOS用封装的API AsyncSocket进行网络通信
- iOS 中客户端和服务器的 Web Service 网络通信
- iOS网络通信类库用AFNetworking替换ASHttpRequest的解决方案
- iOS --- 强大的网络通信类库AFNetworking
- iOS网络通信类库用AFNetworking替换ASHttpRequest的解决方案
- iOS网络通信类库用AFNetworking替换ASHttpRequest的解决方案
- iOS网络通信类库用AFNetworking替换ASHttpRequest的解决方案
- java网络通信(一)使用http的get方法进行网络通信
- 转 Linux调优方案,sysctl.conf的设置
- performSelectorInBackground:
- PLSQL Developer设置及快捷键设置
- Git历险记(3):创建一个自己的本地仓库(1)
- 在Android中通过jni方式使用编译好的FFmpeg库-Android中使用FFmpeg媒体库(二)
- IOS的网络通信的方法
- 不要错过人生的低谷
- 简单,方便,功能全的php分页类
- http://blog.csdn.net/xiaowei_cqu/article/details/7748260
- ora-29471:Oracle 11g DBMS_SQL Security Changes
- GDB 命令详细解释
- 线程安全 单例模式
- SVN二次开发
- Xcode 4.3如何修复Code sense功能失效问题