İlk fiyat mühürlü teklif açık artırması


32

Son sonuç

Rekabet bitti. Tebrikler hard_coded!

Bazı ilginç gerçekler:

  • 40920 açık artırmanın 31600'ünde (% 77.2), ilk turun galibi bu açık artırmada en fazla turu kazandı.

  • Örnek botlar yarışmaya dahil edilirse, ilk dokuz yer bunun dışında değişmez AverageMineve yerlerini değiştirir heurist.

  • Bir açık artırmada en iyi 10 sonuç:

[2, 2, 3, 3] 16637
[0, 3, 3, 4] 7186
[1, 3, 3, 3] 6217
[1, 2, 3, 4] 4561
[0, 1, 4, 5] 1148
[0, 2, 4, 4] 1111
[2, 2, 2, 4] 765
[0, 2, 3, 5] 593
[1, 1, 4, 4] 471
[0, 0, 5, 5] 462
  • Tie sayımı (i-inci turda olduğu ihalelerin sayısı hiçbir kazananı vardı): [719, 126, 25, 36, 15, 58, 10, 7, 19, 38].

  • İ-inci turun ortalaması kazanan teklif: [449.4, 855.6, 1100.8, 1166.8, 1290.6, 1386.3, 1500.2, 1526.5, 1639.3, 3227.1].

sayı tahtası

Bot count: 33
hard_coded            Score: 16141  Total: 20075170
eenie_meanie_more     Score: 15633  Total: 18513346
minus_one             Score: 15288  Total: 19862540
AverageMine           Score: 15287  Total: 19389331
heurist               Score: 15270  Total: 19442892
blacklist_mod         Score: 15199  Total: 19572326
Swapper               Score: 15155  Total: 19730832
Almost_All_In         Score: 15001  Total: 19731428
HighHorse             Score: 14976  Total: 19740760
bid_higher            Score: 14950  Total: 18545549
Graylist              Score: 14936  Total: 17823051
above_average         Score: 14936  Total: 19712477
below_average         Score: 14813  Total: 19819816
Wingman_1             Score: 14456  Total: 18480040
wingman_2             Score: 14047  Total: 18482699
simple_bot            Score: 13855  Total: 20935527
I_Dont_Even           Score: 13505  Total: 20062500
AntiMaxer             Score: 13260  Total: 16528523
Showoff               Score: 13208  Total: 20941233
average_joe           Score: 13066  Total: 18712157
BeatTheWinner         Score: 12991  Total: 15859037
escalating            Score: 12914  Total: 18832696
one_upper             Score: 12618  Total: 18613875
half_in               Score: 12605  Total: 19592760
distributer           Score: 12581  Total: 18680641
copycat_or_sad        Score: 11573  Total: 19026290
slow_starter          Score: 11132  Total: 20458100
meanie                Score: 10559  Total: 12185779
FiveFiveFive          Score: 7110   Total: 24144915
patient_bot           Score: 7088   Total: 22967773
forgetful_bot         Score: 2943   Total: 1471500
bob_hater             Score: 650    Total: 1300
one_dollar_bob        Score: 401    Total: 401

Bu oyunda, kapalı teklif açık artırmasını taklit edeceğiz.

Her müzayede, 4 turdan oluşuyor ve 10 turdan oluşuyor. Başlangıçta, oyuncuların parası yok. Her turun başlangıcında, her oyuncu 500 $ kazanacak ve sonra kendi teklifini yapacaktır. Teklif, sahip oldukları miktardan daha az veya eşit olmayan negatif olmayan bir tam sayı olabilir. Genellikle, en yüksek teklifi veren, raundu kazanır. Bununla birlikte, işleri daha ilginç hale getirmek için, eğer birkaç oyuncu aynı fiyatı teklif ederse, teklifleri dikkate alınmaz (bu yüzden turu kazanamaz). Örneğin, dört oyuncu 400 400 300 200 teklif ederse, 300 teklif verilir; 400 400 300 300 teklif ederlerse kimse kazanamaz. Kazanan teklif ettiklerini öder.

Bir "mühürlü teklif" açık artırması olduğu için, teklif hakkında bilecek tek bilgi sahibi kazanandır ve bir sonraki tur başladığında ne kadar ödedikleri (oyuncu ne kadar herkesin sahip olduğunu bilebilir).


puanlama

Her 4 oyuncu kombinasyonu için bir açık artırma yapılacaktır. Yani, toplamda N bot varsa, N C 4 açık artırması olacaktır. En çok turu kazanan bot, final galibi olur. Beraberlik olması durumunda, toplamda en az ödeyen bot kazanacaktır. Hala bir kravat varsa, teklifle aynı şekilde bu bağlar kaldırılır.


Kodlama

Bir Python 3 sınıfını bir üye işleviyle play_round(ve __init__gerekirse diğerlerine) uygulamalısınız. play_round3 argüman almalı (ben dahil). İkinci ve üçüncü argüman sırayla olacaktır: önceki turun galibi, ardından ne kadar ödediklerini. Kimse kazanmazsa veya ilk tursa, ikisi de -1 olur. Kimliğiniz her zaman 0 olacak ve kimliği 1–3 yalnızca bu yazıdaki konum tarafından belirlenen bir sırada diğer oyuncular olacak


