Jump to content
SuM

Código Morse

Recommended Posts

SuM

Boa tarde!

Estou a fazer um projecto de programação(1º ano), para entregar sábado, em que é suposto o utilizador escrever uma sequência em código morse e algumas palavras que podem estar relaccionadas com o que o código morse diz (a sequência introduzida nao pode conter espaços, por isso é que ele tem de dar palavras ou era impossivel de descobrir o código). Com estes dados é suposto o programa devolver o nº de frases possiveis que o código morse pode traduzir.

Utilizo o visual Studio Express for Windows 7

Quando compilo, quando chega à parte em que é suposto ler as palavras aparece uma janela que diz o seguinte "Unhandled exception at 0x656CADD5 (msvcr110d.dll) in Relatório.exe: 0xC0000005: Access violation writing location 0x00000000."

O código é este:

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

char dic[1000][50]; /*dicionario introduzido*/
int indpal=0;

void trad1letra(char s[], char *dict[])
{
       int i;
       for(i=0; i<strlen(s);i++){
               switch(s[i]){
                       case 'A': strcat(dict[i],".-"); break;
                       case 'B': strcat(dict[i],"-..."); break;
                       case 'C': strcat(dict[i],"-.-."); break;
                       case 'D': strcat(dict[i],"-.."); break;
                       case 'E': strcat(dict[i],"."); break;
                       case 'F': strcat(dict[i],"..-."); break;
                       case 'G': strcat(dict[i],"--."); break;
                       case 'H': strcat(dict[i],"...."); break;
                       case 'I': strcat(dict[i],".."); break;
                       case 'J': strcat(dict[i],".---"); break;
                       case 'K': strcat(dict[i],"-.-"); break;
                       case 'L': strcat(dict[i],".-.."); break;
                       case 'M': strcat(dict[i],"--"); break;
                       case 'N': strcat(dict[i],"-."); break;
                       case 'O': strcat(dict[i],"---"); break;
                       case 'P': strcat(dict[i],".--."); break;
                       case 'Q': strcat(dict[i],"--.-"); break;
                       case 'R': strcat(dict[i],".-."); break;
                       case 'S': strcat(dict[i],"..."); break;
                       case 'T': strcat(dict[i],"-"); break;
                       case 'U': strcat(dict[i],"..-"); break;
                       case 'V': strcat(dict[i],"...-"); break;
                       case 'X': strcat(dict[i],"-..-"); break;
                       case 'Y': strcat(dict[i],"-.--"); break;
                       case 'W': strcat(dict[i],".--"); break;
                       case 'Z': strcat(dict[i],"--.."); break;

               }
       }
}

void compara ( char dict[][], int n, char seqmorse[])
{
       int i = 0;
       int j = 0;
       int c = 0; /*contador de frases*/
       for(i=0; i<= n-1; i++)
       {
               if (dict[i][indpal]==seqmorse[(strlen(dict[i][indpal])-1)])
               {
                       for(j=0; j=='\0'; j++)
                       {
                               compara(dict[i+1][indpal], n,
                                 seqmorse[j+(strlen(dict[i][indpal])-1)]);
                       }
                       c++;
               }
       }
       printf("O numero de frases validas e\': %d",c);
}

void main()
{
       int i, n; /* n -> num palavras*/
       int j, index;
       int p; /*contador de palavras*/
       char cmorse [1000]; /*codigo morse inserido*/
       char *dict[4000][50]; /*dicionario traduzido*/

       i=0;
       index=0;
       printf("Insira o codigo Morse que pretende descodificar:\n");

       scanf("%999[^\n]", cmorse);

       /*
       for(i=0; i<=999; i++)
       {
               if(cmorse[i] != '-' || cmorse[i] != '.')
               {
                       printf ("Codigo invalido");
                       getchar();
                       getchar();
                       exit(0);         /*end program*
               }
       }
       */
       printf("Insira o numero de palavras que o dicionario vai conter: \n");
       scanf("%d", &n);
       if(n>10000)
       {
               printf("O dicionario nao pode conter"
                      "mais do que 10000 palavras");
               exit(0);
       }
       printf("Insira as palavras do dicionario: \n");
       scanf("%9999[^\n]", dic);
       /*
       for(index=0; i<=n+1; index++)
       {
               for(j=0; j<=n+1; j++)
               {
                       scanf("%c", dic[i][j]);
                       p=i++;
               }
       }
       */
       for(i=0;i<=p; i++){
               trad1letra(dic[i], *dict[i][indpal]);
       }
       compara(dict[i][indpal], n, cmorse[j]);
}

