位置: 编程技术 - 正文

Android学习 - Android Socket使用浅析(android入门视频教程)

编辑:rootadmin

推荐整理分享Android学习 - Android Socket使用浅析(android入门视频教程),希望有所帮助,仅作参考,欢迎阅读内容。

文章相关热门搜索词:android study,android入门教程,android学习网站,android怎么学,android学习网站,android入门教程,android学习网站,android study,内容如对您有帮助,希望把文章链接给更多的朋友!

套接字或插座(socket)是一种软件形式的抽象,用于表达两台机器间一个连接的“终端”。针对一个特定的连接,每台机器上都有一个“套接字”,可以想象它们之间有一条虚拟的“线缆”。JAVA有两个基于数据流的套接字类:ServerSocket,服务器用它“侦听”进入的连接;Socket,客户端用它初始一次连接。侦听套接字只能接收新的连接请求,不能接收实际的数据包。套接字是基于TCP/IP实现的,它是用来提供一个访问TCP的服务接口,或者说套接字socket是TCP的应用编程接口API,通过它应用层就可以访问TCP提供的服务。在JAVA中,我们用ServerSocket、Socket类创建一个套接字连接,从套接字得到的结果是一个InputStream以及OutputStream对象,以便将连接作为一个IO流对象对待。通过IO流可以从流中读取数据或者写数据到流中,读写IO流会有异常IOException产生。

套接字底层是基于TCP的,所以socket的超时和TCP超时是相同的。下面先讨论套接字读写缓冲区,接着讨论连接建立超时、读写超时以及JAVA套接字编程的嵌套异常捕获和一个超时例子程序的抓包示例。

1、socket读写缓冲区

一旦创建了一个套接字实例,操作系统就会为其分配缓冲区以存放接收和要发送的数据。

JAVA可以设置读写缓冲区的大小setReceiveBufferSize(intsize)、setSendBufferSize(intsize)。

向输出流写数据并不意味着数据实际上已经被发送,它们只是被复制到了发送缓冲区队列SendQ,就是在Socket的OutputStream上调用 flush()方法,也不能保证数据能够立即发送到网络。真正的数据发送是由操作系统的TCP协议栈模块从缓冲区中取数据发送到网络来完成的。当有数据从网络来到时,TCP协议栈模块接收数据并放入接收缓冲区队列RecvQ,输入流InputStream通过read方法从RecvQ中取出数据。

2、socket连接建立超时

socket连接建立是基于TCP的连接建立过程。TCP的连接需要通过3次握手报文来完成,开始建立TCP连接时需要发送同步SYN报文,然后等待确认报文SYN&#;ACK,最后再发送确认报文ACK。TCP连接的关闭通过4次挥手来完成,主动关闭TCP连接的一方发送FIN报文,等待对方的确认报文;被动关闭的一方也发送FIN报文,然等待确认报文。

正在等待TCP连接请求的一端有一个固定长度的连接队列,该队列中的连接已经被TCP接受(即三次握手已经完成),但还没有被应用层所接受。TCP接受一个连接是将其放入这个连接队列,而应用层接受连接是将其从该队列中移出。应用层可以通过设置backlog变量来指明该连接队列的最大长度,即已被TCP接受而等待应用层接受的最大连接数。

当一个连接请求SYN到达时,TCP确定是否接受这个连接。如果队列中还有空间,TCP模块将对SYN进行确认并完成连接的建立。但应用层只有在三次握手中的第三个报文收到后才会知道这个新连接。如果队列没有空间,TCP将不理会收到的SYN。

如果应用层不能及时接受已被TCP接受的连接,这些连接可能占满整个连接队列,新的连接请求可能不被响应而会超时。如果一个连接请求SYN发送后,一段时间后没有收到确认SYN&#;ACK,TCP会重传这个连接请求SYN两次,每次重传的时间间隔加倍,在规定的时间内仍没有收到SYN&#;ACK,TCP将放弃这个连接请求,连接建立就超时了。

JAVASocket连接建立超时和TCP是相同的,如果TCP建立连接时三次握手超时,那么导致Socket连接建立也就超时了。可以设置Socket连接建立的超时时间

如果在timeout内,连接没有建立成功,在TimeoutException异常被抛出。如果timeout的&#;小于三次握手的时间,那么Socket连接永远也不会建立。

不同的应用层有不同的连接建立过程,Socket的连接建立和TCP一样,仅仅需要三次握手就完成连接,但有些应用程序需要交互很多信息后才能成功建立连接,比如Telnet协议,在TCP三次握手完成后,需要进行选项协商之后,Telnet连接才建立完成。

3、socket读超时

