トランプゲーム「Oorlog」で「戦闘」をシミュレートする


15

私が個人的にオランダ語で「Oorlog」(「戦争」に翻訳されます)という名前で知っているカードゲームのある局面のシミュレーションを構築しましょう。

「Oorlog」はどのように機能しますか?

2組のカード(それぞれ2人のジョーカーを含む)は、プレイするプレイヤーの数に等しく分割されます。各プレイヤーは自分のストックをシャッフルし、自分の前に上下逆さまに置き、すべてのプレイヤーが同時にストックの最初のカードを開きます。
その「戦い」の勝者は、これらのルールに従うカードの価値によって決定されます。ジョーカー/エースがキングを破ります。キングはクイーンを破る。女王はジャックを破る。ジャックは10を破ります。10敗北9; ....さらに、2と3の両方がエース/ジョーカーを破ります。最後のルールは、2または3がエースまたはジョーカーを打ち、エースまたはジョーカーが他のカードを打ち、順番に2または3を打ち負かすサイクルにつながる可能性があります。この場合、2または3が勝ちます。
(このカードゲームではスーツは無関係です。)

2人以上のプレイヤーが同じ最高のカードを持っている場合、それらは「戦争」を持っています。これは、彼らが1枚のカードを上下逆さまに置き、それぞれがストックから新しいカードを開き、再び最高のカードを持っている人を探すことを意味します。これは、一人のプレイヤーが戦闘全体に勝つまで続きます。
(そのバトルのすべてのカードは、バトルに勝ったプレイヤーの捨て札パイルに行きます。その後、全員が新しいカードを開きます。プレイヤーの在庫がカードからなくなると、彼らは捨て札パイルをひっくり返し、この新しい在庫を続けます。これは、プレーヤーがすべてのカードを使い果たすまで続き、カードの量が最も多いプレーヤーが勝ちます。)

3人のプレイヤーとの「戦闘」の例:

  1. 4、8、ジャック:
    ジャックが勝ちます。
  2. 7、エース、クイーン:
    エースが勝ちます。
  3. 10、10、King:
    キングが勝ちます。
  4. 3、ジョーカー、2:
    3勝。
  5. エース、ジョーカー、2:
    2勝。
  6. 3、クイーン、エース:
    3勝。
  7. 女王、女王、9:
    女王と女王は「戦争」をしているので、2枚の新しいカードが続きます:4、8;
    8勝。
  8. 4、4、4:
    すべてが「戦争」を抱えているため、3つの新しいカードが続きます。8、エース、2。
    2勝。
  9. ジャック、5、ジャック:
    ジャックとジャックは「戦争」をしているので、2枚の新しいカードが続きます。
    5と5も等しいので、「戦争」は2つの新しいカードで再び続きます。
    キングが勝ちます。
  10. ジョーカー、ジョーカー、エース:
    すべてが「戦争」をしているので、3枚の新しいカードで続行します。9、7、9。
    9と9も等しいので、「戦争」は2枚の新しいカードで続きます。ジャック、3。
    ジャックが勝ちます。

だから、コードの挑戦に:

入力:

STDIN配列、または配列をシミュレートする文字列(呼び出し-言語が配列をサポートしている場合でも)。この配列には、時系列で戦闘のカードが含まれています(これについてのより明確な理解については、テストケースを参照してください)。

出力:

STDOUTバトルに勝ったプレイヤーのインデックス。
あなたはゼロインデックス(すなわちかどうかを選択することができ01または2(IE)または1インデックス付きの出力を123)。

チャレンジルール:

  • 入力は、配列を表す単一の配列/文字列になります。したがって、単純化するために配列の配列を持つことはできません。また、戦争に参加していないカードの代理アイテムを持つことはできません。
  • フェイスカードには、文字表記ではなく数字表記を使用します。だからエース/ジョーカー=1 ; ジャック= 11; クイーン= 12; とキング= 13
  • このチャレンジでは、常に3人のプレイヤーでプレイしていると想定できます。
  • 最初の3つは「戦い」の始まりを示しています。2人以上のプレイヤーが「戦争」をしている場合、配列内の継続するカードは彼らの戦いを示します(これについてのより明確な理解については、テストケースを参照してください)。

