From c7a32dc91bd955ca4b238a31aec1a21f528f7806 Mon Sep 17 00:00:00 2001 From: Daniel Grace Date: Sat, 18 Jun 2022 00:19:08 -0700 Subject: [PATCH] Sort hints by found/not found and then other world/own world. (#642) This updates notify_hints() as follows: - Sort hints by their 'found' attribute in reverse during the first iteration, so items not found will show at the bottom. - Store a tuple of (hint, hint.as_network_message()) in concerns rather than just the hint so the raw hint data remains available for later sorting. - Do the logging.info call as part of this iteration instead of doing a second iteration pass that does nothing but logging. - Iterate over concerns (and look up connected clients) rather than iterating over all clients (and checking for concerns) --- MultiServer.py | 49 +++++++++++++++++++++++++------------------------ 1 file changed, 25 insertions(+), 24 deletions(-) diff --git a/MultiServer.py b/MultiServer.py index 033a2b34..762fe8f4 100644 --- a/MultiServer.py +++ b/MultiServer.py @@ -556,32 +556,33 @@ def notify_hints(ctx: Context, team: int, hints: typing.List[NetUtils.Hint], onl """Send and remember hints.""" if only_new: hints = [hint for hint in hints if hint not in ctx.hints[team, hint.finding_player]] - if hints: - concerns = collections.defaultdict(list) - for hint in hints: - net_msg = hint.as_network_message() - for player in ctx.slot_set(hint.receiving_player): - concerns[player].append(net_msg) + if not hints: + return + concerns = collections.defaultdict(list) + for hint in sorted(hints, key=operator.attrgetter('found'), reverse=True): + data = (hint, hint.as_network_message()) + for player in ctx.slot_set(hint.receiving_player): + concerns[player].append(data) + if not hint.local and data not in concerns[hint.finding_player]: + concerns[hint.finding_player].append(data) + # remember hints in all cases + if not hint.found: + # since hints are bidirectional, finding player and receiving player, + # we can check once if hint already exists + if hint not in ctx.hints[team, hint.finding_player]: + ctx.hints[team, hint.finding_player].add(hint) + for player in ctx.slot_set(hint.receiving_player): + ctx.hints[team, player].add(hint) - if not hint.local and net_msg not in concerns[hint.finding_player]: - concerns[hint.finding_player].append(net_msg) - # remember hints in all cases - if not hint.found: - # since hints are bidirectional, finding player and receiving player, - # we can check once if hint already exists - if hint not in ctx.hints[team, hint.finding_player]: - ctx.hints[team, hint.finding_player].add(hint) - for player in ctx.slot_set(hint.receiving_player): - ctx.hints[team, player].add(hint) + logging.info("Notice (Team #%d): %s" % (team + 1, format_hint(ctx, team, hint))) - for text in (format_hint(ctx, team, hint) for hint in hints): - logging.info("Notice (Team #%d): %s" % (team + 1, text)) - - for slot, clients in ctx.clients[team].items(): - client_hints = concerns[slot] - if client_hints: - for client in clients: - asyncio.create_task(ctx.send_msgs(client, client_hints)) + for slot, hint_data in concerns.items(): + clients = ctx.clients[team].get(slot) + if not clients: + continue + client_hints = [datum[1] for datum in sorted(hint_data, key=lambda x: x[0].finding_player == slot)] + for client in clients: + asyncio.create_task(ctx.send_msgs(client, client_hints)) def update_aliases(ctx: Context, team: int):