【问题标题】:How to distribute collection of values to dynamic list?如何将值集合分发到动态列表?
【发布时间】:2014-02-17 20:55:43
【问题描述】:

我正在开发 TCP 客户端-服务器控制台应用程序。我有 N 个客户端连接到服务器。在服务器端,我需要共享 M 条记录,并且每条记录应该只发送一次给客户端。每条记录只能由 1 个客户接收。 例如记录数 N=4 和客户数 M=10,结果应该是:

record1 – to client1
record2 – to client2
record3 – to client3
record4 – to client4
record5 – to client1
record6 – to client2
record7 – to client3
record9 – to client4 
record10 – to client5

问题是记录数 M 是固定的,但客户数 N 不固定(有时 N=3,有时 N=5,等等)

您能否建议我一个解决方案来组织这种类型的流量控制?

【问题讨论】:

    标签: c# .net sockets tcpclient tcpserver


    【解决方案1】:

    我会尝试实现这样的东西:

    • 您需要一个列表或集合来保存所有正在连接的客户端。您需要随机访问,即您必须将客户端添加到前面或后面,并且您必须能够随时删除任何元素。如果列表按分配的记录数(升序)排序,则可加分。

    • 当有新记录要处理时(或者当您使用它们遍历列表时):

      • 将记录发送给位于您列表前面的客户。
      • 从列表的前面删除客户端并将其添加到后面(除非列表已排序)。
    • 当新客户端连接时,它会被添加到列表的前面。

    • 如果客户端断开连接,则会将其从列表中删除,并读取记录以进行重新分发。

    如果我在考虑这个问题时没有犯任何错误,那么这应该确保任务数量最少的客户端之一将获得新记录,除非许多客户端在处理过程中中断。在这种情况下,排序列表将是一个优势。

    当然,还有优化的空间,如果您的客户数量在处理过程中(并且仅在您开始这样做之前)没有变化,那么这不是最佳策略。在这种情况下,您可以使用i = n % number_of_clients 简单地确定应该处理记录n 的客户端。

    【讨论】:

    • 虽然我喜欢你的解决方案,但不仅仅是将字典> 作为一种历史记录来完成这项工作,我的意思是它不会更简单吗?
    • 可能,但您仍然需要一遍又一遍地遍历整个列表以确定下一个收件人。
    【解决方案2】:

    您想遍历所有记录,同时遍历客户端,但使用模数确保您在 m > n 时循环回客户端,如下所示:

    var records = GetRecords(); // size m
    var clients = GetClients(); // size n
    
    if (clients.Length == 0)
    {
        // return or throw here, depending on your application
    }
    
    for (var i = 0; i < records.Length; i++)
    {
        var record = records[i];
        var client = clients[i%clients.Length];
    
        SendRecord(record, client);
    }
    

    使用此解决方案,mn 都可以是动态的。

    【讨论】:

    • 只是想补充一点,m &gt; n 没有限制。无论mn 有什么关系,只要至少有一个客户(这将是您在这里缺少的唯一检查),它都可以工作。
    • 是的,我并不是说它只有在m &gt; n 时才有效,只是使用 mod 处理这种情况。关于没有客户的好点,生病更新
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-04-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多