Ek kurallar

1. Deterministik: İşlevinizin davranışı yalnızca bir açık artırmadaki girdi argümanlarına bağlı olmalıdır. Diğer bir deyişle, dosyalara, zamana, genel değişkenlere veya farklı açık artırmalar veya botlar arasında durumları depolayacak hiçbir şeye erişemezsiniz . Bir sözderandom üreteci kullanmak istiyorsanız, kendiniz yazmak daha iyidir (başkalarının randomPython lib'deki programlarını etkilemesini önlemek için ) ve __init__ilk turda veya içinde sabit bir tohumla sıfırladığınızdan emin olun .

2. Kişi Başına Üç Bot: En fazla 3 bot göndermenize izin verilir, böylece botlarınızın bir şekilde "işbirliği yapması" için bir strateji geliştirebilirsiniz.

3. Çok Yavaş Değil: Çok fazla açık artırma olacağından botlarınızın çok yavaş çalışmamasına dikkat edin. Botlarınız bir saniyede en az 1000 açık artırmayı bitirebilmelidir.


kontrolör

İşte kullandığım denetleyici. Tüm botlar bot_listbu yazıdaki sıraya göre ithal edilecek ve eklenecektir .

# from some_bots import some_bots

bot_list = [
    #one_bot, another_bot, 
]

import hashlib

def decide_order(ls):
    hash = int(hashlib.sha1(str(ls).encode()).hexdigest(), 16) % 24
    nls = []
    for i in range(4, 0, -1):
        nls.append(ls[hash % i])
        del ls[hash % i]
        hash //= i
    return nls

N = len(bot_list)
score = [0] * N
total = [0] * N

def auction(ls):
    global score, total
    pl = decide_order(sorted(ls))
    bots = [bot_list[i]() for i in pl]
    dollar = [0] * 4
    prev_win, prev_bid = -1, -1
    for rounds in range(10):
        bids = []
        for i in range(4): dollar[i] += 500
        for i in range(4):
            tmp_win = prev_win
            if prev_win == i: tmp_win = 0
            elif prev_win != -1 and prev_win < i: tmp_win += 1
            bid = int(bots[i].play_round(tmp_win, prev_bid))
            if bid < 0 or bid > dollar[i]: raise ValueError(pl[i])
            bids.append((bid, i))
        bids.sort(reverse = True)
        winner = 0
        if bids[0][0] == bids[1][0]:
            if bids[2][0] == bids[3][0]: winner = -1
            elif bids[1][0] == bids[2][0]: winner = 3
            else: winner = 2
        if winner == -1:
            prev_win, prev_bid = -1, -1
        else:
            prev_bid, prev_win = bids[winner]
            score[pl[prev_win]] += 1
            total[pl[prev_win]] += prev_bid
            dollar[prev_win] -= prev_bid

for a in range(N - 3):
    for b in range(a + 1, N - 2):
        for c in range(b + 1, N - 1):
            for d in range(c + 1, N): auction([a, b, c, d])

res = sorted(map(list, zip(score, total, bot_list)), key = lambda k: (-k[0], k[1]))

class TIE_REMOVED: pass

for i in range(N - 1):
    if (res[i][0], res[i][1]) == (res[i + 1][0], res[i + 1][1]):
        res[i][2] = res[i + 1][2] = TIE_REMOVED
for sc, t, tp in res:
    print('%-20s Score: %-6d Total: %d' % (tp.__name__, sc, t))

Örnekler

Bir takma ad jeneratörü gerekiyorsa, işte basit.

class myrand:
    def __init__(self, seed): self.val = seed
    def randint(self, a, b):
        self.val = (self.val * 6364136223846793005 + 1) % (1 << 64)
        return (self.val >> 32) % (b - a + 1) + a

class zero_bot:
    def play_round(self, i_dont, care): return 0

class all_in_bot:
    def __init__(self): self.dollar = 0
    def play_round(self, winner, win_amount):
        self.dollar += 500
        if winner == 0: self.dollar -= win_amount
        return self.dollar

class random_bot:
    def __init__(self):
        self.dollar = 0
        self.random = myrand(1)
    def play_round(self, winner, win_amount):
        self.dollar += 500
        if winner == 0: self.dollar -= win_amount
        return self.random.randint(0, self.dollar)

class average_bot:
    def __init__(self):
        self.dollar = 0
        self.round = 11
    def play_round(self, winner, win_amount):
        self.dollar += 500
        self.round -= 1
        if winner == 0: self.dollar -= win_amount
        return self.dollar / self.round

class fortytwo_bot:
    def play_round(self, i_dont, care): return 42

Sonuç

all_in_bot           Score: 20     Total: 15500
random_bot           Score: 15     Total: 14264
average_bot          Score: 15     Total: 20000
TIE_REMOVED          Score: 0      Total: 0
TIE_REMOVED          Score: 0      Total: 0

Kazanır all_in_bot. Bunu zero_botve fortytwo_bottoplam puanın aynı olduğunu ve toplamının kaldırıldığını unutmayın.

Bu botlar yarışmaya dahil edilmeyecek. Harika olduklarını düşünüyorsanız bunları kullanabilirsiniz.


Final yarışması 2017/11/23 14:00 (UTC) 'de yapılacak . Bundan önce botlarınızda herhangi bir değişiklik yapabilirsiniz.


5
Her turda veya her açık artırmada (10 tur süren) 500 dolar alıyorlar mı?
Stewie Griffin,

1
@KamilDrakari yarışması, rahatsız edici bot listeden çıkarıldığında tekrar başlayacak.
Colera Su

4
@Shufflepants Doğru, ama bu her zaman KotH zorluklarıyla ilgili. Geçmişte bazı insanlar gerçekten de bu noktaya kadar tüm botlara karşı koymak için sonuna kadar bir bot yaptı. Ancak bu KotH tarzı mücadelenin sadece bir parçası. Ve çoğu KotH mücadelesinin çalışması, buna dahil, avantaj o kadar büyük olmayacak. Aynı anda sadece birçok botla karşı karşıya gelebilirsiniz .. Güzel bir ilk mücadele Colera Su ve PPCG'ye hoş geldiniz! Sonuçları bekliyorum. :)
Kevin Cruijssen


2
Şu anda sıkı bir yarış ...
Zaid

Yanıtlar:


13

hard_coded

class hard_coded:
  def __init__(self):
    self.money = 0
    self.round = 0

  def play_round(self, did_i_win, amount):
    self.money += 500
    self.round += 1
    if did_i_win == 0:
      self.money -= amount
    prob = [500, 992, 1170, 1181, 1499, 1276, 1290, 1401, 2166, 5000][self.round - 1]
    if prob > self.money:
      return self.money
    else:
      return prob    

Bu bot, birçok başka sahte rastgele botlara (ve diğer cevaplardaki botların bir kısmına) karşı genetik eğitimin sonuçlarıdır. Sonunda ince ayar yaparak biraz zaman geçirdim, ancak onun yapısı aslında çok basit.

Kararlar, önceki turların sonuçlarına değil, yalnızca belirli bir parametreye dayanmaktadır.

Anahtar ilk tur gibi gözüküyor: her şeye girmen gerekiyor, 500 teklif vermek güvenli bir hamle. Çok fazla sayıda bot 499 veya 498 numaralı tekliflerle ilk hamleyi geride bırakmaya çalışıyor. İlk turu kazanmak, açık artırmanın geri kalanında büyük bir avantaj sağlıyor. Geride sadece 500 dolar var ve iyileşmek için zamanın var.

İkinci turdaki güvenli bahis 990'ın biraz üzerindedir, ancak 0 vermek bile iyi sonuç veriyor. Çok fazla teklif almak ve kazanmak, bu raundu kaybetmekten daha kötü olabilir.

Üçüncü turda, pek çok bot yükselmeyi bırakıyor:% 50'sinin şu ana kadar 1500 dolardan az parası var, bu nedenle bu turda para harcamasına gerek yok, 1170 iyi bir tradeoff. Dördüncü turda da aynı şey. İlk üçünü kaybettiyseniz, bunu çok ucuza kazanabilirsiniz ve bir sonraki için hala yeterli paranız var.

Bundan sonra, bir raund kazanmak için gereken ortalama para 1500 dolardır (bu mantıklı bir sonuçtur: herkes şimdiye kadar dörtte bir tur kazanır, daha sonra kazanmak için daha az teklif vermek sadece para israfıdır, durum dengelenir ve sadece yuvarlaktır) (bundan sonra)

Son raund tamamıyla girmeli ve diğer raundlar o zamana kadar mümkün olduğu kadar düşük ihale ile son raundu kazanmak için ayarlandı.

2000'den fazla dolar teklif ederek bir çok bot dokuzuncu turu kazanmaya çalışır, bu yüzden bunu hesaba katıp bunları aşmaya çalışıyorum (yine de son iki turu kazanamıyorum ve sonuncusu daha zor olacak).


1
Bu kazanmanın bir yolu. Tebrikler!
Luca H

Ama kabul etmeliyim ki, diğer önerileri daha çok seviyorum, çünkü başka bir düşünce şekli daha var. Diğer botlara karşı nasıl kazanacağımı denemek değil, rastgele herhangi bir bot karşısında iyi bir taktik ne olabilir.
Luca H

Anlayabiliyorum, bazı diğer gönderileri beğenmiştim (ve düşürdüm), ancak bu sınırlı bir alandaki bir sorundur ve birçok gönderim çok karmaşıktır. Sorunun özü 10 sayıdan oluşan bir dizi üretiyor, bu yüzden genel bir prosedür bulmak yerine belirli bir alan için optimizasyon yapmayı seçtim. Ben bir mühendisim, matematikçi değil.
TR

2
@LucaH, yaklaşımın bariz basitliğinin, bu belirli sayı setine ulaşmak için gereken çalışma miktarına inandığını gösteriyor. İstatistiki bir bakış açısıyla kendi botumla benzer bir şey
Zaid

1
Tabii @Zid, içine girecek çok iş var, ama kaba zorlama sadece çok ... kaba;)
Luca H

