2010-08-17 17 views
5

Mi piace essere in grado di generare ripetutamente lo stesso set di dati pseudo-casuali, specialmente con il tweaking del codice sperimentale. Attraverso l'osservazione, direi che rand() sembra dare la stessa sequenza di numeri ogni volta *.stdlib's rand() fornisce sempre la stessa sequenza?

È garantito eseguire questa operazione per ripetute esecuzioni sulla stessa macchina/per macchine diverse/per architetture diverse?

* Per lo stesso seme ovviamente.

risposta

18

Sì, dato lo stesso ambiente per il programma. Dallo standard C § 7.20.2.2/2,

La funzione srand utilizza l'argomento come un seme di una nuova sequenza di numeri pseudo-casuali da restituire da chiamate successive rand. Se viene chiamato lo srand con lo stesso valore di inizializzazione, la sequenza di numeri pseudo casuali deve essere ripetuta. Se rand è chiamato prima delle chiamate al srand sono stati fatti, la stessa sequenza è generato come quando srand viene dapprima chiamato con un valore di seme di 1.

Naturalmente, ciò presuppone che usa la stessa implementazione dettaglio (cioè stessa macchina, stessa libreria nello stesso periodo di esecuzione). Lo standard C non richiede un algoritmo di generazione di numeri casuali standard, quindi, se si esegue il programma con una libreria C standard diversa, è possibile ottenere una sequenza di numeri casuali diversa.

Vedere la domanda Consistent pseudo-random numbers across platforms se è necessaria una sequenza di numeri casuali portatile e garantita con un seme specificato.

+0

standard di WIN ... –

+0

OK. Sono d'accordo che per una particolare lib di runtime la sequenza sarà la stessa. Quindi, una volta creata un'applicazione (rispetto a una specifica versione runtime) genererà sempre la stessa sequenza. Ma questa estensione a diverse versioni del runtime (vale a dire attraverso OS/architettura/versioni di runtime) ecc. Se ciò implicherebbe che lo standard definisce un'implementazione esatta per l'algoritmo rand(), altrimenti come farebbero due sistemi operativi indipendenti sono conformi). –

+3

Non si estende a diverse versioni dei runtime - e se si collega dinamicamente all'implementazione di 'rand()' potrebbe potenzialmente agire diversamente senza ricostruire nulla. –

1

No.

Lo standard C dice:

Se srand viene chiamato con lo stesso valore seme, la sequenza di numeri pseudo-casuali sono ripetuta.

Ma da nessuna parte si dice cosa sia effettivamente la sequenza di numeri pseudo-casuali, quindi differisce tra le implementazioni.

L'unica garanzia è che rand() darà la stessa sequenza di numeri per un dato seme per una determinata implementazione. Non c'è alcuna garanzia che la sequenza sarà la stessa su macchine diverse o architetture diverse - e quasi certamente non lo sarà.

0

Se è necessario utilizzare lo stesso identico insieme di numeri pseudo casuali per scopi sperimentali, una cosa che si può fare è usare srand per generare una lunga sequenza di numeri casuali e scriverli in un file/database. Quindi, scrivi una funzione portatile "generatore di numeri casuali" che restituisce i valori in sequenza da quel file. In questo modo, puoi essere certo che stai utilizzando gli stessi dati di input indipendentemente dalla piattaforma, dall'implementazione srand o dal valore di inizializzazione.

+0

Bella idea. Se avessi un obbligo in tal senso, prenderei certamente questo approccio. La mia domanda è nata più per curiosità che per necessità di una sequenza conosciuta. – Joe

+0

Oppure potresti semplicemente scrivere una tua funzione a caso? – dcousens

0

Quando si passa a un'altra macchina/tempo di esecuzione/qualsiasi cosa si possa essere sfortunata. C'è un'altra scelta possibile della famiglia di funzioni drand48. Questi sono normalizzati per utilizzare lo stesso algoritmo su tutte le macchine.

2

È garantito che la stessa sequenza per lo stesso seme venga passata a srand() - ma solo per la durata di una singola esecuzione del programma. In generale, se un'implementazione ha una scelta di comportamento, non vi è alcun requisito specifico affinché tale scelta rimanga la stessa nelle successive esecuzioni.

Sarebbe conforme per un'implementazione selezionare un "seme principale" all'avvio di ciascun programma e utilizzarlo per perturbare il generatore di numeri pseudo casuali in un modo diverso ogni volta che il programma viene avviato.

Se si desidera un maggiore determinismo, è necessario implementare un PRNG con parametri specifici nel programma.

0

Se ci si trova in un UNIX/Linux ambiente si può vedere lo srand48 drand48() e () a portata di pagine man se non siete potete vedere online manuals per il linguaggio C. I prototipi possono essere trovati a /usr/include/stdlib.h. Il primo utilizza il metodo di congruenza lineare frequentemente utilizzato nelle simulazioni.

Se si fornisce lo stesso seme srand48() cioè srand48 (2) e quindi inserire il dran48() in un ciclo for allora la sequenza sarà lo stesso ogni volta. cioè

include stdio.h 
include stdlib.h 
double drand48(); 
int main(void){ 
    int i; 
    double rn; 
    srand48(2); 
    for(i=0; i<10; i++){ 
     randNum = drand48(); 
     printf("%.6l\n", randNum); 
     return 0; 
} 
Problemi correlati