2012-04-10 13 views
2

現在、私はC++でクライアントサーバーコンソールアプリケーションを作成しています。 winsock2.hライブラリーとUDPプロトコルを使用すると、sendtorecvfromを使用して、メッセージをクライアントからサーバーに送信し、別のクライアントにメッセージを送信します。クライアント1がクライアント2、クライアント2 client1にメッセージを送信しようとするまで、メッセージは受信されません。私は、プログラムがインスタントメッセンジャーのように動作するようにしています。そのため、client1がclient2にメッセージを送信すると、最初にメッセージを送信することなく、すぐにclient2がメッセージを受信します。同期チャットプログラムを同期してメッセージを送受信する方法は?

また、client1がclient2にメッセージを送信する場合、client1が最初のメッセージに返信していない限り、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; 
    } 
} 
+1

[Boost.ASIO](http://www.boost.org/libs/asio/)を参照してください。この正確なシナリオでは、[例](http://www.boost.org/doc/html/boost_asio/examples.html#boost_asio.example.chat)が付属しています。 – ildjarn

+0

@ildjarnありがとう、それらの例は私が欲しいものですが、私はwinsockライブラリに固執することを好むでしょう – Beef

+1

あなたはもっと(非常に醜い)作業中です。 ; - ] – ildjarn

答えて

1

今CLIENT1は、クライアント2にメッセージを送信する場合、彼らはCLIENT1にメッセージを送信しようとするまで、クライアント2は は、メッセージを受信しません。

あなたはこのようにコードを作成しました。

CLIENT1がCLIENT2にメッセージを送信した場合CLIENT2は 最初の1に答えていた場合を除きまた、CLIENT1は は別のメッセージを送信することはできません。

もう一度コードを作成しました。あなたのコードはすべてsendto()の後にrecvfrom()が続くものとします。しかし、あなたの質問はあなたが望むものではないことを示しています。私はそう CLIENT1は、クライアント2にメッセージを送信すると、クライアント2が受信すること、それがなくても、ほぼ瞬時に 、私はインスタントメッセンジャーのようなプログラムを動作させるために探しています

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; 
    } 
} 

以下のコードにいくつかのコメントを追加しました最初にメッセージを送信します。

使用Boost.Asioおよび非同期ソケット、非同期chat_clientexampleは完全にTCPソケットを使用して、この非常に事は、UDPのための例を変更することはかなり簡単ですし。非同期UDP echo serverの例も同様に便利です。 boost::asio::ip::udp::socket::async_recv_from()boost::asio::ip::udp::socket::async_send_to()を使用します。他のBSDソケットインタフェースは、documentationに記述されている同等のマッピングを持っています。

+0

ありがとう、私はあなたのコメントであなたが言ったことを見て、必要な変更を加えようとするが、私はwinsockライブラリにこだわることを好むだろうが、とにかく感謝します。 – Beef

+0

@Beefはブーストを使用しますあなたの人生は簡単です。車輪を再発明する理由はありません。 asioライブラリには、BSDソケットAPI用の**明示的な**マッピングがあります。 –

関連する問題