http://www.cnblogs.com/weilengdeyu/archive/2013/03/08/2949101.html

我们在讲解Socket编程前,先看几个和Socket编程紧密相关的概念:

  1. TCP/IP层次模型

当然这里我们只讨论重要的四层

01,应用层(Application):应用层是个很广泛的概念,有一些基本相同的系统级TCP/IP应用以及应用协议,也有许多的企业应用和互联网应用。http协议在应用层运行。

02,传输层(Tanspot):传输层包括UDP和TCP,UDP几乎不对报文进行检查,而TCP

提供传输保证。

03,网络层(Netwok):网络层协议由一系列协议组成,包括ICMP、IGMP、RIP、OSPF、IP(v4,v6)等。

04,链路层(Link):又称为物理数据网络接口层,负责报文传输。

然后我们来看下tcp层次模型图

从上图中可以看出,应用程序在应用层运行,在传输层,在数据前加上了TCP头,在

网络层加上的IP头,在数据链路层加上了帧。

2,端口

端口号范围:0-65535,总共能表示65536个数。

   按端口号可分为3大类

  (1)公认端口(WellKnownPorts):从0到1023,它们紧密绑定(binding)于一些服务。通常这些端口的通讯明确表明了某种服务的协议。例如:80端口实际上总是HTTP通讯。

  (2)注册端口(RegisteredPorts):从1024到49151。它们松散地绑定于一些服务。也就是说有许多服务绑定于这些端口,这些端口同样用于许多其它目的。例如:许多系统处理动态端口从1024左右开始。

  (3)动态和/或私有端口(Dynamicand/orPrivatePorts):从49152到65535。理论上,不应为服务分配这些端口。实际上,机器通常从1024起分配动态端口。

3.TCP和UDP报文

下面一起来看下TCP和UDP的报文图

从图中我们可以看出TCP和UDP中都有校验和,但是在UDP报文中,一般不使用校验和,这样可以加快数据传输的速度,但是数据的准确性可能会受到影响。换句话说,Tcp协议都有校验和,为了保证传输数据的准确性。

3.Socket

Socket包括Ip地址和端口号两部分,程序通过Socket来通信,Socket相当于操作系统的一个组件。Socket作为进程之间通信机制,通常也称作”套接字”,用于描述IP地址和端口号,是一个通信链的句柄。说白了,就是两个程序通信用的。

生活案例对比:

Socket之间的通信可以类比生活中打电话的案例。任何用户在通话之前,首先要占有一部电话机,相当于申请一个Socket,同时要知道对方的号码,相当于对方有一个固定的Socket,然后向对方拨号呼叫,相当于发出连接请求。假如对方在场并空闲,拿起 电话话筒,双方就可以进行通话了。双方的通话过程,是一方向电话机发出信号和对方从电话机接收信号的过程,相当于向socket发送数据和从socket接收数据。通话结束后,一方挂起电话机,相当于关闭socket,撤销连接。

注意:Socket不仅可以在两台电脑之间通信,还可以在同一台电脑上的两个程序间通信。

4,端口进阶(深入)

通过IP地址确定了网络中的一台电脑后,该电脑上可能提供很多提供服务的应用,每一个应用都对应一个端口。

在Internet上有很多这样的主机,这些主机一般运行了多个服务软件 ,同时提供几种服务,每种服务都打开一个Socket,并绑定到一个端口上,不同的端口对应于不同的服务(应用程序)

例如:http 使用80端口,   ftp使用21端口     smtp使用25端口

5.Socket分类

Socket主要有两种类型:

  1. 流式Socket

是一种面向连接的Socket,针对于面向连接的TCP服务应用,安全,但是效率低

2,数据报式Socket

是一种无连接的Socket,对应于无连接的UDP服务应用,不安全,但效率高

6. Socket一般应用模式(服务器端和客户端)

服务器端的Socket(至少需要两个)

01.一个负责接收客户端连接请求(但不负责与客户端通信)

02.每成功接收到客户端的连接便在服务器端产生一个对应的复杂通信的Socket

021.在接收到客户端连接时创建

022. 为每个连接成功的客户端请求在服务器端都创建一个对应的Socket(负责和客户端通信)

客户端的Socket

  1. 必须指定要连接的服务器地址和端口
  2. 通过创建一个Socket对象来初始化一个到服务器端的TCP连接

通过上图,我们可以看出,首先服务器会创建一个负责监听的socket,然后客户端通过socket连接到服务器指定端口,最后服务器端负责监听的socket,监听到客户端有连接过来了,就创建一个负责和客户端通信的socket。

下面我们来看下Socket更具体的通信过程:

Socket的通讯过程

服务器端:

01,申请一个socket

02,绑定到一个IP地址和一个端口上

03,开启侦听,等待接收连接

客户端:

01,申请一个socket