Edited by pmg
Falta LP; indentacao (8 espacos)

Share this post


Link to post
Share on other sites
pmg

Para que serve esta definição?

char *dict[4000][50]; /*dicionario traduzido*/

dict é um array com 4000 elementos.

Cada um desses elementos é um array de 50 elementos.

Cada um desses (4000*50) elementos é um ponteiro.

Nenhum dos 200,000 ponteiros aponta para algum sitio significativo.


What have you tried?

Não respondo a dúvidas por PM

A minha bola de cristal está para compor; deve ficar pronta para a semana.

Torna os teus tópicos mais atractivos e legíveis usando a tag CODE para colorir o código!

Share this post


Link to post
Share on other sites
pmg

Mas não queres guardar as palavras em ponteiros, pois não?

Para um máximo de 4000 palavras, cada uma com um máximo de 49 caracteres, a definição (com inicialização) mais simples de usar é

char dict[4000][50] = {0};

Cada elemento de dict (dict[0], ..., dict[42], ... dict[3999]) irá ter uma palavra. Por exemplo:

scanf(" %49[^\n]", dict[0]); /* primeira palavra */
printf("%s", dict[42]); /* 43a palavra */

Edited by pmg

What have you tried?

Não respondo a dúvidas por PM

A minha bola de cristal está para compor; deve ficar pronta para a semana.

Torna os teus tópicos mais atractivos e legíveis usando a tag CODE para colorir o código!

Share this post


Link to post
Share on other sites
SuM

Ah, sim. Acho que já percebi. Mas na função trad1letra, nos parâmetros eu uso *dict porque senão dá erro no dict dentro da função. Só que depois na main, ao invocar a função da erro no segundo parâmetro (dict)...

Share this post


Link to post
Share on other sites
pmg

O que queres que a funcao trad1letra() faca?

Ao tentar analisar o teu codigo nao percebi a tua ideia.

Queres converter uma letra na sua representacao em morse (numa string)? E guardar essa string no "dicionario"?

Sugestoes: acaba com as variaveis globais, indenta o teu codigo, e especifica no papel quais as funcoes que precisas e o que cada uma delas faz. No teu programa tens tres funcoes: trad1letra(), compara(), e main(). O que e que cada uma destas funcoes faz? Precisas de mais funcoes? ...


What have you tried?

Não respondo a dúvidas por PM

A minha bola de cristal está para compor; deve ficar pronta para a semana.

Torna os teus tópicos mais atractivos e legíveis usando a tag CODE para colorir o código!

Share this post


Link to post
Share on other sites
SuM

Essa função traduz as palavras introduzidas pelo utilizador (dicionário) em código morse. Testa a primeira letra e vê qual o código correspondente, testa a segunda e etc. Depois, esse conjunto de caracteres fica guardado no array.

E a função "compara", supostamente, compara essas palavras traduzidas com a sequência morse introduzida. Testa todas as palavras do dicionário e vê qual corresponde à primeira palavra da sequência, se encontrar correspondência, testa essas palavras para a restante sequência morse.

O código está indentado, ao copiar é que nao ficou... E não, não preciso de mais funções

Share this post


Link to post
Share on other sites
pmg

No codigo abaixo estas a passar uma string (um array) e um caracter para a funcao trad1letra() (o loop corre um numero indeterminado de vezes porque nunca atribuiste um valor a variavel p).

        for(i=0;i<=p; i++){
               trad1letra(dic[i], *dict[i][indpal]);
       }

Se a funcao traduz as palavras do dicionario em codigo morse e as guarda no array, os parametros nao estao correctos.


What have you tried?

Não respondo a dúvidas por PM

A minha bola de cristal está para compor; deve ficar pronta para a semana.

Torna os teus tópicos mais atractivos e legíveis usando a tag CODE para colorir o código!

Share this post


Link to post
Share on other sites
pmg

Nao sei exactamente o que pretendes com o ciclo abaixo (com a chamada recursiva) ... mas ele so executa uma vez. Na "segunda" vez o j passa a 1 e o teste da falso portanto sai do ciclo

                       for(j=0; j=='\0'; j++)
                       {
                               compara(dict[i+1][indpal], n,
                                 seqmorse[j+(strlen(dict[i][indpal])-1)]);
                       }


What have you tried?

Não respondo a dúvidas por PM

