C# winfroms使用socket客户端服务端代码详解

文章目录

  • 1️⃣ 通信相关说明
    • 1.1服务端与客户端
    • 1.2 信息发送原理
    • 1.3 信息接收原理
  • 2️⃣ socket代码
    • 2.1 客户端代码
    • 2.2 服务端代码
  • 3️⃣ 定时任务处理报文
    • 3.1 Timers定时任务
  • 优质资源分享

作者:xcLeigh
文章地址:https://blog.csdn.net/weixin_43151418/article/details/136257608


C# winfroms使用socket客户端服务端代码详解,声明Socket 第一个参数:寻址方式,第二个参数:传输数据的方式,第三个参数:通信协议Socket socket = new Socket(AddressFamily.InterNetwork,SocketType.Stream,ProtocolType.Tcp); 开启侦听 参数是指可以连接的客户端数量socket.Listen(10);,socket.Accept();这里需要注意,Accept()会阻塞线程,直到连接上客户端。如果放在主线程中,会阻塞前台操作。需要创建一个新的线程。Accept()返回一个socket,客户端连接上之后,服务端自动生成一个socket和连接的客端通信。连接成功后,向客户端发送“连接成功!”

1️⃣ 通信相关说明

1.1服务端与客户端

    启动服务端后,服务端通过持续监听客户端发来的请求,一旦监听到客户端传来的信息(请求),两端便可以互发信息了.
服务端需要绑定一个IP,用于客户端在网络中寻找并建立连接(支持局域网内部客户端与服务端之间的互相通信)

1.2 信息发送原理

    将手动输入字符串信息转换成机器可以识别的字节数组,然后调用套接字的Send()方法将字节数组发送出去

1.3 信息接收原理

    调用套接字的Receive()方法,获取对端传来的字节数组,然后将其转换成人可以读懂的字符串信息

2️⃣ socket代码