02,连接服务器(指明IP地址和端口号)

服务器端接收到连接请求后,产生一个新的socket(端口大于1024)与客户端建立连接并进行通信,原监听socket继续监听。

注意:负责通信的Socket不能无限创建,创建的数量和操作系统有关。

7.Socket的构造函数

Public Socket(AddressFamily addressFamily,SocketType  socketType,ProtocolType  protocolTYpe)

AddressFamily:指定Socket用来解析地址的寻址方案。例如:InterNetWork指示当Socket使用一个IP版本4地址连接

SocketType:定义要打开的Socket的类型

Socket类使用ProtocolType枚举向Windows  Sockets  API通知所请求的协议

注意:

1,端口号必须在 1 和 65535之间,最好在1024以后。

2,要连接的远程主机必须正在监听指定端口,也就是说你无法随意连接远程主机。

如:

IPAddress addr = IPAddress.Parse("127.0.0.1");

IPEndPoint endp = new IPEndPoint(addr,,9000);

服务端先绑定:serverWelcomeSocket.Bind(endp)

客户端再连接:clientSocket.Connect(endp)

3,一个Socket一次只能连接一台主机

4,Socket关闭后无法再次使用

5,每个Socket对象只能与一台远程主机连接。如果你想连接到多台远程主机,你必须创建多个Socket对象。

8.Socket常用类和方法

相关类:

IPAddress:包含了一个IP地址

IPEndPoint:包含了一对IP地址和端口号

方法:

Socket():创建一个Socket

Bind():绑定一个本地的IP和端口号(IPEndPoint)

Listen():让Socket侦听传入的连接吃那个病,并指定侦听队列容量

Connect():初始化与另一个Socket的连接

Accept():接收连接并返回一个新的Socket

Send():输出数据到Socket

Receive():从Socket中读取数据

Close():关闭Socket,销毁连接

接下来,我们同一个简单的服务器和客户端通信的案例,来看下Sokcet的具体用法,效果图如下:


关键代码:

服务器端代码:

  1 private void Form1_Load(object sender, EventArgs e)2 3         {4 5             Control.CheckForIllegalCrossThreadCalls = false;6 7         }8 9  10 11         private void btnListen_Click(object sender, EventArgs e)12 13         {14 15             //ip地址16 17             IPAddress ip = IPAddress.Parse(txtIP.Text);18 19            // IPAddress ip = IPAddress.Any;20 21             //端口号22 23             IPEndPoint point=new IPEndPoint(ip,int.Parse(txtPort.Text));24 25             //创建监听用的Socket26 27             /*28 29              * AddressFamily.InterNetWork:使用 IP4地址。30 31 SocketType.Stream:支持可靠、双向、基于连接的字节流,而不重复数据。此类型的 Socket 与单个对方主机进行通信,并且在通信开始之前需要远程主机连接。Stream 使用传输控制协议 (Tcp) ProtocolType 和 InterNetworkAddressFamily。32 33 ProtocolType.Tcp:使用传输控制协议。34 35              */36 37             //使用IPv4地址,流式socket方式,tcp协议传递数据38 39             Socket socket=new Socket(AddressFamily.InterNetwork,SocketType.Stream,ProtocolType.Tcp);40 41             //创建好socket后,必须告诉socket绑定的IP地址和端口号。42 43             //让socket监听point44 45             try46 47             {48 49                 //socket监听哪个端口50 51                 socket.Bind(point);52 53                 //同一个时间点过来10个客户端,排队54 55                 socket.Listen(10);56 57                 ShowMsg("服务器开始监听");58 59                 Thread thread = new Thread(AcceptInfo);60 61                 thread.IsBackground = true;62 63                 thread.Start(socket);64 65             }66 67             catch (Exception ex)68 69             {70 71                72 73                ShowMsg(ex.Message);74 75             }76 77         }78 79         //记录通信用的Socket80 81         Dictionary<string,Socket> dic=new Dictionary<string, Socket>();82 83        // private Socket client;84 85         void AcceptInfo(object o)86 87         {88 89             Socket socket = o as Socket;90 91             while (true)92 93             {94 95                 //通信用socket96 97                 try98 99                 {
100
101                     //创建通信用的Socket
102
103                   Socket  tSocket = socket.Accept();
104
105                   string point = tSocket.RemoteEndPoint.ToString();
106
107                     //IPEndPoint endPoint = (IPEndPoint)client.RemoteEndPoint;
108
109                     //string me = Dns.GetHostName();//得到本机名称
110
111                     //MessageBox.Show(me);
112
113                  ShowMsg(point + "连接成功!");
114
115                  cboIpPort.Items.Add(point);
116
117                  dic.Add(point, tSocket);
118
119                     //接收消息
120
121                     Thread th = new Thread(ReceiveMsg);
122
123                     th.IsBackground = true;
124
125                     th.Start(tSocket);
126
127                 }
128
129                 catch (Exception ex)
130
131                 {
132
133                     ShowMsg(ex.Message);
134
135                     break;
136
137                 }
138
139             }
140
141         }
142
143         //接收消息
144
145         void ReceiveMsg(object o)
146
147         {
148
149             Socket client = o as Socket;
150
151             while (true)
152
153             {
154
155                 //接收客户端发送过来的数据
156
157                 try
158
159                 {
160
161                     //定义byte数组存放从客户端接收过来的数据
162
163                     byte[] buffer = new byte[1024 * 1024];
164
165                     //将接收过来的数据放到buffer中,并返回实际接受数据的长度
166
167                     int n = client.Receive(buffer);
168
169                     //将字节转换成字符串
170
171                     string words = Encoding.UTF8.GetString(buffer, 0, n);
172
173
174
175                     ShowMsg(client.RemoteEndPoint.ToString() + ":" + words);
176
177                 }
178
179                 catch (Exception ex)
180
181                 {
182
183                    ShowMsg(ex.Message);
184
185                     break;
186
187                 }
188
189             }
190
191         }
192
193
194
195         void ShowMsg(string msg)
196
197         {
198
199             txtLog.AppendText(msg+"\r\n");
200
201         }
202
203
204
205         private void Form1_FormClosing(object sender, FormClosingEventArgs e)
206
207         {
208
209             //主窗体关闭时关闭子线程
210
211
212
213         }
214
215         //给客户端发送消息
216
217         private void btnSend_Click(object sender, EventArgs e)
218
219         {
220
221             try
222
223             {
224
225                 ShowMsg(txtMsg.Text);
226
227                 string ip = cboIpPort.Text;
228
229                 byte[] buffer = Encoding.UTF8.GetBytes(txtMsg.Text);
230
231                 dic[ip].Send(buffer);
232
233                 // client.Send(buffer);
234
235             }
236
237             catch (Exception ex)
238
239             {
240
241                ShowMsg(ex.Message);
242
243             }
244
245
246
247         }

