客户端在tcp / ip套接字程序中发送消息服务器未收到消息

时间:2014-12-19 13:18:24

标签: c# sockets client-server tcp-ip

TCP / IP套接字程序客户端发送文本服务器接收和存储数据库表。我正在修改下面的代码,但我有错误的文本需要时间。

这是客户端代码

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


    namespace ClientApplication
    {
        class Client
        {
            static void Main(string[] args)
            {
                try
                {
                    TcpClient tcpclnt = new TcpClient();
                    Console.WriteLine("Connecting.....");

                    //tcpclnt.Connect("162.144.85.232", 8080);
                    tcpclnt.Connect("162.144.85.232", 4489);


                    Console.WriteLine("Connected");
                    Console.Write("Enter the string to be Sent : ");

                    String str = Console.ReadLine();
                    Stream stm = tcpclnt.GetStream();

                    ASCIIEncoding asen = new ASCIIEncoding();
                    byte[] ba = asen.GetBytes(str);
                    System.Net.ServicePointManager.Expect100Continue = false;
                   Console.WriteLine("Sending.....");

                    stm.Write(ba, 0, ba.Length);

                    byte[] bb = new byte[100];
                    int k = stm.Read(bb, 0, 100);

                    for (int i = 0; i < k; i++)
                        Console.Write(Convert.ToChar(bb[i]));

                    Console.ReadLine();

                    tcpclnt.Close();
                    Console.ReadLine();
                }

                catch (Exception e)
                {
                    Console.WriteLine("Error..... " + e.StackTrace);
                    Console.ReadLine();
                }
            }
    }
    }

这是服务器端代码

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

namespace ServerApplication
{
    class Server
    {
        static void Main(string[] args)
        {
            try
            {
                IPAddress ipadd = IPAddress.Parse("192.168.1.7");
                TcpListener list = new TcpListener(ipadd, 8080);
                list.Start();
                Console.WriteLine("The server is running at port 8080...");
                Console.WriteLine("The Local End point Is:" + list.LocalEndpoint);
                System.Net.ServicePointManager.Expect100Continue = false;
                Socket s = list.AcceptSocket();
                Console.WriteLine("Connections Accepted from:" + s.RemoteEndPoint);
                byte[] b = new byte[100];
                int k = s.Receive(b);
                Console.WriteLine("Recived...");
                for (int i = 0; i < k; i++)
                Console.WriteLine(Convert.ToChar(b[i]));
                ASCIIEncoding asen = new ASCIIEncoding();
                s.Send(asen.GetBytes("The String Was Recived throw Server"));
                Console.WriteLine("\n Sent Acknowlegment");
                s.Close();
                list.Stop();


            }
            catch (Exception e)
            {
                Console.WriteLine("Error..... " + e.StackTrace);

            }

        }
}
}

我正在尝试执行此代码我发生了这样的错误 无法从传输连接读取数据:远程主机强制关闭现有连接。请解决我的问题。

1 个答案:

答案 0 :(得分:0)

您发布的代码存在许多问题,但直接导致您所看到的行为的问题是服务器关闭套接字而不等待客户端完成从连接中读取。

查找&#34; TCP正常关机&#34;欲获得更多信息。与此同时,以下是对您发布的代码的改进,并且不会遇到此问题:

服务器代码:

class Server
{
    static void Main(string[] args)
    {
        try
        {
            TcpListener list = new TcpListener(IPAddress.Any, 8080);
            list.Start();
            Console.WriteLine("The server is running at port 8080...");
            Console.WriteLine("The Local End point Is:" + list.LocalEndpoint);
            Socket s = list.AcceptSocket();
            Console.WriteLine("Connections Accepted from:" + s.RemoteEndPoint);
            byte[] b = new byte[100];
            int k;
            while ((k = s.Receive(b)) > 0)
            {
                Console.WriteLine("Recived...");
                Console.WriteLine(Encoding.ASCII.GetString(b, 0, k));
                s.Send(Encoding.ASCII.GetBytes("The String Was Recived throw Server"));
                Console.WriteLine("\n Sent Acknowlegment");
            }
            s.Shutdown(SocketShutdown.Both);
            s.Close();
            list.Stop();
        }
        catch (Exception e)
        {
            Console.WriteLine("Error..... " + e.StackTrace);
        }
    }
}

客户代码:

class Client
{
    static void Main(string[] args)
    {
        try
        {
            TcpClient tcpclnt = new TcpClient();
            Console.WriteLine("Connecting.....");

            tcpclnt.Connect("192.168.1.7", 8080);

            Console.WriteLine("Connected");
            Console.Write("Enter the string to be Sent : ");

            String str = Console.ReadLine();
            Stream stm = tcpclnt.GetStream();

            byte[] ba = Encoding.ASCII.GetBytes(str);
            Console.WriteLine("Sending.....");

            stm.Write(ba, 0, ba.Length);
            tcpclnt.Client.Shutdown(SocketShutdown.Send);

            byte[] bb = new byte[100];
            int k;

            while ((k = stm.Read(bb, 0, 100)) > 0)
            {
                Console.WriteLine(Encoding.ASCII.GetString(bb, 0, k));
            }

            Console.ReadLine();

            tcpclnt.Close();
            Console.ReadLine();
        }
        catch (Exception e)
        {
            Console.WriteLine("Error..... " + e.StackTrace);
            Console.ReadLine();
        }
    }
}

这里的关键是服务器和客户端继续从连接读取,直到远程端通过调用Socket.Shutdown()发出信号,表示没有更多数据需要读取。

我还删除了System.Net.ServicePointManager.Expect100Continue属性的使用,该属性对此代码没有影响。这只会影响使用ServicePoint类的程序,而且在这里没用。

我也不清楚为什么客户端使用NetworkStream而不是直接获取Client套接字并直接使用它。将I / O包装在例如I / O中时,NetworkStream对象非常有用。 StreamReaderStreamWriter,但您只需使用Stream.Read()Stream.Write(),其语义与Socket.Receive()和{{1}完全相同}, 分别。在任何情况下,请注意,当您使用Socket.Send()对象进行发送和接收时,您仍然需要直接访问基础NetworkStream实例以正确启动正常关闭(端点未启动可能只是关闭Socket,因为在完成发送和接收之前不必关闭。

我还清理了一些ASCII编码文本的处理。