Mafia (auch bekannt als Werewolf) ist ein Partyspiel, das ungefähr so spielt:
- Das Spiel beginnt am Tag 0. Nach jedem Tag
n
kommt eine Nachtn
. Nach jeder Nachtn
kommt ein Tagn+1
. dhD0, N0, D1, N1, D2, N2
... - Zu Beginn von Tag 0 wählt ein Host heimlich Spieler aus, die bestimmte Rollen ausfüllen sollen:
- Einige Spieler werden zur Mafia. Jede Nacht wählt jeder Mafioso einen Spieler. Zu Beginn des nächsten Tages wird der Spieler getötet, der von den meisten Mafiosos ausgewählt wurde. Sie werden dauerhaft aus dem Spiel entfernt und ihre Rolle wird öffentlich bekannt gegeben. Mafia ausgerichtet.
- Einige Spieler werden Polizisten. Jede Nacht wählt jeder Polizist einen Spieler. Zu Beginn des nächsten Tages wird der Cop auf die Ausrichtung des Spielers aufmerksam. Dorforientiert.
- Einige Spieler werden zu Ärzten. Jede Nacht wählt jeder Arzt einen Spieler. Wenn dieser Spieler derselbe ist, den die Mafia getötet hat, werden die Aktionen der Mafia für diese Nacht abgebrochen. Dorforientiert.
- Alle Spieler, die nicht für eine andere Rolle ausgewählt wurden, sind Dorfbewohner. Dorfbewohner haben keine Fähigkeiten, die nicht von der ganzen Stadt geteilt werden. Dorforientiert.
- Jeden Tag außer Tag 0 wählt die gesamte Stadt (dh alle lebenden Spieler) einen Spieler. Am Ende des Tages wird dieser Spieler aus dem Spiel entfernt und seine Rolle wird aufgedeckt. (Am Tag 0 chillt jeder bis zum Einbruch der Dunkelheit.)
- Wenn zu irgendeinem Zeitpunkt keine Mafiosos mehr übrig sind, endet das Spiel mit einem Sieg aller dörflich ausgerichteten Spieler (einschließlich der Toten).
- Wenn die Spieler mit Ausrichtung auf das Dorf zu irgendeinem Zeitpunkt nicht mehr als die Spieler mit Ausrichtung auf die Mafia sind, endet das Spiel, wenn alle Spieler mit Ausrichtung auf die Mafia siegreich sind (einschließlich der Toten).
Für diese Herausforderung ist es Ihr Ziel, einen Bot zu schreiben, um andere Bots bei Mafia zu schlagen!
Wie man einen funktionierenden Bot macht
Sie müssen mir nur eine Datei mit dem Namen liefern run
. In der Verzeichnisstruktur, in der diese Herausforderung stattfinden wird, lebt Ihr Bot hier:
start
controller/
tmp/
players/ # You are here!
some_bot/ # Let's pretend you're some_bot.
to_server
from_server
players
run # This is what you give me
mafia-game-bot/
skynet/
Die run
Datei, wenn sie ausgeführt wird , wird Sie bietet sein Ding. Es ist wichtig zu beachten, dass für diese Datei keine Befehlszeilenargumente oder ähnliches erforderlich sind. Es wird genauso ausgeführt wie ./run
. Wenn Sie auf eine andere Weise ausgeführt werden müssen, müssen Sie dies folgendermaßen umgehen:
real_bot.py
#!/bin/python2
# code goes here
run
#!/bin/bash
./real_bot.py --flags --or --whatever
Ein wichtiger Punkt ist, dass alle Eingaben, die Ihr Bot erhält, in der Datei gefunden werden from_server
und das Steuerungsprogramm nach den Ausgaben Ihres Bots sucht to_server
. Ich habe mich für diese Methode entschieden, damit jede Sprache, die Datei-E / A ausführen kann, teilnehmen kann. Wenn es in Ihrer Sprache einfacher ist, mit stdin und stdout zu arbeiten als mit Datei-E / A, möchten Sie möglicherweise eine run
Datei schreiben , die wie folgt aussieht:
#!/bin/bash
./real_bot.py < from_server > to_server
Das wird es so machen, dass stdin aus der from_server
Datei kommt und stdout direkt zu geht to_server
.
Ihr Bot bleibt für die Dauer des Spiels nicht aktiv. Stattdessen wird es ausgeführt, wenn eine Entscheidung getroffen werden muss. Ebenso wird es nicht informiert, wenn es tot ist, es wird einfach nicht mehr ausgeführt. Planen Sie dies, indem Sie alles, woran Sie sich erinnern möchten, in einer Datei speichern und später lesen. Sie können, schreiben oder lesen aus einer beliebigen Datei in Ihrem Bot Ordner erstellen, aber Sie können nicht schreiben oder lesen irgendwo außerhalb des Ordners, einschließlich Netzwerkzugriff oder irgendetwas . Wenn Ihr Bot etwas weiß, was ihm nicht aus dem Ordner mitgeteilt wurde, oder wenn es etwas berührt , das sich nicht in diesem Ordner befindet, wird Ihr Bot disqualifiziert.
Wie man einen funktionierenden Bot macht
Tag
Zu Beginn des Spiels wird die Datei players
mit einer durch Zeilenumbrüche getrennten Liste aller Spieler im Spiel gefüllt. Es wird nicht aktualisiert, wenn Spieler das Spiel verlassen.
Zu Beginn von Tag 0 finden alle Spieler diese Nachricht in ihrer from_server
Datei:
Rise and shine! Today is day 0.
No voting will occur today.
Be warned: Tonight the mafia will strike.
Wenn Sie der Cop sind, wird die Zeile You are the cop
an das Ende angehängt. Der Arzt sieht You are the doctor
. Die Mafia sieht You are a member of the mafia.\nYour allies are:
und eine durch Zeilenumbrüche getrennte Liste der Mafia-Mitglieder, mit Ausnahme des Spielers, der die Nachricht liest.
Zu Beginn aller anderen Tage erscheint diese Meldung:
Dawn of day `day_number`.
Last night, `victim` was killed. They were `victim_role`.
Investigations showed that `cop_target` is `target_alignment`-aligned.
These players are still alive: `remaining_players`
dayNumber
wird durch die Nummer des Tages ersetzt. victim
wird durch den Namen des Opfers der letzten Nacht ersetzt und victim_role
ist einer von:
a villager
a mafioso
the cop
the doctor
cop_target
ist der Name des Spielers, den der Polizist letzte Nacht untersucht hat, und target_alignment
ist entweder village
oder mafia
. Schließlich remaining_players
ist eine Liste der Spieler, die in diesem Format noch am Leben sind:player1, player2, player3
Die zweite Zeile entfällt, wenn letzte Nacht keine Tötung stattgefunden hat, und die dritte Zeile wird nur dem Polizisten angezeigt.
Zum Beispiel,
Dawn of day 42.
Last night, Xyzzy was killed. They were a villager.
Investigations showed that Randy is mafia-aligned.
These players are still alive: Randy, CopBot, JohnDoe, Steve
Sobald diese Nachricht aus dem Weg ist, beginnt der Tag! Jeder Bot kann 50 Aktionen pro Tag ausführen, wobei eine "Aktion" einen Spieler wählt oder etwas lautes sagt.
Um für einen Spieler zu stimmen, schreibe vote player_name
in deine to_server
Datei und beende sie. Um abzustimmen, niemanden zu töten, schreiben Sie vote no one
. Wenn Sie abstimmen, werden alle Spieler (einschließlich Sie) sehen your_bot votes to kill your_selection
. Stimmen werden am Tag 0 ignoriert.
Eine Reihe vordefinierter Nachrichten kann an alle Spieler gesendet werden. Die ID jeder möglichen Nachricht ist hier aufgelistet:
0: No
1: Yes
2: I am the cop
3: I am the doctor
4: I am a normal villager
5: I trust this player:
6: I think this player is suspicious:
7: I think this player is the cop:
8: I think this player is the doctor:
9: I think this player is a normal villager:
10: I think this player is mafia:
11: Do you think this player is mafia?
12: I tried to save this player:
13: I successfully saved this player:
14: I investigated this player and found that they were mafia-aligned:
15: I investigated this player and found that they were village-aligned:
16: Will you please use your power on this player tonight?
Alle diese Nachrichten mit Ausnahme der ersten fünf beziehen sich auf einen bestimmten Spieler. Um eine dieser Nachrichten auszusprechen, schreiben Sie say message_id player_name
. Schreiben Sie für eine der ersten fünf Nachrichten einfach say message_id
. Sie können beiden optional ein drittes Argument hinzufügen und dabei den Namen eines Spielers angeben, mit dem Sie sprechen (alle Spieler können es weiterhin lesen, aber sie wissen, wer der beabsichtigte Empfänger ist).
Wenn Ihr Bot eine Nachricht sagt, lesen alle Spieler your_bot says "message"
, wo message
sich die Nachricht befindet, die mit der von Ihnen geschriebenen ID verknüpft ist. Wenn die Nachricht einen Betreff enthält, werden ein Leerzeichen und der Betreff direkt nach dem Ende der Nachricht eingefügt. Wenn es einen Empfänger enthält, werden dessen Name, ein Doppelpunkt und ein Leerzeichen unmittelbar vor der Nachricht eingefügt.
Am Ende des Tages laufen alle lebenden Spieler ein letztes Mal, um das Ergebnis der Abstimmung zu sehen. Wenn ein Spieler abgewählt wurde, heißt es:
The town has killed player_name!
They were a villager
... oder a mafioso
, oder the cop
, oder the doctor
.
Wenn kein Spieler abgewählt wurde, heißt es stattdessen:
The town opted to lynch no one today.
Wenn der Controller diese Nachrichten sendet, ignoriert er alle Antworten von Spielern. Der Tag ist vorbei.
Nacht
Nachts können alle außer den Dorfbewohnern ihre Kräfte einsetzen.
Mafia:
Du wirst lesen It is night. Vote for a victim.
. Geben Sie in diesem Fall den Namen des Spielers aus, den Sie töten möchten.
Polizist:
Du wirst lesen It is night. Who would you like to investigate?
. Geben Sie in diesem Fall den Namen des Players aus, den Sie überprüfen möchten.
Arzt:
Du wirst lesen It is night. Who would you like to save?
. Geben Sie in diesem Fall den Namen des Players aus, den Sie schützen möchten.
Danach beginnt der nächste Tag wie gewohnt.
Du darfst dich nur einmal pro Spiel retten.
Allgemeine Information
- Das Spiel läuft nicht ohne 6 oder mehr Spieler.
- Ein Drittel der Spieler, abgerundet, wird Mafia sein. Ein Spieler wird ein Arzt sein, und ein Spieler wird ein Polizist. Alle anderen Spieler sind Dorfbewohner.
- Stimmengleichheit bei der Dorfwahl oder bei der Wahl der Mafia über Nacht wird nach dem Zufallsprinzip geregelt.
- Bot-Namen müssen alphanumerisch + Bindestriche und Unterstriche sein.
- Es ist verboten, die Kenntnis des Codes des Gegners direkt zu nutzen. Theoretisch sollte ich in der Lage sein, Ihren Bot gegen Bots auszuspielen, die Sie noch nie gesehen haben, und eine vergleichbare Leistung zu erzielen.
- Leider muss ich Ihr Programm disqualifizieren, wenn ich Ihr Programm nicht mit ausschließlich kostenloser (wie bei Bier) Software zum Laufen bringen kann.
- Ich behalte mir das Recht vor, Einsendungen zu disqualifizieren, wenn ich sie für böswillig halte. Dies beinhaltet, ist aber nicht beschränkt auf die Verwendung von zu viel Zeit, Speicher oder Speicherplatz. Ich habe das Limit absichtlich weich gelassen, aber denke daran: Ich starte dies auf meinem Heimcomputer, nicht auf einem Supercomputer, und ich möchte nicht, dass es ein Jahr dauert, bis Ergebnisse erzielt werden. Ich erwarte nicht, dass ich das benutzen muss, da meine Standards ziemlich niedrig sind. Das ist im Grunde genommen "wenn ich denke, dass du absichtlich ein Arschloch bist" und wenn du mich davon überzeugen kannst, dass ich sonst meine Entscheidung rückgängig mache.
Wertung
In jeder Runde werden 100 Spiele ausgetragen (dies kann sich erhöhen, wenn sich mehr Bots anschließen, um die Stichprobengröße groß genug zu halten, theoretisch hat dies jedoch keine Auswirkungen). Ich werde aufzeichnen, wie oft jeder Bot als Dorfbewohner gewinnt, im Vergleich dazu, wie oft er als Dorfbewohner spielt, und dasselbe gilt für die Mafia. Ein Bot villager_ratio
ist number of games won as villager / number of games played as villager
, und mafia_ratio
ist das gleiche, aber s/villager/mafia/g
. Die Punktzahl eines Bots ist (villager_ratio - mean villager_ratio) + (mafia_ratio - mean mafia_ratio)
.
Beispiel bot
Randy the Robot ist kein guter Mafia-Spieler. Randy ignoriert so ziemlich alles und wählt zufällig aus, was er sagen möchte, wen er wählen möchte und wen er mit Nachtkräften anvisieren möchte.
run.sh
:
#!/bin/bash
./randy.py < from_server > to_server
randy.py
:
#!/usr/bin/env python
import random
with open('players') as f:
p = f.read().split() + ['no one']
day = True
try:
line = raw_input()
if line.endswith(('?', 'victim.')):
day = False
if not day:
print random.choice(p)
else:
if random.random() > 0.5:
if random.random() > 0.5:
print 'vote {}'.format(random.choice(p))
else:
id = random.randint(0, 17)
print 'say {}{}'.format(id, (' ' + random.choice(p)) if id > 4 else '')
except: pass
Regler
@undergroundmonorail hat ein Steuerungsprogramm für diese Herausforderung geschrieben, das hier verfügbar ist .
Sie haben einen Monat Zeit, um die Antworten zu codieren und einzureichen. Ich gebe dem siegreichen Bot (bei Stimmen mit der höchsten Gewinnquote handelt es sich um Stimmen) mindestens eine Reputationsprämie von 50 (abhängig davon, wie viel Repräsentanten ich in einem Monat verdienen kann).
Hier ist ein Wrapper-Skript von @Blacksilver zur Verwendung mit kompilierten Sprachen:
#!/bin/bash
run="./a.out"
compile="gcc bot.c"
if [ -e $run ]; then
$run
else
$compile
$run
fi
Setzen Sie dies in run
.
Dieser Beitrag wurde von @undergroundmonorail geschrieben (ich habe einige Änderungen vorgenommen).
Er gab es hier an alle weiter, die es fertigstellen und posten wollten.