客户端代码:

  1 Socket client = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);2 3         private void btnConnection_Click(object sender, EventArgs e)4 5         {6 7             //连接到的目标IP8 9             IPAddress ip = IPAddress.Parse(txtIP.Text);10 11             //IPAddress ip = IPAddress.Any;12 13             //连接到目标IP的哪个应用(端口号!)14 15             IPEndPoint point=new IPEndPoint(ip,int.Parse(txtPort.Text));16 17             try18 19             {20 21                 //连接到服务器22 23                 client.Connect(point);24 25                 ShowMsg("连接成功");26 27                 ShowMsg("服务器" + client.RemoteEndPoint.ToString());28 29                 ShowMsg("客户端:" + client.LocalEndPoint.ToString());30 31                 //连接成功后,就可以接收服务器发送的信息了32 33                 Thread th=new Thread(ReceiveMsg);34 35                 th.IsBackground = true;36 37                 th.Start();38 39             }40 41             catch (Exception ex)42 43             {44 45                 ShowMsg(ex.Message);46 47             }48 49         }50 51         //接收服务器的消息52 53         void ReceiveMsg()54 55         {56 57             while (true)58 59             {60 61                 try62 63                 {64 65                     byte[] buffer = new byte[1024 * 1024];66 67                     int n = client.Receive(buffer);68 69                     string s = Encoding.UTF8.GetString(buffer, 0, n);70 71                     ShowMsg(client.RemoteEndPoint.ToString() + ":" + s);72 73                 }74 75                 catch (Exception ex)76 77                 {78 79                     ShowMsg(ex.Message);80 81                     break;82 83                 }84 85             }86 87           88 89         }90 91  92 93         void ShowMsg(string msg)94 95         {96 97             txtInfo.AppendText(msg+"\r\n");98 99         }
100
101
102
103         private void btnSend_Click(object sender, EventArgs e)
104
105         {
106
107             //客户端给服务器发消息
108
109             if (client!=null)
110
111             {
112
113                 try
114
115                 {
116
117                    ShowMsg(txtMsg.Text);
118
119                     byte[] buffer = Encoding.UTF8.GetBytes(txtMsg.Text);
120
121                     client.Send(buffer);
122
123                 }
124
125                 catch (Exception ex)
126
127                 {
128
129                    ShowMsg(ex.Message);
130
131                 }
132
133             }
134
135
136
137         }
138
139
140
141         private void ClientForm_Load(object sender, EventArgs e)
142
143         {
144
145             Control.CheckForIllegalCrossThreadCalls = false;
146
147         }

好了,到这里我们对Socket的讨论就告一个段落了。

转载于:https://www.cnblogs.com/otsf/p/8520419.html

C# Socket网络编程精华篇 (转)相关推荐

  1. C# Socket网络编程精华篇

    我们在讲解Socket编程前,先看几个和Socket编程紧密相关的概念: TCP/IP层次模型 当然这里我们只讨论重要的四层 01,应用层(Application):应用层是个很广泛的概念,有一些基本 ...

  2. Socket网络编程(TCP/IP/端口/类)和实例

    原文:C# Socket网络编程精华篇 转自:微冷的雨 我们在讲解Socket编程前,先看几个和Socket编程紧密相关的概念: TCP/IP层次模型 当然这里我们只讨论重要的四层 01,应用层(Ap ...

  3. Socket网络编程(2)--服务端实现

    中秋了,首先祝大家中秋快乐,闲着无事在家整一个socket的聊天程序,有点仿QQ界面,就是瞎折腾,不知道最后是不是能将所有功能实现. 如果你对socket不了解,请看这篇文章:http://www.c ...

  4. Python Socket网络编程(二)局域网内和局域网与广域网的持续通信

    目录 前言 IP地址 简介 公有IP 私有IP 局域网之间网络通信 前提 功能描述 源码 运行结果 局域网与广域网网络通信 前提 源码 结语 前言 本系列博客是笔者学习Python Socket的过程 ...

  5. Python Socket网络编程(一)初识Socket和Socket初步使用

    目录 前言 网络编程 实质 IP地址和端口 数据传输协议 协议 Socket 概念 套接字 socket对象方法 初步使用 功能 源码 运行结果 结语 前言 本系列博客是笔者学习Python Sock ...

  6. 【Socket网络编程进阶与实战】------ Socket网络编程快速入门

    前言 本篇博客主要是分享,socket网络编程进阶与实践☞socket网络编程快速入门 一.聊一聊Socket 学习目标与收获

  7. python开发之Socket网络编程

    python开发之Socket网络编程 一.SOCKET基础 二.SOCKET通信流程 1. 流程描述: 2. 相关方法及参数介绍: 三.实例(屌丝追女神的故事) 1. 故事1:(一次通信) 2. 故 ...

  8. 《C#网络编程高级篇之网页游戏辅助程序设计(扫描版)》

    <C#网络编程高级篇之网页游戏辅助程序设计>通过编写C#网络编程语言中具有代表性的实例,向读者深入细致地讲解了如何利用C#语言进行网页游戏辅助程序设计.本书通过大量的代码引导读者一步步学习 ...

  9. 【Linux】socket网络编程之服务器与客户端的数据交互

    [Linux]socket网络编程之服务器与客户端的数据交互 前言参考 argc !=2是什么意思 inet pton函数 对stdin,stdout 和STDOUT_FILENO,STDIN_FIL ...

最新文章

  1. 学习jQuery之旅--使用炫酷的jQuery插件
  2. 因为看见,所以发现:QBotVariant谢绝落幕
  3. 设置Windows7各种睡眠方式
  4. 支付宝当面付扫码支付支付后不回调_支付宝当面付门店码
  5. 【拔刀吧少年】之sort uniq tr cut eval常用命令
  6. 【转】[完全免费] 在线UML Class Diagram 类图工具 - 教程第1部分
  7. 我的《野蛮生长》书摘
  8. 2021年11月国产数据库排行榜:openGauss闯入前三,Kingbase流行度与日俱增,TDengine厚积薄发
  9. 服务器2003光盘修复,windows光盘修复系统
  10. 桥牌笔记L4D17:小心阻塞
  11. java浮动广告_浮动的广告代码
  12. 【无人机】【2008.09】用于小型无人机目标定位的轨迹优化
  13. 孤儿进程/僵尸进程/守护进程
  14. 佳能mp236打印机驱动 官方版
  15. BottledWater-PG安装部署
  16. 解决K8S节点NotReady状态
  17. V4L2驱动详解 API翻译
  18. vue 安装不上,报错,解决办法如下
  19. 费马大定理:一部跨越时代的惊险小说
  20. php开发手册要看完吗,9个开发人员应该知道的PHP库

热门文章

  1. 光明行动:共同呵护好孩子的眼睛——广西实施光明行动实地考察调研综述
  2. Logic Pro X for Mac(音乐制作软件)
  3. 如何关闭服务器系统防火墙设置方法,怎么关闭防火墙 Windows自带防火墙关闭方法...
  4. 搭建一个vue小页面
  5. concat,ucase/lcase,left/right,length,replace
  6. AlexNet系列I:模型参数计算
  7. 一图看尽APP各推广渠道“超级用户浓度”| 互联网行业公会
  8. 【ISO/IEC9126】ISO/IEC9126中软件质量模型品质介绍总结
  9. Cg Programming In Unity Projection of Bumpy Surfaces
  10. python学习004-----python中%s的各种用法