【问题标题】:Python coroutine time slicingPython协程时间切片
【发布时间】:2019-04-12 10:47:38
【问题描述】:

我正在从这里学习如何使用协程,文章以视频描述以下内容为例

国际象棋大师 Judit Polgár 举办国际象棋展览,她在其中下棋 多名业余选手。她有两种指挥方式 展览:同步和异步。

假设:

24 opponents
Judit makes each chess move in 5 seconds
Opponents each take 55 seconds to make a move
Games average 30 pair-moves (60 moves total)

同步版本:Judit 一次玩一个游戏,从不同时玩两个 同时,直到游戏完成。每场比赛需要 (55 + 5) * 30 == 1800 秒,或 30 分钟。整个展览耗时 24 * 30 == 720 分钟,即 12 小时。

异步版本:Judit 从一张桌子移动到另一张桌子,一步到位 在每张桌子上。她离开桌子,让对手做出他们的 等待期间的下一步行动。在所有 24 场比赛中一举拿下 Judit 24 * 5 == 120 秒,或 2 分钟。现在整个展览都被剪掉了 低至 120 * 30 == 3600 秒,或仅 1 小时。

本文取自https://youtu.be/iG6fr81xHKA?t=4m29s

如果我要为国际象棋展览编写代码,我的程序将包含 24 个协程,并且必须在 5 秒内完成并移动到下一个协程。

因此,我的问题是,在 python 中编写了 24 个函数,这些函数几乎都在做同样的事情,被认为是不好的编码实践,如果是这样,可以做些什么呢?

编辑

从这个例子https://github.com/prompt-toolkit/python-prompt-toolkit/blob/master/examples/other/coroutines-and-futures.py

我看到我们可以做 24 个函数。

【问题讨论】:

  • 24 functions - 没有。你需要 1 个函数和 24 组参数,对应 24 个游戏。
  • @Poolka 这很有趣。您能否制作一个虚拟的 sn-p 来显示您的意思。

标签: python coroutine


【解决方案1】:

这是实现它的一种方式:

import asyncio


class Player:
    def __init__(self, name: str, seconds_per_turn: float):
        self.name = name
        self.seconds_per_turn = seconds_per_turn
        self.busy = asyncio.Condition()

    async def move(self, game):
        await self.busy.acquire()
        print(f'game {game.game_number} player {self.name} begins {self.seconds_per_turn} second move')
        await asyncio.sleep(self.seconds_per_turn)
        print(f'game {game.game_number} player {self.name} ends {self.seconds_per_turn} second move')
        self.busy.release()


class Game:
    def __init__(self, game_number: int, player1: Player, player2: Player, number_of_turns: int):
        self.game_number = game_number
        self.player1 = player1
        self.player2 = player2
        self.number_of_turns = number_of_turns

    async def start(self):
        print(f'game {self.game_number} started')
        for turn in range(1, self.number_of_turns + 1):
            print(f'game {self.game_number} turn #{turn}')
            await self.player1.move(self)
            await self.player2.move(self)
        print(f'game {self.game_number} ended')


if __name__ == '__main__':
    synchronous = False
    loop = asyncio.get_event_loop()
    judit = Player('judit', 5)
    for i in range(1, 25):
        opponent = Player(f'opponent {i}', 55)
        game = Game(i, judit, opponent, 30)
        if synchronous:
            loop.run_until_complete(game.start())
        else:
            asyncio.ensure_future(game.start())
    loop.run_forever()

输出:

