Ein dynamisches Programm wird dies in kurzer Zeit erledigen.
Angenommen, wir verwalten alle Fragen an die Schüler und wählen dann zufällig eine Teilmenge von aus allen Fragen aus. Definieren wir eine Zufallsvariable , um die beiden Schüler in Frage zu vergleichen Setzen Sie sie auf wenn Schüler A korrekt ist und Schüler B nicht, wenn Schüler B korrekt ist und Schüler A nicht, und ansonsten auf . Die SummeIk=10n=100Xii:1−10
XI=∑i∈IXi
ist der Unterschied in den Punktzahlen für die Fragen in Wir möchten berechnen Diese Wahrscheinlichkeit wird über die gemeinsame Verteilung von undI. Pr(XI>0).IXi.
Die Verteilungsfunktion von sich leichtXi unter der Annahme berechnen, dass die Schüler unabhängig reagieren:
Pr(Xi=1)Pr(Xi=−1)Pr(Xi=0)=Pai(1−Pbi)=Pbi(1−Pai)=1−Pr(Xi=1)−Pr(Xi=0).
Nennen wir diese Wahrscheinlichkeiten als Abkürzung bzw. . Schreibenai, bi,di,
fi(x)=aix+bix−1+di.
Dieses Polynom ist eine Wahrscheinlichkeitsfunktion fürXi.
Betrachten Sie die rationale Funktion
ψn(x,t)=∏i=1n(1+tfi(x)).
(Tatsächlich ist ein Polynom: Es ist eine ziemlich einfache rationale Funktion.) xnψn(x,t)
Wenn als Polynom in , besteht der Koeffizient von aus der Summe aller möglichen Produkte von verschiedenen Dies ist eine rationale Funktion mit Koeffizienten ungleich Null nur für Potenzen von von bisDa gleichmäßig zufällig ausgewählt wird, geben die Koeffizienten dieser Potenzen von wenn sie auf Eins summiert werden, die Wahrscheinlichkeitsgenerierungsfunktion für die Differenz der Bewertungen an. Die Potenzen entsprechen der Größe vonψnttkkfi(x).xx−kxk. Ix,I.
Der Punkt dieser Analyse ist, dass wir einfach und mit angemessener Effizienz berechnen können :ψ(x,t) Multiplizieren Sie einfach die Polynome nacheinander. Um dies zu tun, müssen die Koeffizienten von in für(Wir können natürlich alle höheren Potenzen von ignorieren , die in einem dieser Teilprodukte auftreten). Dementsprechend können alle notwendigen Informationen, die von werden, durch eine Matrix dargestellt werden, wobei Zeilen durch die Potenzen von (von bis ) indiziert und Spalten durch indiziert werdenn1,t,…,tkψj(x,t)j=0,1,…,n.tψj(x,t)2k+1×n+1x−kk0 bis .k
Jeder Schritt der Berechnung erfordert Arbeit proportional zur Größe dieser Matrix, skaliert als Unter Berücksichtigung der Anzahl der Schritte ist dies ein -Zeit-, -Raumalgorithmus . Das macht es für kleine ziemlich schnell Ich habe es in (nicht bekannt für übermäßige Geschwindigkeit) für bis und bis wo es neun Sekunden dauert (auf einem einzelnen Kern). Bei der Einstellung der Frage mit und dauert die Berechnung Sekunden.O(k2).O(k2n)O(kn)k.R
k100n105,n=100k=10,0.03
Hier ist ein Beispiel, in dem die einheitliche Zufallswerte zwischen und und die ihre Quadrate sind (die immer kleiner als die , wodurch Schüler A stark bevorzugt wird). Ich habe 100.000 Untersuchungen simuliert, wie in diesem Histogramm der Nettoergebnisse zusammengefasst:Pai01PbiPai
Die blauen Balken zeigen die Ergebnisse an, bei denen Schüler A eine bessere Punktzahl als B erzielt hat. Die roten Punkte sind das Ergebnis des dynamischen Programms. Sie stimmen wunderbar mit der Simulation überein ( Test, ). Die aller positiven Wahrscheinlichkeiten ergibt in diesem Fall die Antwortχ2p=51%0.7526….
Beachten Sie, dass diese Berechnung mehr ergibt als verlangt: Sie erzeugt die gesamte Wahrscheinlichkeitsverteilung der Differenz der Bewertungen für alle Prüfungen von oder weniger zufällig ausgewählten Fragen.k
Für diejenigen, die eine funktionierende Implementierung verwenden oder portieren möchten, ist hier der R
Code, der die Simulation erzeugt (im Vektor gespeichert Simulation
) und das dynamische Programm ausgeführt hat (mit Ergebnissen im Array P
). Der repeat
Block am Ende dient nur dazu, alle ungewöhnlich seltenen Ergebnisse zusammenzufassen, damit der Test offensichtlich zuverlässig wird. (In den meisten Situationen spielt dies keine Rolle, aber es verhindert, dass sich die Software beschwert.)χ2
n <- 100
k <- 10
p <- runif(n) # Student A's chances of answering correctly
q <- p^2 # Student B's chances of answering correctly
#
# Compute the full distribution.
#
system.time({
P <- matrix(0, 2*k+1, k+1) # Indexing from (-k,0) to (k,k)
rownames(P) <- (-k):k
colnames(P) <- 0:k
P[k+1, 1] <- 1
for (i in 1:n) {
a <- p[i] * (1 - q[i])
b <- q[i] * (1 - p[i])
d <- (1 - a - b)
P[, 1:k+1] <- P[, 1:k+1] +
a * rbind(0, P[-(2*k+1), 1:k]) +
b * rbind(P[-1, 1:k], 0) +
d * P[, 1:k]
}
P <- apply(P, 2, function(x) x / sum(x))
})
#
# Simulation to check.
#
n.sim <- 1e5
set.seed(17)
system.time(
Simulation <- replicate(n.sim, {
i <- sample.int(n, k)
sum(sign((runif(k) <= p[i]) - (runif(k) <= q[i]))) # Difference in scores, A-B
})
)
#
# Test the calculation.
#
counts <- tabulate(Simulation+k+1, nbins=2*k+1)
n <- sum(counts)
k.min <- 5
repeat {
probs <- P[, k+1]
i <- probs * n.sim >= k.min
z <- sum(probs[!i])
if (z * n >= 5) break
if (k.min * (2*k+1) >= n) break
k.min <- ceiling(k.min * 3/2)
}
probs <- c(z, probs[i])
counts <- c(sum(counts[!i]), counts[i])
chisq.test(counts, p=probs)
#
# The answer.
#
sum(P[(1:k) + k+1, k+1]) # Chance that A-B is positive