12

Ortalamanın üstü

Diğer oyuncuların sahip olduğu ortalama paranın üstünde teklif verir. Son raunttaki her şeyi teklif eder.

class above_average:
  def __init__(self):
    self.round = 0
    self.player_money = [0] * 4
  def play_round(self, winner, winning_bid):
    self.round += 1
    self.player_money = [x+500 for x in self.player_money]
    if winner != -1:
      self.player_money[winner] -= winning_bid
    if self.round == 10:
      return self.player_money[0]
    bid = sum(self.player_money[1:]) / 3 + 1
    if bid > self.player_money[0]:
      return self.player_money[0]
    return min(self.player_money[0], bid)

12

Ben bile

class I_Dont_Even:
	def __init__(self):
		self.money = 0
		self.round = 0
	def play_round(self, loser, bid):
		self.money += 500 - (not loser) * bid
		self.round += 1
		return self.money * (self.round & 1 or self.round == 10)

Sadece garip mermilere ve son tura katılır.


7

Unutkan bot ne kadar paraya sahip olduğunu bilmiyor, bu yüzden sadece bu raunda verdiği parayı koyuyor. Sonunda biraz parası bulursa, sadece bir yardım kuruluşuna bağışlar.

class forgetful_bot:
  def play_round(self, winner, amt):
    return 500

