BS to gra karciana, w której celem jest utrata wszystkich kart.
Gra składa się z czterech graczy i talii 52 kart. Każdy gracz otrzymuje losowo 13 kart. Zwykle karty są oznaczone 2 - 10, as, walet, królowa, król, ale dla uproszczenia karty będą oznaczone liczbą od 0 do 12 włącznie. Chociaż liczba kart w ręce gracza jest informacją publiczną, tylko gracz wie, jakie konkretne karty ma na ręce.
Gra przebiega w następujący sposób: pierwszy gracz umieszcza tyle kart z etykietą 0, ile chce, na stosie kart odrzuconych (zwróć uwagę, że nie jest on zobowiązany do zagrania wszystkimi swoimi kartami z etykietą 0 , chociaż zazwyczaj jest to w jego najlepszym interesie ). Musi zagrać co najmniej jedną kartę. Drugi gracz zagrywa tyle kart, ile chce oznaczyć jako 1 , trzeci gracz gra 2 i tak dalej. Po 12 resetuje się do 0.
Co się stanie, jeśli nie masz żadnej karty, którą powinieneś zagrać? Pamiętaj, że musisz zagrać co najmniej jedną kartę - w rzeczywistości możesz zagrać dowolną kartę! (W rzeczywistości, nawet jeśli masz odpowiednią kartę, możesz położyć i zagrać inną kartę). Jednak ktoś może do ciebie zadzwonić i powiedzieć „BS!” Jeśli ten ktoś ma rację i skłamałeś, musisz wziąć wszystkie karty ze stosu kart odrzuconych; w nagrodę gracz, który cię wezwał, losowo umieszcza jedną ze swoich kart na stosie kart odrzuconych. Jeśli oskarżyciel się myli, musi wziąć wszystkie karty ze stosu kart odrzuconych. Pamiętaj, że nie możesz kłamać na temat liczby kart, które grasz.
Bardziej szczegółowe informacje:
- Na początku gry wybiera się czterech losowych graczy. Ponieważ będzie co najmniej 1000 gier, każdy gracz będzie miał szansę zagrać. Kolejność tur ustalana jest losowo na początku gry
- Jeśli zwrócisz jedną poprawną kartę i jedną niepoprawną kartę, uznaje się to za kłamstwo (tzn. Jeśli miałbyś dać 2 s, a dałeś jedną 2 i jedną 1 , to kłamie)
- Jeśli dwóch lub więcej graczy mówi jednocześnie BS, to jeden jest losowo wybierany.
- Twój wynik to procent wygranych gier.
- Jest maksymalnie 1000 rund, przy czym jedna runda jest rozgrywana przez każdego gracza. Zwykle ktoś wygrywa przed tym. Jeśli nikt nie wygrywa, jest on wliczany do całkowitej liczby rozegranych gier, ale nikt nie wygrywa.
Specyfikacja:
Powinieneś napisać klasę, która się rozszerza Player
. Będzie to wyglądać jak:
package players;
import java.util.ArrayList;
import java.util.List;
import controller.*;
public class Player1 extends Player {
@Override
protected List<Card> requestCards(int card, Controller controller) {
Card[] hand = getHand();
List<Card> ret = new ArrayList<Card>();
for (Card c : hand) {
if (c.getNumber() == card) {
ret.add(c);
}
}
if (ret.size() == 0) ret.add(hand[0]);
return ret;
}
@Override
protected boolean bs(Player player, int card, int numberOfCards, Controller controller) {
return numberOfCards >= 3;
}
protected void update(Controller controller) {
// This method gets called once at the end of every round
}
protected void initialize(Controller controller) {
// This method gets called once at the beginning once all the cards are dealt
}
public String toString() {
return "Player 1";
}
}
Metoda requestCards
jest wywoływana, gdy nadejdzie Twoja kolej. Argumentem card
jest numer karty, który powinieneś podać. Zwracasz listę kart, które chcesz umieścić na stosie kart odrzuconych. Gracz powyżej sprawdza, czy ma jakieś karty żądanego typu karty; jeśli nie, po prostu zagrywa swoją pierwszą kartę i ma nadzieję, że nikt nie sprawdzi.
Metoda bs
jest wywoływana za każdym razem, gdy ktoś inny zagrywa kartę. Pierwszy argument to gracz, drugi - karta, którą miał zagrać, a trzeci - liczba tego rodzaju kart, które według niego zagrał. Wróć, true
jeśli chcesz zadzwonić do „BS”. W powyższym kodzie gracz wywołuje „BS” tylko wtedy, gdy drugi gracz twierdzi, że ma 3 lub więcej kart żądanego typu.
Ostatnim argumentem dla obu metod jest controller
kontroler kontrolujący grę. Z kontrolera możesz uzyskać więcej informacji publicznych, takich jak liczba kart na stosie kart odrzuconych lub lista i kolejność graczy.
toString
Metoda jest opcjonalne.
Conroller na GitHub: https://github.com/prakol16/bs
Jeśli chcesz opublikować rozwiązanie inne niż Java, możesz użyć interfejsu podanego na stronie https://github.com/LegionMammal978/bs (podziękowania dla LegionMammal978), a ja postaram się go zintegrować.
Dotychczasowa tablica wyników:
class players.PlayerConMan: 2660/4446 = 59.82905982905983%
class players.CalculatingLiar: 2525/4426 = 57.049254405784005%
class players.PlayerTruthy: 1653/4497 = 36.75783855903936%
class players.Player4: 1446/4425 = 32.67796610169491%
class players.Player1: 536/4382 = 12.23185759926974%
class players.Player3: 493/4425 = 11.141242937853107%
class players.Player2: 370/4451 = 8.312738710402156%
class players.LiePlayer: 317/4432 = 7.152527075812275%
class players.Hoarder: 0/4516 = 0.0%
PlayerConMan wygrywa, ale CalculatingLiar jest już blisko sekundy. Te wyniki wydają się spójne - za każdym razem są dość takie same.
źródło
Controller.toString()
udostępniać go publicznie, ponieważ zwraca ręce wszystkich graczy i stos kart odrzuconych.Odpowiedzi:
ConMan
ConMan obserwuje każdą kartę, która przechodzi przez jego rękę, dzwoniąc do BS, gdy gra nie jest możliwa ze względu na to, gdzie są karty.
Odgrywa prawdę, gdy jest w stanie, ale polega inteligentnie na ostatniej karcie, jeśli ma nastąpić zwycięstwo.
Długo szukałem techniki sprawdzania BS, gdy prawdopodobieństwo było wysokie, że przeciwnik kłamie, lub gdy sprawdzanie BS było korzystne (np. Uzyskiwanie użytecznych kart ze stosu kart odrzuconych), ale w praktyce nie sprawdzałem BS wcale ja najwięcej punktów.
źródło
Gracz 3131961357_10
Wybiera losowego gracza w każdej grze i zawsze wywołuje BS tego gracza.
źródło
Prawda
Nie do końca skończony, ponieważ nie wiem, jak powiedzieć wynik sprawdzania BS (jeśli wziął stos, lub ktoś inny w przypadku remisu, lub zrobiłem).
W tej chwili dzwoń do BS tylko wtedy, gdy mogę to udowodnić. Nie kłam, chyba że muszę. Muszę poprawić algorytm kłamstwa. Staram się jak najbardziej zbliżyć do tego, jak gram w BS przeciwko innym graczom (minus losowe umieszczenie dodatkowych kart pod nimi, aby zagrać 5 lub 6 bez ich wiedzy).
źródło
cards = cards.get(0)
.cards
jest listą, więc nie możesz przypisaćCard
doList<Card>
. Czy próbujesz usunąć wszystko oprócz pierwszego elementu?numberOfCards
ponieważ jest on już odrzucany pobs
wywołaniu)CalculatingLiar
Ten próbuje grać prawdę. Jeśli kłamie, używa karty, której nie użyje w najbliższej przyszłości. Stara się również wygrać poprzez sprawdzenie BS innych graczy, ponieważ ostatnia karta prawie nigdy nie pasuje.
źródło
Hoarder
Bardzo prosta strategia, zbiera karty, aż będzie mogła rzucić się na pasmo uczciwości i wygrać. Nie mogłem tego przetestować, mam nadzieję, że moja Java nie jest zbyt zardzewiała.
źródło
remainingCards.remove(card)
powinien mieć rzutowanie naInteger
, w przeciwnym razie Java uważa, że dzwonisz.remove(int)
, co jest usuwane przez indeks.LiePlayer
Ustanawia co najmniej 2 karty, nawet jeśli oznacza to rozciągnięcie prawdy.
źródło
Card[] hand = getHand();
jest potrzebny na górzebs(..)
(Player.hand
jest prywatny). Ponadto ulega awarii, jeśli masz w ręce mniej niż 2 karty.i<cards.length
; ręka nie jest zdefiniowana wCard c : hand
. A czasami przechodzi w nieskończoną pętlę, ponieważ nie robisz tego++i
w pętli. Dodałbym je, ale nie jestem pewien, czy dokładnie tak chcesz.