有没有一种方法可以优化多个python循环?

时间:2018-07-06 02:58:59

标签: python loops for-loop

我正在尝试制作多人网络游戏,我有一个用python完成的服务器。由于游戏是多人游戏,因此我需要分别更新每个玩家;这需要for循环,此刻我的代码使用了许多for循环,这给我带来了一些不良影响。副作用包括速度减慢。我对于for循环的另一个问题是,它们会根据循环的次数来改变速度。这导致以下问题:循环需要循环通过的项目数会根据连接的玩家数量而变化,从而弄乱了我为掩盖延迟而做出的客户端预测功能。

这是我的主要代码:

      PlayerData = {} 

    for Player in Players:
        if(Player.id > 50):
            PlayerData['playerx' + str(Player.id)] = Player.x
            PlayerData['playery' + str(Player.id)] = Player.y


            PlayerData['playera' + str(Player.id)] = int(Player.angle)

            PlayerData['playerstat' + str(Player.id)] = Player.alive

            if(Player.id > 50):
                if(Player.alive == 0):
                    Players.remove(Player) 

        for ID in clientIds:
            PlayerData['id'] = str(clientIds[len(clientIds) - 1].id)

        PlayerData['players'] = ids




        if(Player.id <= 50):
            hrIds.append(Player.id)
            PlayerData['hx' + str(Player.id)] = Player.x
            PlayerData['hy' + str(Player.id)] = Player.y
            #PlayerData['ha' + str(Player.id)] = int(Player.angle)


    PlayerData['hr'] = hrIds
    PlayerJsonData = json.dumps(PlayerData)
    await websocket.send(PlayerJsonData)
    recivedData = await websocket.receive()
    rData = json.loads(recivedData)

    for ID in clientIds:
        if(rData['id'] == str(ID.id)):
            if(ID.IG == 0):
                 if(rData['playerstat'] == 1):
                    Players.append(player_classes.Basic(-1300, -1300, ID.ws, ID.id, 1)) 
                    ID.IG = 1




    for Player in Players:

        for Player2 in Players:
             if(Player.id > 50):
                Player.detect_collide(Player2)


                if(rData['id'] == str(Player.id)):
                    if(rData['direction'] == "up"):
                            Player.accelerate(rData['direction'])
                            Player.moveUp(Player2)

                    if(rData['direction'] == "left"):
                        Player.accelerate(rData['direction'])
                        Player.moveLeft(Player2)

                    if(rData['direction'] == "down"):
                        Player.accelerate(rData['direction'])
                        Player.moveDown(Player2)

                    if(rData['direction'] == "right"):
                        Player.accelerate(rData['direction'])
                        Player.moveRight(Player2)


                    if(rData['direction'] == "none"):
                        Player.decelerate(rData['direction'])  

编辑:我向Players添加更多类时发生了我的主要循环速度问题

1 个答案:

答案 0 :(得分:0)

您应该避免两次检查同一对玩家的碰撞。

让我们举一个非常简单的示例,其中Players列表包含0、1、2、3。

通过您的代码,您将获得许多冗余测试:

  • 在循环0处,针对1、2和3测试0
  • 在循环1中,您针对0、2和3测试了1 ===>(但已经测试了0-1)
  • 在循环2中,您针对0、1和3测试了2 ===>(但是0-2 / 1-2已经过测试)
  • 在循环3中,您针对0、1和2 ===>测试了3(但已经测试了0-3 / 1-3 / 2-3)

所以代替:

for Player in Players:
    for Player2 in Players:

要做:

for i, Player in enumerate(Players):
    for Player2 in Players[i + 1:]:

如果我们再次使用包含0、1、2、3的列表,我们将具有以下行为:

  • 在循环0处,针对1,2,3测试0
  • 在循环1中,您针对2、3测试了1
  • 在循环2中,您针对3测试了2

这样,它将迭代次数从N ^ 2减少到N(N-1)/ 2。