[C] Gioco dei dadi

frab1
ciao,

ho scritto un programmino che lancia $2$ dadi,uno dopo l'altro, $36000$ volte ...e stampa le occorrenze dei valori ottenuti...valori che, dati $2$ dadi a $6$ facce per uno, restituiscono ovviamente un valore nell'intervallo $[2,16]$..

ho un dubbio...non mi stampa tutte le occorrenze! Il 12 non esce mai su 36000 lanci!??! :shock: :shock:

ecco il mio codice:
#include <stdio.h>
#include <stdlib.h>
#define FACCE 6
#define DUEFACCE 12
#define LANCI 36000


int lancia_dado(int n);

int main(void)
{
	int i=0,tot=0;	//conta lanci
	int dado1;	//conterra' valore faccia
	int dado2;
	int freq[DUEFACCE]={};	//frequenze dei vari lanci in un vettore a FACCE-elementi

	for(i=0;i<LANCI;i++) {
		dado1=lancia_dado(FACCE);
		dado2=lancia_dado(FACCE);
		tot=dado1+dado2;
	//	printf("Tot lancio %d-esimo: %d\n",i+1,tot);
		++freq[tot];		//aggiunge 1 laddove c'è il tot corrispondente uscito!!
	}
	
	printf("Stampa delle percentuali relative ai %d lanci di 2 dadi a %d facce per uno:\n",LANCI,FACCE);

	for(i=1;i<DUEFACCE;i++)
		printf(" %d : %d\n",i+1,freq[i]);
	return(0);

}

int lancia_dado(int n)
{
  return(rand() % n);		//val=a+rand() % (b-a+1)
}


Non vedo l'errore pero' :cry: :roll:

Risposte
apatriarca
rand() % 6 assume valori da 0 a 5, per cui dovresti sommare uno al risultato restituito da tale funzione..

frab1
"apatriarca":
rand() % 6 assume valori da 0 a 5, per cui dovresti sommare uno al risultato restituito da tale funzione..


a mente fredda direi che cosi non potrei mai fare il doppio uno, o sbaglio?
Se esce 1 e devo aggiungere 1 avro' 2...

EDIT: cavolata!!!
se va da 0 a 5 aggiungendo vado da 1 a 6! Grazie!

apatriarca
Tu hai bisogno di valori da 1 a 6. Hai valori da 0 a 5 per cui incrementando di uno tutti i valori ottieni l'intervallo desiderato. Il doppio uno lo ottieni quando ottieni due zero.

frab1
sisi, poi ho editato la risposta. :-)
Ma ora mi trovo con la situazione opposta...il doppio 1 non esce mai..
#define FACCE 6
#define DUEFACCE 12
#define LANCI 36000


int lancia_dado(int n);

int main(void)
{
	int i=0,tot=0;	//conta lanci
	int dado1;	//conterra' valore faccia
	int dado2;
	int freq[DUEFACCE]={};	//frequenze dei vari lanci in un vettore a FACCE-elementi

	for(i=0;i<LANCI;i++) {
		dado1=lancia_dado(FACCE)+1;
		dado2=lancia_dado(FACCE)+1;
		tot=dado1+dado2;
	//	printf("Tot lancio %d-esimo: %d\n",i+1,tot);
		++freq[tot];		//aggiunge 1 laddove c'è il tot corrispondente uscito!!
	}
	
	printf("Stampa delle percentuali relative ai %d lanci di 2 dadi a %d facce per uno:\n",LANCI,FACCE);

	for(i=1;i<DUEFACCE;i++)
		printf(" %d : %d\n",i+1,freq[i]);
	return(0);

}

int lancia_dado(int n)
{
  return(rand() % n);		//val=a+rand() % (b-a+1)
}

Dante.utopia
"$ man srand":
The rand() function returns a pseudo-random integer in the range 0 to
RAND_MAX inclusive (i.e., the mathematical range [0, RAND_MAX]).

The srand() function sets its argument as the seed for a new sequence
of pseudo-random integers to be returned by rand(). These sequences
are repeatable by calling srand() with the same seed value.

If no seed value is provided, the rand() function is automatically
seeded with a value of 1.


#include <stdio.h>
#include <string.h>
#include <time.h>

#define FACCE 6
#define DADI 2
#define LANCI 36000

int lancia_dado(int n);

int main(void)
{
   int i=0,tot=0;
   int dado1;  
   int dado2;
   int freq[DADI*FACCE]; 

   //rand seeding
   srand(time(NULL));

   /**  void *memset(void *s, int c, size_t n);
	*
	*	The  memset()  function  fills  the  first  n  bytes of the memory area
    *   pointed to by s with the constant byte c.
	*/
   memset((int *)freq, 0, DADI*FACCE*sizeof(int));

   for(i=0;i<LANCI;i++) {
      dado1=lancia_dado(FACCE);
      dado2=lancia_dado(FACCE);
      tot=dado1+dado2;
      ++freq[tot-2];  // tot is ever upper than 2 for any values of dado1 and dado2 
   }
   
   printf("Stampa delle percentuali relative ai %d lanci di 2 dadi a %d facce per uno:\n",LANCI,FACCE);

   //You can't  go out of the allocated range [0, DADI*FACCE]
   for(i=0;i<DADI*FACCE-1;i++)
      printf(" %d : %d\n",i+2,freq[i]);
   return(0);
}

int lancia_dado(int n)
{
  return (rand() % n)+1; 
}

frab1
Grazie Dante.Utopia! Non capisco perfettamente a cosa serve l'uso della srand e del relativo seme, sono necessari sempre e comunque?
Non capisco molto anche la memset che nel mio programma di corso non c'è...
Riesci a darmi qualche delucidazione? ;-)

E non capisco il $-2$ alla riga:
++freq[tot-2]

Dante.utopia
La rand() genera dei numeri pseudo casuali e per farlo utilizza il numero precedentemente creato. Di default questo è uno, ciò fa si che ogni volta che avvii il programma ti genera gli stessi numeri, se tu invece insemini il rand con un numero il più possibile casuale(come il tempo di sistema, o la temperatura della cpu) allora la rand() darà l'impressione di generare realmente numeri casuali!

la memset non fa altro che settare tutti gli elementi dell'array a zero. Equivalentemente puoi scrivere:

int array[ARRAY_LEN];
for(i=0;i<ARRAY_LEN;i++)
        array[i]=0;

frab1
per settare a zero non basta scrivere:
int freq[DADI*FACCE]={};
mi sembra un po' piu semplice :-)

ps: non capisco quel $-2$ alla riga..
++freq[tot-2];	

Dante.utopia
"frab":
per settare a zero non basta scrivere:
int freq[DADI*FACCE]={};
mi sembra un po' piu semplice :-)

Forse hai ragione, il mio metodo è un po old school!

Tu hai dichiarato un'array di 12 elementi che vanno da 0 a 11; essendo tot come minimo uguale a due partirai incrementando freq[2] e finirai con freq[13] andando a scrivere in zone non allocate!

Rispondi
Per rispondere a questa discussione devi prima effettuare il login.