A minha bola de cristal está para compor; deve ficar pronta para a semana.

Torna os teus tópicos mais atractivos e legíveis usando a tag CODE para colorir o código!

Share this post


Link to post
Share on other sites
SuM

Agora não tenho erros no programa, já corrigi as funções. No entanto, não compila, dá o seguinte erro: "Unhandled exception at 0x00C619B7 in Relatório.exe: 0xC00000FD: Stack overflow (parameters: 0x00000000, 0x00352000)."

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


char* trad1pal(char s[])	//função que traduz 1 palavra para morse
{
int i;
char trad[100]={0};
for(i=0; i<strlen(s);i++)
{
	switch(s[i])
	{
		case 'A': strcat(trad,".-"); break;
		case 'B': strcat(trad,"-..."); break;
		case 'C': strcat(trad,"-.-."); break;
		case 'D': strcat(trad,"-.."); break;
		case 'E': strcat(trad,"."); break;
		case 'F': strcat(trad,"..-."); break;
		case 'G': strcat(trad,"--."); break;
		case 'H': strcat(trad,"...."); break;
		case 'I': strcat(trad,".."); break;
		case 'J': strcat(trad,".---"); break;
		case 'K': strcat(trad,"-.-"); break;
		case 'L': strcat(trad,".-.."); break;
		case 'M': strcat(trad,"--"); break;
		case 'N': strcat(trad,"-."); break;
		case 'O': strcat(trad,"---"); break;
		case 'P': strcat(trad,".--."); break;
		case 'Q': strcat(trad,"--.-"); break;
		case 'R': strcat(trad,".-."); break;
		case 'S': strcat(trad,"..."); break;
		case 'T': strcat(trad,"-"); break;
		case 'U': strcat(trad,"..-"); break;
		case 'V': strcat(trad,"...-"); break;
		case 'X': strcat(trad,"-..-"); break;
		case 'Y': strcat(trad,"-.--"); break;
		case 'W': strcat(trad,".--"); break;
		case 'Z': strcat(trad,"--.."); break;

	}
}
return trad;
}
int compara ( char dict[][100], int n, char seqmorse[])   /*função que compara as palavras
  														traduzidas com a sequência morse*/
{
int i = 0;
int c = 0;  //contador de frases
int tampal; //tamanho da palavra

for(i=0; i<= n-1; i++)
{
	tampal = strlen(dict[i]);
	if (strncmp(dict[i], seqmorse, tampal)==0)
	{
		compara(dict, n, seqmorse+tampal);
	}
	 if(strcmp(dict[i], seqmorse)==0)
	{
		c++;
	}
}
return c;

}

void main()
{

int i, n;  // n -> num palavras
int j, index;
int p; //contador de palavras
char cmorse [1000];  //codigo morse inserido
char dic[10000][100]; //dicionario introduzido
char dict[10000][100]= {0};  //dicionario traduzido


i=0;

printf("Insira o codigo Morse que pretende descodificar:\n");
/*do
	scanf("%s", cmorse);
while (*cmorse!='-') || (*cmorse!=".");*/

scanf("%999[^\n]", cmorse);

printf("Insira o numero de palavras que o dicionario vai conter: \n");

/*do
	scanf("%d", &n);
	if(n>10000)
	{
		printf("O dicionario nao pode conter mais do que 10000 palavras");
	}
while (n>10000);
*/
scanf("%d", &n);

/*printf("Insira as palavras do dicionario: \n");*/

for(i=0; i<=n+1; i++)
{
	printf("Insira uma palavra: \n");
	scanf("%s",dic[i]);
	strcpy(dict[i], trad1pal(dic[i])); // copia a tradução da palavra
}

printf("\nO numero de frases validas e': %d", compara(dict, n, cmorse));

}

Edited by pmg
GeSHi

Share this post


Link to post
Share on other sites
pmg
char* trad1pal(char s[])        //função que traduz 1 palavra para morse
{
       int i;
       char trad[100]={0};
       for(i=0; i<strlen(s);i++)
       {
           /* ... switch que altera trad ... */
       }
       return trad;
}

Nao podes retornar trad.

O objecto trad só existe dentro da função trad1pal(). Quando a função acaba de executar, logo a seguir ao return, o array deixa de existir.

O que é comum fazer-se é passar a localização onde guardar o resultado.

Edited by pmg

What have you tried?

Não respondo a dúvidas por PM

A minha bola de cristal está para compor; deve ficar pronta para a semana.