如果输入缓冲队列RecvQ中没有数据,read操作会一直阻塞而挂起线程,直到有新的数据到来或者有异常产生。调用setSoTimeout(inttimeout)可以设置超时时间,如果到了超时时间仍没有数据,read会抛出一个SocketTimeoutException,程序需要捕获这个异常,但是当前的socket连接仍然是有效的。

如果对方进程崩溃、对方机器突然重启、网络断开,本端的read会一直阻塞下去,这时设置超时时间是非常重要的,否则调用read的线程会一直挂起。

TCP模块把接收到的数据放入RecvQ中,直到应用层调用输入流的read方法来读取。如果RecvQ队列被填满了,这时TCP会根据滑动窗口机制通知对方不要继续发送数据,本端停止接收从对端发送来的数据,直到接收者应用程序调用输入流的read方法后腾出了空间。

4、socket写超时

socket的写超时是基于TCP的超时重传。超时重传是TCP保证数据可靠性传输的一个重要机制,其原理是在发送一个数据报文后就开启一个计时器,在一定时间内如果没有得到发送报文的确认ACK,那么就重新发送报文。如果重新发送多次之后,仍没有确认报文,就发送一个复位报文RST,然后关闭TCP连接。首次数据报文发送与复位报文传输之间的时间差大约为9分钟,也就是说如果9分钟内没有得到确认报文,就关闭连接。但是这个&#;是根据不同的TCP协议栈实现而不同。

Android学习 - Android Socket使用浅析(android入门视频教程)

如果发送端调用write持续地写出数据,直到SendQ队列被填满。如果在SendQ队列已满时调用write方法,则write将被阻塞,直到SendQ有新的空闲空间为止,也就是说直到一些字节传输到了接收者套接字的RecvQ中。如果此时RecvQ队列也已经被填满,所有操作都将停止,直到接收端调用read方法将一些字节传输到应用程序。

当Socket的write发送数据时,如果网线断开、对端进程崩溃或者对端机器重启动,TCP模块会重传数据,最后超时而关闭连接。下次如再调用write会导致一个异常而退出。

Socket写超时是基于TCP协议栈的超时重传机制,一般不需要设置write的超时时间,也没有提供这种方法。

5、双重嵌套异常捕获

如果ServerSocket、Socket构造失败,只需要仅仅捕获这个构造失败异常而不需要调用套接字的close方法来释放资源(必须保证构造失败后不会留下任何需要清除的资源),因为这时套接字内部资源没有被成功分配。如果构造成功,必须进入一个try finally语句块里调用close释放套接字。请参照下面例子程序。

执行上面的程序,在程序运行一会儿之后,断开client和server之间的网络连接,在机器上输出如下:

Server上的输出:

断开了网络连接之后没有数据输出。

Client上的输出:

断开网络连接后客户端进程挂起:

当hello6被发送到server端后,网络连接被断开,这时server端不能接收任何数据而挂起。client端仍然继续发送数据,实际上hello7、hello8、hello9、hello都被复制到SendQ队列中,write方法立即返回。当client的SendQ队列被填满之后,write方法就被阻塞。TCP模块在发送报文hello7之后,没有收到确认而超时重传,再重传几次之后关闭了TCP连接,同时导致被阻塞的 write方法异常返回。

通过抓包工具,我们可以看到超时重传的报文。

6、判断远端服务器是否已经断开连接

如何判断远端服务器是否已经断开连接,如果断开那么需要重新连接。首先想到socket类的方法isClosed()、isConnected()、isInputStreamShutdown()、isOutputStreamShutdown()等,但经过试验并查看相关文档,这些方法都是本地端的状态,无法判断远端是否已经断开连接。然后想到是否可以通过OutputStream发送一段测试数据,如果发送失败就表示远端已经断开连接,类&#;ping,但是这样会影响到正常的输出数据,远端无法把正常数据和测试数据分开。最后又回到socket类,发现有一个方法sendUrgentData,查看文档后得知它会往输出流发送一个字节的数据,只要对方Socket的SO_OOBINLINE属性没有打开,就会自动舍弃这个字节,而SO_OOBINLINE属性默认情况下就是关闭的。于是,下面一段代码就可以判断远端是否断开了连接:

用ping实现

ping的方法有个严重的BUG,就是你只能判断对方是否连接网络,而不能判断客户端是否开启。我在写聊天室时经常要注意客户端异常退出的问题(比如客户直接调用任务管理器结束程序进程),其实在通过socket.getoutstream和socket.getinputstream流对客户端发送、接受信息时如果socket没连接上是会抛出异常的,这也就是为什么Java会要求网络编程都要写在try里面,所以只要在catch里面写入客户端退出的处理就行了,没必要专门去想什么方法。

7、Android socket编程

