玩Pickomino


10

Pickomino游戏中,桌子中间放着几块瓷砖,每块瓷砖上都有一个不同的正整数。每回合,玩家以某种方式掷骰子并获得分数,这是一个非负整数。

现在,玩家将选择仍低于或等于其分数的最高编号的图块,从中间移除图块并将其添加到堆栈中。如果由于中间的所有数字均高于玩家的分数而无法这样做,则玩家将失去其堆栈中最上面的图块(该图块最近添加),并返回中间。如果玩家没有剩余的瓷砖,则什么也不会发生。

挑战

模拟对自己玩游戏的玩家。您会在中间找到一个磁贴列表,以及一个获得的分数列表。在评估所有回合之后,返回玩家的磁贴列表。

挑战规则

  • 您可以假设包含图块的列表是有序的,并且两次都不包含任何整数。
  • 您可以按任意顺序获取两个输入列表
  • 输出必须保持切片在堆栈上的顺序,但是您可以决定列表是从上到下还是从下到上排序。

通用规则

  • 这是,因此最短答案以字节为单位。
    不要让代码高尔夫球语言阻止您使用非代码高尔夫球语言发布答案。尝试针对“任何”编程语言提出尽可能简短的答案。
  • 标准规则适用于具有默认I / O规则的答案,因此您可以使用STDIN / STDOUT,具有正确参数的函数/方法以及返回类型的完整程序。
  • 默认漏洞是禁止的。
  • 如果可能的话,请添加一个带有测试代码的链接(即TIO)。
  • 建议为您的答案添加说明。

(摘自第6个测试用例)

Tiles: [21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36]
Scores: [22, 22, 22, 23, 21, 24, 0, 22]

第一个分数是22,所以取中间<= 22的最高分块,也就是22本身。

Middle: [21, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36]
Stack: [22]
Remaining scores: [22, 22, 23, 21, 24, 0, 22] 

下一个分数是22,因此在中间<= 22的位置获得最高的牌。由于已经取得22,因此玩家必须取得21。

Middle: [23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36]
Stack: [22, 21]
Remaining scores: [22, 23, 21, 24, 0, 22]

下一个分数是22,但是所有<= 22的数字都已被采用。因此,玩家失去了堆叠(21)上的最上面的瓦片,该瓦片返回到中间。

Middle: [21, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36]
Stack: [22]
Remaining scores: [23, 21, 24, 0, 22]

下一个得分是23、21和24,因此玩家从中间拿走了这些牌。

Middle: [25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36]
Stack: [22, 23, 21, 24]
Remaining scores: [0, 22]

玩家破产并得分为零。因此,编号为24的图块(堆栈中的最顶部)返回到中间。

Middle: [24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36]
Stack: [22, 23, 21]
Remaining scores: [22]

最后的分数是22,但是所有<= 22的图块都已被占用,因此玩家失去了堆栈中最上面的图块(21)。

Middle: [21, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36]
Final Stack and Output: [22, 23]

测试用例

(最上面的图块位于输出列表的最后)

Tiles: [21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36]
Scores: [26, 30, 21]
Output: [26, 30, 21]

Tiles: [21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36]
Scores: [35, 35, 36, 36]
Output: [35, 34, 36, 33]

Tiles: [21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36]
Scores: [22, 17, 23, 19, 23]
Output: [23]

Tiles: [21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36]
Scores: []
Output: []

Tiles: [21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36]
Scores: [22, 17, 23, 19, 23, 0]
Output: []

Tiles: [21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36]
Scores: [22, 22, 22, 23, 21, 24, 0, 22]
Output: [22, 23]

Tiles: [1, 5, 9, 13, 17, 21, 26]
Scores: [6, 10, 23, 23, 23, 1, 0, 15]
Output: [5, 9, 21, 17, 13, 1]

Tiles: []
Scores: [4, 6, 1, 6]
Output: []

沙盒


我们可以假设中间没有零值的图块吗?
无知的体现,

@EmbodimentofIgnorance它说“正整数”,所以是的。
与Orjan约翰森

由于图块是唯一的,因此将它们用作位掩码是否可以接受?
Arnauld

@TRITICIMAGVS是的,如果中间的堆空了,则玩家无法从中间拿起一块砖,因此他们会丢掉一块砖(如果有)
Black Owl Kai

@Arnauld那是可以接受的
Black Owl Kai

Answers:


3

Haskell中119个 111 104 103字节

ØrjanJohansen节省了1个字节

