C# 多线程网络通信
2013-06-29 16:29
183 查看
博客园 :梦工厂2012
本月由于事情太多,没能有太多的时间去写博客.不过还好在月底抽时间写了这个多线程网络通信的程序 .程序说明:控制端 创建一个写线程threadWrite和一个读线程threadRead ,写线程用于向控制端发送操控指令.读线程用于读取被控制端姿态数据.这里C# 编写了一个模拟被控端ServerConsole .源代码如下,
using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Net.Sockets; using System.Net; using System.Timers; using System.Threading; namespace ServerConsole { class Program { //创建写线程 private static Thread threadWrite; static int send_num = 0; static NetworkStream streamToClient, streamFromClient; static void Main(string[] args) { ushort[] data=new ushort[4]; const int BufferSize = 10; int received_num = 0; byte[] buffer = new byte[BufferSize]; int bytesRead; Console.WriteLine("Server is runing"); IPAddress ip = new IPAddress(new byte[]{192,168,0,1}); TcpListener listener = new TcpListener(ip, 8500); listener.Start(); Console.WriteLine("Start listening"); while(true) { //为TCP网络服务提供提供客户端连接 TcpClient remoteClient = listener.AcceptTcpClient(); //Receive the request of connection // 打印连接到的客户端信息 Console.WriteLine("Client Connected!{0} <-- {1}", remoteClient.Client.LocalEndPoint, remoteClient.Client.RemoteEndPoint); streamToClient = remoteClient.GetStream(); streamFromClient = remoteClient.GetStream(); /*--------------------------------Creat the write thread----------------------------------------*/ threadWrite = new Thread(new ThreadStart(write)); Console.WriteLine("实例化线程"); /*-------------------------------------------------------------------------------------------------*/ Handshaking(); //Hand shake ,与上位机进行握手 while(true) { try { bytesRead = streamFromClient.Read(buffer, 0, BufferSize); received_num++; if (bytesRead == 0) throw new Exception("读取到0字节"); Console.WriteLine("Reading data,{0}bytes...", bytesRead); ushort temp = checksum(buffer, 8); if (temp == ((ushort)buffer[8] + (ushort)(buffer[9] << 8))) { Console.WriteLine("校验正确"); data[0] = (ushort)(buffer[0] + (buffer[1] << 8)); data[1] = (ushort)(buffer[2] + (buffer[3] << 8)); data[2] = (ushort)(buffer[4] + (buffer[5] << 8)); data[3] = (ushort)(buffer[6] + (buffer[7] << 8)); Console.WriteLine("The result is {0},{1},{2},{3},接收{4},发送{5}.", data[0], data[1], data[2], data[3],received_num,send_num); } else Console.WriteLine("校验不正确!"); } catch (Exception ex) { Console.WriteLine(ex.Message); break; } } //while Console.WriteLine("\n输入Q键退出,其他键继续!"); ConsoleKey key; key = Console.ReadKey(true).Key; if (key == ConsoleKey.Q) return; else { Console.WriteLine("continute...."); received_num = 0; send_num = 0; } } //whlie } //main private static void write() { byte[] send_byte = new byte[18]; while (true) { for (int i = 0; i < 16;i++ ) { send_byte[i] = (byte)2; } ushort temp = checksum(send_byte, 16); send_byte[16] = (byte)(temp & 0x00ff); //low send_byte[17] = (byte)((temp & 0xff00) >> 8); //high //下面进行数据的发送...... try { streamToClient.Write(send_byte, 0, send_byte.Length); // 发往客户端 send_num++; } catch (Exception x) { Console.WriteLine(x.Message); return; } Thread.Sleep(20); } } /// <summary> /// 与 上位机进行握手 /// </summary> private static void Handshaking() { byte[] buffer = new byte[1]; lock (streamFromClient) { int bytesRead = streamFromClient.Read(buffer, 0, 1); Console.WriteLine("Reading data,{0}bytes...", bytesRead); } if (buffer[0] == 0x41) { Console.WriteLine("Received: {0}", Encoding.ASCII.GetString(buffer, 0, buffer.Length)); buffer[0] = 0x42; lock (streamToClient) { streamToClient.Write(buffer, 0, buffer.Length); } Console.WriteLine("sent;{0}", Encoding.ASCII.GetString(buffer, 0, buffer.Length)); if(!threadWrite.IsAlive) { threadWrite.Start(); Console.WriteLine("start the write thread "); } } } /// <summary> /// CRC16校验函数 /// </summary> /// <param name="array"></param> /// <param name="Len"></param> /// <returns></returns> private static ushort CRC16(char[] array, int Len) { int CRC; UInt16 IX, IY; CRC = 0xffff; //set all 1 for (IX = 0; IX < Len; IX++) { CRC = CRC ^ (UInt16)(array[IX]); for (IY = 0; IY <= 7; IY++) { if ((CRC & 1) != 0) CRC = (CRC >> 1) ^ 0xA001; else CRC = CRC >> 1; } } return (ushort)CRC; } //checksum校验 private static ushort checksum(byte[] array, int Len) { ushort check_sum = 0, i; //char temp[8]; for (i = 0; i < Len; i += 2) { check_sum += (ushort)((array[i + 1] << 8) + array[i]); } return check_sum; } } }
代码简介:代码写的用点乱,大家将就看吧. 主程序用于接收 控制数据 ,如外我创建一个写线程用于向控制端数据.这里收到的数据我全部写为 (byte)1,发送的数据全部写为(byte)2 ,校验采用累加和校验 .被控端与操控端采用0x41 0x42 进行简单的握手,其实感觉是有点多于了.操控端与被控端没有太大的区别,数据通信部分是相同的,创建连接的代码有点不同.
基本过程:
//实例化通信类
TcpClient client = new TcpClient();
client.Connect(url_conrtol, Convert.ToInt32(portNumber)); // 与服务器连接
streamToServer = client.GetStream();
读写过程 与上面帖的代码相同.
在程序编写过程中,我使用多线程和networkstream 的read,write对流的读写,因为是单机点对点通信并没有发现有什么问题(read 阻塞 ,write 不阻塞 ),read 阻塞不影响发送 . 网上有资料说: Write 和 Read 方法用于简单的单线程同步阻止 I/O。若要使用不同的线程来处理 I/O,则请考虑使用BeginWrite 和 EndWrite 方法,或 BeginRead 和 EndRead 方法进行通信。程序中用用于lock关键字,具体是否起到作用,本人仍在查找资料.
每个程序都是本人花费一定的时间经过多次修改所得,直到程序最优,有些看似简单的问题其实一点也不简单!!博文为本人所写转载请表明出处C# 多线程网络通信
相关文章推荐
- C#网络通信(2)--TCP编程和多线程
- C#做了个多线程网络通信的例子
- 在C#中使用SerialPort类实现串口通信 遇到多线程问题
- Java基于多线程的网络通信实现服务器计算正方形面积
- C#网络编程TCP通信的粘包问题讨论
- C#Socket 网络通信异步处理
- C#网络通信 同步方式总结
- c#网络通信框架networkcomms内核解析之十 支持优先级的自定义线程池
- socket多线程服务器网络通信
- 【开源下载】客户端根据服务器端的指令弹出提示窗口(c#网络通信源码)
- 第01天多线程网络:(16):GCD实现线程间通信
- Linux Socket 网络编程 基于GTK+ 的多线程实现的局域网通信软件
- Android 网络:基于TCP协议通信,多线程,实现简单的C/S聊天室
- Java 网络编程中 TCP 通信服务端的多线程模型
- 【源码】c#编写的安卓客户端与Windows服务器程序进行网络通信
- C#与Java通过protobuf进行网络通信过程中遇到的问题
- 网络通信2-多线程下载网络资源
- 网络多线程-NSOperation线程间通信
- DirectX编程:C#中利用Socket实现网络语音通信[初级版本]
- 简单的现实多线程的Socket网络通信,对前面一篇的补充的加入线程