【问题标题】:TcpClient creation seem to be very slow. Can I cache those?TcpClient 创建似乎很慢。我可以缓存那些吗?
【发布时间】:2011-06-18 22:40:41
【问题描述】:

我有一个程序,客户端通过 TCP-IP 相互通信。当一个客户做某事时,他会一一通知其他客户这件事发生了。这是我用来发送数据的代码:

public static string SendDirect(string data, string hostName, int portNumber)
        {
            string responseData;

            try
            {
                var client = new TcpClient(hostName, portNumber);

                Stream s = client.GetStream();
                var sw = new StreamWriter(s) { AutoFlush = true };

                sw.WriteLine(data);

                s.Close();
                client.Close();

                s.Dispose();
                sw.Dispose();

                responseData = "OK";
            }
            catch (SocketException ex)
            {
                responseData = ex.Message;
            }

            return responseData;
        }

线

var client = new TcpClient(hostName, 端口号);

对于某些机器来说有时会很慢。例如,在我的家庭网络中,大约需要 2 或 3 秒。你能看出 15 个客户有多糟糕吗?

我想知道不每次都关闭客户端并始终保持其中 30-40 个打开的成本是多少,或者是否可能?我假设需要对一些机制进行检查以确保它们还活着并确保它们都正确关闭,但我想知道这个想法本身是否正确..

谢谢!

【问题讨论】:

    标签: c# sockets tcpclient


    【解决方案1】:

    没有什么可以阻止或限制您一次创建多个客户端/连接。实际上,启动和关闭大量连接可能会触发不同的安全问题(试图抵御可能的 DDOS 攻击或其他)。您不妨加快解析主机名并缓存这些主机名的过程。实际上,不一定是创建对象会减慢您的速度。

    操作系统可能会限制每秒挂起的连接数(想想在 Windows 下每秒 10 个),但除此之外应该没有任何问题。在我看来,你不应该打开/关闭单个命令的连接。您应该考虑同时保持打开状态,TcpClientStreamWriter。只需确保在完成写入数据包后刷新即可。为了提高性能,您应该考虑手动刷新,特别是如果有多个命令/数据包要发送到每个客户端,因为每个数据包将占用最小的 TCP 窗口大小(通常约为 1492-1500 字节)。

    【讨论】:

    • 解析主机名是什么意思?你的意思是获取IP并使用它们?所以,你说我想做的是正道?打开并保持 40 个左右的连接不会受到伤害吗?因为是的,目前正如你所见,我在每个命令上打开/关闭其中的 40 个。
    • 你有任何关于保持/刷新流的示例代码吗?我所有的数据包都非常小,现在不到 1k。
    • 如果您的基础架构、设计等支持,让它们保持开放是非常好的。特别是与永久重新连接相比。解析 DNS 名称是获取与特定主机名匹配的 IP 的过程(无论如何,这应该由操作系统缓存,但仍可能导致速度变慢)。要保留流,请不要关闭它并且不要处置对象。要刷新,大多数(如果不是全部)流都支持 Flush() 方法。
    猜你喜欢
    • 1970-01-01
    • 2021-12-11
    • 1970-01-01
    • 1970-01-01
    • 2015-02-16
    • 1970-01-01
    • 2010-10-25
    • 1970-01-01
    • 2014-09-06
    相关资源
    最近更新 更多