【问题标题】:Why disposing NetworkStream disconnects client为什么处理 NetworkStream 会断开客户端
【发布时间】:2017-01-25 16:06:36
【问题描述】:

当以下基本代码发送或接收数据时,客户端断开连接。

我的理解是 using 块会释放它创建的对象,即 NetworkStream 对象,但为什么 TcpClient Socket 会断开连接?

控制台输出是... 真的 假的

class Program
    {
        static void Main(string[] args)
        {
            Console.Title = "Client";

            Process p = Process.Start(@"C:\Users\Teddy\Documents\visual studio 2015\code\TesyingNetworkStream\Server\bin\Debug\server.exe");
            Thread.Sleep(1000);

            IPEndPoint EP = new IPEndPoint(
                    IPAddress.Parse("192.168.1.10"), 4000
                    );

            TcpClient cli = new TcpClient();
            cli.Connect(EP);

            UseClient(cli);

            Console.ReadLine();
            p.Kill();
            p.Close();
        }

        private static void UseClient(TcpClient cli)
        {
            using (NetworkStream ns = cli.GetStream())
            {
                Console.WriteLine(cli.Connected);//True
            }
            Console.WriteLine(cli.Connected);//False
        }
    }

如果重要的话,这里是服务器代码。

class Program2
    {
        static void Main(string[] args)
        {
            Console.Title = "Server";

            TcpListener lis = new TcpListener(
                new IPEndPoint(
                    IPAddress.Any, 4000
                    ));

            lis.Start();

            lis.AcceptTcpClient();

            while (true)
            {
                Thread.Sleep(10);
            }
        }
    }

【问题讨论】:

    标签: c# using networkstream disconnect


    【解决方案1】:

    这是GetStream()函数实现(来自.NET framework source):

    public NetworkStream GetStream() {
        if (m_CleanedUp){
            throw new ObjectDisposedException(this.GetType().FullName);
        }
        if (!Client.Connected) {
            throw new InvalidOperationException(SR.GetString(SR.net_notconnected));
        }
        if (m_DataStream == null) {
            m_DataStream = new NetworkStream(Client, true);
        }
        return m_DataStream;
    }
    

    注意true 在对NetworkStream 构造函数的调用中。这是ownsSocket 参数。来自MSDN

    如果ownsSocket参数的值为true,则NetworkStream取 底层 Socket 的所有权,并调用 Close 方法 关闭底层 Socket。

    NetworkStreamDispose 实现 Close 的流,然后关闭套接字。

    【讨论】:

      【解决方案2】:

      这是因为cli.GetStream(); 不会在您每次调用它时都创建一个新流,所以连接只有一个流,并且每次调用cli.GetStream(); 都会返回相同的流对象。当您处理向 TcpClient 发出信号的共享流时,您就完成了,它标志着 TcpClient 已断开连接。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2019-03-05
        • 1970-01-01
        • 1970-01-01
        • 2021-06-24
        • 1970-01-01
        • 2016-03-10
        相关资源
        最近更新 更多