game 1 started
game 1 turn #1
game 1 player judit begins 5 second move
game 2 started
game 2 turn #1
game 3 started
game 3 turn #1
game 4 started
game 4 turn #1
game 5 started
game 5 turn #1
game 6 started
game 6 turn #1
game 7 started
game 7 turn #1
game 8 started
game 8 turn #1
game 9 started
game 9 turn #1
game 10 started
game 10 turn #1
game 11 started
game 11 turn #1
game 12 started
game 12 turn #1
game 13 started
game 13 turn #1
game 14 started
game 14 turn #1
game 15 started
game 15 turn #1
game 16 started
game 16 turn #1
game 17 started
game 17 turn #1
game 18 started
game 18 turn #1
game 19 started
game 19 turn #1
game 20 started
game 20 turn #1
game 21 started
game 21 turn #1
game 22 started
game 22 turn #1
game 23 started
game 23 turn #1
game 24 started
game 24 turn #1
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 2 player judit begins 5 second move
game 2 player judit ends 5 second move
game 2 player opponent 2 begins 55 second move
game 3 player judit begins 5 second move
game 3 player judit ends 5 second move
game 3 player opponent 3 begins 55 second move
game 4 player judit begins 5 second move
game 4 player judit ends 5 second move
game 4 player opponent 4 begins 55 second move
game 5 player judit begins 5 second move
game 5 player judit ends 5 second move
game 5 player opponent 5 begins 55 second move
game 6 player judit begins 5 second move
game 6 player judit ends 5 second move
game 6 player opponent 6 begins 55 second move
game 7 player judit begins 5 second move
game 7 player judit ends 5 second move
game 7 player opponent 7 begins 55 second move
game 8 player judit begins 5 second move
game 8 player judit ends 5 second move
game 8 player opponent 8 begins 55 second move
game 9 player judit begins 5 second move
game 9 player judit ends 5 second move
game 9 player opponent 9 begins 55 second move
game 10 player judit begins 5 second move
game 10 player judit ends 5 second move
game 10 player opponent 10 begins 55 second move
game 11 player judit begins 5 second move
game 11 player judit ends 5 second move
game 11 player opponent 11 begins 55 second move
game 12 player judit begins 5 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #2
game 12 player judit ends 5 second move
game 12 player opponent 12 begins 55 second move
game 13 player judit begins 5 second move
game 2 player opponent 2 ends 55 second move
game 2 turn #2
game 13 player judit ends 5 second move
game 13 player opponent 13 begins 55 second move
game 14 player judit begins 5 second move
game 3 player opponent 3 ends 55 second move
game 3 turn #2
game 14 player judit ends 5 second move
game 14 player opponent 14 begins 55 second move
game 15 player judit begins 5 second move
game 4 player opponent 4 ends 55 second move
game 4 turn #2
game 15 player judit ends 5 second move
game 15 player opponent 15 begins 55 second move
game 16 player judit begins 5 second move
game 5 player opponent 5 ends 55 second move
game 5 turn #2
game 16 player judit ends 5 second move
game 16 player opponent 16 begins 55 second move
game 17 player judit begins 5 second move
game 6 player opponent 6 ends 55 second move
game 6 turn #2
game 17 player judit ends 5 second move
game 17 player opponent 17 begins 55 second move
game 18 player judit begins 5 second move
game 7 player opponent 7 ends 55 second move
game 7 turn #2
game 18 player judit ends 5 second move
game 18 player opponent 18 begins 55 second move
game 19 player judit begins 5 second move
game 8 player opponent 8 ends 55 second move
game 8 turn #2
game 19 player judit ends 5 second move
game 19 player opponent 19 begins 55 second move
game 20 player judit begins 5 second move
game 9 player opponent 9 ends 55 second move
game 9 turn #2
game 20 player judit ends 5 second move
game 20 player opponent 20 begins 55 second move
game 21 player judit begins 5 second move
game 10 player opponent 10 ends 55 second move
game 10 turn #2
game 21 player judit ends 5 second move
game 21 player opponent 21 begins 55 second move
game 22 player judit begins 5 second move
game 11 player opponent 11 ends 55 second move
game 11 turn #2
game 22 player judit ends 5 second move
game 22 player opponent 22 begins 55 second move
game 23 player judit begins 5 second move
game 12 player opponent 12 ends 55 second move
game 12 turn #2
game 23 player judit ends 5 second move
game 23 player opponent 23 begins 55 second move
game 24 player judit begins 5 second move
game 13 player opponent 13 ends 55 second move
game 13 turn #2
game 24 player judit ends 5 second move
game 24 player opponent 24 begins 55 second move
game 1 player judit begins 5 second move
game 14 player opponent 14 ends 55 second move
game 14 turn #2
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 2 player judit begins 5 second move
game 15 player opponent 15 ends 55 second move
game 15 turn #2
game 2 player judit ends 5 second move
game 2 player opponent 2 begins 55 second move
game 3 player judit begins 5 second move
game 16 player opponent 16 ends 55 second move
game 16 turn #2
game 3 player judit ends 5 second move
game 3 player opponent 3 begins 55 second move
[...]

通过将synchrounous 设置为True,第一场比赛必须在第二场比赛开始之前完成。

输出synchrounous = True:

game 1 started
game 1 turn #1
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #2
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #3
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #4
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #5
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #6
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #7
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #8
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #9
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #10
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #11
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #12
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #13
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #14
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #15
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #16
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #17
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #18
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #19
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #20
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #21
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #22
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #23
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #24
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #25
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #26
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #27
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #28
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #29
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 turn #30
game 1 player judit begins 5 second move
game 1 player judit ends 5 second move
game 1 player opponent 1 begins 55 second move
game 1 player opponent 1 ends 55 second move
game 1 ended
game 2 started
game 2 turn #1
game 2 player judit begins 5 second move
game 2 player judit ends 5 second move
game 2 player opponent 2 begins 55 second move
game 2 player opponent 2 ends 55 second move
game 2 turn #2
game 2 player judit begins 5 second move
game 2 player judit ends 5 second move
game 2 player opponent 2 begins 55 second move
game 2 player opponent 2 ends 55 second move
game 2 turn #3
game 2 player judit begins 5 second move
[...]

【讨论】:

    猜你喜欢
    • 2019-11-23
    • 1970-01-01
    • 2018-02-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-11-26
    • 2017-06-15
    • 2012-08-12
    相关资源
    最近更新 更多