0

私の知る限り、UDPは次のよ​​うに機能します。

送信したいデータがある場合、UDP クライアントに「このデータを送信してください」と言います。

UDP クライアントは、その理由を確認し、選択した IP とポートにデータを送信します。

それが成功した場合、または正しい順序で処理された場合は別の話ですが、データが送信されたので、他に何も要求しませんでした。

この観点からすると、データを送信して組み立てることはほとんど不可能です。たとえば、1 MB の画像があり、それを送信します。

だから私はそれを60kbのファイル(またはパッケージに合うもの)に分割して送信し、最初から最後まで1つずつ送信します。

したがって、理論的には、すべてが追加された場合、画像はまったく同じになるはずです。

しかし、パッケージが他のパッケージよりも早く到着するか遅く到着するかを示す法律がないため、その理論は破綻します。そのため、ある種の待機タイマーを作成し、順序どおりに到着することを期待する場合にのみ可能になる場合があります。それらは送信されます。

とにかく、私が理解したいのは、なぜこれが機能するのかということです:

   void Sending(object sender, NAudio.Wave.WaveInEventArgs e)
    {
        if (connect == true && MuteMic.Checked == false)
        {
            udpSend.Send(e.Buffer, e.BytesRecorded, otherPartyIP.Address.ToString(), 1500);
        }
    }

受信:

        while (connect == true)
        {
            byte[] byteData = udpReceive.Receive(ref remoteEP);
            waveProvider.AddSamples(byteData, 0, byteData.Length);
        }

つまり、これは基本的に、udp を介してオーディオ バッファを送信します。

受信パーは、受信した udp データをバッファーに追加して再生します。

これで動作します。

そして、私は疑問に思います..なぜですか?

これはどのように機能するのでしょうか。データが正しい順序で送信されて追加され、一定のオーディオ ストリームとして表示されるのはなぜですか?

画像でこれを行うと、おそらくすべてのデータが取得されます。

しかし、それらはおそらくランダムな順序であり、パッケージなどにマークを付けることによってのみ解決できます。そして、それには単に理由がなく、TCP が引き継ぎます。

ですから、誰かがこれを説明できれば、私にはわかりません。

これは、画像を送信するときのコード例です。うまく機能します。しかし、バイト配列全体が送信されていない場合、つまり画像の一部が破損している場合にうまく機能するようです (理由はわかりませんが、おそらくバイト配列のサイズに関係している可能性があります)。

送信:

                           using (var udpcap = new UdpClient(0))
                           {
                               udpcap.Client.SendBufferSize *= 16;
                               bsize = ms.Length;
                               var buff = new byte[7000];
                               int c = 0;
                               int size = 7000;
                               for (int i = 0; i < ms.Length; i += size)
                               {
                                   c = Math.Min(size, (int)ms.Length - i);
                                   Array.Copy(ms.GetBuffer(), i, buff, 0, c);
                                   udpcap.Send(buff, c, adress.Address.ToString(), 1700);
                               }

受け取る:

                    using (var udpcap = new UdpClient(1700))
                    {
                        udpcap.Client.SendBufferSize *= 16;
                        var databyte = new byte[1619200];

                        int i = 0;
                        for (int q = 0; q < 11; ++q)
                        {
                            byte[] data = udpcap.Receive(ref adress);
                            Array.Copy(data, 0, databyte, i, data.Length);
                            i += data.Length;
                        }
                        var newImage = Image.FromStream(new MemoryStream(databyte));
                         gmp.DrawImage(newImage,0,0);
                        }
4

2 に答える 2