http://altboy.blog.51cto.com/5440160/1921720

客户端/服务器架构

  • 即C/S架构,其实web服务在某种意义上也算是C/S架构

  • 一个特点是服务器端持续运行对外提供服务

为何学习socket一定要先学习互联网协议:

  1. C/S架构的软件是基于网络进行通信的

  2. 网络的核心就是一堆协议,即标准,想要开发一款基于网络通信的软件就必须遵循这些标准

  3. socket是处在应用层和传输层中间的一组接口

说到这,那么socket到底是个什么呢?Socket是应用层与TCP/IP协议族通信的中间软件抽象层,它是一组接口。在设计模式中,socket其实就是一个门面模式,它把复杂的TCP/IP协议族隐藏在socket接口后面,对用户来说,一组简单的接口就是全部,让socket去组织数据,以符合指定的协议。所以,无需深究TCP/UDP协议,socket已经为我们封装好了

基于文件类型的套接字家族:AFUNIX基于网络类型的套接字家族:AFINET

套接字的工作流程

先从服务器端说起。服务器端先初始化Socket,然后与端口绑定(bind),对端口进行监听(listen),调用accept阻塞,等待客户端连接。在这时如果有个客户端初始化一个Socket,然后连接服务器(connect),如果连接成功,这时客户端与服务器端的连接就建立了。客户端发送数据请求,服务器端接收请求并处理请求,然后把回应数据发送给客户端,客户端读取数据,最后关闭连接,一次交互结束

服务端套接字函数

s.bind()    绑定(主机,端口号)到套接字
s.listen()  开始TCP监听
s.accept()  被动接受TCP客户的连接,(阻塞式)等待连接的到来

客户端套接字函数

s.connect()     主动初始化TCP服务器连接
s.connect_ex()  connect()函数的扩展版本,出错时返回出错码,而不是抛出异常

公共用途的套接字函数

s.recv()            接收TCP数据
s.send()            发送TCP数据(send在待发送数据量大于己端缓存区剩余空间时,数据丢失,不会发完)
s.sendall()         发送完整的TCP数据(本质就是循环调用send,sendall在待发送数据量大于己端缓存区剩余空间时,数据不丢失,循环调用send直到发完)
s.recvfrom()        接收UDP数据
s.sendto()          发送UDP数据
s.getpeername()     连接到当前套接字的远端的地址
s.getsockname()     当前套接字的地址
s.getsockopt()      返回指定套接字的参数
s.setsockopt()      设置指定套接字的参数
s.close()           关闭套接字

面向锁的套接字方法

s.setblocking()     设置套接字的阻塞与非阻塞模式
s.settimeout()      设置阻塞套接字操作的超时时间
s.gettimeout()      得到阻塞套接字操作的超时时间

面向文件的套接字的函数

s.fileno()          套接字的文件描述符
s.makefile()        创建一个与该套接字相关的文件

代码示例:

服务端

from socket import *
phone=socket(AF_INET,SOCK_STREAM)
phone.bind(('127.0.0.1',8081))
phone.listen(5) conn,addr=phone.accept()
while True:
   data=conn.recv(1024)
   print('server===>')
   print(data)
   conn.send(data.upper())
conn.close()
phone.close()

客户端

from socket import *

phone=socket(AF_INET,SOCK_STREAM)
phone.connect(('127.0.0.1',8081)) while True:
   msg=input('>>: ').strip()
   phone.send(msg.encode('utf-8'))
   print('client====>')
   data=phone.recv(1024)
   print(data)

注意:这时候当客户端输入消息为空的话程序会卡住,那是因为无论是服务端还是客户端都要到自己所在主机缓冲区去拿消息,因为这时发送为空,服务端根本就不会有任何反应,所以客户端的缓冲区也不会有任何内容,所以这时它会一直徒劳的等待。。。

这时的解决办法当然要在客户端想办法,很简单,我们不让客户端发送空消息即可,在send()方法之前加判断:

if not msg :continue

你肯定以为这个时候就完事了,这时请尝试断开客户端链接试试。。。试想,既然作为服务端,顾名思义就是要持续不断的为不同的客户端持续的提供服务,怎么能一个客户端用完即结束呢?解决方案如下:

while True: #链接循环
   conn,addr=phone.accept()    print('电话线路是',conn)
   print('客户端的手机号是',addr)    while True: #通信循环
       try:
           data=conn.recv(1024)
           if not data:break
           print('客户端发来的消息是',data)            conn.send(data.upper())
       except Exception:
           break    conn.close() phone.close()

注意:可能会有人遇到重启服务端时Address already in use 的情况,这个是由于你的服务端仍然存在四次挥手的timewait状态在占用地址(如果不懂,请深入研究1.tcp三次握手,四次挥手 2.syn洪水攻击 3.服务器高并发情况下会有大量的timewait状态的优化方法)

解决方法:

#加入一条socket配置,重用ip和端口

phone=socket(AF_INET,SOCK_STREAM)
phone.setsockopt(SOL_SOCKET,SO_REUSEADDR,1) #就是它,在bind前加
phone.bind(('127.0.0.1',8080))