(#)=span.(<)
(a%(b:c))d|(g,e:h)<-b#d=(e:a)%c$g++h|g:h<-a,(i,j)<-g#d=h%c$i++g:j|1>0=a%c$d
(a%b)c=a
([]%)

在线尝试!

假设图块按降序排序。

这里没有什么幻想。第一个参数是玩家的筹码,第二个是他们的分数,第三个是中间的筹码。


1
这不可能是正确的,因为sort它在上升。但是,TIO测试用例永远不会到达该分支。我强烈建议每次迭代时都测试所有情况。
与Orjan约翰森

@ØrjanJohansen谢谢!立即修复。至少我不必再导入了!
Ad Hoc Garf Hunter,

用保存一个字节(#)=span.(<)
与Orjan约翰森

@ØrjanJohansen进行了更改。有趣的是,我较早尝试过,并认为它增加了一个字节。
Ad Hoc Garf Hunter,

3

Japt,24个字节

钱币!那没有我想象的那样好!

以相反的顺序输入。

®=Va§Z)Ì?NpVjZ:VpNo)nÃN¤

尝试在TIO上运行所有测试用例

®=Va§Z)Ì?NpVjZ:VpNo)nÃN¤     :Implicit input of N=[U=scores, V=tiles]
®                            :Map each Z in U
 =                           :  Reassign to Z
  Va                         :    0-based index of last element in V (-1 if not found)
    §Z                       :      Less than or equal to Z
      )                      :  End reassignment
       Ì                     :  Sign of difference with -1 (1 if found, 0 if not)
        ?                    :  If truthy (not zero)
         Np                  :    Push to N
           VjZ               :      Remove and return the element at index Z in V
              :              :  Else
               Vp            :    Push to V
                 No          :      Pop the last element of N
                   )         :    End Push
                    n        :    Sort V
                     Ã       :End map
                      N¤     :Slice the first 2 elements (the original inputs) off N

2

Perl 6,89个字节

{my@x;@^a;@^b>>.&{@x=|@x,|(keys(@a@x).grep($_>=*).sort(-*)[0]//(try ~@x.pop&&()))};@x}

在线尝试!

我认为还有更多字节可以解决...


2

C#(Visual C#中交互式编译器)159个 158 154字节

称为 f(tiles)(scores)

n=>m=>{var s=new Stack<int>();m.Add(0);n.ForEach(k=>{var a=m.Except(s).Where(x=>x<=k).Max();if(a<1)m.Add(s.Count<1?0:s.Pop());else s.Push(a);});return s;}

如果System.Void实际上只是返回类型,而不仅仅是反射的占位符。我将能够替代if(a<1)m.Add(s.Count<1?0:s.Pop());else s.Push(a);var t=a>1?m.Add(s.Count<1?0:s.Pop()):s.Push(a);节省两个字节。

在线尝试!

//Function taking in a list and returning
//another function that takes in another list and returns a stack
n=>m=>{
//Initialize the stack
var s=new Stack<int>();
//Add a zero to the tiles, to ensure no exceptions appear due to accessing
//non-existent elements in an empty collection later
//when we try to filter it later and getting the biggest element
m.Add(0);
//Iterate through our scores
n.ForEach(k=>{
//Create a variable called a, which we will use later
var a=
//Get all the elements in the middle that haven't appeared in our stack
m.Except(s).
//And throw away all elements that are bigger than our current score
Where(x=>x<=k).
//And get the biggest element there, and that is now the value of a
//Without the m.Add(0), we would get an exception here
Max();
//Self-explanatory, if a is less than 1 aka if a equals 0
//Checks if all elements in the middle are bigger than our score 
//Except for our self added 0, of course
if(a<1)
//Add 0 to the middle if the stack is empty
//Remember, zeros don't affect the list
m.Add(s.Count<1?0:
//Else pop the stack and add that to the middle
s.Pop());
//If a isn't 0, add a to the stack
else s.Push(a);});
//Afterwards, return the stack
return s;}


2

JavaScript(Node.js),80字节

与ES6版本的逻辑相同,但将图块作为BigInt位掩码,将分数作为BigInts数组。

m=>s=>s.map(g=x=>!x||m>>x&1n?m^=1n<<(x?r.push(x)&&x:r.pop()||~x):g(--x),r=[])&&r

在线尝试!


JavaScript(ES6), 100 98 94  87字节

将输入作为(tiles)(scores)。磁贴可以以任何顺序传递。

t=>s=>s.map(g=x=>m[x]?m[x?r.push(x)&&x:r.pop()]^=1:g(x-1),t.map(x=>m[x]=1,m=[r=[]]))&&r

在线尝试!

已评论

t => s =>                 // t[] = tiles; s[] = scores
  s.map(g = x =>          // for each score x in s[]:
    m[x] ?                //   if m[x] is set:
      m[                  //     update the 'middle':
        x ?               //       if x is not equal to 0:
          r.push(x) && x  //         push x in the stack r[] and yield x
        :                 //       else:
          r.pop()         //         pop the last value from the stack
                          //         (may be undefined if the stack is empty)
      ] ^= 1              //     toggle the corresponding flag in m[]
    :                     //   else:
      g(x - 1),           //     try again with x - 1
    t.map(x =>            //   initialization of the 'middle': for each value x in t[]:
      m[x] = 1,           //     set m[x]
      m = [r = []]        //     the stack r[] is stored as the first entry of m[],
                          //     which ensures that g will always stop when x = 0
    )                     //   end of initialization
  ) && r                  // end of main loop; return r[]

1

木炭,35字节

Fη«≔⌈Φ講κιι¿ι«≔Φθ⁻κιθ⊞υι»¿υ⊞θ⊟υ»Iυ

在线尝试!链接是详细版本的代码。说明:

Fη«

循环得分。

≔⌈Φ講κιι

寻找可用的最高瓷砖。

¿ι«

如果存在,那么...

≔Φθ⁻κιθ

...从中间取下瓷砖...

⊞υι

...并将其添加到堆栈中。

»¿υ

否则,如果堆栈不为空...

⊞θ⊟υ

从堆栈中删除最新的图块,然后将其返回到中间。

»Iυ

从最旧到最新打印结果堆栈。


1

Python 2,120字节

m,s=input()
t=[]
for n in s:
 i=[v for v in m if v<=n]
 if i:v=max(i);t+=[v];m.remove(v)
 else:m+=t and[t.pop()]
print t

在线尝试!


1

05AB1E27 22 字节

vÐy>‹ÏDgĀià©K®së\sª])¨

在线尝试验证所有测试用例

说明:

v            # Loop `y` over the (implicit) input-list of scores:
 Ð           #  Triplicate the tiles list (takes it as implicit input in the first iteration)
  y>‹        #  Check for each if `y` <= the value in the tiles list
     Ï       #  Only leave the values at the truthy indices
 D           #  Duplicate the remaining tiles
  ¯Êi        #  If this list is not empty:
     à       #   Pop the list, and push its maximum
      ©      #   Store it in the register, without popping
       K     #   Remove it from the tiles list
        ®    #   Push the maximum again
         s   #   Swap the maximum and tiles-list on the stack
    ë        #  Else:
     \       #   Remove the duplicated empty tiles-list from the stack
      sª     #   Add the last tile to the tiles-list
]            # Close the if-else and loop
 )           # Wrap everything on the stack into a list
  ¨          # Remove the last item (the tiles-list)
             # (and output the result implicitly)

