Điểm Yahtzee tốt nhất


26

Yahtzee là một trò chơi được chơi với năm con xúc xắc sáu mặt và một bảng điểm với mười ba ô khác nhau để điền vào một điểm. Mỗi ô có quy tắc ghi điểm riêng:

  • 1s, 2s, 3s, 4s, 5s, 6s tất cả các điểm số bằng tổng số xúc xắc tương ứng (nghĩa là một cuộn [3, 2, 3, 1, 5] được ghi là 3 giây sẽ được thưởng 6 điểm: 3 cho mỗi 3).
  • 3 loại một và 4 loại (như âm thanh của chúng, ba hoặc bốn con xúc xắc lăn giống nhau) điểm số bằng tổng của cả năm con xúc xắc.
  • Full house (hai con xúc xắc hiển thị một giá trị, ba con còn lại hiển thị khác) đạt 25 điểm
  • Nhỏ thẳng (bốn giá trị liên tiếp) đạt 30 điểm
  • Lớn thẳng (tất cả các giá trị liên tiếp) đạt 40 điểm
  • Yahtzee (tất cả súc sắc hiển thị cùng một giá trị) đạt 50 điểm

Thứ mười ba (cơ hội) có ý nghĩa trong trò chơi, nhưng không nhiều cho thử thách này; Ngoài ra, trò chơi có phần thưởng cho thêm Yahtzees không có ý nghĩa ở đây. Bởi vì thử thách là ...

Đưa ra năm con xúc xắc làm đầu vào (năm số nguyên 1-6, tuy nhiên đầu vào thuận tiện, bạn có thể giả sử đầu vào luôn hợp lệ), xuất số điểm cao nhất có thể cho 'bàn tay' đó. Đối với mục đích của thử thách này, chỉ có các phương pháp cho điểm trong danh sách trên là hợp lệ (cụ thể, cơ hội không phải là hộp điểm hợp lệ cho thử thách này). Điểm số phải là đầu ra dưới dạng giá trị số thập phân của nó, cho dù đó là số nguyên hay biểu diễn chuỗi của nó, bất cứ điều gì. Nó phải được nhận ra ngay lập tức như một con số. Khoảng trắng hàng đầu / dấu là tốt, đây là về việc ghi điểm và không trình bày.

Code golf, vì vậy câu trả lời có ít byte nhất trong một ngôn ngữ nhất định sẽ thắng. Sơ hở tiêu chuẩn bị cấm.

Các trường hợp thử nghiệm

(Lưu ý rằng tất cả đều độc lập, thử thách là ghi một 'xúc xắc'):

in: 1 5 4 3 2
out: 40
in: 1 1 4 3 1
out: 10
in: 2 2 6 5 3
out: 6
in: 2 4 2 4 6
out: 8
in: 1 1 1 1 1
out: 50
in: 5 2 5 3 6
out: 10
in: 1 6 3 4 2
out: 30
in: 1 3 1 1 3
out: 25
in: 6 5 5 6 6
out: 28
in: 1 2 3 5 6
out: 6

3
Thay vào đó chúng ta nên đóng câu hỏi cũ hơn? IMO đây là một câu hỏi hay hơn câu hỏi đó ...
Giuseppe

5
IMO đây hoàn toàn không phải là một bản sao của trò chơi yahtzee Điều này nói rõ đây là điểm số cao nhất cho một tay, trong đó câu hỏi còn lại là yêu cầu toàn bộ số điểm từ danh sách các cuộn chết. Cuối cùng, và quan trọng nhất, tôi không thấy bất kỳ câu trả lời nào từ bản dupe có thể có thể được sử dụng ở đây trong kịch bản "sao chép-dán". Vui lòng xem xét mở lại.
DevelopingDeveloper


