-
Posts
6.526 -
Cadastrado em
-
Última visita
Tipo de conteúdo
Artigos
Selos
Livros
Cursos
Análises
Fórum
Tudo que arfneto postou
-
Use esse botão <> e coloquie seu programa dentro do formulário, ou fica muito difícil pra copiar para um editor quando alguém quer testar pra ajudar. Explique como reproduzir o problema. "Não dá certo" é um pouco vago.
-
Deve fazer isso hoje? E tem uma pergunta? Um código?
-
Em banco de dados você cria a tabela com os campos, define os campos pelos quais quer ordenar como chaves e, na hora de ler, no select acrescenta ORDER BY no final. Só isso. Se o que está dizendo nada tem a ver com bancos de dados eu postei uma função dias atrás em C e que até roda em C++ que faz isso enquanto lê do arquivo, usando uma variação do que é conhecido por insertion sort, aquele bem ingênuo que vai, claro, inserindo na ordem, como uma criança faria. Eis um código para inserir o registro R na tabela CSV. Pode adaptar em minutos para o seu caso. Sugiro ler com calma e entender como funciona. int insere_registro(Registro* R, CSV* csv) { int pos = csv->N; for (; pos > 0; pos = pos - 1) { if (csv->R[pos - 1].ispb > R->ispb) csv->R[pos] = csv->R[pos - 1]; else break; }; // achou o lugar csv->R[pos] = *R; csv->R[pos].ispb = R->ispb; csv->R[pos] = *R; csv->N += 1; return csv->N; }; Eis a ideia: você olha do fim pro começo procurando o lugar pra colocar o novo se o que está vendo na tabela é maior você vai puxando pra cima abrindo lugar para o novo quando sair do loop pos vai marcar o lugar certo e você copia o novo para lá. Insertion Sort. Sobre seu programa Use aquele botão <> neste forum para colocar seu código dentro de um formulário, como está vendo aqui neste tópico. Assim facilita para alguém copiar para testar e tentar te ajudar. Não use menus para testar seu programa. Só coloque isso depois que estiver funcionando. Só perde tempo assim. E perde muito tempo. main() deve ser SEMPRE a primeira função de seu programa. Use protótipos e declare as funções no início SEM nomes para os argumentos/ E use argumentos... Escreva seu programa em torno dos dados. Sempre. NUNCA use variáveis globais. É um problema e vai sempre dar errado. Por alguma razão os autores recomendam não usar. Ou deveriam. Os professores recomendam não usar. Ou deveriam. Empresas proíbem. Se usa função retorna void perde uma oportunidade de no mínimo retornar uma condição de erro. Se ela não tem argumentos em geral quer dizer que está usando uma variável global e é uma bobagem. Use typedef para dar um nome às suas estruturas. Assim é mais legível e evita o inferno de ter que digitar struct coisa x toda hora. NUNCA declare nada num struct. Se copiar para outro arquivo a declaração vai junto. E fica difícil de achar. Veja o f solitário no seu programa... Use uma convenção para seus tipos, como a primeira letra maiúscula como é costume em java, ou algum padrão tipo um prefixo ST_ ou sei lá, pra você saber quando lê que é um tipo e não uma variável qualquer Ao invés de struct pecas { char nome[34]; int codigo; float valor; int e; int quantidade, quant, conf, totalquant; } f; Entenda que seria bem melhor, se fosse usar assim, declarar a struct como f e a variável como pecas. Pense bem: no programa vai usar um nome bobinho como f toda hora? junto com todas aquelas variáveis de uma letra? Não ficaria melhor escrever pecas.codigo = 324; do que f.valor = 34.56; Não declare mais de uma variável por linha. C não cobra por linha de programa. E depois é um inferno você ficar procurando onde está a declaração de conf por exemplo. E quando tem ponteiros e valores é o d!@80 também. Veja int a,* e, c=0; int d=22, f = 300, coisa = 3; E compare int a = 0; int c = 0; // sempre inicialize tudo int coisa = 22; int d=22, int* e = NULL; // o tipo de e eh int* int f = 300; E veja como é mais simples achar as coisas, descobrir o tipo de algo e tal. E que assim typedef struct { char nome[34]; int codigo; float valor; int e; int quantidade; int quant; int conf; int totalquant; } Peca; // e depois em main() Peca pecas[300]; // plural :) afinal sao 300 Peca uma_peca; Peca* estoque = pecas; estaria bem melhor. Tem certeza de que faz sentido ter um campo quant, um campo quantidade e um campo totalquant no mesmo registro??? E não teria um nome mais expressivo para e? Vai lembrar do que é e daqui a 4 dias? 40 dias? E veja que a struct define uma peca e não várias, de modo que o plural não se aplica Quando você declara uma função void cadastra() quase sempre está errado. Veja a diferença int res = cadastra(&uma_peca, estoque); e você já imagina que cadastra vai retornar algum status e vai inserir uma peça em um estoque. No mínimo já deu pra ver que pode ter mais de um estoque, por exemplo...
-
C Programa em C para simular operações de uma fila (FIFO)
arfneto respondeu ao tópico de Ferraz.Gabrielle em C/C#/C++
Uma função "administrativa" da porque também é muito citada Define(F,el,P) para alterar a prioridade do elemento el para o valor P. Mas não é assim essencial. Muitos citam também vazia() cheia() tamanho() e coisas assim. Mas são todas triviais. -
O propósito do autor deve ter sido ter algo interativo. Nunca li esse livro. Assim o leitor digita algo e vê o resultado e tal. Mas não é nada produtivo e você vai ver isso a cada vez que insistir nisso. Só vai perder seu tempo. fflush(stdin) Isso é bobagem e é uma pena que esteja até em livros e em artigos pela internet. Já expliquei isso outras vezes e a razão é simples fflush() só está definido para arquivos de saída. É oficial. o comportamento de fflush() para arquivos de entrada é indefinido. Apenas a Microsoft usa isso na entrada e nem é certo que vá funcionar em todas situações. se usou fgets() não tem nada no buffer para você "limpar". Se quer mesmo fazer isso em Windows o oficial é FlushConsoleInputBuffer() e é só uma linha e é oficial e suportado rem todas as versões desde os anos 80. Você vai mesmo a cada vez que for testar seu programa digitar ao menos 2 ou 3 conjuntos de dados da agenda? Sério? Usando isso typedef struct contatos { char nome [50], telefone [40], email [40]; }agenda; Ao invés disso typedef struct { char nome[40]; char telefone[20]; char email[30]; } Agenda; E depois Agenda agenda[5] = { { "nome1", "tel1", "email1" }, { "nome2", "tel2", "email2" }, { "nome3", "tel3", "email3" }, { "nome4", "tel4", "email4" } }; int cont = 4; E isso int cont = 4; lista_agenda(agenda, cont); agenda[cont] = agenda[0]; cont = cont + 1; lista_agenda(agenda, cont); Não sei o que fez você mudar isso em relação ao que te mostrei. Espero que não tenha visto isso nesse seu livro. Se viu recomendo mudar de livro. Não há razão para declarar contatos. Justamente para não declarar a struct contatos é que está usando o typedef: para poder usar agenda. Use alguma convenção para esses typedef. Tem gente que usa a primeira letra em maiúscula como te mostrei, tem gente que usa um prefixo, tem gente que usa tudo em maiúsculas. Escolha algo, mas recomendo fazer isso. Evite ao máximo declarar mais de uma variável na mesma linha. É só problema. Dificulta mudar algo, achar as variáveis, inicializar as coisas. Isso está em muitos guias de conduta de empresas e escolas e na internet. E podia bem estar em seu livro Viu como inserir um cara a mais no fim da agenda? Como usar uma função para poder listar os caras? Siga por esse caminho e vai terminar antes. Use uma função para inserir e outra para listar (sim, eu já te deixei uma) e coloque isso no programa. Uma função que insere() recebe uma struct e grava na agenda. Simples assim. Dese modo quando você ler e quiser inserir um valor você só escreve insere(valor,agenda); Não mistures as coisas. Assim não: printf ("Código: %d\n", rand()%5); /*inclui essa função rand pra gerar codigo, mas como imprimir esse codigo gerado?*/ printf ("Digite o nome:"); /*se digito letras da erro. só permite digitar um caractere ???*/ fgets (dados[cont].nome, 50, stdin); fflush (stdin); printf ("Digite o telefone:"); fgets (dados[cont].telefone, 40, stdin); fflush (stdin); printf ("Digite o e-mail:"); fgets (dados[cont].email, 40, stdin); Veja a diferença Agenda um; // nunca misture as coisas printf ("Código: %d\n", rand()%5); /*inclui essa função rand pra gerar codigo, mas como imprimir esse codigo gerado?*/ printf ("Digite o nome:"); /*se digito letras da erro. só permite digitar um caractere ???*/ fgets um.nome, 50, stdin); printf ("Digite o telefone:"); fgets (um.telefone, 40, stdin); printf ("Digite o e-mail:"); fgets (um.email, 40, stdin); insere( um, agenda ); Você nunca mistura as coisas lendo direto dentro da sua estrutura. Isso fica no meio do programa e como já expliquei só vai atrasar tudo. Veja acima e entenda que você pode usar insere direto e gravar um cara ou 6.700 deles num comando só. E isso é produtivo e não o contrário. E você pode chamar insere() com dados constantes e testar o programa já, como te mostrei. Isso não foi uma boa ideia: printf ("Código: %d\n", rand()%5); /*inclui essa função rand pra gerar codigo, mas como imprimir esse codigo gerado?*/ rand()%5 vai retornar um número entre 0 e 4. Para que isso? Apenas use um código sequencial, a própria posição na agenda. E rand() pode duplicar e você precisa tratar isso: se vierem dois 3 em seguida por exemplo, ou vai gravar um sobre o outro? Não somou nada e criou um problema. Note que rand() em geral começa por uma chamada a srand(). Leu a documentação?
-
C Programa em C para simular operações de uma fila (FIFO)
arfneto respondeu ao tópico de Ferraz.Gabrielle em C/C#/C++
Você não disse nada sobre qual seria sua dificuldade. Programou alguma outra fila? alguma outra estrutura? Uma pilha talvez? Uma lista ligada? Um fila com prioridade não vai acrescentar muito. Com o máximo definido em 10 posições e nenhuma restrição de como implementar pode ser até simples. Parece claro que vai usar uma struct com o código do processo, do usuário e a prioridade de execução. O tamanho do arquivo como "dado armazenado" é algo meio bobinho já que é bem óbvio que precisa saber quantos caras tem na fila a cada momento. Não escreveu nada? Nem os dados? Comece sue programa sempre em torno dos dados. Escreva a estrutura dos dados e da fila. E entenda que são coisas separadas. A fila nada tem a ver com os dados. Nunca misture as coisas. Há uma razão para o A em ADT. Esses tipos todos são abstratos. o A. Filas, pilhas, filas com prioridade --- porque --- árvores, tries, hash, todos. No oficial da porque você só precisa de 3 funções: insere(el,F) insere o elemento el na fila F max(F) retorna 'el' o primeiro da fila Extrai(F) exclui o primeiro da fila Na hora de implementar recomendo que escreva lista(F) primeiro de tudo, porque é claro que precisa poder listar antes de criar criar pode ser uma consequência de tentar insere() numa lista vazia, certo? Não precisa ser uma função separada Escreva as estruturas e declare uns valores como constantes e termine o programa. Espere até a última hora para ler valores ou criar menus ou essas coisas que tomam muito tempo e não acrescentam nada. Como o enunciado se for só isso nada diz sobre como implementar use apenas um vetor de 10 estruturas e uma estrutura de controle como achar mais fácil pra controlar. Como nada foi restrito você pode implementar a prioridade na entrada ou na saída E escreva aqui sobre suas dúvidas e podemos ajudar. Sobre porque postei vários programas completos aqui neste forum, não sei se em C ou C++. Talvez possa localizar clicando no meu perfil e em explorar conteúdo ou algo assim. Não me lembro agora ao certo. -
Acho que sim. Faça algo objetivo agora. Apenas declarou tudo vazio. Eu te mostrei como. usou robos e planetas mas a struct define um único robo e um unico planeta. Porque plural? se mudou a terminologia clássica para usar robos porque usou n_troopers e não n_robos ? evite declarar mais de uma variável por linha. Não ajuda em nada e conforme o programa cresce só atrapalha não use o mesmo nome para struct e instâncias. Não leva a nada. Muita gente usa prefixos ou a primeira letra em maiúscula
-
Existe uma correspondência entre cada linha que você põe no programa e algum resultado... O cara vai escolher a posição do item que vai remover e você vai ler posicao, naquele scanf() E tem que mover os que estão depois daquele escolhido para a esquerda para sumir o que o cara escolheu remover. Você só copiou o exemplo que te mostrei de como copiar o segundo no primeiro.
-
não fez nem perto do jeito que eu disse. E te mostrei um exemplo Que leu dessa parte que eu te expliquei? Está igualzinho em seu programa E isso?
-
Tem? Você vai perguntar pra ele qual vai remover, quando corrigir aquele comando scanf() que está errado lá em seu programa. Quando souber você vai usar um loop, um comando, por exemplo um for() que já aceita os índices, e apenas faz o que precisa: move os caras pra esquerda para cobrir a posição do que saiu. A fila anda.
-
Agora que deve ter percebido também não respondeu Eu te mostrei como deixar os vazios atrás...Basta usar aquele comando várias vezes...
-
Entendeu o que expliquei? Não respondeu nada. Use os índices. Se quer copiar o segundo para o primeiro escreva Elemento[2] = Elemento[1];
-
Não pode fazer isso em C. Leia as mensagens de erro que o compilador está te dando e vai ver que lá está escrito que o tamanho tem que ser constante. Um número. Não pode deixar em branco e ler o tamanho depois. novo vetor elementos: printf("novo vetor",elementos); O que é isso com os dois pontos? Que pretendia escrever? Era um comentário? E o printf() está errado. Não pode imprimir um vetor em C só digitando o nome... Precisa usar os índices e imprimir um a um. Esse trecho também não tem sentido. scanf() espera um endereço. E a atribuição também está bem errada. A notação para pegar o índice é [ ] e você até sabe porque usou na declaração Você tem um livro? Recomendo muito arrumar um livro. Seu curso não adota um livro? Sua escola não assina uma biblioteca online talvez?
-
C Passar dados de um arquivo csv para uma struct
arfneto respondeu ao tópico de ArthurRodr em C/C#/C++
Isso que te mostrei é o código. E a rotina que mostrei antes. E a lógica que está acima. O resto é só leitura e gravação mesmo Esse é o código: int insere_registro(Registro* R, CSV* csv) { if (csv->total >= csv->capacidade) return -1; // nao cabe int pos = csv->total; for (; pos > 0; pos = pos - 1) { if (csv->R[pos-1]->id > R->id) csv->R[pos] = csv->R[pos - 1]; else break; }; // achou o lugar csv->R[pos] = (Registro*)malloc(sizeof(Registro)); csv->R[pos]->id = R->id; for (int i = 0; i < csv->campos; i += 1) csv->R[pos]->campo[i] = R->campo[i]; csv->total += 1; return csv->total; }; mas usa ponteiros e alocação dinâmica. No seu caso é bem mais simples: basta usar o contador N lá na estrutura que mostrei e copiar as linhas como declarado lá. Digitando em cima direto aqui seria algo assim int insere_registro(Registro* R, CSV* csv) { int pos = csv->N; for (; pos > 0; pos = pos - 1) { if (csv->R[pos - 1].ispb > R->ispb) csv->R[pos] = csv->R[pos - 1]; else break; }; // achou o lugar csv->R[pos] = *R; csv->R[pos].ispb = R->ispb; csv->R[pos] = *R; csv->N += 1; return csv->N; }; e mágica: o registro vai para a posição certa, na ordem -
C Passar dados de um arquivo csv para uma struct
arfneto respondeu ao tópico de ArthurRodr em C/C#/C++
Não entendo o que quer dizer. Talvez você tenha misturado tudo em uma única sentença. A partir de que ponto? process_field() só mostra uma mensagem. Não é nada ativo. Você tem um enunciado mais preciso? O que era pra ser aquilo? Se entendeu o que eu expliquei e entendeu o algoritmo na aula sabe que o insertion sort é provavelmente o mais simples desses algoritmos exceto talvez o radix sort. E entendeu que o insertion sort, como o nome já diz, vai inserindo os caras na ordem um a um até acabar. E assim sendo se está lendo de um arquivo não é nada inteligente gravar tudo na memória pra depois ir lá e colocar na ordem. Expliquei isso também, e dei um exemplo, o clássico exemplo do baralho: Se alguém te dá as cartas pra por em ordem, uma a uma, alguém nesse mundo ia esperar receber todas e colocar uma a uma na ordem de entrada na mesa para depois voltar lá na mesa e pegar a pilha e ir colocando em ordem inserindo a partir da primeira? Não, provavelmente já iria colocando na ordem. Essencialmente isso é Insertion Sort afinal. Veja essa animação meiga E eu te mandei o código Você precisa ler do arquivo e colocar na tal struct como falou. Só que seu programa não tem nenhuma que sirva. É bobagem usar uma struct com os campos e colocar os valores lá. Não vai usar pra nada. O programa que tem, esse sem titulo1.cpp é um programa em C com extensão cpp e não é nada bom se foi feito por um professor. Um arquivo csv é uma tabela perfeita, com MxN linhas e colunas. Seu arquivo tem 7 campos e 250 linhas. Eis as 4 primeiras ISPB,Nome_Reduzido,Numero_Codigo,Participa_da_Compe,Acesso_Principal,Nome_Extenso,Início_da_Operação 00000000,BCO DO BRASIL S.A.,001,Sim,RSFN,Banco do Brasil S.A. ,22/04/2002 00000208,BRB - BCO DE BRASILIA S.A.,070,Sim,RSFN,BRB - BANCO DE BRASILIA S.A. ,22/04/2002 00038121,Selic ,n/a,Não,RSFN,Banco Central do Brasil - Selic ,22/04/2002 Exercitando a imaginação vamos supor que process_fields() fosse para escolher o campo de classificação, mas você e seu colega disseram que é fixo o primeiro campo. Então de nada serve essa rotina. Então uma struct que resolveria o seu problema --- e o de seu colega --- poderia ser algo ingênuo como typedef struct { int ispb; // o campo para classificar char L[200]; // e a linha } Registro; typedef struct { int N; Registro R[300]; } CSV; CSV tabela; Sobre os dados Registro tem 2 campos: um com a "chave" de classificação, o tal primeiro campo. e outro com a linha como estava CSV tem dois campos: um N que vai contar quantos caras leu, e uma tabela de 300 registros, suficiente para seu teste Então sua variável tabela nesse exemplo é uma lista de até 300 linhas do arquivo. Claro que na prática não se faria assim, com tudo fixo, mas é só um exercício de introdução Você lê as linhas, pode até mudar essa process_fields() que de nada serve para tratar cada linha: pega o primeiro campo. Trivial: basta pegar o que veio na leitura e ir até a primeira vírgula, lá vai estar o número de oito dígitos que vai ser o critério de classificação. copia a linha toda pro campo linha, sem olhar pra ela porque de nada serve Use o código que mostrei para inserir esse Registro na tabela, contando o valor em N. E pronto. leia as linhas direto pra tabela usando a rotina que mostrei e ao final pode usar um simples loop e mostrar todas as linhas porque estarão já na ordem, classificadas pelo insertion sort. -
C Passar dados de um arquivo csv para uma struct
arfneto respondeu ao tópico de ArthurRodr em C/C#/C++
Não entendi o que quer dizer. Para seu exercício basta rolar na tela as linhas, mas classificados pelo primeiro campo através do insertion sort, não é? Isso não faz diferença. Os algoritmos de sort classificam qualquer coisa. O formato csv pode conter qualquer coisa. Você escreveu aquele código que postou? -
C Passar dados de um arquivo csv para uma struct
arfneto respondeu ao tópico de ArthurRodr em C/C#/C++
Entendo Você leu o que expliquei nesse e no outro tópico? Entendeu o que perguntei sobre isso? O sort e o arquivo csv O sort nada tem a ver com o arquivo csv. Na verdade, como o campo que quer usar é o primeiro, um número, é o mais simples possível: classificar por um int. E o nome dos campos e tal de nada serve aqui. Só trata mesmo a posição deles e o primeiro campo Você entendeu o que eu expliquei sobre o insertion sort? No outro tópico eu postei uma função que faz isso (insertion sort) enquanto lê, e assim quando termina de ler já está classificado -
C Passar dados de um arquivo csv para uma struct
arfneto respondeu ao tópico de ArthurRodr em C/C#/C++
Acho que sim. Mas não entendo a ideia do seu código. Qual a ideia de process_field()? Onde vai guardar os dados afinal? Não vejo lugar no programa. char buffer[1024]; char chave[1024]; int linha = 0; int coluna = 0; int aspas = 0; int posicao_chave = 0; Você em buffer[] mas chave[] também só tem lugar para um registro Entendeu o que eu expliquei sobre o sort? Leu o que escrevi no outro tópico? Qual a sua dúvida nesse exercício? O que não foi explicado de que fala? o selection sort ou o formato csv? Já escreveu outros programas em C? Em alguma outra linguagem? -
Estão certos de que todos esses valores são inteiros? Talvez a resistência mas as voltagens provavelmente não e a divisão também acho que não... R1 e R2 são int. Tem certeza de que é uma divisão assim que quer? double Vout = ( ( (double)R2 / R1+R2) * Vin ); Talvez algo assim... Sugiro pegar um valor conhecido e testar... adicionado 0 minutos depois como @Midori sugeriu...
-
C Passar dados de um arquivo csv para uma struct
arfneto respondeu ao tópico de ArthurRodr em C/C#/C++
Tenho a impressão que você quer fazer algo um pouco diferente do que escreveu: o que fazer é classificar o arquivo todo pelo valor da primeira coluna, certo? Essa é a mesma discussão desse tópico aqui, não é? Veja o que escrevi lá sobre isso há pouco, pra eu não ter que escrever de novo. Depois pode responder aqui pra ver se podemos fazer algo -
C Ler Arquivo csv e ordenar usando InsertionSort
arfneto respondeu ao tópico de willian gersanti em C/C#/C++
Esse problema é o mesmo discutido aqui? Você já escreveu algum programa em C? Tem um livro? Conhece alguma outra linguagem de programação? Selection, Insertion e Radix são os algoritmos de sort mais intuitivos, os que uma criança usa sem saber pra por coisas em ordem. Acho que inserção é o primeiro que a pessoa tenta, porque você pega uma coisa e coloca no meio das outras já na ordem. Então perguntei isso agora porque sempre vejo as pessoas lendo os dados para dentro de um vetor na ordem em que estavam no arquivo, para só depois colocar em ordem, se na vida real ninguém jamais faira isso. Imagine que vai classificar as cartas de um baralho e alguém vai te passando as cartas: você iria esperar receber todas para classificar ou já iria colocando na ordem? Esse é o insertion sort. Ao ler você põe na ordem. Quando chega o último registro está tudo pronto. Se precisar parar no caminho é só marcar onde parou e depois retomar. Selection Sort, ao vivo, em C int insere_do_disco(char* linha, int Len, Registro* FS) { if (FS->T >= FS->capacidade) { // FS->capacidade += FS->bloco; // novo tamanho char** novo = realloc(FS->R, sizeof(char*) * FS->capacidade); if (novo != NULL) FS->R = novo; }; // if() int pos = FS->T; for (; pos > 0; pos = pos - 1) { if (strcmp(FS->R[pos - 1], linha) > 0) FS->R[pos] = FS->R[pos - 1]; else break; }; // for() // achou o lugar FS->R[pos] = (char*)malloc(Len); strcpy(FS->R[pos], linha); FS->T += 1; return FS->T; // devolve o total de filmes atualizado }; Essa função faria essa inserção por exemplo. A ideia é aquela da criança: vai vendo do fim pro começo se o valor que está entrando é maior que o que temos: se não é vai abrindo um espaço e puxando os caras pra cima até achar a posição certa, e lá coloca o novo. Desde o primeiro. Quando ler o último--- e inserir o último --- estará em ordem. -
C Ler Arquivo csv e ordenar usando InsertionSort
arfneto respondeu ao tópico de willian gersanti em C/C#/C++
Se você está até procurando usar insertion sort e está inserindo todos os dados no vetor, porque já não insere na ordem usando ... insertion sort? Porque insere todos na ordem em que estão no arquivo para depois classificar, e usando curiosamente insertion sort num vetor onde acabou de inserir todos os dados? -
Olá Sabe usar funções? São apenas blocos de código com nomes e parâmetros mas facilitam muito as coisas. Você tem um livro? Seu curso adota um? Recomendo muito ter um livro. Evite ao máximo usar menus antes de seu programa estar pronto. Só vai atrasar tudo: é muito chato de testar e demora demais. Crie constantes de teste e programe as funções todas antes de colocar um menu e ficar em frente ao terminal inventando campos à toa. Veja esse resultado #0: Nome: 'nome1' Tel: 'tel1' e-mail 'email1' #1: Nome: 'nome2' Tel: 'tel2' e-mail 'email2' #2: Nome: 'nome3' Tel: 'tel3' e-mail 'email3' #3: Nome: 'nome4' Tel: 'tel4' e-mail 'email4' 4 entradas na agenda Para esse programa #include<stdio.h> #include<stdlib.h> #include<string.h> #include<locale.h> typedef struct { char nome[40]; char telefone[20]; char email[30]; } Agenda; int main() { setlocale(LC_ALL, "Portuguese"); Agenda agenda[5] = { { "nome1", "tel1", "email1" }, { "nome2", "tel2", "email2" }, { "nome3", "tel3", "email3" }, { "nome4", "tel4", "email4" } }; int cont = 4; for (int i = 0; i < cont; i = i + 1) { printf("#%d: Nome: '%s' Tel: '%s' e-mail '%s'\n", i, agenda[i].nome, agenda[i].telefone, agenda[i].email ); }; // for() printf("\n%d entradas na agenda\n\n", cont); return 0; }; Comece com algo assim. Já tem 4 itens na agenda, já mostra algo. Cabe mais um pra testar a inserção. Não precisa ler nada para inserir, basta escrever agenda[cont] = agenda[0]; cont = cont + 1; por exemplo e copia o primeiro item para a posição 4, no fim. Não faz diferença. Mas agora não cabe mais. De volta ao programa, control-c control-v e lista de novo com 5: #0: Nome: 'nome1' Tel: 'tel1' e-mail 'email1' #1: Nome: 'nome2' Tel: 'tel2' e-mail 'email2' #2: Nome: 'nome3' Tel: 'tel3' e-mail 'email3' #3: Nome: 'nome4' Tel: 'tel4' e-mail 'email4' 4 entradas na agenda #0: Nome: 'nome1' Tel: 'tel1' e-mail 'email1' #1: Nome: 'nome2' Tel: 'tel2' e-mail 'email2' #2: Nome: 'nome3' Tel: 'tel3' e-mail 'email3' #3: Nome: 'nome4' Tel: 'tel4' e-mail 'email4' #4: Nome: 'nome1' Tel: 'tel1' e-mail 'email1' 5 entradas na agenda E o programa claro, só tem o trecho copiado de diferente #include<stdio.h> #include<stdlib.h> #include<string.h> #include<locale.h> typedef struct { char nome[40]; char telefone[20]; char email[30]; } Agenda; int main() { setlocale(LC_ALL, "Portuguese"); Agenda agenda[5] = { { "nome1", "tel1", "email1" }, { "nome2", "tel2", "email2" }, { "nome3", "tel3", "email3" }, { "nome4", "tel4", "email4" } }; int cont = 4; for (int i = 0; i < cont; i = i + 1) { printf("#%d: Nome: '%s' Tel: '%s' e-mail '%s'\n", i, agenda[i].nome, agenda[i].telefone, agenda[i].email ); }; // for() printf("\n%d entradas na agenda\n\n", cont); agenda[cont] = agenda[0]; cont = cont + 1; for (int i = 0; i < cont; i = i + 1) { printf("#%d: Nome: '%s' Tel: '%s' e-mail '%s'\n", i, agenda[i].nome, agenda[i].telefone, agenda[i].email ); }; // for() printf("\n%d entradas na agenda\n\n", cont); return 0; }; No entanto as coisas andam mais depressa. SEM LER DO TECLADO. Agora eu usei duas vezes o mesmo código e provavelmente vou usar muitas vezes, isso de listar o que tem na agenda. Uma exemplo de função então seria conveniente. O resultado é claro o mesmo mas veja o programa #include<stdio.h> #include<locale.h> typedef struct { char nome[40]; char telefone[20]; char email[30]; } Agenda; int lista_agenda(Agenda[],int); // agenda, total de itens int main() { setlocale(LC_ALL, "Portuguese"); Agenda agenda[5] = { { "nome1", "tel1", "email1" }, { "nome2", "tel2", "email2" }, { "nome3", "tel3", "email3" }, { "nome4", "tel4", "email4" } }; int cont = 4; lista_agenda(agenda, cont); agenda[cont] = agenda[0]; cont = cont + 1; lista_agenda(agenda, cont); return 0; }; int lista_agenda(Agenda A[], int N) { for (int i = 0; i < N; i = i + 1) { printf("#%d: Nome: '%s' Tel: '%s' e-mail '%s'\n", i, A[i].nome, A[i].telefone, A[i].email ); }; // for() printf("\n%d entradas na agenda\n\n", N); return 0; } Mais simples, porque pode só escrever lista_agenda() e chamar de qualquer lugar do programa. É só um exemplo que copiei de seu programa pra mostrar uma maneira de escrever. Nem é a melhor maneira. Mas serve para ilustrar uns pontos. sobre typedef typedef cria um tipo, um alias. Então declarar typedef struct { char nome[40]; char telefone[20]; char email[30]; } Agenda; cria um tipo Agenda e você pode declarar coisas desse tipo. Uma das vantagens é que você não precisa ficar repetindo struct em toda declaração. Poste seu programa como está agora.
-
C percorrer uma palavra e imprimir quantos tipos de letras ela possui.
arfneto respondeu ao tópico de andre costac em C/C#/C++
em que linguagem vinha programando depois de C? Seu programa parece muito complicado para esse objetivo. Escreva seu programa sempre em torno dos dados. SEMPRE. Pense assim: uma palavra não tem muita opção em termos de letras. Sua função é assim int letras_diferentes(char palavra[] ,int tam ); Então em C palavra é uma string, uma sequência de até 30 caracteres com o último valendo zero. Só isso. E o que pode ter um char? É um byte. Pode ter 256 valores entre 0 e 255. Como são letras, a gente pode até imaginar que vá ter apenas letras, ou algum espaço, ou algum professor chato testou com "teste234". Mas importa mesmo? Não. Só precisamos contar quantos são diferentes e retornar o número. Para ser diferente tem que estar lá pelo menos uma vez. Assim se eu pegar um papel e for marcando quantas letras tem na palavra... palavra p aaa l v r teste tt ee s aaaaa Então já deu pra ver que se a gente marcar assim basta contar o número de linhas no papel e teremos quantas letras diferentes tem na palavra Escrevendo em C deve ficar igualzinho int letras_diferentes(char palavra[], int tam) { char tabela[256] = { 0 }; for (int i = 0; i < tam; i += 1) tabela[palavra[i]] += 1; // a letra int n = 0; for (int i = 0; i < 256; i += 1) if(tabela[i] != 0) n = n + 1; // + essa return n; }; Sim, só isso. char tabela[256] = { 0 }; é uma maneira simples de inicializar todos os valores da tabela com zero. Claro que pode trocar por um loop. Como a tabela tem lugar pra todo mundo você não precisa de lógica para testar as letras. Só vai lá na posição e soma. É como se tivesse no papel um formulário pronto para ir marcando as letras. Pense nisso. É só somar lá. Nem precisa somar: é só colocar qualquer valor diferente de zero, porque a gente só quer retornar o total de letras diferentes, não importa se todas são a mesma. O segundo loop apenas soma quantos caras na tabela tem valor não zero, ou seja, apareceram ao menos uma vez. Como a gente fez "no papel" acima. E a função retorna esse valor. Veja o resultado de um programa de teste 'teste': 3 letras diferentes 'palavra': 5 letras diferentes 'aaaaaaaaaaaaaaaab': 2 letras diferentes 'a': 1 letras diferentes 'abcdeabcdeabcdeabcdeabcdeabcd': 5 letras diferentes Veja como declarar por exemplo umas palavras pra testar: const char teste[5][30] = { "teste", "palavra", "aaaaaaaaaaaaaaaab", "a", "abcdeabcdeabcdeabcdeabcdeabcd" // 29 letras }; Sim, 5 palavras com até 30 bytes e alguns testes importantes: uma letra só, 29 letras (não pode usar 30 porque a última é o null que termina a string) e os exemplos que a gente colocou acima. É bobagem ficar lendo do teclado num programa antes dele estar pronto. E main() como seria? for (int i = 0; i < 5; i = i + 1) printf("'%s': %d letras diferentes\n", teste[i], letras_diferentes(teste[i], strlen(teste[i])) ); Só isso. teste é o vetor acima, com as 5 palavras. o loop chama a função passando as palavras e o printf() mostra o resultado que está acima. E a vida segue. Eis o programa todo #include <stdio.h> #include <stdlib.h> int letras_diferentes(char[], int); int main() { const char teste[5][30] = { "teste", "palavra", "aaaaaaaaaaaaaaaab", "a", "abcdeabcdeabcdeabcdeabcdeabcd" // 29 letras }; for (int i = 0; i < 5; i = i + 1) printf("'%s': %d letras diferentes\n", teste[i], letras_diferentes(teste[i], strlen(teste[i])) ); return 0; }; // main() int letras_diferentes(char palavra[], int tam) { char tabela[256] = { 0 }; for (int i = 0; i < tam; i += 1) tabela[palavra[i]] += 1; // conta a letra int n = 0; for (int i = 0; i < 256; i += 1) if(tabela[i] != 0) n = n + 1; // esse tinha return n; }; // fim Estou postando isso porque achei tudo as soluções aqui muito complicadas sem razão. Confirme se entendeu. -
C Criar uma função que receba o primeiro caractere registrado na matriz
arfneto respondeu ao tópico de Yank Marsh em C/C#/C++
Você não respondeu nada sobre os exemplos que perguntei em relação ao detalhes do Visual Studio. Eu instalei esses outros na mesma máquina e estou comparando. O Code::Blocks e o Dev-C++ e o Visual Studio e o VS Code e o Eclipse. Fiquei curioso adicionado 3 minutos depois Recomendo ir lá nas opções do compilador e marcar --version para ver qual versão de gcc está usando e na opção de warnings marcar -Wall no formulário se usa programas compilados lá para postar no forum. Assim você vai saber o que outros vão ver. E é boa política de todo modo. adicionado 6 minutos depois E se Code::Blocks continua com a opção ***** de assumir o C++ de 98 e o C de 89 como padrão sugiro mudar isso também de imediato usando -std=c99 ou -std=c11 ou -std=c17 e confirmar que isso está indo para o gcc. Não dá pra imaginar que não tenha nada errado em usar C de 1989 ou C++ de 1998 sem perder nada de bom que se tenha criado nesse período de mais de 30 anos...
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