1

Pyth,32个字节

VE ?JeS+0f!>TNQ=-QeaYJaQ.)|Y]0;Y

在此处在线尝试,或在此处一次验证所有测试用例。

这里某处必须有改进的空间-任何建议将不胜感激!

VE ?JeS+0f!>TNQ=-QeaYJaQ.)|Y]0;Y   Implicit: Q=input 1 (middle), E=input 2 (scores), Y=[]
VE                            ;    For each score, as N, in the second input:
         f    Q                      Filter Q, keeping elements T where:
          !>TN                         T is not greater than N 
                                       (less than or equal is the only standard inequality without a token in Pyth, grrr)
       +0                            Prepend 0 to the filtered list
     eS                              Take the largest of the above (_e_nd of _S_orted list)
    J                                Store the above in J
   ?                                 If the above is truthy:
                   aYJ                 Append J to Y
                  e                    Take last element of Y (i.e. J)
               =-Q                     Remove that element from Q and assign the result back to Q
                                     Else:
                          |Y]0         Yield Y, or [0] if Y is empty
                        .)             Pop the last element from the above (mutates Y)
                      aQ               Append the popped value to Q
                               Y   Print Y

1

Perl -apl -MList:Util=max5,97个字节

$_=$".<>;for$i(@F){(($m=max grep$_<=$i,/\d+/g)&&s/ $m\b//?$s:$s=~s/ \d+$//?$_:$G).=$&}$_=$s;s/ //

蒂奥

在下一行读取分数和图块并打印输出。

怎么样

  • -apl-p循环遍历行并打印,自动-a分割,-l从输入中剪切并在输出中添加换行符
  • $_=$".<> :读取下一行(平铺)并将空格添加到默认var中 $_
  • for$i(@F){... }循环$i遍历@F当前行的字段(分数)
  • (.. ?.. :.. ).=$&将先前的匹配附加到三元l值
  • ($m=max grep$_<=$i,/\d+/g)&&s/ $m\b//?$s如果找到并从图块中删除的最大值($_),l值是得分($s
  • $s=~s/ \d+$//?$_ 否则,如果可以从分数中删除最后一个数字,则为平铺
  • :$G 最终是垃圾,因为不可能发生
  • $_=$s;s/ // 将分数设置为默认变量,并删除前导空间
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.