15
Ben olumsuz oyuncu değilim, ama belki de 'botunuza hiç çaba harcamamış olmanızdan dolayıdır
Mischa

9
Bu ilk cevaplardan biri. Topu yuvarlamak için bir şey gerekir.
Khuldraeseth na'Barya

Oy vermedim ama belki topun yuvarlanması için bir şey gerekli olsa da, belki biraz daha ilginç bir şey mi yaptınız? Bu One Dollar Bob ile pratik olarak aynıdır Özellikle de tür almak için kullanıldığı başladı
HyperNeutrino

7

Bir üst

Python hakkında fazla bir şey bilmiyorum, bu yüzden bir çeşit hata yapabilirim

class one_upper:
    def __init__(self): 
        self.money = 0
        self.round = 0
    def play_round(self, winner, win_amount):
        self.money += 500
        if winner == 0: self.money -= win_amount
        self.round += 1
        bid = win_amount + 1
        if self.money < bid or self.round == 10:
            bid = self.money
        return bid

önceki kazanan teklifinden 1 veya daha yüksek olan teklifler veya son rauntta giriĢtirme.

Gelecekte win_amount-1 olduğunda farklı bir stratejiye karar verebilirim


7

Hasta Botu

class patient_bot:
    def __init__(self):
        self.round = 0
        self.money = 0
    def rand(self, seed, max):
        return (394587485 - self.money*self.round*seed) % (max + 1)
    def play_round(self, winner, amount):
        self.round += 1
        self.money += 500
        if winner == 0:
            self.money -= amount
        if self.round < 6:
            return 0
        else:
            bid = 980 + self.rand(amount, 35)
            if self.money < bid or self.round == 10:
                bid = self.money
            return bid

İlk beş tur için hiçbir şey teklif etmiyor, sonraki dört tur için ~ 1000 dolar teklif ediyor ve son turda sahip olduğu her şeyi teklif ediyor.


7

Copycat Veya Sad

Üçüncü ve son bot.
Bu bot, bir önceki kazananla aynı tutarı teklif edecektir (kendisi de dahil). Ancak, eğer yapacak kadar parası yoksa üzücü olacak ve bunun yerine gözyaşı ile birlikte 1 dolarlık bir fatura teklif edecek. Son turda her şey yoluna girecek.

class copycat_or_sad:
  def __init__(self):
    self.money = 0
    self.round = -1
  def play_round(self, winner, win_amount):
    # Default actions:
    #  Collect 500 dollars
    self.money += 500
    #  If it was the winner: subtract the win_amount from his money
    if winner == 0:
      self.money -= win_amount
    #  One round further
    self.round += 1

    # If it's the final round: bid all-in
    if self.round == 9:
      return self.money
    # Else-if there was no previous winner, or it doesn't have enough money left: bid 1
    if win_amount < 1 or self.money < win_amount:
      return 1
    # Else: bid the exact same as the previous winner
    return win_amount

Python'da asla program yapmam, bu yüzden herhangi bir hata görürseniz bana bildirin.


2
Bu -1, ilk açık artırmada teklif veriyor.
Okx

7

Test sürüşü

Steadybox'ın yeni gönderilere ekleyerek oluşturduğu önceki bir deneme çalışmasını düzenledim .

