Kartenpaarwahrscheinlichkeit


9

Berechnen Sie bei einem Deck, das aus N Kopien von Karten mit ganzzahligen Werten [ 1 , M ] für insgesamt N * M Karten besteht, die Wahrscheinlichkeit, dass eine Karte mit dem Wert 1 neben einer Karte mit dem Wert 2 liegt .

Ihre Lösung kann genau oder angenähert sein und muss nicht bei jedem Lauf mit denselben Eingaben gleich sein. Die gegebene Antwort sollte innerhalb von +/- 5% der tatsächlichen Lösung liegen (abgesehen von wirklich seltenen Chancen, dass das RNG nicht zu Ihren Gunsten ist). Ihr Programm sollte die Antwort in angemessener Zeit geben (z. B. weniger als 10 Minuten auf Ihrer Hardware). Sie können davon ausgehen, dass M und N angemessen klein sind und keine Fehlerprüfung erforderlich ist.

Das Deck ist nicht zyklisch. Wenn also die erste Karte eine 1 und die letzte eine 2 ist , entspricht dies nicht den Adjazenzanforderungen.

Als Testfall beträgt die erwartete Lösung für N = 4 und M = 13 (ein Standard-Kartenspiel mit 52 Karten) ~ 48,6%.

Hier ist ein Beispiel für eine Implementierung ohne Golf in Python + NumPy, bei der zufällige Mischvorgänge verwendet werden:

from __future__ import division
from numpy import *

def adjacent(N, M):
    deck = array([i for i in range(1, M+1)]*N)
    trials = 100000
    count = 0
    for i in range(trials):
        random.shuffle(deck)
        ores = (deck == 1)
        tres = (deck == 2)
        if(any(logical_and(ores[1:], tres[:-1])) or
           any(logical_and(ores[:-1], tres[1:]))):
            count += 1
    return count/trials

Die Ausgabe kann in jeder Form erfolgen, die Sie für zweckmäßig halten (Funktionsrückgabewert, Terminalausgabe, Datei usw.), und die Eingabe kann in jeder Form erfolgen, die Sie für zweckmäßig halten (Funktionsparameter, Terminaleingabe, Befehlszeilenargument usw.).

Es gelten Standardschlupflöcher.

Dies ist Code Golf, der kürzeste Code (in Bytes) gewinnt.

Bestenliste


1
Adjazenz, die sich nicht herumwickelt, ist eine täuschend komplizierte Wendung
Sparr

@ Sparr Du hast mir eine Idee gegeben! :-)
Luis Mendo

Antworten:


2

Pyth, 23 22 Bytes

csm}1sM.:.S*vzUQ2J^T4J

Führt 10000 Iterationen aus. Die Nummer kann ohne Bytekosten geändert werden. Die Eingabe ist durch Zeilenumbrüche getrennt. Dauert auf meinem Computer ungefähr 9 Sekunden.

Demonstration

csm}1sM.:.S*vzUQ2J^T4J
                 J^T4     J = 10000
  m              J        Do the following J times.
           *vzUQ          Set up the deck. (0 .. n-1, repeated m times.)
         .S               Shuffle the deck.
       .:       2         Find all 2 elment substrings.
     sM                   Add them up.
   }1                     Check if any pairs add to 1 ([0, 1] or [1, 0])
 s                        Add up the results (True = 1, False = 0)
c                     J   Divide by J.

2

MATL , 44 46 Bytes

Hierbei wird Version 3.1.0 der Sprache verwendet, die vor dieser Herausforderung liegt.

Die Berechnung erfolgt mit einer Schleife, die 1000 zufällige Realisierungen zeichnet. Der Lauf dauert einige Sekunden. Es könnte auf vektorisierte Weise schneller gemacht werden. Die Eingabe erfolgt in der Form [N M].

Alte Version : Erzeugt ein zufälliges Kartenspiel und überprüft es zweimal: zuerst vorwärts und dann rückwärts.

itpw1)1e3:"2$twZ@w/Y]t1HhXfnwH1hXfn|bb]xxN$hYm

Neue Version : Erzeugt ein zufälliges Kartenspiel und fügt dann eine gespiegelte Version mit einem 0dazwischen liegenden hinzu. Auf diese Weise kann die Überprüfung nur einmal in Vorwärtsrichtung durchgeführt werden. Dies spart zwei Bytes.

itpw1)1e3:"2$twZ@w/Y]tP0whh1HhXfngbb]xxN$hYm

Beispiel

>> matl itpw1)1e3:"2$twZ@w/Y]tP0whh1HhXfngbb]xxN$hYm
> [4 13]
0.469

Erläuterung

