Ir ao conteúdo
  • Cadastre-se

Lucas.Rocha_21

Membro Júnior
  • Posts

    17
  • Cadastrado em

  • Última visita

  1. Estava vendo as funções responsáveis pela leitura e gravação de strings via arquivo texto e me deparei com a função fgets, que recebe como parâmetro um vetor de carácter, a quantidade de strings que serão lidas e o ponteiro que aponta para o meu arquivo texto. Para tal é necessário que eu aloque em tempo de copilação um vetor com uma quantidade fixa de espaço para armazenar o conteúdo das linhas, como pode ver neste programa-teste que fiz: #include <stdio.h>#include <stdlib.h>#include <locale.h>int main(void){ FILE *arquivoTexto; char letra; int cont = 0; char temp2[100]; setlocale(LC_ALL, ""); //aceitar acentos arquivoTexto = fopen("teste.txt", "w"); if(!arquivoTexto) //ou arquivoTexto == NULL { printf("Arquivo nao pode ser gravado"); exit(1); } fputs("Isto é um teste para ver se este arquivo\n", arquivoTexto); fputs("texto conseguiu gravar os arquivos adequadamente:\n", arquivoTexto); fputs("Mesmo com quebra de linhas\te inclusive tabulações.\n", arquivoTexto); fputs("Encerro este texto para afirmar que consegui.", arquivoTexto); printf("O arquivo foi gravado corretamente.\nAbra-o para ver\n\n"); fclose(arquivoTexto); arquivoTexto = fopen("teste.txt", "r"); if(!arquivoTexto) //ou arquivoTexto == NULL { printf("Arquivo nao pode ser lido"); exit(1); } while(!feof(arquivoTexto)) { fgets(temp2, 100, arquivoTexto); printf("%s", temp2); } return 0;} Como vocês percebem, cada linha do meu texto não possui um número fixo de caracteres. Uma delas é maior que a outra. Logo preciso "desperdiçar memória" chutando um valor alto para armazenar as strings. Gostaria de saber se tenho como alocar dinamicamente este vetor temp2 para que ele armazene a linha, não importa o número de caracteres que ela tenha e como procederia para fazer isto. Ou esta função fgets só aceita vetores estáticos? trabalhando com arquivos 3.rar
  2. Vou te ajudar com a ideia do número 2. Você declara uma variável inteiro que receba o conteúdo do 1º elemento da matriz (ex: maior = vetor[0][0]) e então dentro de dois laços (i e j) compara com cada elemento da matriz. Se este elemento for maior que a variável maior, este elemento será o maior, a coluna será j e a linha será i (aquele laço dos dois for). Assim: maior = vetor[0][0]; for(i = 0; i < 2; i++){ for (j = 0; j < 2; j++){ if (vetor[i][j] > maior) { maior = vetor[i][j]; coluna = j + 1; linha = i + 1; } } } Me baseei num vetor 2x2. No caso de 5x7, só alterar para i < 5 e j < 7
  3. Miguel, Já que não conseguiu rodar o programa (você falou por MP), vou colocar aqui o código completo... #include <stdio.h>#include <stdlib.h>int* SomaElementosColuna(int rows, int cols, int **matriz);void ImprimeMatrizDinamica(int **matriz, int rows, int cols);void ImprimeVetorDinamica(int *vetor, int cols);int main(void){ int i, j, linhas, colunas; int **matrizDados; int *resultado; printf("Entre com o numero de linhas: "); scanf("%i", &linhas); printf("\nEntre com o numero de colunas: "); scanf("%i", &colunas); matrizDados = (int**)malloc(linhas * sizeof(int*)); if(!matrizDados){ printf("\nNao foi possivel alocar memoria\n"); exit(1); } for(i = 0; i < linhas; i++) { *(matrizDados + i) = (int*)malloc(colunas * sizeof(int)); if(!(matrizDados + i)){ printf("\nNao foi possivel alocar memoria\n"); exit(1); } } for(i = 0; i < linhas; i++) { for(j = 0; j < colunas; j++){ printf("\nEntre com a linha %i coluna %i :", i + 1, j + 1); scanf("%i", *(matrizDados + i) + j); } } ImprimeMatrizDinamica(matrizDados, linhas, colunas); resultado = SomaElementosColuna(linhas, colunas, matrizDados); ImprimeVetorDinamica(resultado, colunas); return 0;}void ImprimeMatrizDinamica(int **matriz, int rows, int cols){ int i, j; printf("\nMatriz inserida:\n"); for(i = 0; i < rows; i++) { for(j = 0; j < cols; j++){ printf(" %6i ", *(*(matriz + i) + j)); } printf("\n"); }}void ImprimeVetorDinamica(int *vetor, int cols){ int i; printf("\nResultado da soma das colunas:\n"); for(i = 0; i < cols; i++) { printf(" %6i ", *(vetor + i)); } printf("\n");}int* SomaElementosColuna(int rows, int cols, int **matriz){ int *soma; int i, j, m; soma = (int*) calloc(cols, sizeof(int)); for(j = 0; j < cols; j++){ for(i = 0; i < rows; i++){ *(soma + j) = *(soma + j) + *(*(matriz + i) + j); } } return soma;} Como falei acima, se não souber ponteiro e alocação dinâmica, vai dançar porque o programa é basicamente isto. Entre as linhas 15 e 18 peço para o usuário que insira a quantidade de linhas e colunas desejadas. Depois disto, na linha 19, é alocado um vetor de ponteiros em matrizDados, com um teste caso não consiga alocar. Se não conseguiu entender, é só olhar o desenho que pus no meu post acima. Na linha 26, para cada ponteiro, aloquei um vetor de inteiro com a quantidade de elementos da coluna. Ponteiro para ponteiros é essencial para que seja alocada uma matriz dinamicamente (com m linhas e n colunas). E isto em tempo de execução. Perceba que não aloquei nada antes do programa copilar, como seria o caso do vetor estático que escrevi acima. Entre as linhas 36 e 41, você insere os dados nesta matriz. Um detalhe interessante: *(*(matriz + i) + j) ==> retorna valor já que é o conteúdo do conteúdo da matriz[j]. *(matriz + i) + j => é equivalente a escrever &matriz[j]. retorna endereço. Da maneira que escrevi, não precisa do "&". Depois ele vai imprimir os dados da matriz que digitou E na linha 45 é onde a mágica acontece. Passo linhas e colunas como parâmetros de entrada da função porque preciso de uma condição de parada. E o ponteiro de ponteiro matriz onde está alocado a minha matriz (volte ao desenho se não entendeu). Já expliquei acima como este programa funciona. E no fim ele imprime o vetor resultado com a soma dos elementos das colunas. Reforçando, sem entender ponteiro e alocação dinâmica, tudo que escrevi parece grego. Copie e cole o código no seu programa de desenvolvimento em C e veja-o rodando. Talvez entenda mais fácil assim. Abraços.
  4. Olá, Miguel. Tudo beleza? Este problema é que você colocou é bastante desafiador porque exige de você um conhecimento de alocação dinâmica e também um pouco de "ponteiro de ponteiros" (o popular **matriz) haha. Só em ouvir este nome me dá calafrio. No programa principal - int main(void) - fará o seguinte: Primeiramente você vai requisitar ao usuário a quantidade de linhas e colunas da matriz de inteiros. Depois você vai alocar com a função malloc a quantidade de linhas (serão os ponteiros para onde será apontado as colunas) Depois você vai alocar cada inteiro num for até a quantidade de linhas um vetor com quantidade de colunas. Para melhor entendimento, eu fiz um desenho de ponteiros e matrizes alocada dinamicamente: Depois você vai inserir os dados na matriz alocada dinamicamente. Em seguida, nesta função da soma dos elementos da coluna, receberá como parâmetros de entradas o número de linhas, colunas e o ponteiro de ponteiro matriz. Dentro desta função vai alocar um vetor dinamicamente (vetor soma) com a quantidade de elementos de uma coluna, onde vai armazenar o resultado. Logo, o retorno dela é um vetor. Desta maneira a assinatura da função seria esta: int* SomaColunas(int linhas, int colunas, int **matriz) Um exemplo só. A partir disso você vai somar as colunas dentro de dois for, assim: int *soma; int i, j; soma = (int*) calloc(cols, sizeof(int)); for(j = 0; j < cols; j++){ for(i = 0; i < rows; i++){ *(soma + j) = *(soma + j) + *(*(matriz + i) + j); } } return soma; A malandragem aqui é ter invertido a ordem do i e j para que assim a matriz seja percorrida coluna por coluna (em vez de linha por linha). Aconselho você a alocar o vetor soma com calloc() porque com ela já vai atribuir 0 a todos os valores (enquanto malloc() deixa lixo). Espero que entenda a explicação. Tenho o programa aqui pronto rodando. Se mesmo assim não funcionar, disponibilizo o código completo. Qualquer coisa, procure sobre "ponteiros e matrizes" e "alocação dinâmica". Acho que vai te ajudar. ==================/====================== Agora que vi seu código... Está errado num fato simples. Não posso fazer isto: int vetor[10];i = 15;vetor[i] = 3; Isso é um erro fatal. Vetores estáticos tem seu espaço alocado antes do programa ser executado (tempo de copilação). Este valor NÂO pode ser alterado. Se eu fizer esta atribuição que fiz acima, nada me garante que no endereço de memória onde tá armazenado o vetor não seja código do próprio programa ou qualquer outra aplicação do sistema operacional. Por isto que para este problema, você precisa de conhecimento de ponteiros e alocação dinâmica porque AI sim, este será alocado e armazenado na memória do computador em tempo de execução.
  5. Diferente de alguns outros tópicos que surgem eventualmente nos quais a pessoa coloca simplesmente o enunciado do exercício e deixa um vazio profundo para que você resolva por ela , este aqui está pronto e feito por mim haha. Para quem não sabe, palíndromo são aquele grupo de palavras (ou orações) que é lido da mesma maneira na ordem direita para esquerda e vice-versa. Um exemplo é a palavra arara ou então ovo. A minha dúvida é o seguinte: No código que eu digitei, gostaria de saber se há uma maneira mais eficiente de inserir a palavra na lista que não seja digitar caracter por caracter e pressionando ENTER. Gostaria por exemplo em digitar em uma linha só do prompt a palavra ou oração e apertando enter continua o programa. Um vetor temporário para tal não seria bem o desejado. Caso contrário, a lista seria inútil. A intenção da lista é justamente poder colocar a palavra o quão grande quanto eu queira já que o espaço para a palavra seria armazenado em tempo de execução e não em tempo de copilação. Código: #include <stdio.h>#include <stdlib.h>#include <string.h>#include "lista.h"#include "pilha.h"#include <locale.h>void TransfereParaPilha (MinhaLista *x, MinhaPilha *y);int Compara(MinhaLista *x, MinhaPilha *y);void main(void){ setlocale(LC_ALL, ""); TipoCelula *lista; MinhaPilha *PilhaTeste; lista = inicializar(); PilhaTeste = novapilha(); char letra; while(letra != '\n') { printf("Insira uma letra e digite ENTER\n(ou aperte ENTER 2 vezes para sair || 3 vezes para continuar).......: "); scanf("%c%*c", &letra); if (letra != '\n') lista = inserir_ultimo(lista, (tolower(letra))); } if(!TestaListaVazia(lista)) { printf("A palavra é "); imprimir(lista); TransfereParaPilha(lista, PilhaTeste); if(Compara(lista, PilhaTeste) == 1) printf("\ne é palíndromo"); else printf("\ne não é palíndromo"); } else printf("\nNão digitou a palavra!\n");}void TransfereParaPilha (MinhaLista *x, MinhaPilha *y){ TipoCelula *listatemp; listatemp = x; while(listatemp != NULL) { push(y, listatemp -> letra); listatemp = listatemp -> proximo; }}int Compara(MinhaLista *x, MinhaPilha *y){ TipoCelula *listatemp; listatemp = x; char temp; while(!TestePilhaVazia(y)) { if (listatemp -> letra != ' ') { do { temp = pop(y); } while (temp == ' '); if(temp != listatemp -> letra) return 0; } listatemp = listatemp -> proximo; } if(TestePilhaVazia(y)) //quer dizer que já comparei com todos os elementos return 1;} Aviso: Este programa faz uso das bibliotecas customizadas "lista.h" e "pilha.h" que eu fiz. Logo, se você copiar diretamente para o main.c de seu projeto, vai "dar ruim"! O programa funciona da seguinte maneira. Você vai inserindo letra por letra a palavra desejada e nisto, vai sendo transferido para a lista onde ela estará armazenada. Se eu der enter duas vezes (justamente por causa do %*c) que desconsidera o ENTER que aperto a cada letra, lá no buffer, eu desisto de colocar a palavra, a lista portanto é vazia e logo não digitei a palavra. Para continuar o programa preciso dar enter 3 vezes. A terceira é para o programa dar prosseguimento. Explicado isto, depois cada elemento da lista é jogado para uma pilha e começa a comparação. O programa é capaz por exemplo de ignorar os espaços. Neste caso "A caca" seria um palíndromo (e é um palíndromo!). Para tal verifico primeiro se o elemento da lista é um espaço. Se for, peço para que ele avance uma letra. Caso contrário, vejo se o elemento da pilha é um espaço. Se for um espaço, ele vai desempilhando quantas vezes forem necessárias até que não seja mais espaço. Caso o elemento da pilha e da lista forem diferentes, a palavra não é um palíndromo. Se a pilha estiver vazia, quer dizer que eu comparei todos os elementos da lista. Então neste caso, a palavra seria um palíndromo. Abaixo, o arquivo do projeto. palindromo_lista_pilha - 2.0.rar
  6. Ué... crie uma variável chamada soma e faça int soma; soma = num1 + num2 + num3 + num4; printf("%i", soma);
  7. Vamos lá: para fazer este programa, eu utilizei de parte da lógica que o @LNV falou: void main(void){ int base, a, espaco, temp, asterisco, i; printf("Insira o comprimento da base......: "); scanf("%i", &base); a = (base / 2) + 1; espaco = a - 1; if (base % 2 != 0) asterisco = 1; else asterisco = 0; printf("\n"); for (i = a; i > 0; i--){ //impressão dos espaços temp = espaco; while (temp != 0){ printf("%c", 32); temp--; } //impressao dos asteriscos temp = asterisco; while (temp != 0) { printf("%c", 42); temp--; } asterisco += 2; espaco--; printf("\n"); }} Um detalhe a se notar ao rodar o programa é que: se o comprimento da base for par, obviamente cada linha do triângulo terá asteriscos pares, não tendo a ponta com somente 1 asterisco. Se for ímpar, cada linha terá número ímpar de asterisco. Desse modo, vamos trabalhar com número par. Ao colocar a = 6 por exemplo, de acordo com a lógica acima, terá 4 linhas (uma delas vazia. O número de espaços é sempre um menor a base, para que assim se ponha asteriscos. Importante salientar que a variável temp vai manipular tanto o número de espaços quanto a impressão do asterisco. Primeiramente vai imprimir os espaços até temp chegar a zero. Na tabela ASCII, o espaço é equivalente ao número 32. Primeiramente teremos uma linha vazia, já que na condição acima (base % 2 != 0), em outras palavras, se a base for ímpar, tem um asterisco na ponta. Caso contrário não tem. Não entrará no segundo while. Asteriscos vai ser incrementado em dois em dois (atenção: escrever "asterisco += 2" é a mesma coisa que "asterisco = asterisco + 2") e espaços será decrementado até acabar a quantidade de linhas. No final há uma quebra de linha. Espero que tenha ajudado
  8. Alternativamente, você pode utilizar ponteiros neste exercício. Veja o meu código: #include <stdio.h>#include <stdlib.h>void main(void){ char vogais[] = "aeiou"; char frase[100]; char *p = frase; char *q = vogais; char c; int i; int j = 0; printf("Insira uma frase\n"); gets(frase); printf("\nAs vogais: " ); for (i = 0; i < strlen(frase); i++) { c = tolower(*(p + i)); while (j < strlen(vogais)) { if (c == *(q + j)) { printf("%c", *(p + i)); break; } else { j++; } } j = 0; }} Eu criei duas strings. Uma delas contém as vogais possíveis. A outra string armazenará a frase. Como vi que é novato, ponteiros são variáveis que armazenam endereço de memória de uma outra variável O ponteiro do tipo char p por exemplo, vai apontar para o endereço do primeiro caracter de frase (neste caso não preciso do "&" porque o nome sozinho do array já me representa o endereço do primeiro índice). Do mesmo jeito foi feito com q em relação a string vogais. Os inteiros i e j serão úteis abaixo para a comparação dos termos. Explicado as variáveis, vamos ao programa: Assim que você digitar a frase, ele vai entrar num for que vai comparar letra a letra até o '\0' de frase (que seria o equivalente a i[strlen(frase)] = '\0'). É quando indica que a frase acabou. Neste caso, para corrigir a diferenciação de maiúsculas e minúsculas, criei uma variável char c que armazena temporariamente cada letra da frase, mas em minúsculo, com a função tolower. Escrever *(p + i) - utilizando-se o conceito de aritmética de ponteiros, é a mesma coisa que escrever frase , uma vez que p aponta pra frase. Após c armazenar a letra em minúsculo, vai comparar se é igual a alguma das vogais na string vogais. Se for igual a *(q + j), que é igual a vogais[j], ele vai imprimir a letra do jeito que está na frase (maiúsculo ou minúsculo) e vai sair do while através do comando break. Se não, vai incrementar j e vai comparar o caracter c com outras vogais. Em ambos os casos, no final eu zero o j para que recomece a comparação com as outras letras das frase e assim sucessivamente. Quando você rodar este programa vai entender melhor o que digitei e verá que funciona. Espero que tenha sido útil
  9. Esta supressão seria isto? printf("Digite seu nome: ");scanf("%s%*c", nome);printf("Qual o sexo?");scanf("%c", &sexo); o %*c???
  10. Pode nos disponibilizar o código fonte deste programa que você fez? Tenho até uma sugestão... Limpe o buffer entre os dois scanf quando pede nome e sobrenome. Quando você digita o nome e pressiona o enter, provavelmente está armazendo o caracter enter em sobrenome. Por isto a saída pode estar dando vazio. Insere este código depois da leitura do nome: fflush(stdin);
  11. Mas antes de ver listas, pilhas e filas, você precisa saber arrays muito bem. Até porque logo mais a frente você vai ser introduzido ao conceito de ponteiros e ela está ligeiramente ligada a matrizes e vetores.
  12. Errado. Seria mais ou menos isto: if (i == c) { matriz[i][c] = pow(4, i);} Desse modo, caso i seja 0, vai ser armazenado o valor 1 a matriz[0][0]. Já se i for 1, vai armazenar o valor 4 em matriz[0][0] e assim sucessivamente. Sabe porque o teu código tá errado? Porque desta maneira que você escreveu pow(matriz[i][j], 0) Primeiramente você ainda não sabe o que tem na memória em matriz[j] já que você simplesmente a inicializou. Não declarou nenhum valor ainda. Logo, tem lixo na memória. Segundo que está sempre elevando qualquer coisa a zero. E na potenciação, qualquer coisa elevado a zero dá um.
  13. Realmente estes valores pré-estabelecidos tem um padrão. Olha só: 4 elevado a 0 dá 1. 4 elevado a 1 dá 4 4 elevado a 2 dá 16 4 elevado a 3 dá 64. Estes valores tem um padrão. Pensa um pouco que aí você vai conseguir inserir estes valores em tempo de execução.
  14. Então você quer imprimir uma matriz no qual: matriz[0][0] = 1;matriz[1][1] = 4;matriz[2][2] = 16;matriz[3][3] = 64; Caso contrário, você pode inserir outros valores? Pois é isto que deu a entender no seu código.
  15. Você pode criar a matriz 4x4 por exemplo, depois crie uma variável i (inicialize-a com zero) while (i < 4){ printf("%i ", matriz[i][i]); i++;} Deste modo vai imprimir os valores que estão na diagonal principal da sua matriz. Só um detalhe que esqueci de mencionar: No método acima ela vai imprimir linearmente. Lembre-se que matriz na computação não tem o mesmo conceito de matriz na matemática. Na realidade na memória os números estão armazenados linearmente. É só dito assim para facilitar a abstração. Tanto é que em inglês tudo é o mesmo nome: array.

Sobre o Clube do Hardware

No ar desde 1996, o Clube do Hardware é uma das maiores, mais antigas e mais respeitadas comunidades sobre tecnologia do Brasil. Leia mais

Direitos autorais

Não permitimos a cópia ou reprodução do conteúdo do nosso site, fórum, newsletters e redes sociais, mesmo citando-se a fonte. Leia mais

×
×
  • Criar novo...