1. TCP与UDP的优缺点
- TCP面向连接;UDP无连接
- TCP有序、可靠;UDP不可靠、数据包无序且可能丢失
- TCP自动将数据拆包且进行流量控制;UDP需要手动拆包,手动发送数据,手动进行流量控制
- TCP是点对点;UDP支持一对一、一对多、多对一、多对多的通信
- TCP对系统资源要求高;UDP对系统资源要求少
- TCP工作效率比UDP低,UDP具有较好的实时性
2. TCP与UDP在游戏中的应用场景
TCP:可以容忍延迟并且有很好的屏蔽延迟的设计,如纸牌类和MMO
UDP:不能容忍延迟,如DOTA类和动作类
3. TCP与UDP代码实现
只实现了基本收发功能,没有进行合理性分析,TCP有客户端和服务器之分,UDP则没有但考虑到区分代码中还是将其分为了客户端和服务器。
TCP
namespace socket_TCP
{
class Program
{
static Socket TcpServer;
static Socket connection;
static void Main(string[] args)
{
TcpServer = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
IPAddress address = IPAddress.Parse("127.0.0.1");
IPEndPoint point = new IPEndPoint(address, 8005);
TcpServer.Bind(point);
TcpServer.Listen(10);
Console.WriteLine("TCP服务器已启动-------");
//开启一个新线程,用于等待客户端连接
Thread threadwatch = new Thread(watchconnecting);
//将窗体线程设置为与后台同步,随着主线程结束而结束
threadwatch.IsBackground = true;
threadwatch.Start();//启动线程
}
//服务器等待客户端的连接
public static void watchconnecting()
{
connection = TcpServer.Accept();//程序执行到Accept方法时会被阻塞,直到接收到客户端的连接请求,才执行下一句
Console.WriteLine(connection.RemoteEndPoint.ToString() + "连接成功!");
//开启一个新线程,用于接受消息
Thread threadrec = new Thread(recData);
threadrec.IsBackground = true;
threadrec.Start();
}
//服务器接受客户端发来的消息
public static void recData(object c)
{
try
{
while (true)
{
byte[] buffer = new byte[1024];
int len = connection.Receive(buffer,buffer.Length,0);
if (len == 0)
{
break;
}
else
{
string str = Encoding.UTF8.GetString(buffer, 0, len);
Console.WriteLine(connection.RemoteEndPoint + ":" + str);
}
}
}
catch (Exception ex)
{
Console.WriteLine(ex.ToString());
}
}
//服务器向客户端发送消息
public static void sendData(string str)
{
byte[] data = Encoding.UTF8.GetBytes(str);
TcpServer.Send(data);
}
}
}
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Threading;
using System.Net;
using System.Net.Sockets;
namespace socket_TCPclient
{
public partial class Form1 : Form
{
Socket TcpClient;
public Form1()
{
InitializeComponent();
}
private void button1_Click(object sender, EventArgs e)
{
TcpClient = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
IPAddress address = IPAddress.Parse("127.0.0.1");
IPEndPoint point = new IPEndPoint(address,8005);
TcpClient.Connect(point);
Thread td = new Thread(recData);
td.IsBackground = true;
td.Start();
}
private void recData()
{
while (true)
{
byte[] temp = new byte[1024];
int len = TcpClient.Receive(temp);
if (len == 0)
{
break;
}
else
{
string str = Encoding.UTF8.GetString(temp);
textBox2.Text = str;
}
}
}
private void button2_Click(object sender, EventArgs e)
{
if (textBox1.Text == null || textBox1.Text == "")
{
MessageBox.Show("发送消息为空");
}
else
{
byte[] sendData = Encoding.UTF8.GetBytes(textBox1.Text);
TcpClient.Send(sendData);
}
}
}
}
UDP
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Net;
using System.Net.Sockets;
namespace socket_UDPServer
{
class Program
{
static void Main(string[] args)
{
Socket socketServer = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
IPAddress address = IPAddress.Parse("127.0.0.1");
IPEndPoint point = new IPEndPoint(address, 8050);
socketServer.Bind(point);
Console.WriteLine("等待客户端数据-------");
while (true)
{
EndPoint remotepoint = new IPEndPoint(IPAddress.Any,0);
byte[] dataRec = new byte[1024];
int len = socketServer.ReceiveFrom(dataRec,ref remotepoint);
string temp = Encoding.UTF8.GetString(dataRec);
Console.WriteLine(temp);
}
}
}
}
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Net;
using System.Net.Sockets;
namespace socket_UDPClient
{
class Program
{
static void Main(string[] args)
{
Socket UDPClient = new Socket(AddressFamily.InterNetwork,SocketType.Dgram,ProtocolType.Udp);
IPAddress address = IPAddress.Parse("127.0.0.1");
IPEndPoint point = new IPEndPoint(address, 8050);
Console.WriteLine("请输入发送信息------");
string temp = Console.ReadLine();
byte[] sendData = Encoding.UTF8.GetBytes(temp);
UDPClient.SendTo(sendData,sendData.Length,SocketFlags.None,point);
UDPClient.Close();
}
}
}