Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/sockets/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
TCP客户端C#等待新数据可用_C#_Sockets_Asynchronous_Tcpclient - Fatal编程技术网

TCP客户端C#等待新数据可用

TCP客户端C#等待新数据可用,c#,sockets,asynchronous,tcpclient,C#,Sockets,Asynchronous,Tcpclient,我尝试使用tcpclient从tcp服务器检索数据,发送请求并接收响应,除了一件事,它工作正常。 当我尝试多次使用networkstream.readasync,然后再使用networkstream.writeasync时,readasync函数读取上一个writeasync的上一个响应,而不是上一个。要解决这个问题,我必须在读取之前设置一个超时。有没有办法不设置超时,而是等待新数据可用 伪代码示例: connectasync(host,port); //reads a hello messag

我尝试使用tcpclient从tcp服务器检索数据,发送请求并接收响应,除了一件事,它工作正常。 当我尝试多次使用networkstream.readasync,然后再使用networkstream.writeasync时,readasync函数读取上一个writeasync的上一个响应,而不是上一个。要解决这个问题,我必须在读取之前设置一个超时。有没有办法不设置超时,而是等待新数据可用

伪代码示例:

connectasync(host,port);
//reads a hello message from the server
networkstram.readasync();
//sending a request to the server
networkstram.writeasync();
//reads again the hello message from the previous read 
//not the response from the previously sended writeasync 
networkstram.readasync()
伪代码解决方案:

connectasync(host,port);
//reads a hello message from the server
networkstram.readasync();
//sending a request to the server
networkstram.writeasync();
//wait for 1 second
wait(1000)
//reads correctly
networkstram.readasync()
如果您有更好的方法来等待新的可用数据,而不是使用固定超时,请告诉我。 多谢各位

更新 注意:我甚至尝试了同步版本的读写操作,但仍然相同。 我只是使用异步来不阻塞用户界面

    public async Task<string> sendQuery()
    {

        
        try
        {
            client.Connect(ConfigParameters.ip, ConfigParameters.port);
            if (client.Connected == true)
            {
                Console.WriteLine("Connected");
                var networkStream = client.GetStream();
                


                // Receive data from server
                //Receiving HELLO message from the server
                byte[] buffer = new byte[1024];
                await networkStream.ReadAsync(buffer, 0, buffer.Length);
                var serverResponse = Encoding.ASCII.GetString(buffer);
                Console.WriteLine("Server: " + serverResponse);
                Array.Clear(buffer,0,buffer.Lenght);
                Array.Resize(ref buffer, 1024);

                // Send data to server
                // send query to the server
                
                string data = QueryStore.queryStart+QueryStore.query1.getLRC() + QueryStore.queryEnd;
                buffer = System.Text.Encoding.ASCII.GetBytes(data);
                await networkStream.WriteAsync(buffer, 0, buffer.Length);
                 Array.Clear(buffer,0,buffer.Lenght);
                Array.Resize(ref buffer, 1024);
                
                // Receive data from server
                // receive still HELLO message
                buffer = new byte[1024];
                await networkStream.ReadAsync(buffer, 0, buffer.Length);
                serverResponse = Encoding.ASCII.GetString(buffer);
                Console.WriteLine("Server: " + serverResponse);
                
                networkStream.Close();
                client.Close();
                return "ok";
            }

        }
        catch(SocketException)
        {
           client.Close();
           return "error";
        }
        finally 
        {
            client.Close();
            return "";
        }
        
    }
公共异步任务sendQuery()
{
尝试
{
client.Connect(ConfigParameters.ip、ConfigParameters.port);
if(client.Connected==true)
{
控制台。写入线(“连接”);
var networkStream=client.GetStream();
//从服务器接收数据
//从服务器接收HELLO消息
字节[]缓冲区=新字节[1024];
等待networkStream.ReadAsync(buffer,0,buffer.Length);
var serverResponse=Encoding.ASCII.GetString(缓冲区);
Console.WriteLine(“服务器:”+serverResponse);
Array.Clear(buffer,0,buffer.Lenght);
调整数组大小(参考缓冲区,1024);
//向服务器发送数据
//将查询发送到服务器
字符串数据=QueryStore.queryStart+QueryStore.query1.getLRC()+QueryStore.queryEnd;
缓冲区=System.Text.Encoding.ASCII.GetBytes(数据);
等待networkStream.WriteAsync(buffer,0,buffer.Length);
Array.Clear(buffer,0,buffer.Lenght);
调整数组大小(参考缓冲区,1024);
//从服务器接收数据
//仍然收到问候信息
缓冲区=新字节[1024];
等待networkStream.ReadAsync(buffer,0,buffer.Length);
serverResponse=Encoding.ASCII.GetString(缓冲区);
Console.WriteLine(“服务器:”+serverResponse);
networkStream.Close();
client.Close();
返回“ok”;
}
}
捕获(SocketException)
{
client.Close();
返回“错误”;
}
最后
{
client.Close();
返回“”;
}
}

请显示实际代码。您的大纲建议使用同步工作流,那么为什么要使用异步?在async中,您通常在发出新调用之前等待完成-也就是说,您从完成回调发出新调用。看起来您忘记了等待异步操作,因此您可能在
WriteAsync
有机会启动之前调用了
ReadAsync
。您可能也看到了针对未等待的异步操作的代码分析器警告。发布实际代码我添加了部分实际代码,因为我无法共享完整的代码。数据以最大1500字节的块接收。在多个区块中接收较长的消息,在收到所有区块之前,您无法关闭连接。@jdweng@Panagiotis Kanavos是的,但在我的情况下,服务器每个请求发送一个响应,通常少于1500字节。