C#中異步Stocket中EndReceive報遠程主機強迫關閉了一個現有的連接問題


有兩個問題如下
第一個問題,我足足等了2分鍾,ReceiveCallback里的斷點才進去,怎么會等這么長時間
第二個問題,ServerSocket 中的EndReceive報“遠程主機強迫關閉了一個現有的連接”這個錯誤
調試截圖如下






ClientSocket 中的Program.cs代碼如下

using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Net.Sockets;
using System.Text;
using System.Threading.Tasks;

namespace SendTest
{
    public class StateObject
    {
        public Socket workSocket = null;
        public const int BUFFER_SIZE = 1024;
        public byte[] buffer = new byte[BUFFER_SIZE];
        public StringBuilder sb = new StringBuilder();
    }

    class Program
    {
        static Socket clientSocket;
        static void Main(string[] args)
        {
            IPAddress ip = IPAddress.Parse("127.0.0.1");
            clientSocket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
            try
            {
                clientSocket.Connect(new IPEndPoint(ip, 8081)); //配置服務器IP與端口
                Console.WriteLine("連接服務器成功");
            }
            catch
            {
                Console.WriteLine("連接服務器失敗,請按回車鍵退出!");
                return;
            }
            Send();
        }

        /// <summary>
        /// 發送消息
        /// </summary>
        private static void  Send()
        {
            if (clientSocket != null)
            {
                try
                {
                    byte[] byteData = Encoding.UTF8.GetBytes("我是客戶端,尋求幫助");
                    clientSocket.BeginSend(byteData, 0, byteData.Length, SocketFlags.None, new AsyncCallback(SendCallback), clientSocket);
                    Console.WriteLine("BeginSend 執行完畢");
                    Console.ReadLine();
                }
                catch (Exception ex)
                { 
                    
                }
            }
        }

        /// <summary>
        /// 發送消息回掉函數
        /// </summary>
        /// <param name="ar"></param>
        private static void SendCallback(IAsyncResult ar)
        {
            try
            {
                Socket client = (Socket)ar.AsyncState;
                if (client != null)
                {
                    int bytesSent = client.EndSend(ar);
                }
            }
            catch (Exception ex)
            {

            }
        }
    }
}

ServerSocket 中的Program.cs代碼如下

using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Net.Sockets;
using System.Text;
using System.Threading;
using System.Threading.Tasks;

namespace ReceiveTest
{
    class Program
    {
        static Socket clientSocket;
        static void Main(string[] args)
        {
            IPAddress ip = IPAddress.Parse("127.0.0.1");
            clientSocket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
            try
            {
                clientSocket.Connect(new IPEndPoint(ip, 8081)); //配置服務器IP與端口
                Console.WriteLine("連接服務器成功");
            }
            catch
            {
                Console.WriteLine("連接服務器失敗,請按回車鍵退出!");
                return;
            }

            Thread myThread = new Thread(Receive);
            myThread.Start();
            Console.ReadLine();
        }

        /// <summary>
        /// 接收消息
        /// </summary>
        private static void Receive()
        {
            if (clientSocket != null)
            {
                try 
                {
                    StateObject state = new StateObject();
                    state.workSocket = clientSocket;
                    clientSocket.BeginReceive(state.buffer, 0, StateObject.BUFFER_SIZE, 0, new AsyncCallback(ReceiveCallback), state);
                    Console.WriteLine("BeginReceive 執行完畢");
                }
                catch (Exception ex)
                {

                }
            }
        }

        /// <summary>
        /// 接收消息回掉函數
        /// </summary>
        /// <param name="ar"></param>
        private static void ReceiveCallback(IAsyncResult ar)
        {
            try
            {
                StateObject so = (StateObject)ar.AsyncState;
                Socket s = so.workSocket;
                int read = s.EndReceive(ar);
                if (read > 0)
                {
                    string msg = Encoding.ASCII.GetString(so.buffer, 0, read);
                }
            }
            catch (Exception ex)
            {

            }
        }

        public class StateObject
        {
            public Socket workSocket = null;
            public const int BUFFER_SIZE = 1024;
            public byte[] buffer = new byte[BUFFER_SIZE];
            public StringBuilder sb = new StringBuilder();
        }
    }
}

1 个解决方案

#1


此問題已經解決了,解決思路
1.同步發,同步接的Demo我也做了一份,發送沒有問題,接收也沒有問題
2.異步發,異步接的這個Demo,在異步接里面報錯EndReceive報“遠程主機強迫關閉了一個現有的連接問題”就有問題,所以我就想,那么我就用異步發,同步接總行了吧,果然同步接就好着呢,可以接到異步發來的消息
3.我就想同樣的異步發代碼,但是同步接可以接到消息,異步接就報錯不行,我就對比同步接和異步接的代碼,發現問題如下,果然問題出現在這里了,修復后,異步發異步接就好了
如下圖所示
同步接代碼




而異步接里面直接用的是clientSocket,沒有用clientSocket.Accept()去得到一個新的Scoket


改造異步接代碼如下圖所示就好了


執行結果如下
关注微信公众号

注意!

本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系我们删除。



 
粤ICP备14056181号  © 2014-2020 ITdaan.com