Socket网络编程初探的更多相关文章

  1. SOCKET网络编程5

    SOCKET网络编程快速上手(二)——细节问题(5)(完结篇) 6.Connect的使用方式 前面提到,connect发生EINTR错误时,是不能重新启动的.那怎么办呢,是关闭套接字还是直接退出进程呢 ...

  2. Linux Socket 网络编程

    Linux下的网络编程指的是socket套接字编程,入门比较简单.在学校里学过一些皮毛,平时就是自学玩,没有见识过真正的socket编程大程序,比较遗憾.总感觉每次看的时候都有收获,但是每次看完了之后 ...

  3. Python Socket 网络编程

    Socket 是进程间通信的一种方式,它与其他进程间通信的一个主要不同是:它能实现不同主机间的进程间通信,我们网络上各种各样的服务大多都是基于 Socket 来完成通信的,例如我们每天浏览网页.QQ ...

  4. Python全栈【Socket网络编程】

    Python全栈[socket网络编程] 本章内容: Socket 基于TCP的套接字 基于UDP的套接字 TCP粘包 SocketServer 模块(ThreadingTCPServer源码剖析) ...

  5. python之Socket网络编程

    什么是网络? 网络是由节点和连线构成,表示诸多对象及其相互联系.在数学上,网络是一种图,一般认为专指加权图.网络除了数学定义外,还有具体的物理含义,即网络是从某种相同类型的实际问题中抽象出来的模型.在 ...

  6. Python之路【第七篇】python基础 之socket网络编程

    本篇文章大部分借鉴 http://www.cnblogs.com/nulige/p/6235531.html python socket  网络编程 一.服务端和客户端 BS架构 (腾讯通软件:ser ...

  7. Socket网络编程-基础篇

    Socket网络编程 网络通讯三要素: IP地址[主机名] 网络中设备的标识 本地回环地址:127.0.0.1 主机名:localhost 端口号 用于标识进程的逻辑地址 有效端口:0~65535 其 ...

  8. Socket网络编程--FTP客户端

    Socket网络编程--FTP客户端(1)(Windows) 已经好久没有写过博客进行分享了.具体原因,在以后说. 这几天在了解FTP协议,准备任务是写一个FTP客户端程序.直接上干货了. 0.了解F ...

  9. windows下的socket网络编程

    windows下的socket网络编程 windows下的socket网络编程 clinet.c 客户端 server.c 服务器端 UDP通信的实现 代码如下 已经很久没有在windows下编程了, ...

随机推荐

  1. 【矩阵---求A的1到N次幂之和】

    引例: Matrix Power Series: 题目大意,给定矩阵A,求A^+A^+A^+...A^N. 题解:已知X=a,可以通过以下矩阵求出ans=a^+a^+...a^=矩阵^(n+)后右上格 ...

  2. Python Web开发最难懂的WSGI协议,到底包含哪些内容?

    原文出处: PythonScientists 我想大部分Python开发者最先接触到的方向是WEB方向(因为总是有开发者希望马上给自己做个博客出来,例如我),既然是WEB,免不了接触到一些WEB框架, ...

  3. Video.js事件

    Home 膘叔 » Archives 文章: 备份一个video的JS [打印] 分类: Javascript 作者: gouki 2012-02-16 17:58 备份一个JS,不是为了代码很优秀, ...

  4. HDFS之二:HDFS文件系统JavaAPI接口

    HDFS是存取数据的分布式文件系统,HDFS文件操作常有两种方式,一种是命令行方式,即Hadoop提供了一套与Linux文件命令类似的命令行工具.HDFS操作之一:hdfs命令行操作 另一种是Java ...

  5. 016--python文件处理

    一.操作文件流程 1.打开文件,得到文件句柄并赋值给一个变量 2.通过句柄对文件进行操作 3.关闭文件 示例代码: f = open('chenli.txt') #打开文件 first_line = ...

  6. Python学习之旅—生成器与迭代器案例剖析

    前言 前面一篇博客笔者带大家详细探讨了生成器与迭代器的本质,本次我们将实际分析一个具体案例来加深对生成器与迭代器相关知识点的理解. 本次的案例是一个文件过滤操作,所做的主要操作就是过滤出一个目录下的文 ...

  7. c++ 头文件 及 sort 和 vector简单介绍

    c++  sort :http://www.16kan.com/post/997260.html http://wenku.baidu.com/view/e064166daf1ffc4ffe47ac6 ...

  8. 图像分类与KNN

    1 图像分类问题 1.1 什么是图像分类 所谓图像分类问题,就是已有固定的分类标签集合,然后对于输入的图像,从分类标签集合中找出一个分类标签,最后把分类标签分配给该输入图像.虽然看起来挺简单的,但这可 ...

  9. 51nod 1051 最大子矩阵和(DP)

    题意 略 分析 一道经典的DP题,但是我弱到差点做不出来,真的垃圾 设置\(sum(i,j)代表1-i行第j列的前缀和\),然后枚举行i和行j,再枚举列k,做一遍类似一维的最大子段和即可 #inclu ...

  10. 键值观察 KVO

    http://www.cnblogs.com/dyf520/p/3805297.html Key-Value Observing Programming Guide 1,注册Key-Value Obs ...