首页 > 解决方案 > Python pygame 客户端/服务器运行缓慢

问题描述

我在 Youtube 上找到了一个基本的太空入侵者 pygame,我想对其进行修改,以便到目前为止,服务器正在执行所有处理和绘图,而客户端只发送键盘输入(全部在 localhost 上运行)。问题是在我实现了这个机制之后,游戏不再那么敏感了。在我按下一个键到船实际移动的时间后,它似乎有大约 1 秒的延迟(当从 pycharm 开始游戏时,当它从 cmd 开始时更糟)。

我不知道为什么会发生这种情况,因为实际上没有什么繁重的事情需要处理,我真的可以使用你的帮助。

我还监控了wireshark中的以太网流量,似乎每秒发送大约60-70个数据包。

这是包含所有必要内容的 github 链接:https ://github.com/PaaulFarcas/CS-Game

标签: pythonpygameclient-server

解决方案


我希望主循环中的这段代码是问题所在:

    recv = conn.recv(661)
    keys = pickle.loads(recv)

套接字函数conn.recv()阻塞,直到收到 661 个字节,或者有一些套接字事件(如被关闭)。因此,您的程序正在阻塞等待数据到达的主循环的每次迭代。

您可以尝试socket.setblocking( False )按照手册使用

但是我更喜欢使用该select模块(手动链接),因为我喜欢它提供的更好的控制水平。基本上,您可以使用它来了解套接字上是否有任何数据(或者是否有错误)。这为您提供了一个简单的选择读取缓冲区类型的逻辑循环:

procedure receiveSocketData
    Use select on the socket, with an immediate timeout.
    Did select indicate any data arrived on my socket?
        Read the data, appending it to a Rx-buffer
        Does the Rx-buffer contain enough for a whole packet?
            take the packet-chunk from the head of the Rx-buffer
            decode & return it
        Else
            Keep the Rx-Buffer somewhere safe
            return None
    Did any errors happen on my socket
        clear Rx-Buffer
        close socket
        return error

我想使用一个未知大小的数据包,您可以尝试取消腌制它,并在成功时返回 OK ......不过这效率很低。我会使用固定大小的数据包和struct模块以网络字节顺序打包和解包。


推荐阅读