Sei vicino, ma il problema con la tua risposta è che c'è più di un modo per scrivere un numero come somma di altri due numeri.
Se m<n
, questo funziona perché i numeri 0,1,...,m-1
appaiono ciascuno con uguale probabilità e l'algoritmo termina quasi sicuramente.
Questa risposta non funziona in generale perché esiste più di un modo per scrivere un numero come somma di altri due numeri. Ad esempio, c'è solo un modo per ottenere 0
ma ci sono molti modi per ottenere m/2
, quindi le probabilità non saranno uguali.
Esempio: n = 2
e m=3
0 = 0+0
1 = 1+0 or 0+1
2 = 1+1
così la distribuzione di probabilità dal tuo metodo è
P(0)=1/4
P(1)=1/2
P(2)=1/4
che non è uniforme.
Per risolvere questo problema, è possibile utilizzare una fattorizzazione unica. Scrivi m
nella base n
, tenendo traccia del più grande esponente necessario, ad esempio e
. Quindi, trova il multiplo più grande di m
più piccolo di n^e
, chiamalo k
. Infine, genera i numeri e
con randn()
, prendili come espansione n
di base del numero x
, se x < k*m
, restituisci x
, altrimenti riprova.
Supponendo che m < n^2
, quindi
int randm() {
// find largest power of n needed to write m in base n
int e=0;
while (m > n^e) {
++e;
}
// find largest multiple of m less than n^e
int k=1;
while (k*m < n^2) {
++k
}
--k; // we went one too far
while (1) {
// generate a random number in base n
int x = 0;
for (int i=0; i<e; ++i) {
x = x*n + randn();
}
// if x isn't too large, return it x modulo m
if (x < m*k)
return (x % m);
}
}
Avete ulteriori informazioni su 'n' e' m'? – PengOne
Parte della domanda era cosa dovevo dare per n e m per far funzionare questo, ma penso che funzioni per qualsiasi numero. – WisaF
Stai assumendo una serie di cose su n, m: 1) entrambi sono numeri interi, 2) entrambi sono positivi – RHSeeger