Buraya gönderiyorum, bu yüzden bağlantının daha yeni sürümlerle güncellenebileceği bir yer var, bu gönderi bir topluluk wikidir, bu nedenle yeni bir gönderi gönderirseniz, eski bir yazıyı değiştirirseniz veya bir şey görürseniz güncellemek için çekinmeyin başka bir gönderimden yeni!

İşte test çalıştırması için link! (S Y)


yıkıcı olması gereken botumun iki "gerçek" gönderimi aştığını mı söylemeliyim?
thegreatemu

@ thegreatemu Botların birbirleriyle nasıl etkileşime girdiğini görmek ilginç. Tek bir yeni bot sıralamayı önemli ölçüde değiştirebilir. Bulduğum ilginç bir şey de, eğer histokratın silinen kara liste botu katılırsa, iki botumun sıralamaların en üstüne çıkması. :)
Jo.

6

Yarısı

Bu bot, geride kalabileceği final turu haricinde, kalanların yarısını teklif eder.

class half_in:
  def __init__(self):
    self.money = 0
    self.round = -1
  def play_round(self, winner, win_amount):
    # Default actions:
    #  Collect 500 dollars
    self.money += 500
    #  If it was the winner: subtract the win_amount from his money
    if winner == 0:
      self.money -= win_amount
    #  One round further
    self.round += 1

    # If it's the final round: bid all in
    if self.round == 9:
      return self.money
    # Else: Bid half what it has left:
    return self.money / 2

Python'da asla program yapmam, bu yüzden herhangi bir hata görürseniz bana bildirin.


6

Graylist

