C# 如何向连接到套接字服务器的所有客户端广播消息
我试图使一个程序,可以发送命令到所有客户端从1台服务器。我一直在向所有客户端发送命令。我目前有以下代码:C# 如何向连接到套接字服务器的所有客户端广播消息,c#,sockets,C#,Sockets,我试图使一个程序,可以发送命令到所有客户端从1台服务器。我一直在向所有客户端发送命令。我目前有以下代码: using System; using System.Collections.Generic; using System.Net; using System.Net.Sockets; using System.Text; namespace Server { class Program { private static byte[] _buffer = ne
using System;
using System.Collections.Generic;
using System.Net;
using System.Net.Sockets;
using System.Text;
namespace Server
{
class Program
{
private static byte[] _buffer = new byte[1024];
private static List<Socket> _clientSockets = new List<Socket>();
private static int SERVERPORT = 5555;
private static Socket _serverSocket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
static void Main(string[] args)
{
SetupServer();
while (!Console.ReadKey().Equals("]")) //Stops the Console for closing after I type something in the console
{
}
}
private static void SetupServer()
{
Console.WriteLine("Setting up server...");
_serverSocket.Bind(new IPEndPoint(IPAddress.Any, SERVERPORT));
_serverSocket.Listen(100);
_serverSocket.BeginAccept(new AsyncCallback(AcceptCallback), null);
}
private static void AcceptCallback(IAsyncResult AR)
{
Socket socket = _serverSocket.EndAccept(AR);
_clientSockets.Add(socket);
Console.WriteLine("Client conntected");
string response = string.Empty;
response = Console.ReadLine();
byte[] data = Encoding.ASCII.GetBytes(response);
socket.BeginSend(data, 0, data.Length, SocketFlags.None, new AsyncCallback(SendCallback), null);
_serverSocket.BeginAccept(new AsyncCallback(AcceptCallback), null);
}
private static void ReceiveCallback(IAsyncResult AR)
{
Socket socket = (Socket)AR.AsyncState;
//int received = socket.EndReceive(AR);
//byte[] dataBuf = new byte[received];
//Array.Copy(_buffer, dataBuf, received);
//string text = Encoding.ASCII.GetString(dataBuf);
string response = string.Empty;
response = Console.ReadLine();
byte[] data = Encoding.ASCII.GetBytes(response);
socket.BeginSend(data, 0, data.Length, SocketFlags.None, new AsyncCallback(SendCallback), null);
socket.BeginReceive(_buffer, 0, _buffer.Length, SocketFlags.None, new AsyncCallback(ReceiveCallback), socket);
}
private static void SendCallback(IAsyncResult AR)
{
try {
Socket socket = (Socket)AR.AsyncState;
socket.EndSend(AR);
}
catch {
}
//It gets alot of NullReferenceExceptions. It does work this way but I dont trust it.
}
public static void sendMessage(IAsyncResult AR)
{
Socket socket = (Socket)AR.AsyncState;
string response = string.Empty;
response = Console.ReadLine();
byte[] data = Encoding.ASCII.GetBytes(response);
socket.BeginSend(data, 0, data.Length, SocketFlags.None, new AsyncCallback(SendCallback), null);
}
}
}
使用系统;
使用System.Collections.Generic;
Net系统;
使用System.Net.Sockets;
使用系统文本;
命名空间服务器
{
班级计划
{
专用静态字节[]_buffer=新字节[1024];
私有静态列表_clientSockets=new List();
专用静态int-SERVERPORT=5555;
私有静态套接字_serverSocket=新套接字(AddressFamily.InterNetwork,SocketType.Stream,ProtocolType.Tcp);
静态void Main(字符串[]参数)
{
SetupServer();
while(!Console.ReadKey().Equals(“])//在控制台中键入内容后停止控制台关闭
{
}
}
私有静态void SetupServer()
{
Console.WriteLine(“设置服务器…”);
_绑定(新的IPEndPoint(IPAddress.Any,SERVERPORT));
_serverSocket.Listen(100);
_serverSocket.BeginAccept(新的AsyncCallback(AcceptCallback),null);
}
私有静态void AcceptCallback(IAsyncResult AR)
{
套接字套接字=_serverSocket.EndAccept(AR);
_clientSockets.Add(socket);
Console.WriteLine(“客户端连接”);
字符串响应=string.Empty;
response=Console.ReadLine();
字节[]数据=Encoding.ASCII.GetBytes(响应);
socket.BeginSend(数据,0,数据.Length,SocketFlags.None,新异步回调(SendCallback),null);
_serverSocket.BeginAccept(新的AsyncCallback(AcceptCallback),null);
}
私有静态void ReceiveCallback(IAsyncResult AR)
{
套接字套接字=(套接字)AR.AsyncState;
//int received=插座端接收(AR);
//byte[]dataBuf=新字节[已接收];
//复制(_缓冲区,数据缓冲区,已接收);
//字符串文本=Encoding.ASCII.GetString(dataBuf);
字符串响应=string.Empty;
response=Console.ReadLine();
字节[]数据=Encoding.ASCII.GetBytes(响应);
socket.BeginSend(数据,0,数据.Length,SocketFlags.None,新异步回调(SendCallback),null);
socket.BeginReceive(_buffer,0,_buffer.Length,SocketFlags.None,new AsyncCallback(ReceiveCallback),socket);
}
私有静态void SendCallback(IAsyncResult AR)
{
试一试{
套接字套接字=(套接字)AR.AsyncState;
socket.EndSend(AR);
}
抓住{
}
//它有很多NullReferenceException。它确实是这样工作的,但我不相信它。
}
公共静态无效发送消息(IAsyncResult AR)
{
套接字套接字=(套接字)AR.AsyncState;
字符串响应=string.Empty;
response=Console.ReadLine();
字节[]数据=Encoding.ASCII.GetBytes(响应);
socket.BeginSend(数据,0,数据.Length,SocketFlags.None,新异步回调(SendCallback),null);
}
}
}
当轮到每个客户机时,我能够向其发送命令。例如,我启动服务器。我先启动client1,然后启动client2。当我在控制台中键入某个内容时,首先轮到client1,以便他接收命令。当我再次键入某个内容时,client2会一次又一次地接收命令
我想知道是否有一种方法可以同时发送给所有客户。谢谢 为什么要使用Begin/End方法而不是异步方法,例如acceptsync、sendsync等?代码会变得简单得多我是网络新手,所以我遵循了一些指导,是他们把我带到这里的。我不完全了解所有内容。SendCallback中出现NullReferenceExceptions是因为您将
null
传递为AsyncState-将BeginSend调用的最后一个参数从null
更改为socket
,以解决此问题。foreach(客户端套接字中的var socket)socket.BeginSend。。。但是请注意,您使用的是多线程,并且没有保护列表,如果您在使用列表时某些客户端连接/断开连接,则会导致异常。@Gusman我已经尝试过了。使用此方法,您可以向所有客户端发送命令,但仍然必须连接所有客户端。这意味着如果你开了3个客户。您必须输入3次才能连接所有3个客户端。因为必须输入命令才能重新循环并接受另一个输入连接。因为它会一直停留在response=Console.WriteLine()上,直到您编写一些东西为止。