2.1 客户端代码

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Net;
using System.Net.Sockets;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Windows.Forms;namespace TcpMsgClient
{public partial class FrmClient : Form{public FrmClient(){InitializeComponent();//关闭对文本框的非法线程操作检查TextBox.CheckForIllegalCrossThreadCalls = false;}//创建 1个客户端套接字 和1个负责监听服务端请求的线程Socket socketClient = null;Thread threadClient = null;/// <summary>/// 连接服务端事件/// </summary>/// <param name="sender"></param>/// <param name="e"></param>private void btnListenServer_Click(object sender, EventArgs e){//定义一个套字节监听  包含3个参数(IP4寻址协议,流式连接,TCP协议)socketClient = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);//需要获取文本框中的IP地址IPAddress ipaddress = IPAddress.Parse(this.txtIP.Text.Trim());//将获取的ip地址和端口号绑定到网络节点endpoint上IPEndPoint endpoint = new IPEndPoint(ipaddress, int.Parse(this.txtPort.Text.Trim()));//这里客户端套接字连接到网络节点(服务端)用的方法是Connect 而不是Bindtry{socketClient.Connect(endpoint);this.txtMsg.AppendText("客户端连接服务端成功!" + "\r\n");this.btnListenServer.Enabled = false;//创建一个线程 用于监听服务端发来的消息threadClient = new Thread(RecMsg);//将窗体线程设置为与后台同步threadClient.IsBackground = true;//启动线程threadClient.Start();}catch (Exception ex) {this.txtMsg.AppendText("远程服务端断开,连接失败!" + "\r\n");}}/// <summary>/// 接收服务端发来信息的方法/// </summary>private void RecMsg(){while (true) //持续监听服务端发来的消息{try{//定义一个1M的内存缓冲区 用于临时性存储接收到的信息byte[] arrRecMsg = new byte[1024 * 1024];//将客户端套接字接收到的数据存入内存缓冲区, 并获取其长度int length = socketClient.Receive(arrRecMsg);//将套接字获取到的字节数组转换为人可以看懂的字符串string strRecMsg = Encoding.UTF8.GetString(arrRecMsg, 0, length);//将发送的信息追加到聊天内容文本框中txtMsg.AppendText("服务端 " + GetCurrentTime() + "\r\n" + strRecMsg + "\r\n");}catch (Exception ex) {this.txtMsg.AppendText("远程服务器已中断连接!"+"\r\n");this.btnListenServer.Enabled = true;break;}}}/// <summary>/// 发送字符串信息到服务端的方法/// </summary>/// <param name="sendMsg">发送的字符串信息</param>private void ClientSendMsg(string sendMsg){try {//将输入的内容字符串转换为机器可以识别的字节数组byte[] arrClientSendMsg = Encoding.UTF8.GetBytes(sendMsg);//调用客户端套接字发送字节数组socketClient.Send(arrClientSendMsg);//将发送的信息追加到聊天内容文本框中txtMsg.AppendText("天涯 " + GetCurrentTime() + "\r\n" + sendMsg + "\r\n");}catch(Exception ex){this.txtMsg.AppendText("远程服务器已中断连接,无法发送消息!" + "\r\n");}}private void btnSendMsg_Click(object sender, EventArgs e){//调用ClientSendMsg方法 将文本框中输入的信息发送给服务端ClientSendMsg(this.txtClientSendMsg.Text.Trim());this.txtClientSendMsg.Clear();}private void txtClientSendMsg_KeyDown(object sender, KeyEventArgs e){//当光标位于文本框时 如果用户按下了键盘上的Enter键if (e.KeyCode == Keys.Enter){//则调用客户端向服务端发送信息的方法ClientSendMsg(this.txtClientSendMsg.Text.Trim());this.txtClientSendMsg.Clear();}}/// <summary>/// 获取当前系统时间的方法/// </summary>/// <returns>当前时间</returns>private DateTime GetCurrentTime(){DateTime currentTime = new DateTime();currentTime = DateTime.Now;return currentTime;}}
}

2.2 服务端代码

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Net;
using System.Net.Sockets;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Windows.Forms;namespace TcpMsgServer
{public partial class FrmServer : Form{public FrmServer(){InitializeComponent();//关闭对文本框的非法线程操作检查TextBox.CheckForIllegalCrossThreadCalls = false;}Thread threadWatch = null; //负责监听客户端的线程Socket socketWatch = null;  //负责监听客户端的套接字/// <summary>/// 启动服务/// </summary>/// <param name="sender"></param>/// <param name="e"></param>private void btnServerConn_Click(object sender, EventArgs e){try{//定义一个套接字用于监听客户端发来的信息  包含3个参数(IP4寻址协议,流式连接,TCP协议)socketWatch = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);//服务端发送信息 需要1个IP地址和端口号IPAddress ipaddress = IPAddress.Parse(this.txtIP.Text.Trim()); //获取文本框输入的IP地址//将IP地址和端口号绑定到网络节点endpoint上IPEndPoint endpoint = new IPEndPoint(ipaddress, int.Parse(this.txtPort.Text.Trim())); //获取文本框上输入的端口号//监听绑定的网络节点socketWatch.Bind(endpoint);//将套接字的监听队列长度限制为20socketWatch.Listen(20);//创建一个监听线程threadWatch = new Thread(WatchConnecting);//将窗体线程设置为与后台同步threadWatch.IsBackground = true;//启动线程threadWatch.Start();//启动线程后 txtMsg文本框显示相应提示txtMsg.AppendText("开始监听客户端传来的信息!" + "\r\n");this.btnServerConn.Enabled = false;}catch (Exception ex) {txtMsg.AppendText("服务端启动服务失败!" + "\r\n");this.btnServerConn.Enabled = true;}}//创建一个负责和客户端通信的套接字Socket socConnection = null;/// <summary>/// 监听客户端发来的请求/// </summary>private void WatchConnecting(){while (true)  //持续不断监听客户端发来的请求{socConnection = socketWatch.Accept();txtMsg.AppendText("客户端连接成功! " + "\r\n");//创建一个通信线程ParameterizedThreadStart pts = new ParameterizedThreadStart(ServerRecMsg);Thread thr = new Thread(pts);thr.IsBackground = true;//启动线程thr.Start(socConnection);}}/// <summary>/// 发送信息到客户端的方法/// </summary>/// <param name="sendMsg">发送的字符串信息</param>private void ServerSendMsg(string sendMsg){try{//将输入的字符串转换成 机器可以识别的字节数组byte[] arrSendMsg = Encoding.UTF8.GetBytes(sendMsg);//向客户端发送字节数组信息socConnection.Send(arrSendMsg);//将发送的字符串信息附加到文本框txtMsg上txtMsg.AppendText("服务器 " + GetCurrentTime() + "\r\n" + sendMsg + "\r\n");}catch (Exception ex) {txtMsg.AppendText("客户端已断开连接,无法发送信息!" + "\r\n");}}/// <summary>/// 接收客户端发来的信息/// </summary>/// <param name="socketClientPara">客户端套接字对象</param>private void ServerRecMsg(object socketClientPara){Socket socketServer = socketClientPara as Socket;while (true){//创建一个内存缓冲区 其大小为1024*1024字节  即1Mbyte[] arrServerRecMsg = new byte[1024 * 1024];try{//将接收到的信息存入到内存缓冲区,并返回其字节数组的长度int length = socketServer.Receive(arrServerRecMsg);//将机器接受到的字节数组转换为人可以读懂的字符串string strSRecMsg = Encoding.UTF8.GetString(arrServerRecMsg, 0, length);//将发送的字符串信息附加到文本框txtMsg上txtMsg.AppendText("天涯 " + GetCurrentTime() + "\r\n" + strSRecMsg + "\r\n");}catch (Exception ex) {txtMsg.AppendText("客户端已断开连接!" + "\r\n");break;}}}/// <summary>/// 发送消息到客户端/// </summary>/// <param name="sender"></param>/// <param name="e"></param>private void btnSendMsg_Click(object sender, EventArgs e){//调用 ServerSendMsg方法  发送信息到客户端ServerSendMsg(this.txtSendMsg.Text.Trim());this.txtSendMsg.Clear();}/// <summary>/// 快捷键 Enter 发送信息/// </summary>/// <param name="sender"></param>/// <param name="e"></param>private void txtSendMsg_KeyDown(object sender, KeyEventArgs e){//如果用户按下了Enter键if (e.KeyCode == Keys.Enter){//则调用 服务器向客户端发送信息的方法ServerSendMsg(txtSendMsg.Text.Trim());this.txtSendMsg.Clear();}}/// <summary>/// 获取当前系统时间的方法/// </summary>/// <returns>当前时间</returns>private DateTime GetCurrentTime(){DateTime currentTime = new DateTime();currentTime = DateTime.Now;return currentTime;}/// <summary>/// 获取本地IPv4地址/// </summary>/// <returns></returns>public IPAddress GetLocalIPv4Address() {IPAddress localIpv4 = null;//获取本机所有的IP地址列表IPAddress[] IpList = Dns.GetHostAddresses(Dns.GetHostName());//循环遍历所有IP地址foreach (IPAddress IP in IpList) {//判断是否是IPv4地址if (IP.AddressFamily == AddressFamily.InterNetwork){localIpv4 = IP;}else {continue;}}return localIpv4;}/// <summary>/// 获取本地IP事件/// </summary>/// <param name="sender"></param>/// <param name="e"></param>private void btnGetLocalIP_Click(object sender, EventArgs e){//接收IPv4的地址IPAddress localIP = GetLocalIPv4Address();//赋值给文本框this.txtIP.Text = localIP.ToString();}}
}

3️⃣ 定时任务处理报文

3.1 Timers定时任务

    在内部多线程情况下,这个定时任务,支持,启动,设定条件,满足后执行任务,不满做执行设定任务,然后自动销毁。

using SimulateMaster.Bean;
using SimulateMaster.page;
using Sunny.UI;
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Timers;namespace SimulateMaster.Util
{public class MsgReply{private ServiceMain _serviceMain;private readonly System.Timers.Timer _timer;public static string clicentInfo_value = ""; //设备信息【IP:端口】public static string mainName_value=""; //窗体名称public static string msgContent= MsgUtils.MSG_QDLL;//报文内容public int msgNum=0;//重发次数 最多三次public MsgReply(string msgValue,string clientInfo,string mainName, ServiceMain serviceMain){clicentInfo_value = clientInfo;mainName_value = mainName;_serviceMain = serviceMain;msgContent = msgValue;// 设置定时器间隔(单位为毫秒)_timer = new System.Timers.Timer(5000);// 添加 Elapsed 事件处理程序_timer.Elapsed += OnTimerElapsed;// 开始计时器_timer.Start();}protected virtual void OnTimerElapsed(object sender, ElapsedEventArgs e){FileUtils.WriteFileLog("定时任务触发没有接收到回复报文!", "报文接收定时任务");}public void Dispose(){FileUtils.WriteFileLog(clicentInfo_value + "定时任务关闭!", "报文接收定时任务");if (_timer != null && _timer.Enabled)_timer.Stop();_timer?.Dispose();}}
}
--------------- 业精于勤,荒于嬉 ---------------

请添加图片描述

--------------- 行成于思,毁于随 ---------------

优质资源分享

🧡🧡🧡🧡🤍【总览】程序员前端、后端资源合集

🧡🧡🧡🧡🤍【源码】程序员优质资源汇总

🧡🧡🧡🧡🤍【博主推荐】JAVA SSM框架的后台管理系统(附源码)

🧡🧡🧡🧡🤍【博主推荐】SpringBoot API接口对数据库增删改查,路由,TOKEN,WebSocket完整版(附源码)

🧡🧡🧡🧡🤍【博主推荐】HTML制作一个美观的个人简介网页(附源码)

🧡🧡🧡🧡🤍【博主推荐】html好看的个人简历网页版(附源码)

🧡🧡🧡🧡🤍【博主推荐】html好看的个人主页(附源码)

🧡🧡🧡🧡🤍【博主推荐】html好看的邀请函(附源码)

🧡🧡🧡🧡🤍【博主推荐】html好看的音乐播放器(附源码)

🧡🧡🧡🧡🤍【博主推荐】html好看的拼图小游戏(附源码)

🧡🧡🧡🤍🤍【博主推荐】html好看的拼图验证码(附源码)

🧡🧡🧡🧡🧡【博主推荐】html界面绘制SVG图形(附源码)

🧡🧡🧡🧡🤍【博主推荐】html操作SVG图(附源码)

🧡🧡🧡🧡🤍【博主推荐】html下拉框树形(附好看的登录界面)

🧡🧡🧡🧡🤍【博主推荐】HTML5响应式手机WEB(附源码)

🧡🧡🧡🧡🤍【博主推荐】大数据可视化大屏(源码下载)

🧡🧡🧡🧡🧡【博主推荐】html引用百度地图定位闪烁弹框树形(附源码)

🧡🧡🧡🧡🤍【博主推荐】HTML酷炫动画表白求爱界面(附源码)


请添加图片描述


     💞 关注博主 带你实现畅游前后端

     🏰 加入社区 带你体验马航不孤单

     💯 神秘个人简介 带你体验不一样得介绍

     🎀 酷炫邀请函 带你体验高大上得邀请


     ① 🉑提供云服务部署(有自己的阿里云);
     ② 🉑提供前端、后端、应用程序、H5、小程序、公众号等相关业务;
     如🈶合作请联系我,期待您的联系。
    :本文撰写于CSDN平台,作者:xcLeigh所有权归作者所有) ,https://blog.csdn.net/weixin_43151418,如果相关下载没有跳转,请查看这个地址,相关链接没有跳转,皆是抄袭本文,转载请备注本文原地址。


     亲,码字不易,动动小手,欢迎 点赞 ➕ 收藏,如 🈶 问题请留言(评论),博主看见后一定及时给您答复,💌💌💌


原文地址:https://blog.csdn.net/weixin_43151418/article/details/136257608(防止抄袭,原文地址不可删除)

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/263026.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

用友U8-OA协同工作系统doUpload.jsp接口任意文件上传漏洞

声明 本文仅用于技术交流&#xff0c;请勿用于非法用途 由于传播、利用此文所提供的信息而造成的任何直接或者间接的后果及损失&#xff0c;均由使用者本人负责&#xff0c;文章作者不为此承担任何责任。 1、系统介绍 用友协同云是新一代的企业社交化协同办公平台&#xff0c…

LangChain原理学习笔记

最新越发觉得AI的发展&#xff0c;对未来是一场革命&#xff0c;LangChain已经在工程设计上有了最佳实践&#xff0c;类似于AI时代的编程模型或编程框架&#xff0c;有点Spring框架的意思。之前在LangChain上也有些最佳实践&#xff0c;所以在这里分享记录下。 LangChain解决什…

每日五道java面试题之spring篇(二)

目录&#xff1a; 第一题 Spring事务传播机制第二题 Spring事务什么时候会失效?第三题 什么是bean的⾃动装配&#xff0c;有哪些⽅式&#xff1f;第四题 Spring中的Bean创建的⽣命周期有哪些步骤&#xff1f;第五题 Spring中Bean是线程安全的吗&#xff1f; 第一题 Spring事务…

加载arcgis切片服务网络请求有大量404错误

需求&#xff1a; 前端访问arcgis切片服务时&#xff0c;在网络请求中出现大量404&#xff08;Not Found&#xff09;错误&#xff0c;切片时设置了感兴趣区域&#xff0c;在感兴趣范围内请求切片时能够正常返回切片。 问题分析&#xff1a; 设置感兴趣区域切片的目的是减少站…

Docker vs VM

关于应用程序的托管和开发&#xff0c;市场中的技术和产品琳琅满目。对比 Docker 和 VM&#xff0c;如何取舍&#xff1f;这主要由自身团队的因素决定&#xff0c;在选择 Docker 的情况下&#xff0c;你需要保证程序可在容器和虚拟机中运行。另外&#xff0c;成本和易用性也是重…

ArcgisForJS如何在线编辑ArcGIS Server发布的几何要素?

文章目录 0.引言1.ArcGIS创建几何要素2.ArcGIS Server发布几何要素3.ArcgisForJS在线编辑ArcGIS Server发布的几何要素 0.引言 ArcGIS For JS 是一种用于创建和编辑地理信息的 JavaScript 库&#xff0c;它允许用户在线编辑 ArcGIS Server 发布的几何要素。本文从ArcGIS创建几…

P8630 [蓝桥杯 2015 国 B] 密文搜索

P8630 [蓝桥杯 2015 国 B] 密文搜索 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)https://www.luogu.com.cn/problem/P8630 题目分析 基本上是hash的板子&#xff0c;但实际上对于密码串&#xff0c;只要判断主串中任意连续的八个位置是否存在密码串即可&#xff1b;那么我们…

使用Python制作进度条有多少种方法?看这一篇文章就够了!

前言 偶然间刷到一个视频&#xff0c;说到&#xff1a;当程序正在运算时&#xff0c;会有一个较长时间的空白期&#xff0c;谁也不知道程序运行的进度如何&#xff0c;不如给他加个进度条。 于是我今个就搜寻一下&#xff0c;Python版的进度条都可以怎么写&#xff01; 送书…

PNPM 批量检查和更新项目依赖

&#x1f680; 作者主页&#xff1a; 有来技术 &#x1f525; 开源项目&#xff1a; youlai-mall &#x1f343; vue3-element-admin &#x1f343; youlai-boot &#x1f33a; 仓库主页&#xff1a; Gitee &#x1f4ab; Github &#x1f4ab; GitCode &#x1f496; 欢迎点赞…

国家建筑装配式内装产业基地在沪成立,副主任单位优积科技协同助推绿色低碳循环发展

上海市室内装饰行业协会装配式内装产业专业委员会成立大会暨“国家建筑装配式内装产业基地”项目启动会于3月21日下午1点在上海光大酒店隆重举行。出席此次活动的包括市装协会长徐国俭&#xff0c;市装协党支部书记兼秘书长丛国梁&#xff0c;市装协装配式内装委主任顾泰昌&…

热点参数流控(Sentinel)

热点参数流控 热点流控 资源必须使用注解 @SentinelResource编写接口 以及 热点参数流控处理器 /*** 热点流控 必须使用注解 @SentinelResource* @param id* @return*/ @RequestMapping("/getById/{id}") @SentinelResource(value = "getById", blockHand…

华清远见嵌入式学习——驱动开发——day9

目录 作业要求&#xff1a; 作业答案&#xff1a; 代码效果&#xff1a; ​编辑 Platform总线驱动代码&#xff1a; 应用程序代码&#xff1a; 设备树配置&#xff1a; 作业要求&#xff1a; 通过platform总线驱动框架编写LED灯的驱动&#xff0c;编写应用程序测试&…

转运机器人,AGV底盘小车:打造高效、精准的汽车电子生产线

为了满足日益增长的市场需求&#xff0c;保持行业领先地位&#xff0c;某汽车行业电子产品企业引入富唯智能AMR智能搬运机器人及其智能物流解决方案&#xff0c;采用自动化运输措施优化生产节拍和搬运效率&#xff0c;企业生产效率得到显著提升。 项目背景&#xff1a; 1、工厂…

C++中的STL数据结构

内容来自&#xff1a;代码随想录&#xff1a;哈希表理论基础 1.常见的三种哈希结构 当我们想使用哈希法来解决问题的时候&#xff0c;我们一般会选择如下三种数据结构 数组 set &#xff08;集合&#xff09; map(映射) 在C中&#xff0c;set 和 map 分别提供以下三种数据结构…

HTTPS(超文本传输安全协议)被恶意请求该如何处理。

HTTPS&#xff08;超文本传输安全协议&#xff09;端口攻击通常是指SSL握手中的一些攻击方式&#xff0c;比如SSL握手协商过程中的暴力破解、中间人攻击和SSL剥离攻击等。 攻击原理 攻击者控制受害者发送大量请求&#xff0c;利用压缩算法的机制猜测请求中的关键信息&#xf…

什么是SSD型云服务器?

​  SSD云服务器是一种使用固态硬盘代替传统HDD进行存储的虚拟机。SDD 使用闪存单元来存储数据&#xff0c;与云计算技术相结合&#xff0c;形成强大且高效的存储解决方案&#xff0c;可以随时随地访问。 SSD云服务器如何工作? SSD云服务器是利用虚拟化和云计算技术创建的。…

ElementUI table表格组件实现双击编辑单元格失去焦点还原,支持多单元格

在使用ElementUI table表格组件时有时需要双击单元格显示编辑状态&#xff0c;失去焦点时还原表格显示。 实现思路&#xff1a; 在数据中增加isFocus:false.控制是否显示在table中用cell-dblclick双击方法 先看效果&#xff1a; 上源码&#xff1a;在表格模板中用scope.row…

最新Unity游戏主程进阶学习大纲(2个月)

过完年了&#xff0c;很多同学开始重新规划自己的职业方向,找更好的机会,准备升职或加薪。今天给那些工作了1~5年的开发者梳理”游戏开发客户端主程”的学习大纲&#xff0c;帮助大家做好面试准备。适合Unity客户端开发者。进阶主程其实就是从固定的几个方面搭建好完整的知识体…

python编程中模块的调用方法

模块&#xff0c;就是制造大型程序的“零件"。这些零件可以是外购的也可以是“自造”的。它们的使用方法很简单&#xff0c;就是“拿来”——import. “拿来”模块的方法有from***import*** 和import***&#xff0c;宗旨就是“拿来”——import. 对不对&#xff1f;

Vision Transfomer系列第二节---Tricks测试

目录 学习式和固定式位置编码测试dropout的作用测试block深度的作用测试embeding维度大小的作用测试多头的作用测试Overlap Patch的作用 学习式和固定式位置编码测试 主要测试无位置编码\可学习位置编码和固定式位置编码的训练效果: 其中固定式位置编码采用之前博客的正余弦位…