2
FWIW, tôi đã nhận ra câu hỏi cũ hơn khi tôi đặt câu hỏi này cùng nhau. Suy nghĩ của tôi lặp lại những gì @DevelopingDeveloper nói. Đã từng làm điều này như một bài tập trước đây, tôi đã tìm thấy một số cơ hội thú vị để tối ưu hóa quá trình này. Tôi cũng chỉ nghĩ rằng đây là một thử thách gọn gàng hơn.
brhfl

"Thứ mười ba (cơ hội) có ý nghĩa trong trò chơi, nhưng không quá nhiều cho thử thách này" Vậy nó có được tính không?
Unihedron

Câu trả lời:


6

R , 146 141 byte

function(d)max(unique(d<-sort(d))*(g=table(d)),any(g>2)*sum(d),all(2:3%in%g)*25,(s=sum((R=diff(d))==1))<4&all(R<2)*30,(s>3)*40,(0==sd(d))*50)

Hãy thử trực tuyến!

Vượt trội bởi plannapus

Lấy đầu vào dưới dạng danh sách và trả về điểm số.

vô dụng một chút:

function(d){
 d <- sort(d)
 u <- unique(d)                  # unique dice
 g <- table(d)                   # table of counts
 Ns <- u*g                       # scores as 1s, 2s, ... etc.
 NKind <- any(g>2)*sum(d)        # 3 or 4 of a kind if any counts are at least 3
 FHouse <- all(2:3%in%g)*25      # full house is 25 if 2 & 3 are in counts
 R <- diff(d)                    # consecutive differences
 s <- sum(R==1)                  # sum of differences equal to 1
 sStraight <- s<4 &              # if the number of 1s is 3 and
               all(R<2)*30       # no consecutive numbers are 2 apart
 bStraight <- (s>3)*40           # all 1s means big straight
 Yahtzee <- sd(d)==0             # sd = 0 means all are equal
 max(Ns,NKind,FHouse,sStraight,bStraight,Yahtzee)
}


f(c(1,2,3,5,6))thất bại - nó sẽ mang lại 6 và thay vào đó mang lại 30. Có vẻ như điều này là do bạn đang đếm xem có bao nhiêu cặp (sắp xếp sau) khác nhau bởi một, thực tế là bốn cho chuỗi trên, mặc dù nó không phải là một đường thẳng của bốn. Tôi nghĩ rằng tôi đã gặp phải điều này khi tôi thực hiện điều này như một bài tập trước đây và có lẽ tôi nên thêm nó như một trường hợp thử nghiệm ...
brhfl

@brhfl cái này đã được sửa.
Giuseppe


4

R, 136 134 byte

function(n,y=table(factor(n,1:6)),z=sum(!diff(diff(sort(n)))))max(1:6*y,c(25,sum(n),10*3:5)[c(all(y<4&y-1),any(y>2),z>1,z>2,any(y>4))])

Chơi xuống 2 byte nhờ @Giuseppe !

Thụt lề

function(n, #vector of die scores
         y=table(factor(n,1:6)), #Contingency table
         z=sum(!diff(diff(sort(n))))) #Diff of diff of ordered scores
    max(1:6*y,
        c(25,sum(n),10*3:5)*c(all(y<4&y-1), #Full house
                            any(y>2), #3 and 4 of a kind
                            z>1, #Small straight
                            z>2, #Long straight
                            any(y>4))] #Yahtzee

Một vài trường hợp thử nghiệm:

> f=function(n,y=table(factor(n,1:6)),z=sum(!diff(diff(sort(n)))))max(1:6*y,c(25,sum(n),10*3:5)*c(all(y<4&y-1),any(y>2),z>1,z>2,any(y>4)))
> f(c(2,4,2,4,6))
[1] 8
> f(c(1,2,3,5,6))
[1] 6
> f(c(6,5,5,6,6))
[1] 28
> f(c(6,5,3,1,4))
[1] 30
> f(c(6,5,3,2,4))
[1] 40

1
Huh, tôi đã xem xét factormột giây nóng trước khi tôi bị phân tâm. Nhưng tôi nghĩ rằng nếu tôi sử dụng cách tiếp cận của bạn với z( strong câu trả lời của tôi), tôi có thể đánh gôn xuống 134 ...
Giuseppe

