Communication client‑serveur

Principes fondamentaux

Une fois la connexion TCP établie, les données transitent via le NetworkStream ;
Le réseau ne peut transmettre que des tableaux d’octets byte[]. Le texte doit d’abord être encodé en octets, puis décodé pour retrouver la chaîne de caractères à la réception.

La transmission ne se limite pas au texte : fichiers et images peuvent aussi être convertis en tableaux d’octets. Cette section implémente d’abord un chat textuel.

Description des API clés

  1. Côté serveur
    listener.AcceptTcpClient()
  • Méthode bloquante (attente interrompue) : le thread se met en pause jusqu’à ce qu’un client initie une connexion ;
  • Retourne un objet TcpClient qui représente cette connexion client ;
  • Récupérez le flux réseau avec tcpClient.GetStream().
  1. Lecture‑écriture du flux réseau
  • stream.Write(tableau d'octets, décalage, longueur) : Envoyer des données
  • stream.Read(tableau tampon, décalage, longueur max de lecture) : Recevoir des données, renvoie le nombre réel d’octets lus
  1. Attention à l’encodage
    Les exemples du cours utilisent Encoding.Unicode (UTF‑16). L’encodage doit être identique côté émetteur et côté récepteur, sinon des caractères indésirables apparaîtront.

Serveur WinForms

Contrôles :
textBoxIP, textBoxPort, textBoxInfo (zone d’affichage des messages)

using System;
using System.Net;
using System.Net.Sockets;
using System.Text;
using System.Windows.Forms;

namespace TcpServer
{
    public partial class Form1 : Form
    {
        IPAddress ip;
        TcpListener listener;
        TcpClient tcpClient;

        public Form1()
        {
            InitializeComponent();
        }

        private void buttonStart_Click(object sender, EventArgs e)
        {
            ip = IPAddress.Parse(textBoxIP.Text);
            listener = new TcpListener(ip, Convert.ToInt32(textBoxPort.Text));
            listener.Start();

            textBoxInfo.Text = $"服务器启动-{DateTime.Now.ToShortTimeString()}\r\n" + textBoxInfo.Text;

            // 阻塞!主线程卡住
            tcpClient = listener.AcceptTcpClient();
            textBoxInfo.Text = $"连接成功-{DateTime.Now.ToShortTimeString()}\r\n" + textBoxInfo.Text;

            NetworkStream stream = tcpClient.GetStream();
            byte[] byteArray = new byte[1024];

            // 阻塞等待客户端发送消息
            int length = stream.Read(byteArray, 0, 1024);
            string receiveMessage = Encoding.Unicode.GetString(byteArray, 0, length);

            textBoxInfo.Text = $"接收到:{receiveMessage}-{DateTime.Now.ToShortTimeString()}\r\n" + textBoxInfo.Text;
        }
    }
}Langage du code : PHP (php)

Client WinForms

Contrôles :
textBoxIP, textBoxPort, textBoxInfo, textBoxInput (champ de saisie)
buttonStart【Connexion】, buttonSend【Envoyer】

using System;
using System.Net.Sockets;
using System.Text;
using System.Windows.Forms;

namespace TcpClientChat
{
    public partial class Form1 : Form
    {
        TcpClient tcpClient;

        public Form1()
        {
            InitializeComponent();
        }

        private void buttonStart_Click(object sender, EventArgs e)
        {
            tcpClient = new TcpClient();
            try
            {
                tcpClient.Connect(textBoxIP.Text, Convert.ToInt32(textBoxPort.Text));
                textBoxInfo.AppendText("连接成功!\r\n");
            }
            catch (Exception ex)
            {
                MessageBox.Show("连接失败-" + ex.Message);
            }
        }

        private void buttonSend_Click(object sender, EventArgs e)
        {
            string message = textBoxInput.Text;
            textBoxInfo.Text = $"发送“{message}”-{DateTime.Now.ToShortTimeString()}\r\n" + textBoxInfo.Text;

            NetworkStream stream = tcpClient.GetStream();
            byte[] byteArray = Encoding.Unicode.GetBytes(message);
            stream.Write(byteArray, 0, byteArray.Length);
        }
    }
}Langage du code : PHP (php)

Ce code implémente l’envoi de messages entre client et serveur.

Communication client‑serveur

Previous:

Laisser un commentaire

Votre adresse e-mail ne sera pas publiée. Les champs obligatoires sont indiqués avec *