• Revista PROGRAMAR: Já está disponível a edição #53 da revista programar. Faz já o download aqui!

amp

Dúvida em C

7 mensagens neste tópico

Bom dia,

Eu tenho de fazer um programa que crie uma rede quadrada (matriz quadrada) de tamanho indicado pelo utilizador, em que cada elemento da rede vai ser preenchido com 0 ou 1. A probabilidade de cada elemento ser preenchido com 1 é também indicada pelo utilizador. Já o numero de redes geradas é indicado na shell.

A minha dúvida é a seguinte: se, por exemplo, no lado da rede digitar "9e5", na altura em que vou pedir a probabilidade, como o buffer do teclado não está limpo, o scanf("%lf",&prob); vai buscar o 'e' que eu tinha digitado atrás e não aceita a probabilidade porque o valor real de 'e' é 0.0000. Como é que eu posso evitar isto? Já tentei a função fflush(stdin) e a __fpurge(stdin), mas a primeira apenas dá no Windows e a segunda no Linux. Alguém conhece uma forma eficiente de contornar isto?

Outra coisa. Para eu fazer uma pausa no programa (+-1s) entre a impressão das redes, como é que eu o poderia fazer? Eu já fiz de uma maneira (está comentado no programa), mas gostava de saber se há alguma forma mais simples (uma função já definida?,compilação condicional?) de o fazer.

Façam críticas ao programa se puderem

Obrigado,

ampat

# include <stdio.h> 
# include <stdlib.h> 
# include <math.h> 
# include <string.h> 
//# include <time.h> 

//Funcao - Gera, aleatoriamente, uma configuracao de rede 
void 
gera_config (double prob, long int L, unsigned char *nodo) 
{ 
  long int i,vol=L*L; 
   
  for(i=0;i<vol;++i) 
    nodo[i]=( ( (double)rand()/(double)RAND_MAX ) < prob ? 1 : 0 ); 
} 

//Funcao - Imprime a configuracao da rede 
void 
printf_config ( long int L,unsigned char *nodo) 
{ 
  long int i,vol=(L*L); 
   
  for(i=0;i<vol;++i) 
    { 
      if( (i%L)==0) 
    printf("\n    "); 
      printf("%d ",nodo[i] ); 
    } 
} 

//Funcao - Inicializa a rede de percolacao a zeros 
void 
inic_nodo (long int L,unsigned char *nodo) 
{ 
  long int i,vol=L*L; 
   
  for (i=0;i<vol;++i) 
    nodo [i]=0; 
} 

//Funcao - Mostra as mensagens de erro e procede à saida do programa 
void 
erro(int n) 
{ 
  switch(n) 
    { 
    case (-1): 
      printf("\n    *** Numero de argumentos invalido ***\n\n"); 
      printf(" A entrada na linha de comando deve ser na forma:\n"); 
      printf("\n\t<nome_programa> <numero_repeticoes>\n\n"); 
      break; 
    case (-2): 
      printf("\n   *** Erro: Valor invalido para o num. de repeticoes ***\n"); 
      printf("\tEste numero deve ser um inteiro nao negativo \n\n"); 
      break; 
    case (-3): 
      printf("\n\n   *** Erro: Inseriu um tamanho para o lado invalido ***\n"); 
      printf("\tO tamanho tem de ser um inteiro maior que 0\n\n"); 
      break; 
    case (-4): 
      printf("\n *** Erro: Valor invalido para a probabilidade ***\n"); 
      printf("     Este valor tem de ser um real entre 0 e 1\n\n"); 
      break; 
    } 
   
  exit(n); 
} 

//Main 
int 
main(int argc, char **argv) 
{ 
  unsigned char *nodos; 
  int i=0,num=0,L,teste=0; 
  double prob; 
  //double t0,t1; 
   
  //verifica o num. de argumentos 
  if(argc!=2) 
    erro(-1); 

  //Verifica o argumento inserido (num. de visualizacoes) 
  if(sscanf(argv[1],"%d",&num)==0 || num<0) 
    erro(-2);      

  //Titulo e legenda  
  printf("\n\t*** PERCOLACAO NUMA REDE QUADRADA ***\n\n"); 
  printf("Legenda da rede:\n\n"); 
  printf("  1 - A celula da rede encontra-se ocupada\n"); 
  printf("  0 - A celula da rede encontra-se vazia\n\n"); 
   
  //Pede o tamanho do lado da rede 
  printf("\nEscolha o tamanho do lado da rede?\n"); 
  printf("Res:"); 
  teste=scanf("%d ",&L); 
  if(teste==0 || L<1) 
    erro(-3); 
     
//Pede a probabilidade de ocupacao 
  printf("\nE qual a probabildade de ocupacao de cada celula?\n"); 
  printf("Res: "); 
  teste=scanf(" %lf",&prob);  
  if( teste==0 || fabs(prob-0.5)>0.5) 
      erro(-4); 
   
  nodos=(unsigned char *)malloc( (L*L)*sizeof(unsigned char) ); 
     
  //printf("\nValores inseridos:\n\n"); 
  //printf("  Num. de visualizacoes  : %d\n",num); 
  //printf("  Tamanho do lado da rede: %d\n",L); 
  //printf("  Prob. de ocupacao      : %lf\n",p); 
   
  for(i=1;i<=num;++i) 
    { 
      //t0=time(NULL)+1; 
      //while(t1<t0) 
      //t1=time(NULL);     
      printf("\n\n** Visualizcao numero %d **",i); 
       
      //Inicializa a rede a zeros e mostra-a no ecran 
      inic_nodo(L,nodos); 
      printf("\n\n  Rede inicializada a zeros\n"); 
      printf_config(L,nodos); 
       
      //Gera uma configuracao da rede e mostra-a no ecran 
      gera_config(prob,L,nodos); 
      printf("\n\n  Configuracao da rede preenchida \n"); 
      printf_config(L,nodos); 
      printf("\n"); 
    } 
   
  printf("\n\n"); 
   
  return 0; 
}  

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

A solução pode passar por deixares sempre o buffer limpo.

Por exemplo, depois do primeiro scanf podes fazer while(getchar()!='\n');. Isto deve eliminar todos os caracteres até encontrar um '\n'.

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Mas isso não resolve o problema. O programa não detecta quando é que getchar()=='\n' e continua sempre a ler.

E quanto à pausa no programa, existem soluções? ;)

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Quando acabas de introduzir um valor não carregas no ENTER?

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Sim, mas eu testei e não deu  :hmm:. Vou ver outra vez.;)

Edit:Afinal deu. Devo ter feito algo de errado na tentativa anterior;)

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Há algum contra em usar o código que eu tenho a comentado no while() para pausar o programa?

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Há algum contra em usar o código que eu tenho a comentado no while() para pausar o programa?

Desperdício de ciclos. O sleep não serve?

0

Partilhar esta mensagem


Link para a mensagem
Partilhar noutros sites

Crie uma conta ou ligue-se para comentar

Só membros podem comentar

Criar nova conta

Registe para ter uma conta na nossa comunidade. É fácil!


Registar nova conta

Entra

Já tem conta? Inicie sessão aqui.


Entrar Agora