Select()に基づいて再送信するためのタイマーの使用法をテストするために、基本的なクライアント/サーバーエコープログラムを作成しようとしています(ただし、意図したとおりに機能しなかった場合は、デバッグを簡素化するためにそのビットをコメントアウトする必要がありました)。関連するコードのスニペットは次のとおりです。
サーバ:
from socket import *
import sys
import select
address = ('localhost', 6005)
server_socket = socket(AF_INET, SOCK_DGRAM)
server_socket.bind(address)
while(1):
print "Listening"
recv_data, addr = server_socket.recvfrom(2048)
print recv_data
if recv_data == "Request 1" :
print "Received request 1"
server_socket.sendto("Response 1", address)
Elif recv_data == "Request 2" :
print "Received request 2"
data = "Response 2"
server_socket.sendto(data, address)
クライアント:
from socket import *
import sys
import select
address = ('localhost', 6005)
client_socket = socket(AF_INET, SOCK_DGRAM)
num_retransmits = 0
while(num_retransmits < 60):
num_retransmits = num_retransmits + 1
data = "Request 1"
client_socket.sendto(data, address)
print "Sending request 1"
recv_data, addr = client_socket.recvfrom(2048)
print recv_data, "!!"
クライアントでの出力は単に「Sendingrequest1」であり、recvfrom呼び出し以下でブレークポイントが使用された場合、ブレークポイントに到達しません。ですから、クライアントは何も受け取っておらず、受け取るまで持ちこたえていると思います。一方、サーバーでの出力は次のとおりです。
などなど
最初のループの後、サーバーは再びループし、RESPONSE 1を出力します。これは、サーバーが要求1を受信し、応答1をクライアントに送信し、ループすることを意味します...しかし、2回目のループの後、応答1はまだですそのソケットに!そのため、recv_dataを出力すると、応答1が出力されます。一方、クライアントはrecv_dataを受信していないため、出力していません。サーバーのソケットのバッファーに残っています。
助けてください-私は他のエコープログラムを見てみましたが、それらはすべてTCPを使用しているようで、かなり簡単です(そして私はほとんど同じ手順に従ったと思います)。理由はわかりません。 UDPプログラムが機能していません。sendall()呼び出しを調べてみましたが、TCPでしか機能しないようです。
アドレスではなくアドレスに送信する必要があります。
from socket import *
import sys
import select
address = ('localhost', 6005)
server_socket = socket(AF_INET, SOCK_DGRAM)
server_socket.bind(address)
while(1):
print "Listening"
recv_data, addr = server_socket.recvfrom(2048)
print recv_data
if recv_data == "Request 1" :
print "Received request 1"
server_socket.sendto("Response 1", addr)
Elif recv_data == "Request 2" :
print "Received request 2"
data = "Response 2"
server_socket.sendto(data, addr)
ここで起こっているのは、サーバーが'Response 1'
をlocalhost:6005
に送信し、localhost:6005
もリッスンしているのですぐに受信することです。
正しいように、サーバーは(address, port)
にバインドしてリッスンします。クライアントが最初にバインドせずに接続すると、未使用の(address, port)
が自動的に割り当てられます。既知の(address, port)
を明示的に設定するためにbind
を使用するか、addr
によって返されるrecvfrom
を使用して、クライアントがそれに応答するために使用している(address, port)
を判別する必要があります。
サーバー側の10行目
recv_data、addr = server_socket.recvfrom(2048)
する必要があります
recv_data、addr = server_socket.sendto(2048)
?
ps>私は初心者です。 = P