class Graylist:
  def __init__(self):
    self.round = 0
    self.player_money = [0] * 4
    self.ratios = {1}
    self.diffs = {0}
  def play_round(self, winner, winning_bid):
    self.round += 1
    if winner != -1:
      if winner >0 and winning_bid>0:
        self.ratios.add(self.player_money[winner]/winning_bid)
        self.diffs.add(self.player_money[winner]-winning_bid)
      self.player_money[winner] -= winning_bid
    self.player_money = [x+500 for x in self.player_money]
    tentative_bid = min(self.player_money[0],max(self.player_money[1:])+1, winning_bid+169, sum(self.player_money[1:])//3+169)
    while tentative_bid and (tentative_bid in (round(m*r) for m in self.player_money[1:] for r in self.ratios)) or (tentative_bid in (m-d for m in self.player_money[1:] for d in self.diffs)):
      tentative_bid = tentative_bid - 1
    return tentative_bid

Histocrat tarafından yapılan kara liste gönderiminden esinlenilen bu bot, diğer oyuncuların tüm önceki bahislerinde kazandıkları bahisleri hem tam paralarına kıyasla bahis oranları, hem de bahis miktarları ile tam miktarları arasındaki fark olarak hatırlıyor . Beraberlik kaybetmekten kaçınmak için (görünüşe göre bu yarışmada aslında büyük bir faktördür) rakiplerinin o anki paraları göz önüne alındığında aynı sonuçları verebilecek herhangi bir sayıya girmekten kaçınır.

EDIT: teklifin başlangıç ​​değeri şu anda en düşük değeri kullanır: şu anki parası, en zengin rakibin parasından 1, son kazanan bahisten X, ya da rakiplerin ortalama parasından daha fazla Y. X ve Y muhtemelen yarışmanın bitiminden önce değiştirilecek olan sabitlerdir.


6

AverageMine

Bu oyuncu, her turdaki kazananın yüzdesini (teklif / toplam para) hesaplar ve diğer tüm oyunculardan daha fazla parası olmadığı sürece (toplam para * ortalama kazanma yüzdesi + 85) teklifini verir, ardından 1 en yüksek rakibiden daha fazla teklif verir. . Başlangıç ​​tutarının% 99,0 oranında teklifiyle başlar.

class AverageMine:
    nplayers = 4
    maxrounds = 10
    def __init__(self):
        self.money = [0] * self.nplayers
        self.wins = [0] * self.nplayers
        self.round = 0
        self.average = 0
    def play_round(self, winner, win_amt):
        self.round += 1
        for i in range(self.nplayers):
            if i == winner:
                self.average = (self.average * (self.round - 2) + (win_amt / self.money[i])) / (self.round - 1)
                self.money[i] -= win_amt
                self.wins[i] += 1
            self.money[i] += 500
        if self.round == 1:
            return int(0.990 * self.money[0])
        elif self.round < self.maxrounds:
            if self.money[0] > self.money[1] + 1 and self.money[0] > self.money[2] + 1 and self.money[0] > self.money[3] + 1:
                return max(self.money[1],self.money[2],self.money[3]) + 1
            bid = int(self.average * self.money[0]) + 85
            return min(self.money[0],bid)
        else:
            bid = self.money[0]
            return bid

6

Eenie Meanie Daha fazlası

Bu oyuncu, bir değişken hariç Meanie ile aynıdır. Bu sürüm daha agresif bir şekilde teklif veriyor ve bazı oyuncuların müzayedenin değerli olduğunu düşündüğünden daha fazla harcamasına neden oluyor.

class eenie_meanie_more:
    def __init__(self):
        self.money = [0] * 4
        self.rounds = 11
        self.total_spent = 0

    def play_round(self, winner, winning_bid):
        self.money = [x+500 for x in self.money]
        self.rounds -= 1
        if winner != -1:
            self.money[winner] -= winning_bid
            self.total_spent += winning_bid
        bid = 500
        if self.rounds > 0 and self.total_spent < 20000:
            bid = int((20000 - self.total_spent)/self.rounds/4)+440
        return min(bid, max(self.money[1:])+1, self.money[0])

5

Distribütör

Bu bot bir raund kaybettiğinde, fazladan nakit parayı bir sonraki turun tümüne dağıtır. İlk turda diğerlerinin 500 $ ile bağ kuracaklarını ve eleneceklerini düşünerek 499 $ 'a koyuyor.

class distributer:
  def __init__(self):
    self.money = 0
    self.rounds = 11
  def play_round(self, winner, amt):
    self.money += 500
    self.rounds -= 1
    if self.rounds == 10:
      return 499
    if winner == 0:
      self.money -= amt
    return ((self.rounds - 1) * 500 + self.money) / self.rounds

1
Kullanma roundsyerine self.roundshatalara neden olur. İle aynı money.
Jeremy Weirich

5

Meanie

Bu oyuncu, oyuncu sayısı ve kalan turlar arasında ortalama teklifi almak için oyuna girecek olan toplam parayı alır. Bu hedef şu anda elinde tutulan diğer oyuncuların hepsinden daha fazlaysa, teklifini en büyük rakibi artı bir dengesine düşürür. Eğer oyuncu hedefini karşılayamazsa, hepsi içeridedir.

class meanie:
    def __init__(self):
        self.money = [0] * 4
        self.rounds = 11
        self.total_spent = 0

    def play_round(self,winner,winning_bid):
        self.money = [x+500 for x in self.money]
        self.rounds -= 1
        if winner != -1:
            self.money[winner] -= winning_bid
            self.total_spent += winning_bid
        bid = 500
        if self.rounds > 0 and self.total_spent < 20000:
            bid = int((20000 - self.total_spent)/self.rounds/4)+1
        return min(bid,max(self.money[1:])+1,self.money[0])

5

Kazananı Yen

Şimdiye kadar en çok galibiyet alan oyuncudan 1 teklif ver

class BeatTheWinner:
    nplayers = 4
    maxrounds = 10
    def __init__(self):
        self.money = [0] * self.nplayers
        self.wins = [0] * self.nplayers
        self.round = 0

    def play_round(self, winner, win_amt):
        self.round += 1
        for i in range(self.nplayers):
            self.money[i] += 500
            if i == winner:
                self.money[i] -= win_amt
                self.wins[i] += 1
        mymoney = self.money[0]
        for w,m in sorted(zip(self.wins, self.money),reverse=True):
            if mymoney > m:
                return m+1
        #if we get here we can't afford our default strategy, so
        return int(mymoney/10)

4
Olun her m,wdoğru sırayla?
Jo.

5

Eksi bir

class minus_one:
    def __init__(self):
        self.money = 0
    def play_round(self, winner, amount):
        self.money += 500
        if winner == 0:
            self.money -= amount
        return self.money - 1

5

Teklif Daha Yüksek

class bid_higher:
    def __init__(self):
        self.dollar = 0
        self.round = 0
    def play_round(self, winner, win_amount):
        self.dollar += 500
        self.round += 1
        inc = 131
        if winner == 0: self.dollar -= win_amount
        if self.round == 10: return self.dollar
        if win_amount == 0: win_amount = 500
        if self.dollar > (win_amount + inc):
            return win_amount + inc
        else:
            if self.dollar > 1:
                return self.dollar -1
            else:
                return 0

Hala python öğrenme; son kazanandan biraz daha yüksek teklif verin.


PPCG'ye Hoşgeldiniz! Sizin bot değiştirmek eğer daha iyi bir skor alır gibi görünüyor inc = 100için inc = 101.
Steadybox

Burada gerçekten kendi menfaatlerime karşı geliyorum, ancak sıraları takip ederek ve son rauntta all-in yaparak skorunuzu kolayca artırabilirsiniz;)
Leo

Önerileriniz için teşekkürler; Son turda bir all-in ekledim, artış
ayarını yaptım

Merhaba, umarım sakıncası yoktur, ancak tüm mevcut gönderilerle bir test tezgahı hazırladım ve kodunuzun bazen son rauntta geçersiz değerler döndürdüğünü öğrendim, bu yüzden hatayı yeniden düzenleyerek düzelttim sipariş birkaç satır. Sahip olmadığınız bir şeyi değiştirdiysem özür dilerim, değişiklikleri geri almaktan ve hatayı başka bir şekilde düzeltmekten çekinmeyin!
Leo

@Leo: Sorun değil, ilgilendiğiniz için teşekkürler ..
rancid_banana

4

FiveFiveFive

