2

現在、C++ でクライアント サーバー コンソール アプリケーションを作成しています。winsock2.hライブラリと UDP プロトコルを使用して、とsendtoを使用recvfromしてクライアントからサーバーにメッセージを文字列として送信し、サーバーはそのメッセージを別のクライアントに送信します。現在、client1 が client2 にメッセージを送信すると、client2 は受信しません。 client1 にメッセージを送信しようとするまで、メッセージを送信しません。client1 が client2 にメッセージを送信すると、client2 は最初にメッセージを送信しなくてもほぼ即座にメッセージを受信できるように、プログラムをインスタント メッセンジャーのように動作させたいと考えています。

また、client1 が client2 にメッセージを送信する場合、client2 が最初のメッセージに応答しない限り、client1 は別のメッセージを送信できません。

さらに詳しい情報が必要な場合やコードを確認したい場合は、質問してください。

送信コード:

while( getline( cin, line ) )
{
    // send a string to the server.
    sendto( hSocket, line.c_str(), line.size(), 0, 
        reinterpret_cast<sockaddr*>( &serverAddress ),
        sizeof( serverAddress ) );

    // recieve the response.
    int n = recvfrom( hSocket, recvLine, MAXLINE, 0, NULL, NULL );
    if( n == -1 )
    {
        cout << "no reply" << endl;
    }
    else
    {
        recvLine[n] = 0;
        string const terminateMsg = "server exit";
        string msg = recvLine;
        if( msg == terminateMsg )
        {
            cout << "Server terminated" << endl;
            break;
        }
        cout << n << ": " << recvLine << endl;
    }
}
4

1 に答える 1

1

現在、client1 が client2 にメッセージを送信すると、client2 は client1 にメッセージを送信しようとするまでメッセージを受信しません。

あなたはそれをそのようにコーディングしました。

また、client1 が client2 にメッセージを送信する場合、client2 が最初のメッセージに応答しない限り、client1 は別のメッセージを送信できません。

繰り返しますが、そのようにコーディングしました。あなたのコードは、 everysendto()の後にrecvfrom(). しかし、あなたの質問は、それがあなたが望んでいるものではないことを示しています。以下のコードにコメントを追加しました

while( getline( cin, line ) )
{
    // send a string to the server. <-- will never get here a 2nd time through the loop without recvfrom() returning
    sendto( hSocket, line.c_str(), line.size(), 0, 
        reinterpret_cast<sockaddr*>( &serverAddress ),
        sizeof( serverAddress ) );

    // recieve the response. <--- will never get here without getline() returning
    int n = recvfrom( hSocket, recvLine, MAXLINE, 0, NULL, NULL );
    if( n == -1 )
    {
        cout << "no reply" << endl;
    }
    else
    {
        recvLine[n] = 0;
        string const terminateMsg = "server exit";
        string msg = recvLine;
        if( msg == terminateMsg )
        {
            cout << "Server terminated" << endl;
            break;
        }
        cout << n << ": " << recvLine << endl;
    }
}

client1 が client2 にメッセージを送信すると、client2 は最初にメッセージを送信しなくてもほぼ即座にメッセージを受信できるように、プログラムをインスタント メッセンジャーのように動作させたいと考えています。

Boost.Asio と非同期ソケットを使用します。async chat_clientの は、TCP ソケットを使用してこれを完全に実行します。UDP の例を変更するのはかなり簡単です。非同期UDP エコー サーバーの例も役立つ場合があります。boost::asio::ip::udp::socket::async_recv_from()と を使いたいと思うでしょうboost::asio::ip::udp::socket::async_send_to()。他の BSD ソケット インターフェイスには、ドキュメントで説明されている同等のマッピングがあります。

于 2012-04-10T01:35:52.353 に答える