SocketServer类,服务器实现:

服务器端调用:

客户端实现:

注意在AndroidManifest.xml中加入对网络的访问权限:

android多线程开发保持清晰顺序实践 今天在开发的过程中需要给之前的程序加上多线程操作,避免networrkonmainthread。由于代码很多,变量之间错综复杂,后面的变量需要在前面代码的线程中

getRunningTasks接口在Android LL上的使用 最近在做的一个小项目中,需要实时获取Activity栈顶以及它所属的AppProcess。根据之前的了解,知道AndroidAPI有提供一个接口publicListActivityManager.RunningTaskInf

eclipse转手Android studio 要注意的地方 大家好。我刚从Eclipse(EC)转手Androidstudio(AS),想看看大家所谓的很牛逼很高大上的AS有多好,带着好奇和新鲜感我下了Androidstudio,然后把之前eclipse的

标签: android入门视频教程

本文链接地址:https://www.jiuchutong.com/biancheng/378173.html 转载请保留说明!

上一篇:Android学习 - Android新的menu实现ActionMode(android study)

下一篇:android多线程开发保持清晰顺序实践(Android多线程开发)

  • 税后经营净利率什么意思
  • 银行共管账户现在可以开设吗
  • 合同资产和合同负债属于什么科目
  • 定期定额户申报表怎么填
  • 个人所得税累计扣除标准
  • 购入包装物计入
  • 所得税季报什么时间扣款
  • 停车费收入增值税申报表怎么填
  • 对方公司已经注销,欠钱收不回
  • 转让房产收取的增值税
  • 疫苗接种防疫站
  • 合同解除收取对方的违约金交什么税
  • 保证金转租金的会计处理
  • 负数发票跨月怎么重开
  • 回拨工费经费怎么做会计分录?
  • 一般纳税人没有开票要交税吗
  • 上市公司现金分红对股价的影响
  • 去国税申请开票需要法人和财务去吗?
  • 金税盘提示离线开票时间超限深圳
  • 个人年终奖如何交税
  • 包销和代销哪个风险大
  • 初级考试备考计划
  • 承兑贴现给其他企业怎么做账
  • 小规模纳税人按季收入不达30万
  • 未摊销金额怎么算
  • 金融服务公司收取金融服务费
  • 建筑行业营改增税率变化
  • 出口退税率为0%退税收入怎么算
  • 车辆购置税会计科目怎么做账
  • 银行贷款发放怎么做凭证
  • 入库的原材料属于什么科目
  • 盈余公积科目是什么科目
  • u盘数据全部丢失
  • executor进程
  • 现金收入如何做账务处理
  • yolo v5 focus
  • yolov5输出result
  • php获取文件内容的函数
  • 自然人三方协议支付宝怎么处理
  • 跨年坏账准备转回
  • 一张专票可以开几项
  • 进项税额大于销项税额期末留抵
  • 融资租赁利息一般多少
  • mongodb使用案例
  • 百旺金赋怎么开红字发票
  • 安装SQL2005的实训体会
  • c#连接数据库的基本步骤是什么
  • 经营活动的现金流量占全部现金流量的比重越大
  • 合伙企业对外投资需要全体合伙人同意吗
  • 去银行提取备用金不是会计本人需要给谁打电话
  • 收款预缴增值税怎么做账
  • 佣金怎样算
  • 企业购进货物暂欠货款
  • 劳务费能否作为农民工工资优先支付
  • 公司银行账号注销需要法人到场吗
  • 财经网课 app
  • mysql通过文档读取并执行命令之快速为mysql添加多用户和数据库技巧
  • mysql 创建root用户和普通用户及修改删除功能
  • centosuuid
  • bios setup在哪里
  • wondows文件保护
  • win8.1无线
  • 带上Windows 8去旅行 让你的旅途更轻松
  • pycharm远程调试linux
  • perl-dbd-mysql是什么
  • js确认框s弹出框确定和取消
  • 关于中秋节的古诗
  • webpack使用场景
  • AJAX和jQuery动态加载数据的实现方法
  • 原生js import
  • unity 替代
  • unity3d 画线
  • javascript模块化
  • 合作社的税率是多少
  • 江苏高速通行费标准
  • 日照公交305发车时间表
  • 沥青进口需要配额吗
  • 上饶税务局电话号码
  • 如何抵扣税款
  • 统一社会信用代码有什么用
  • 免责声明:网站部分图片文字素材来源于网络,如有侵权,请及时告知,我们会第一时间删除,谢谢! 邮箱:opceo@qq.com

    鄂ICP备2023003026号

    网站地图: 企业信息 工商信息 财税知识 网络常识 编程技术

    友情链接: 武汉网站建设