İlk turu atlar ve kalan turlarda 555 $ teklif eder. Son rauntta, eğer diğer 2 bot aynı miktarda değilse (ve büyük olasılıkla bağlayamazlarsa) girecek.

class FiveFiveFive:
    nplayers = 4
    maxrounds = 10
    def __init__(self):
        self.money = [0] * self.nplayers
        self.wins = [0] * self.nplayers
        self.round = 0

    def play_round(self, winner, win_amt):
        self.round += 1
        for i in range(self.nplayers):
            self.money[i] += 500
            if i == winner:
                self.money[i] -= win_amt
                self.wins[i] += 1
        if self.round == 1:
            return 0
        elif self.round < self.maxrounds:
            return min(555, self.money[0])
        else:
            bid = self.money[0]
            return bid if self.money.count(bid) < 3 else bid-1

4

Neredeyse Hepsi İçinde

class Almost_All_In:
	def __init__(self):
		self.money = 0
		self.round = 0
	def play_round(self, loser, bid):
		self.money += 500 - (not loser) * bid
		self.round += 1
		return self.money - self.round % 3 * 3 - 3

Her zaman tekliflerinden biraz daha az teklif verir.


4

Hızla Yükseliyor

Her turda parasının fraksiyonlarını artırarak teklif verir (lütfen Python'u kullandığımdan beri herhangi bir hata olursa bana bildirin)

class escalating:
  def __init__(self):
    self.money = 0
    self.round = 0
  def play_round(self, winner, win_amount):
    # Default actions:
    #  Collect 500 dollars
    self.money += 500
    #  If it was the winner: subtract the win_amount from his money
    if winner == 0:
      self.money -= win_amount
    #  One round further
    self.round += 1

    # bid round number in percent times remaining money, floored to integer
    return self.money * self.round // 10

4

Ortalamanın altında

Yukarıdaki ortalamaya benzer, ancak biraz daha düşük olur

class below_average:
  def __init__(self):
    self.round = 0
    self.player_money = [0] * 4
  def play_round(self, winner, winning_bid):
    self.round += 1
    self.player_money = [x+500 for x in self.player_money]
    if winner != -1:
      self.player_money[winner] -= winning_bid
    if self.round == 10:
      return self.player_money[0]
    bid = sum(self.player_money[1:]) / 3 - 2
    if bid > self.player_money[0]:
      return self.player_money[0]
    return min(self.player_money[0], bid)

4

HighHorse

Bu oyuncu, tüm parasını eksi, geçerli olduğu tur sayısının tamamını girdiği son tur hariç, teklif eder.

class HighHorse:
    maxrounds = 10
    def __init__(self):
        self.money = 0
        self.round = 0
    def play_round(self, winner, win_amt):
        self.round += 1
        if 0 == winner:
            self.money -= win_amt
        self.money += 500
        if self.round < self.maxrounds:
            return self.money - self.round
        else:
            bid = self.money
            return bid

4

scheduler'in

Maksimumunun altında bir tane teklif vermekle hepsini içeri girmek arasında geçiş yapar.

class Swapper:
    def __init__(self):
        self.money = 0
        self.round = 0
    def play_round(self, loser, bid):
        self.money += 500 - (not loser) * bid
        self.round += 1
        if self.round & 1:
            return self.money - 1
        return self.money

Steadybox'ın eksi_onunu yenebilecek bir şey bulmam gerektiğini düşündüm. :)


4

Modüler Kara Liste

class blacklist_mod:
  def __init__(self):
    self.round = 0
    self.player_money = [0] * 4
    self.blacklist = {0, 499}
  def play_round(self, winner, winning_bid):
    self.round += 1
    self.player_money = [x+500 for x in self.player_money]
    if winner != -1:
      self.player_money[winner] -= winning_bid
      self.blacklist.add(winning_bid % 500)
      self.blacklist |= {x % 500 for x in self.player_money[1:]}
    tentative_bid = self.player_money[0]
    autowin = max(self.player_money[1:])+1
    if tentative_bid < autowin:
      while tentative_bid and (tentative_bid % 500) in self.blacklist:
        tentative_bid = tentative_bid - 1
    else:
      tentative_bid = autowin
    self.blacklist.add(tentative_bid % 500)
    return tentative_bid

Modulo 500 ile uyumlu olmayan en yüksek tutarı daha önce görülmemiş herhangi bir sayıya yatırır.

Garantili bir kazanç elde edince kara listenin uygulanmaması için düzenlenmiştir.


İlginçtir ki, diğer botunuzdaki son güncellemenin bu botu olumsuz yönde etkilediği görülüyor. Şu anda, blacklist_modbeşinci afiş üzerinde iken, blacklistikinci sırada yer alıyor. Eski sürümü blacklistyerine kullanılmışsa blacklist, altıncı yere düşer, ancak blacklist_mod liderlik eder !
Steadybox

blacklistTamamen atmak bile daha sağlam bir ipucu veriyor gibi görünüyor , ama bu sonuçsuz. blacklist_mod
Steadybox

Oh, teşekkürler, bu mantıklı - eski özel durum mantığı olmadan erken aynı algoritmaya yakınlar, bu nedenle birbirlerinin ayak parmaklarına basıyorlar. Sanırım sadece orijinal botu kaldıracağım; Etrafında kalmak için iyi bir sebep düşünemiyorum.
histocrat

4

Heurist

Heurist nerede çizgi çizmek için bilmesi için, tekrarlanabilir olasılık biri olarak bu oyunu davranır.

Aynı zamanda hatalı bir durum olduğu için kazanabildiği zaman kazanabileceği minimum seviyeyi teklif eder.

class heurist:
    def __init__(self):
        self.money = 0
        self.round = -1
        self.net_worth = [0] * 4
    def play_round(self, winner, bid):
        self.round += 1
        self.money += 500
        if winner == 0: self.money -= bid
        if winner != -1: self.net_worth[winner] -= bid
        self.net_worth = [x+500 for x in self.net_worth]
        max_bid = [498,1000,1223,1391,1250,1921,2511,1666,1600,5000][self.round]
        if self.money > max_bid:
            return 1 + min(max_bid,max(self.net_worth[1:3]))
        else:
            return self.money

Yasal Uyarı: max_biddeğişebilir


4

bob_hater

Bu bot Bob'u sevmiyor ve bu nedenle Bob'a karşı kazanmak için her zaman 2 $ teklif verecek.

class bob_hater:
    def play_round(bob,will,loose):
        return 2

4

Hava atmak

Bu, gerçekten karmaşık bir şey gerektirmeyen durumlarda matematik yeteneğini gösteren kişidir. Son tura kadar (içinde girdiği yer), teklifini belirlemek için lojistik bir model kullanıyor, daha çok düşmanı kalan paralarının daha büyük bir kısmı varsa.

class Showoff:
  def __init__(self):
      self.moneys = [0, 0, 0]
      self.roundsLeft = 10
  def play_round(self, winner, winning_bid):
      import math
      self.moneys = [self.moneys[0] + 500,
                     self.moneys[1] + 1500,
                     self.moneys[2] + 1500]
      self.roundsLeft -= 1
      if winner > 0:
          self.moneys[1] -= winning_bid
      if winner == 0:
          self.moneys[0] -= winning_bid
      if self.roundsLeft == 0:
          return self.moneys[0]
      ratio = self.moneys[1] / self.moneys[2]
      logisticized = (1 + (math.e ** (-8 * (ratio - 0.5)))) ** -1
      return math.floor(self.moneys[0] * logisticized)

Kullanılan lojistik eğrisi f (x) = 1 / (1 + e -8 (x-0.5) ) olup, x mevcut düşman parasının turdaki toplam potansiyel para parasına oranıdır. Diğerleri ne kadar fazlaysa, o kadar fazla teklif verir. Bu, ilk turda neredeyse 500 dolar değerinde bir teklif vermenin olası yararına sahip.


3

AntiMaxer

Tüm oyuncuların parasının karşılığını alabileceğimiz en yüksek miktarı eşleştir. Herhangi bir botun o turdaki all-in'e bağlanmasına neden olur.

class AntiMaxer:
    nplayers = 4
    maxrounds = 10
    def __init__(self):
        self.money = [0] * self.nplayers
        self.wins = [0] * self.nplayers
        self.round = 0

    def play_round(self, winner, win_amt):
        self.round += 1
        for i in range(self.nplayers):
            self.money[i] += 500
            if i == winner:
                self.money[i] -= win_amt
                self.wins[i] += 1
        return max((m for m in self.money[1:] if m<=self.money[0]),
                   default=0)    

3

Basit bot

class simple_bot:
    def __init__(self):
        self.round = 0
        self.money = 0
    def rand(self, seed, max):
        return (394587485 - self.money*self.round*seed) % (max + 1)
    def play_round(self, winner, amount):
        self.round += 1
        self.money += 500
        if winner == 0:
            self.money -= amount
        bid = 980 + self.rand(amount, 135)
        if self.money < bid or self.round == 10:
            bid = self.money
        return bid

Neredeyse Hasta Bot ile aynı, ancak hasta olarak değil. Bir alır çok olsa da, ondan daha iyi bir puan.


3

Wingman 2

Bir kanatlı iyidir, iki kişi daha iyi olmalı?

class wingman_2:
    def __init__(self):
        self.dollar = 0
        self.round = 0
    def play_round(self, winner, win_amount):
        self.round += 1
        self.dollar += 500
        inc = 129
        if win_amount == 0: win_amount = 500
        if winner == 0: self.dollar -= win_amount
        if self.round == 10: return self.dollar
        if self.dollar > win_amount + inc:
            return win_amount + inc
        else:
            if self.dollar > 1: return self.dollar -1
            else:
                return 0

Sınıfta şeyler için girinti gerektiğinden kod çalışmaz
HyperNeutrino


1
Sonuçların diğer botların havuzuna çok hassas olduğunu buldum; Artış değerindeki küçük değişiklikler orantısız sonuçlara sahip görünüyor.
rancid_banana
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.