C# 为什么 "Flush"不强制字节通过网络流传输?

标签 c# sockets tcp tcpclient networkstream

我有一个项目,我试图将序列化对象发送到服务器,然后等待返回“OK”或“ERROR”消息。

我似乎遇到了与以下海报类似的问题:TcpClient send/close problem

问题是我似乎能够发送原始对象的唯一方法是关闭连接,但是(当然)我迫不及待地想看看服务器是否成功处理了对象。

private void button4_Click(object sender, EventArgs e)
{
    RequestPacket req = new RequestPacket();

    /// ... Fill out request packet ...

    /// Connect to the SERVER to send the message...
    TcpClient Client = new TcpClient("localhost", 10287);
    using (NetworkStream ns = Client.GetStream())
    {
        XmlSerializer xml = new XmlSerializer(typeof(RequestPacket));
        xml.Serialize(ns, req);

        /// NOTE: This doesn't seem to do anything.... 
        ///       The server doesn't get the object I just serialized.
        ///       However, if I use ns.Close() it does... 
        ///          but then I can't get the response.
        ns.Flush();

        // Get the response. It should be "OK".
        ResponsePacket resp;

        XmlSerializer xml2 = new XmlSerializer(typeof(ResponsePacket));
        resp = (ResponsePacket)xml2.Deserialize(ns);


        /// ... EVALUATE RESPONSE ...
    }

    Client.Close()
}

更新:作为对一位评论者的回应,我认为客户没有错。它只是在等待对象,直到我关闭套接字之前对象永远不会出现......但是,如果我错了,我会很乐意公开吃乌鸦。 =) 这是客户端:

    static void Main(string[] args)
    {
        // Read the port from the command line, use 10287 for default
        CMD cmd = new CMD(args);
        int port = 10287;

        if (cmd.ContainsKey("p")) port = Convert.ToInt32(cmd["p"]);

        TcpListener l = new TcpListener(port);
        l.Start();

        while (true)
        {
            // Wait for a socket connection.
            TcpClient c = l.AcceptTcpClient();
            
            Thread T = new Thread(ProcessSocket);

            T.Start(c);
        }
    }


    static void ProcessSocket(object c)
    {
        TcpClient C = (TcpClient)c;

        try
        {
            RequestPacket rp;
            //// Handle the request here.
            using (NetworkStream ns = C.GetStream())
            {
                XmlSerializer xml = new XmlSerializer(typeof(RequestPacket));
                rp = (RequestPacket)xml.Deserialize(ns);
            }

            ProcessPacket(rp);
        }
        catch
        {
            // not much to do except ignore it and go on.
        }
    }

是的......就这么简单。

最佳答案

呃哦,你可以怪Nagle's algorithm .虽然它与 C# 无关,但它是 TCP/IP 堆栈的默认行为。启用 NoDelay使用 SetSocketOption 的套接字选项方法。但要小心,禁用 Nagle 算法会降低吞吐量。

我也不确定您在套接字之上使用的那个流,因为我根本不是 C# 开发人员,但尝试删除它的实例以便它确实写入:-)

关于C# 为什么 "Flush"不强制字节通过网络流传输?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15400318/

相关文章:

c# - 重新生成设置.settings

java - SSL Server套接字需要身份验证选项

sockets - 将多播目标地址设置为FFFF.FFFF.FFFF可以使其成为广播吗?

python - 如何在 python 中限制 ZMQ (ZeroMQ - PyZMQ) 队列缓冲区大小?

php - 如何使用 PHP 监听 TCP 端口?

c# - 我应该如何在 .NET 中实现分布式远程方法调用系统?

wcf - 带有 SSL 证书的 Net.TCP 是否可以在互联网上使用

c# - 升级到 .NET 4.7 后为 "Predefined type System.ValueTuple is not defined or imported"

c# - 弹出窗口为 View 中的每个窗口显示相同的结果

c# - 我如何编写一个 C# 循环来计算 future 5 年每年增加 2% 的学费