C#Socket非同期チャットルーム
Socket非同期通信、スレッドプールはシステムによってスレッドを維持する
注:非同期呼び出しでは、同期呼び出しの方法は使用できません.スレッドがブロックされます.
Server:
Client:
注:非同期呼び出しでは、同期呼び出しの方法は使用できません.スレッドがブロックされます.
Server:
using System;
using System.Collections.Generic;
using System.Text;
using System.Net;
using System.Net.Sockets;
namespace SocketDemo
{
class ClientInfo
{
public Socket Socket { get; set; }
public bool IsOpen { get; set; }
public string Address { get; set; }
}
// Client
class ClientManager
{
static List clientList = new List();
public static void Add(ClientInfo info)
{
if (!IsExist(info.Address))
{
clientList.Add(info);
}
}
public static bool IsExist(string address)
{
return clientList.Exists(item => string.Compare(address, item.Address, true) == 0);
}
public static void Close(string address)
{
clientList.ForEach(item =>
{
if (string.Compare(address, item.Address, true) == 0)
{
item.IsOpen = false;
}
});
}
// ClientList
public static void SendMsgToClientList(string msg, string address = null)
{
byte[] bt = Encoding.UTF8.GetBytes(msg);
clientList.ForEach(item =>
{
if (item.IsOpen && (address == null || item.Address != address))
{
item.Socket.BeginSend(bt, 0, bt.Length, SocketFlags.None, new AsyncCallback(SendTarget), item.Socket);
}
});
}
private static void SendTarget(IAsyncResult res)
{
//Socket client = (Socket)res.AsyncState;
//int size = client.EndSend(res);
}
}
//
class ReceiveHelper
{
public byte[] Bytes { get; set; }
public void ReceiveTarget(IAsyncResult res)
{
Socket client = (Socket)res.AsyncState;
int size = client.EndReceive(res);
if (size > 0)
{
string stringdata = Encoding.UTF8.GetString(Bytes, 0, size);
string address = client.RemoteEndPoint.ToString(); // Client IP
if (stringdata.IndexOf("exit") > -1)
{
ClientManager.SendMsgToClientList(address + " ", address);
ClientManager.Close(address);
Console.WriteLine(address + " ");
Console.WriteLine(address + " " + DateTimeOffset.Now.ToString("G"));
return;
}
else
{
Console.WriteLine(stringdata);
Console.WriteLine(address + " " + DateTimeOffset.Now.ToString("G"));
ClientManager.SendMsgToClientList(stringdata, address);
}
}
//
client.BeginReceive(Bytes, 0, Bytes.Length, SocketFlags.None, new AsyncCallback(ReceiveTarget), client);
}
}
//
class AcceptHelper
{
public byte[] Bytes { get; set; }
public void AcceptTarget(IAsyncResult res)
{
Socket server = (Socket)res.AsyncState;
Socket client = server.EndAccept(res);
string address = client.RemoteEndPoint.ToString();
ClientManager.Add(new ClientInfo() { Socket = client, Address = address, IsOpen = true });
ReceiveHelper rs = new ReceiveHelper() { Bytes = this.Bytes };
IAsyncResult recres = client.BeginReceive(rs.Bytes, 0, rs.Bytes.Length, SocketFlags.None, new AsyncCallback(rs.ReceiveTarget), client);
//
server.BeginAccept(new AsyncCallback(AcceptTarget), server);
}
}
class Program
{
static void Main(string[] args)
{
Socket server = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
server.Bind(new IPEndPoint(IPAddress.Parse("127.0.0.1"), 200)); // IP+
server.Listen(10); //
Console.WriteLine(" ...");
AcceptHelper ca = new AcceptHelper() { Bytes = new byte[2048] };
IAsyncResult res = server.BeginAccept(new AsyncCallback(ca.AcceptTarget), server);
string str = string.Empty;
while (str != "exit")
{
str = Console.ReadLine();
Console.WriteLine("ME: " + DateTimeOffset.Now.ToString("G"));
ClientManager.SendMsgToClientList(str);
}
server.Close();
}
}
}
Client:
using System;
using System.Text;
using System.Net;
using System.Net.Sockets;
namespace ConsoleApplication
{
class Program
{
static byte[] inbytes = new byte[2048];
static byte[] oubytes = new byte[2048];
static void Main(string[] args)
{
// Server
Socket client = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
client.BeginConnect("127.0.0.1", 200, new AsyncCallback(ConnectTarget), client);
//
string str = string.Empty;
while (str != "exit")
{
Console.WriteLine("ME: " + DateTimeOffset.Now.ToString("G"));
str = Console.ReadLine();
inbytes = Encoding.UTF8.GetBytes(str);
client.BeginSend(inbytes, 0, inbytes.Length, SocketFlags.None, new AsyncCallback(SendTarget), client);
}
client.Close();
}
static void ConnectTarget(IAsyncResult res)
{
Socket client = (Socket)res.AsyncState;
client.EndConnect(res);
client.BeginReceive(oubytes, 0, 2048, SocketFlags.None, ReceiveTarget, client);
}
static void SendTarget(IAsyncResult res)
{
//Socket client = (Socket)res.AsyncState;
//int size = client.EndSend(res);
}
static void ReceiveTarget(IAsyncResult res)
{
Socket client = (Socket)res.AsyncState;
int size = client.EndReceive(res);
if (size > 0)
{
Console.WriteLine(Encoding.UTF8.GetString(oubytes, 0, size));
Console.WriteLine(client.RemoteEndPoint + " " + DateTimeOffset.Now.ToString("G"));
}
//
client.BeginReceive(oubytes, 0, 2048, SocketFlags.None, new AsyncCallback(ReceiveTarget), client);
}
}
}