Torna os teus tópicos mais atractivos e legíveis usando a tag CODE para colorir o código!

Share this post


Link to post
Share on other sites
SuM

mas como depois no main eu faço strcpy(dict, trad1pal(dic)); funciona

E agora, em vez de compilar no visual studio estou a compilar no code blocks, lá já compila e funciona direito. No entanto, a minha função compara não está totalmente correcta

Share this post


Link to post
Share on other sites
pmg

mas como depois no main eu faço strcpy(dict, trad1pal(dic)); funciona

Não!

Se eu meter gasóleo no meu carro, ele funciona --> o que não quer dizer que esteja correcto!

Corrige o erro


What have you tried?

Não respondo a dúvidas por PM

A minha bola de cristal está para compor; deve ficar pronta para a semana.

Torna os teus tópicos mais atractivos e legíveis usando a tag CODE para colorir o código!

Share this post


Link to post
Share on other sites
Nu^2

Nao podes retornar trad.

O objecto trad só existe dentro da função trad1pal(). Quando a função acaba de executar, logo a seguir ao return, o array deixa de existir.

O que é comum fazer-se é passar a localização onde guardar o resultado.

No return, a variável trad é equivalente a ter um apontador para char, logo é a localização onde está guardado o resultado... depois aquele apontador pode ser usado logo de seguida na main para ter acesso à string, e guardá-la... não há problemas, está correto e penso que não há outra maneira para devolver strings...

Share this post


Link to post
Share on other sites
HappyHippyHippo

No return, a variável trad é equivalente a ter um apontador para char, logo é a localização onde está guardado o resultado... depois aquele apontador pode ser usado logo de seguida na main para ter acesso à string, e guardá-la... não há problemas, está correto e penso que não há outra maneira para devolver strings...

a explicação do @pmg foi bem clara :

O objecto trad só existe dentro da função trad1pal(). Quando a função acaba de executar, logo a seguir ao return, o array deixa de existir.

sim existe vários métodos para fazer o pretendido, seja fornecer à função o local onde guardar o resultado ou o uso de memória dinâmica. podes até gravar em ficheiro (se bem que não aconselho ...)


IRC : sim, é algo que ainda existe >> #p@p

Share this post


Link to post
Share on other sites
pmg

... penso que não há outra maneira para devolver strings...

Primeiro: essa maneira que descreves esta errada, nao funciona! Nunca mais uses essa maneira. Se o professor disser para a usares pede ao professor para vir ao P@P.

As maneiras usuais para devolver strings sao a) alocar memoria dentro da funcao, devolver essa memoria, e, na funcao chamante, libertar a memoria em causa e b) passar a memoria para a string resultado (neste caso a gestao dessa memoria nao tem nada a ver com a funcao em causa)

Eu gosto muito mais da opcao b).

Exemplo:

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

/* a) alocacao dentro da funcao */
char *duplicaletras(const char *src) {
 char *dst = malloc(2 * strlen(src) + 1);
 char *dstbak = dst;
 if (dst) {
   while ((*dst++ = *src++)) { *dst = *(dst - 1); dst++; }
 }
 return dstbak;
}

/* b) passa memoria para resultado */
size_t removevogais(char *dst, size_t len, const char *src) {
 size_t copied = 1; /* pretend the '\0' is a copy */
 while (*src && copied < len) {
   if (!strchr("aeiou", *src)) {
     copied++;
     *dst++ = *src;
   }
   src++;
 }
 *dst = 0; /* terminar a string */
 return copied;
}

int main(void) {
 char *expanded, condensed[10];

 expanded = duplicaletras("Hello, World!");
 if (expanded) {
   printf("Resultado de duplicaletras(): %s\n", expanded);
 } else {
   printf("duplicaletras() devolveu erro.\n");
 }
 free(expanded);

 removevogais(condensed, sizeof condensed, "Hello, World!"); 
 printf("'Resultado' de removevogais(): %s\n", condensed);
 return 0;
}


What have you tried?

Não respondo a dúvidas por PM

A minha bola de cristal está para compor; deve ficar pronta para a semana.

Torna os teus tópicos mais atractivos e legíveis usando a tag CODE para colorir o código!

Share this post


Link to post
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.


×
×
  • Create New...

Important Information

By using this site you accept our Terms of Use and Privacy Policy. We have placed cookies on your device to help make this website better. You can adjust your cookie settings, otherwise we'll assume you're okay to continue.