Ngoài ra, bạn có thể lưu ba byte bằng cách sử dụng all(y<4&y-1)và sử dụng *thay vì [và đặt ynội tuyến thay vì làm đối số chức năng và nó vẫn vượt qua tất cả các trường hợp kiểm tra: Hãy thử trực tuyến!
Giuseppe

Ngoài ra, tôi đã cấu trúc lại maxvà tôi nghĩ rằng nó đã lưu byte từ thiết lập ynội tuyến.
Giuseppe

3

Mẻ, 359 byte

@echo off
set/at=s=m=r1=r2=r3=r4=r5=r6=0
for %%r in (%*)do set/a"m+=!(m-r%%r),r%%r+=1,t+=%%r,p=s-r%%r*%%r,p&=p>>9,s-=p
goto %m%
:1
if %r1% neq %r6% set s=40&goto g
:2
set/at=r3*r4*(r2*(r1+r5)+r5*r6)
if %t% gtr 0 set s=30
goto g
:3
set/a"s=r1^r2^r3^r4^r5^r6"
if %s%==1 if %t% lss 25 set s=25&goto g
:4
set/as=t
goto g
:5
set s=50
:g
echo %s%

Giải trình:

@echo off
set/at=s=m=r1=r2=r3=r4=r5=r6=0
for %%r in (%*)do set/a"m+=!(m-r%%r),r%%r+=1,t+=%%r,p=s-r%%r*%%r,p&=p>>9,s-=p
goto %m%

Tính số xúc xắc cho mỗi số, cộng với tối đa, cộng với tổng số xúc xắc, cộng với tổng số xúc xắc cao nhất của cùng một số.

:1
if %r1% neq %r6% set s=40&goto g

Nếu tất cả các con xúc xắc là khác nhau, điều này có thể là một đường thẳng dài, nhưng điều đó cần phải có 1hoặc không 6.

:2
set/at=r3*r4*(r2*(r1+r5)+r5*r6)
if %t% gtr 0 set s=30
goto g

Mặt khác, hoặc nếu nhiều nhất là hai con xúc xắc giống nhau, thì đây vẫn có thể là một đoạn thẳng ngắn. Phải có ít nhất a 3và a 4và cũng là sự kết hợp của bốn số còn lại.

:3
set/a"s=r1^r2^r3^r4^r5^r6"
if %s%==1 set s=25&goto g

Nếu có ba con xúc xắc giống nhau, hãy kiểm tra một ngôi nhà đầy đủ, kể từ đó 3^2==1. Tuy nhiên, một số ngôi nhà đầy đủ, chẳng hạn như 6s và 5s, có điểm số cao hơn 3 loại.

:4
set/as=t
goto g

Mặt khác, hoặc nếu có bốn cái giống nhau, thì tổng điểm.

:5
set s=50

Và nếu có năm cái giống nhau, thì Yahtzee!

:g
echo %s%

Đầu ra điểm số tốt nhất.


1
Cảm ơn đã nhắc nhở tôi về cạm bẫy đầy đủ [5,5,6,6,6] được bảo vệ toàn diện - Tôi đã thêm điều này như một trường hợp thử nghiệm. Tôi biết có một vài trường hợp rìa kỳ lạ mà tôi đã quên.
brhfl

3

Thạch , 58 byte

ċЀ`Ṁ>2ȧS
ṢI=1Ạµ-ƤẸ,E;ṢI$E$;⁸Lƙ`Ṣ⁼2,3¤a3,5,4,2.Ṁ×⁵»Ç»Sƙ`Ṁ$

Hãy thử trực tuyến!


Điều đó hoàn toàn hợp lệ, nhưng tôi tò mò và không biết Jelly đủ để tự mình giải quyết nó ... tại sao nhà đầy đủ trở lại 25.0trong khi không có trường hợp nào khác có dấu vết .0?
brhfl

@brhfl Chà, bởi vì nó được suy ra là 2.5 × 10 = 25.0(số học trôi nổi), trong khi những cái khác như 30được suy ra là 3 × 10 = 30(số học số nguyên).
Erik the Outgolfer

2
Cảm ơn! Tôi đã không thực sự từ câu hỏi của tôi tốt; Tôi tò mò hơn về phương pháp mà bạn đang sử dụng để phát hiện ra một ngôi nhà đầy đủ dẫn đến việc làm toán khác đi - nhưng bây giờ tôi nghĩ về nó, tôi đoán rằng nó chỉ là người chơi gôn để làm 2.5, 3, 4, 5 * 10 so với 25, 30, 40, 50. Hãy nghĩ rằng tôi đã trả lời câu hỏi của riêng tôi.
brhfl

@brhfl Chính xác, vì × 10là 2 byte, 2.5giống như 2 byte 253,5,4lưu lại 3 byte 30,50,40, nên đã lưu 3 + 0 - 2 = 1 byte.
Erik the Outgolfer

2

Perl 6 , 159 byte

->\b{max map {$_(b)},|(1..6).map({*{$_}*$_}),{.kxxv.sum*?.values.grep(*>2)},{25*(6==[*]
.values)},30*?*{3&4&(1&2|2&5|5&6)},40*?*{2&3&4&5&(1|6)},50*(*.keys==1)}

Hãy thử trực tuyến!

Vì đầu vào có thể được chấp nhận "tuy nhiên là thuận tiện", nên hàm của tôi lấy nó làm ví dụ của Baglớp, là một thùng chứa có tính đa bội. A Bagcũng là một container kết hợp; $bag{$key}trả lại bao nhiêu lần $keyxảy ra trong túi.

Phần lớn của hàm chỉ là một danh sách các hàm đánh giá từng tay Yahtzee có thể, trả về điểm cho tay đó hoặc bằng 0 nếu các điều kiện cho tay không được đáp ứng.

  • |(1..6).map({ *{$_} * $_ })là danh sách sáu hàm đánh giá tay dựa trên các lần chạy lặp lại của các số 1-6. Các đầu hàng |san phẳng danh sách này vào danh sách xung quanh.
  • {.kxxv.sum * ?.values.grep(* > 2) }đánh giá tay 3 và 4 của một loại. .kxxvtrên một Bagtrả về các khóa được lặp đi lặp lại với bội số của mỗi, khôi phục danh sách ban đầu của các cuộn chết, và .sumtất nhiên là tổng hợp súc sắc. Tổng đó được nhân với một giá trị boolean ( ?) là đúng nếu túi .values(nghĩa là bội số) chứa giá trị lớn hơn 2.
  • { 25 * (6 == [*] .values) }đánh giá tay nhà đầy đủ. 25 được nhân với một giá trị boolean, điều này đúng nếu tích của bội số là 6, điều này đối với năm con xúc xắc chỉ có thể xảy ra nếu một con là 3 và con kia là 2.
  • 30 * ?*{ 3 & 4 & (1 & 2 | 2 & 5 | 5 & 6) }đánh giá bàn tay nhỏ thẳng. Đó là một WhateverCodechức năng; ngôi sao thứ hai *Bag. Biểu thức giữa các dấu ngoặc là đường giao nhau của các giá trị 3 và 4, và 1 và 2, hoặc 2 và 5, hoặc 5 và 6. Nhìn lên đường nối này trong Bagkết quả trong một đường nối của bội số tương ứng. Nếu các giá trị của 3 và 4, và ít nhất một trong số 1 và 2, hoặc 2 và 5, hoặc 5 và 6, là khác không, thì điểm nối là đúng khi được ép buộc thành một boolean (với ?), và boolean này được nhân với 30 để có được điểm số.
  • 40 * ?*{ 2 & 3 & 4 & 5 & (1 | 6) }tương tự đánh giá bàn tay thẳng lớn. Nó đơn giản hơn vì xúc xắc phải bao gồm mỗi số 2-5 và 1 hoặc 6.
  • 50 * (*.keys == 1)đánh giá bàn tay Yahtzee. Nó chỉ đơn giản là 50 lần một giá trị boolean, điều này đúng nếu số lượng xúc xắc riêng biệt là một.

2

Pip , 65 63 byte

n:_NgM\,6MXn*\,6AL[2<MXn23=JSNn3<Y#MX Jn^0MXn=5]*[$+g25--y*t50]

Đưa xúc xắc như năm đối số dòng lệnh. Hãy thử trực tuyến!

Ungolfed + giải thích

(Đây là phiên bản gốc.)

                    g is list of cmdline args; t is 10 (implicit)

Y                   Yank into y:
  _Ng                function that counts occurrences of its argument in g
 M                   mapped to
  \,6                inclusive range from 1 to 6
                    This gives us how many dice are showing each number 1-6

s:                  Assign to s:
  # MX               length of max of
      Jy ^ 0         join y into string and split on zeros
                    This gives us the length of the longest straight

MX                  Max of
   y * \,6           each die frequency in y, times its value
 AL                  to which list append
   [                 this list:
                      3- and 4-of-a-kind:
    MXy > 2 & $+g      If max frequency is 3 or more, sum of g (else 0)
                      Full house:
    23 = J SNy & 25    Sort y and join into string; if it's 000023, 25 (else 0)
                      Straights:
    s > 3 & --s*t      If s is 4 or more, (s-1)*10 (else 0)
                      Yahtzee:
    MXy = 5 & 50       If max frequency is 5, 50 (else 0)
   ]
                    The result of the last expression is autoprinted

1

Ruby , 184 byte

Chương trình đầy đủ. Để làm cho việc kiểm tra đầu vào dễ dàng hơn, hãy thêm $/=' 'vào đầu để đọc ở định dạng "chữ số được phân tách bằng dấu cách". (191 ký tự)

a=$<.map &:to_i
b=a.|c=[]
d=(1..6).map{|x|e=a.count x
c<<x*e
e}
e=a.sum
p !b[1]?50:b[4]&&!(a&[1,6])[1]?40:(1..3).any?{|x|(a&[*x..x+3])[3]}?30:(d-[0,2,3])[0]?d.max>2?e:c.max: [25,e].max

Tôi đặt ra phá vỡ rào cản 200 byte và tôi đã xoay sở để phá hủy nó với hàng tá byte còn lại, một cách dễ dàng!

Hãy thử trực tuyến!

Giải trình

Không phải là một rất tốt mặc dù. Hy vọng bạn có một số kiến ​​thức về Ruby ~

a=$<.map &:to_i # a: input as [number]*5
b=a.|c=[]       # c: [], b: a.uniq
d=(1..6).map{|x|
    e=a.count x # e: occurrence count in a 
    c<<x*e      # add (number * occurrence count) to c
    e           # return value in d
}
e=a.sum         # e: sum of input
p !b[1] ? 50 :  #   condition to print 50 <= if a.uniq has length 0 (el 1 is nil)
  b[4] &&       #   condition to print 40 <= if a.uniq has length 5 (el 4 exists)
  !(a&[1,6])[1] ? 40 : # <- arr & [mask]  # and a does not have both 1 and 6
  (1..3).any?{|x| # condition to print 30 <= if any of 1..4, 2..5, 3..6
  (a&[*x..x+3])[3]} ? 30 : # [3] to assert entire mask is found in a
  (d-[0,2,3])[0] ? # if, after removing 0 (not found) 2 (a pair) 3 (a triple)
                   # and something is found, this is not full house
  d.max > 2 ?   # is triple / quadruple ?
     e :        # weakly dominating alternatives
     c.max      # choose best by-suit
  : [25,e].max  # choose best by-score
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.