一般的なルール:

  • これにはタグが付いているため、バイト単位の最短回答が優先されます。
    これは、非コードゴルフ言語が入るべきではないという意味ではありません。「あらゆる」プログラミング言語に対して、できるだけ短いコードとゴルフの答えを考えてみてください。
  • 出力に使用したインデックス(ゼロまたは1インデックス)を記載してください。

テストケース:

Test case 1:  [4, 8, 11]                 ->  2 (or 3)
Test case 2:  [7, 1, 12]                 ->  1 (or 2)
Test case 3:  [10, 10, 13]               ->  2 (or 3)
Test case 4:  [3, 1, 2]                  ->  0 (or 1)
Test case 5:  [1, 1, 2]                  ->  2 (or 3)
Test case 6:  [3, 12, 1]                 ->  0 (or 1)
Test case 7:  [12, 12, 9, 4, 8]          ->  1 (or 2)
Test case 8:  [4, 4, 4, 8, 1, 2]         ->  2 (or 3)
Test case 9:  [11, 5, 11, 5, 5, 10, 13]  ->  2 (or 3)
Test case 10: [1, 1, 1, 9, 7, 9, 11, 3]  ->  0 (or 1)
Test case 11: [13, 13, 4, 1, 3]          ->  1 (or 2)
Test case 12: [13, 4, 13, 2, 3]          ->  2 (or 3)

4
英語の名前は確かに戦争です(ジョーカーを差し引いて、2-and-3-beat-aceルールを差し引いたものです)。
マーティンエンダー

また、@ MartinEnderは、引き分けがある場合、両方のプレイヤーが3枚のカードを裏向きに裏返し、4枚目のカードを表向きにします。4番目がラウンドの勝者を決定し、裏向きのカードが「戦争のネタバレ」です。また、1人のプレイヤーがすべてのカードを手に入れるまでゲームは続けられませんか?これがローカルルールであるかどうかわからない、他の誰かがこれを覚えていますか?それが私がプレイを覚えている方法です。
魔法のタコUr

1
@MagicOctopusUrn捨て札の山をひっくり返して、1人のプレイヤーがすべて持ってくるまでプレイを続けたことを覚えています。
カミルドラカリ

1
@kamildrakariええ!それも私がプレイした方法です。私はルイジアナでこれを演奏して育ちました。
魔法のタコUr

@MagicOctopusUrn私の経験はミネソタ州からのもので、現在2つのデータポイントがあるので、すべてのアメリカが同じであると言っても安全だと思います。
カミルドラカリ

回答:


4

q-142文字

