gpt4 book ai didi

c# - 如何使用带字典的定时器

转载 作者:太空宇宙 更新时间:2023-11-03 16:05:42 26 4
gpt4 key购买 nike

我是字典的新手,发现它们非常有用。我有一个接受多个客户端连接的 c# 服务器控制台。每次客户端连接时,都会将其添加到服务器字典中。我目前正在使用 .net 3.5(并且不会很快升级)并且我使用的字典既不是线程安全的也不是静态的。客户通常会自行退出,但我需要实现故障保护。如果客户端没有自行退出,我想在 5 分钟后使用计时器关闭连接。连接关闭后,该项目需要从字典中删除。我将如何让我的字典和计时器工作来实现这一目标?我被困住了,已经用尽了我的资源。我正在使用“_clientSockets.Remove(current)”来关闭连接

下面是我目前拥有的字典和计时器的代码片段:

private static Timer aTimer = new System.Timers.Timer(10000);
private static Object thisLock = new Object();
public static void Main()
{
Console.ReadKey();
aTimer.Elapsed += new ElapsedEventHandler(OnTimedEvent);
aTimer.Interval = 1000 * 60 * 5;
aTimer.Enabled = true;

Console.WriteLine("Press the Enter key to exit the program.");
Console.WriteLine(DateTime.Now);
Console.ReadLine();

Dictionary<int, DateTime> ServDict = new Dictionary<int, DateTime>();

ServDict.Add(9090, DateTime.Now.AddMinutes(5));
ServDict.Add(9091, DateTime.Now.AddMinutes(5));
ServDict.Add(9092, DateTime.Now.AddMinutes(5));
ServDict.Add(9093, DateTime.Now.AddMinutes(5));
ServDict.Add(9094, DateTime.Now.AddMinutes(5));
Console.WriteLine("Time List");

foreach (KeyValuePair<int, DateTime> time in ServDict)
{
Console.WriteLine("Port = {0}, Time in 5 = {1}",
time.Key, time.Value);
}
Console.ReadKey();
}

private static void OnTimedEvent(object source, ElapsedEventArgs e)
{
Console.WriteLine("The trigger worked, The Elapsed event was raised at {0}", e.SignalTime);
Console.WriteLine(DateTime.Now);
}

最佳答案

使用您的方法,无法将字典中的特定键与特定超时相关联。您必须每隔 n 秒“轮询”一次您的字典(其中 n 是您可以错过 5 分钟标记的时间)并检查您收到数据后已经过了多长时间。

更好的解决方案可能是将您的客户包装在一个类中(并且只包含一个列表,您可能甚至不需要字典)?在这种情况下,该类的每个实例都可以持有一个“超时”计时器,该计时器在 5 分钟后到期并调用关闭连接功能。同一个事件处理程序还可以引发一个事件,持有所有客户端的类都会注册该事件,以便它可以将其从事件列表中删除。

无论何时接收到数据,客户端类都会重置计时器。这可以通过使用 System.Threading.Timer 并对其调用 Change(dueTime, period) 来轻松实现。

像下面这样的东西应该可以工作:

public class Client
{
public event Action<Client> Timeout;
System.Threading.Timer timeoutTimer;

public Client()
{
timeoutTimer = new Timer(timeoutHandler, TimeSpan.FromMinutes(5), TimeSpan.FromMinutes(5));
}

public void onDataRecieved()
{
timeoutTimer.Change(TimeSpan.FromMinutes(5), TimeSpan.FromMinutes(5));
}

public void timeoutHandler(object data)
{
CloseConnection();
if (Timeout != null)
Timeout(this);
}
}

class Program
{
List<Client> connectedClients = new List<Client>

void OnConnected(object clientData)
{
Client newClient = new Client();
newClient.Timeout += ClientTimedOut;
connectedClients.Add(newClient);
}

void ClientTimedOut(Client sender)
{
connectedClients.Remove(sender);
}
}

关于c# - 如何使用带字典的定时器,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19527785/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com