i                 % input: [N M]
tpw1)             % produce N*M and N
1e3:"             % repeat 1000 times
  2$twZ@w/Y]      % produce random deck of cards from 1 to N*M
  tP0whh          % append 0 and then flipped version of deck
  1Hh             % vector [1 2]
  Xf              % find one string/vector within another                          
  ng              % was it found at least once?
  bb              % bubble up element in stack, twice                     
]                 % end                                                     
xx                % delete top of the stack, twice
N$h               % vector with all elements in stack
Ym                % mean value


1

Pyth, 16 Bytes

JE?>J1-1^-1c2JQZ

Demonstration.

Dies folgt dem

  • eine fundierte Vermutung anstellen,
  • Überprüfen Sie, ob es nah genug ist.
  • wiederholen

Strategie der Programmierung. Die gewinnende Vermutung in diesem Fall ist

1 - (1 - 2 / M) ** N

was ungefähr besagt, dass es NChancen gibt, in Eimer zu fallen, und ein Bruchteil der gültigen Eimer ist 2 / M. Die Eimer sind Slots neben 0s und die Chancen sind 1s.

Der Fehler scheint nie (überraschenderweise) über 3% zu steigen und konvergiert gegen 0%, wenn die Parameter größer werden (wie ich es erwarten würde).

Die Eingabe ist durch Zeilenumbrüche getrennt.

              Q  Q = eval(input())
JE               J = eval(input())
  ?>J1           if J > 1
      -1^-1c2JQ  then 1 - (1 - 2 / J) ** Q
               Z else 0

Sie können einen Charakter speichern, wenn Sie die offensichtliche Tatsache akzeptieren False == 0, und dies JE&>J1-1^-1c2JQstattdessen tun .


Dies ist mein erster Versuch bei Pyth (und meine erste Antwort), daher sind Kritik und Hilfe besonders willkommen.
Veedrac

1

MATL , 44 38 Bytes

Dies verwendet auch MATL Version 3.1.0 , die früher als diese Herausforderung ist.

Neue Version, danke an Luis Mendo für das Speichern von 4 Bytes!

iiXI*XJxO1e4XH:"JZ@I\TTo3X53$X+1=a+]H/

Alte Version (44 Bytes):

OiitXIx*XJx1e4XH:"JJZrI\[1 1]3X5,3$X+1=a+]H/

Erläuterung

i               % take input for N
i               % take input for M
XI              % save M into clipboard I
*XJ             % multiply N and M and store in clipboard J
x               % clear the stack
O               % make a zero to initialise count of pairs
1e4XH:"         % 1e4=10000, XH saves into clipboard H, : makes the vector 1:1e4
                % which is used to index a for loop, started using "
    JZ@         % Use randperm to generate a random permutation of the vector 1:N*M
    I\          % take the result mod M, now each card has a value one less than before
    TTo3X53$X+  % convolve vector of card values with [1 1] to do pairwise summation
    1=a         % find if any sums equal 1, which means there is a [0 1] or [1 0]         
    +           % add the logical value to the count of pairs
]
H/              % divide the count by the number of deals to get the probability

Beispielsweise,

>> matl 'iiXI*XJxO1e4XH:"JZ@I\TTo3X53$X+1=a+]H/'
> 4
> 13
0.4861

Hinweis (21.5.16): Ab MATL Release 18.0.0 X+wurde entfernt, Y+kann aber an seiner Stelle verwendet werden. Die Änderungen von MATL Version 3.1.0 zu 18.0.0 bedeuten, dass diese Antwort jetzt in nur 31 Bytes geschrieben werden kann *xO1e4:"2:Gtb*Z@w\TT2&Y+1=ah]Ym.


Ich weiß, dass es bereits eine MATL-Antwort gibt, aber ich denke, die Methoden sind ganz anders, deshalb habe ich diese immer noch gepostet.
David

Ich liebe Faltung!
Luis Mendo

Sie können ein wenig Wechsel [1 1]in sparen TTo. Außerdem brauchen Sie kein Komma
Luis Mendo

@ LuisMendo danke! Ich dachte, es muss einen besseren Weg gegeben haben, das zu tun!
David

Jetzt sehe ich, wie Faltung hier funktioniert. Die 0-basierte Benennung der Karten war sehr clever!
Luis Mendo

0

Mathematica, 93 92 91 Bytes

N@Count[RandomSample@Flatten[Range@#~Table~{#2}]~Table~{a=1*^5},{b=___,1,2,b}|{b,2,1,b}]/a&

Immer noch auf der Suche nach einer geschlossenen Form ...


Es wird eine verschachtelte Schleife von Permutationsberechnungen beinhalten.
Sparr
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.