{p:til 3;while[1<(#:)p;h:(n:(#:)p)#x;x:n _x;$[1~min h;p:$[max a:h in(2;3);$[1<(#:)(?:)h(&:)a;p(&:)h=3;p(&:)a];p(&:)h=1];p:p(&:)h=max h]];(*:)p}

注:インデックスはゼロです。

qにstdinを読み取るという概念はないため、関数として呼び出す必要があります。 {p:til 3;while[1<(#:)p;h:(n:(#:)p)#x;x:n _x;$[1~min h;p:$[max a:h in(2;3);$[1<(#:)(?:)h(&:)a;p(&:)h=3;p(&:)a];p(&:)h=1];p:p(&:)h=max h]];(*:)p}[1,2,3]

実際にはかなり長いですが、多くのコーナーケースがあります。アクティブなプレイヤーのリストを保持し、ループでカードのリストを消費します。最も問題なのは[13, 2, 3]3ビートのように、2通常のように正しい勝者を検出することですが、通常のケースに入れるには複製する必要がありました。


3

JavaScript(ES6)、146バイト

f=a=>(b=a.splice(0,3)).filter(m=>m-n,n=Math.max(...b.includes(1)?b.filter(m=>m<4):b)).length>1?b.indexOf(n):f([...b.map(m=>m-n?0:a.shift()),...a])

ゼロベースのインデックスを返します。最初の取引を別の配列として許可している場合は127バイト(これはもちろん任意の数のハンドでも機能します):

f=(b,a)=>b.filter(m=>m==n,n=Math.max(...b.includes(1)?b.filter(m=>m<4):b)).length<2?b.indexOf(n):f(b.map(m=>m-n?0:a.shift()),a)

0

Java 8、257バイト

int c(int[]a){int t=0,f=0,q,r=0,i=-1,l=a.length,x[];for(;++i<3;t=a[i]>t?a[r=i]:t)a[i]+=a[i]==1?f++*0+13:0;for(;i-->0;t=f>0&a[i]<4?t!=3?a[r=i]:t>a[i]?a[r=i]:t:t);for(f=-1,x=new int[q=l<7?3:l>7?l-3:5];l>3&++i<q;)x[i]=t==a[i]|i>2?a[++f+3]:0;return l>3?c(x):r;}

わかりました、私の挑戦は私がそれがそのような単一の配列のすべてにあると思ったより難しいです。;)しかし、このチャレンジを投稿してから1年以上前なので、自分で試してみることにしました。複数の回避策と癖でかなり時間がかかりました。だから、それは間違いなくもう少しゴルフをすることができますが、私はその別の時間を調べます。これはすでに予想よりもずっと長くかかりました。

説明:

ここで試してみてください。

int c(int[]a){      // Method with integer-array parameter and integer return-type
  int t=0,f=0,q,    //  Temp integers
      r=0,          //  Result-integer
      i=-1,         //  Index-integer
      l=a.length,   //  Length of the input-array
      x[];          //  Temp array we use when there is a war
  for(;++i<3;       //  Loop (1) from 0 to 3 (exclusive)
      t=            //    After every iteration, change `t` to:
        a[i]>t?     //     If the current item is larger than `t`:
         a[r=i]     //      Use the current item (and save its index in `r`)
        :           //     Else:
         t)         //      Leave `t` the same
    a[i]+=a[i]==1?  //   If the current item is a 1 (Ace/Joker):
         f++*0      //    Increase `f` by 1,
         +13        //    and change the 1 to 14 (by increasing with 13)
        :           //   Else:
         0;         //    Leave the current item the same (by increasing with 0)
                    //  End of loop (1) (implicit / single-line body)
  for(;i-->0;       //  Loop from 2 down to 0 (inclusive)
    t=f>0&a[i]<4?   //   If a Joker/Ace was present, and the current item is 2 or 3:
       t!=3?        //    And if it's not a 3 (so either 2 or 14)
        a[r=i]      //     Change `t` to the current item (and save its index in `r`)
       :t>a[i]?     //    Else-if the current item is 2, and `t` is a Joker/Ace:
        a[r=i]      //     Change `t` to the current item (and save its index in `r`
       :            //    Else:
        t           //     Leave `t` the same
      :             //   Else:
       t            //    Leave `t` the same
  );                //  End of loop (2)
  for(f=-1,         //  Reset `f` to -1
      x=new int[    //  Create the temp array `x` with length:
       q=l<7?       //   If the current length is 6 or lower:
          3         //    New length after war is 3
         :l>7?      //   Else-if the current length is 8 or higher:
          l-3       //    New length after war is current length - 3
         :          //   Else(-if current length is 7)
          5];       //    New length after war is 5
      l>3&          //  If there is a war:
          ++i<q;)   //   Loop (3) from 0 to the new length (exclusive)
    x[i]=t==a[i]    //    If the current item is at war,
         |i>2?      //    or the current item is after the first 3 items:
          a[++f+3]  //     Fill the new array with the correct next item
         :          //    Else:
          0;        //     Fill the item of the new array with 0
                    //     (since it won't participate in the next round)
                    //   End of loop (3)
  return l>3?       //  If there was a war:
          c(x)      //   Recursive-call with the new array
         :          //  Else:
          r;        //   Return the index of the card that won
}                   // End of method
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.