Manipulao de registros em arquivos utilizando ndices
Publicado por Perfil removido (ltima atualizao em 11/08/2010)
[ Hits: 11.716 ]
Manipulação de registros em arquivos com uso de índice primário e dois índices secundários. Importa e faz um parse do arquivo arqdad.txt. Efetua buscas binárias, implementa uma abordagem de restauração de registros. Utiliza uma estrutura dinâmica para armazenamento e manipulação dos índices em memória principal.
#include <stdio.h> #include <string.h> #include <malloc.h> /* Constantes usadas pela aplicação */ char LIMPAR[] = "clear"; char IMPORTACAO[] = "arqdad.txt"; char DADOS[] = "dados.dat"; char HEADER[] = "header.dat"; char IDXNOME[] = "idxnome"; char IDXRED[] = "idxred"; /* Estrutura básica para armazenamento/tratamento de registros. Esta estrutura apresenta campos de tamanho fixo baseados nos tamanhos máximos apresentados nos campos dos registros. */ typedef struct cand { char inscricao[8]; char nome[33]; char nascimento[7]; char red[4]; char geo[5]; char his[5]; char bio[5]; char mat[5]; char port[5]; char le[6]; char fis[5]; char qui[5]; char final[7]; char clas[4]; char obs[4]; } cand; /* Estrutura de armazenamento/tratamento de chaves primárias composta por: - Valor da chave primária (key); - RRN do registro (rrn); - Marcador de item de índice ativo (ativo); - Ponteiro para próximo elemento da lista ligada. */ typedef struct nodePk { char key[8]; int rrn; char ativo; struct nodePk *prox; } nodePk; /* Estrutura para armazenamento/tratamento das listas invertidas; Uma lista invertida é criada para cada nó da lista de chaves secundárias e mantém ponteiros para os nós da lista de chave primária (acesso late binding); Composta por: - Ponteiro para a chave primária correspondente; - Ponteiro para próximo elemento da lista ligada. */ typedef struct nodeInvertida { struct nodePk *pk; struct nodeInvertida *prox; } nodeInvertida; /* Estrutura para armazenamento/tratamento de chaves secundários. Cada nó do tipo "nodeSk" cria uma lista invertida. Para isso, mantém: - Valor da chave secundária (key); - Ponteiros de início e fim da lista invertida correspondente ao nó (first e last); - Ponteiro para próximo elemento da lista ligada. */ typedef struct nodeSk { char key[33]; struct nodeInvertida *first; struct nodeInvertida *last; struct nodeSk *prox; } nodeSk; //Node inicial e final do índice primário nodePk *pkFirst, *pkLast; //Nodes iniciais e finais dos índices secundários nodeSk *skNomeFirst, *skNomeLast, *skRedFirst, *skRedLast; //Ponteiros para criação de vetores em tempo de execução para busca binária nodeSk **vetorSkNome, **vetorSkRed; nodePk **vetorPk; //Tamanho dos vetores gerados int tamanhoVetor, tamSkNome, tamSkRed, tamPk; /* Variável de FLAG: quando valorada em: - 0 : Executa rotina de busca sem dar opção de exclusão; - 1 : Executa rotina de busca dando opção de exclusão. */ char excluirBusca = 0; /* Realiza a criação dos arquivos de dados e cabeçalho quando os mesmos ainda não existem. */ void criarArquivos() { FILE *file; file = fopen(DADOS, "rb"); if (!file) { file = fopen(DADOS, "wb"); fclose(file); } file = fopen(HEADER, "rb"); if (!file) { file = fopen(HEADER, "wb"); fprintf(file, "i=n"); fclose(file); } } /* Realiza o trabalho de inserção das chaves primárias nos índices; Efetua a inserção das chaves já na forma ORDENADA; Caso já houver o valor de chave primária que se pretende inserir, a função retornará o endereço do nó em que está alocada a respectiva chave; Recebe como parâmetro: - o valor da chave a ser inserida (key); - o rrn (deslocamento) no arquivo de dados (rrn); - ponteiro para o início da lista (first); - ponteiro para o final do índice (last); Devolve: - Endereço do nó em que está a chave que foi inserida; */ nodePk* inserirPk(char *key, int rrn, nodePk **first, nodePk **last) { nodePk *node, *iterador, *ante; //Ponteiros para realização de percurso node = (nodePk *) malloc(sizeof(nodePk)); strcpy(node->key, key); node->rrn = rrn; node->ativo = 1; node->prox = NULL; // Verificação de lista vazia. if (!*first) { *first = node; *last = node; } else { iterador = *first; ante = *first; while (iterador) { if (strcmp(iterador->key, key)==0) { return iterador; } if (strcmp(iterador->key, key)>=0) { break; } ante = iterador; iterador = iterador->prox; } if (iterador==NULL) { (*last)->prox = node; *last = node; } else if (iterador==ante) { node->prox = iterador; *first = node; } else { ante->prox = node; node->prox = iterador; } } return node; } /* Realiza o trabalho de inserção dos elementos da lista invertida; Efetua a inserção das chaves já na forma ORDENADA; Recebe como parâmetro: - o valor ponteiro para o nó que contém a chave primária correspondente; - ponteiro para o início da lista (first); - ponteiro para o final do índice (last); */ void inserirInvertida(nodePk *pk, nodeInvertida **first, nodeInvertida **last) { nodeInvertida *node, *iterador, *ante; node = (nodeInvertida *) malloc(sizeof(nodeInvertida)); node->pk = pk; node->prox = NULL; //Verificação de lista vazia/inserção if (!*first) { *first = node; *last = node; } else { iterador = *first; ante = *first; while (iterador) { if (strcmp(iterador->pk->key, pk->key)>=0) { break; } ante = iterador; iterador = iterador->prox; } if (iterador==NULL) { (*last)->prox = node; *last = node; } else if (iterador==ante) { node->prox = iterador; *first = node; } else { ante->prox = node; node->prox = iterador; } } } /* Realiza o trabalho de inserção das chaves secundárias nos índices; Efetua a inserção das chaves já na forma ORDENADA; Recebe como parâmetro: - o valor da chave a ser inserida (key); - ponteiro para o nó que contém a chave primária correspondente; - ponteiro para o início da lista (first); - ponteiro para o final do índice (last); */ void inserirSk(char *key, nodePk *pk, nodeSk **first, nodeSk **last) { nodeSk *node, *iterador, *ante; node = (nodeSk *) malloc(sizeof(nodeSk)); strcpy(node->key, key); node->prox = NULL; node->first = NULL; node->last = NULL; //Verificação de índice vazio/inserção if (!*first) { *first = node; *last = node; //inserção de itens na lista invertida inserirInvertida(pk, &((*first)->first), &((*first)->last)); return; } else { iterador = *first; ante = *first; while (iterador) { if (strcmp(iterador->key, key)==0) { free(node); //inserção de itens na lista invertida inserirInvertida(pk, &(iterador->first), &(iterador->last)); return; } if (strcmp(iterador->key, key)>0) { break; } ante = iterador; iterador = iterador->prox; } if (iterador==NULL) { (*last)->prox = node; *last = node; } else if (iterador==ante) { node->prox = iterador; *first = node; } else { ante->prox = node; node->prox = iterador; } //inserção de itens na lista invertida inserirInvertida(pk, &(node->first), &(node->last)); } } /* Percorre a lista de índice secundário e retorna seu tamanho Recebe como parâmetro: - ponteiro para o início da lista de índice secundário */ int tamIndiceSk(nodeSk *first) { int i = 0; nodeSk *iter = first; while (iter) { i++; iter = iter->prox; } return i; } /* Cria um vetor a partir de uma lista ligada, percorrendo a lista ligada. Recebe como parâmetro o ponteiro para o início da lista. */ nodeSk** listaParaVetor(nodeSk *first) { int i, n; nodeSk **elementos; n = tamIndiceSk(first); elementos = (nodeSk **) malloc(sizeof(nodeSk *)*n); for (i=0; i<n; i++) { elementos[i] = first; first = first->prox; } tamanhoVetor = n; return elementos; } /* Percorre a lista de índice primário e retorna seu tamanho Recebe como parâmetro: - ponteiro para o início da lista de índice primário */ int tamIndicePk(nodePk *first) { int i = 0; nodePk *iter = first; while (iter) { if (iter->ativo) { i++; } iter = iter->prox; } return i; } /* Cria um vetor a partir de uma lista ligada, percorrendo a lista ligada. Recebe como parâmetro o ponteiro para o início da lista. */ nodePk** listaParaVetorPk(nodePk *first) { int i, n; nodePk **elementos; n = tamIndicePk(first); elementos = (nodePk **) malloc(sizeof(nodePk *)*n); for (i=0; i<n; i++) { while (!(first->ativo)) { first = first->prox; } elementos[i] = first; first = first->prox; } tamanhoVetor = n; return elementos; } /* Atualiza tamanhos dos índices e recria os vetores. */ void atualizaVetores() { free(vetorSkNome); free(vetorSkRed); free(vetorPk); vetorPk = listaParaVetorPk(pkFirst); tamPk = tamanhoVetor; vetorSkNome = listaParaVetor(skNomeFirst); tamSkNome = tamanhoVetor; vetorSkRed = listaParaVetor(skRedFirst); tamSkRed = tamanhoVetor; } /* Recebe uma string e um tamanho. Atribui, até o limite dado como parâmetro, espaços, encerrando com o caracter {FONTE}. */ void completaEspacos(char *str, int tamanho) { int i=0, x=0; if (str[i]==0) return; for (i=0; i<tamanho; i++) { x = i; if (str[i]==0) break; } for (i=x; i<tamanho; i++) { str[i] = ' '; } str[tamanho-1] = 0; } /* Permite ao usuário adicionar um novo item ao arquivo de dados; Os registros adicionados são incluídos também nos índices primário e secundário; */ void inserir() { cand c; int rrn, tamCampo; system(LIMPAR); getchar(); printf("INSERIR INFORMAÇÕES DE NOVO CANDIDATO\n"); do { printf("\nNúmero de inscrição(máx:7): "); gets(c.inscricao); tamCampo = strlen(c.inscricao); } while (tamCampo>7); completaEspacos(c.inscricao, 8); do { printf("\nNome (máx:32): "); gets(c.nome); tamCampo = strlen(c.nome); } while (tamCampo>32); do { printf("\nNascimento(máx:6): "); gets(c.nascimento); tamCampo = strlen(c.nascimento); } while (tamCampo>6); completaEspacos(c.nascimento, 7); do { printf("\nRedação (máx:3): "); gets(c.red); tamCampo = strlen(c.red); } while (tamCampo>3); completaEspacos(c.red, 4); do { printf("\nGeografia (máx:4): "); gets(c.geo); tamCampo = strlen(c.geo); } while (tamCampo>4); completaEspacos(c.geo, 5); do { printf("\nHistória (máx:4): "); gets(c.his); tamCampo = strlen(c.his); } while (tamCampo>4); completaEspacos(c.his, 5); do { printf("\nBiologia (máx:4): "); gets(c.bio); tamCampo = strlen(c.bio); } while (tamCampo>4); completaEspacos(c.bio, 5); do { printf("\nMatemática (máx:4): "); gets(c.mat); tamCampo = strlen(c.mat); } while (tamCampo>4); completaEspacos(c.mat, 5); do { printf("\nPortuguês (máx:4): "); gets(c.port); tamCampo = strlen(c.port); } while (tamCampo>4); completaEspacos(c.port, 5); do { printf("\nLíngua Estrangeira (máx:5): "); gets(c.le); tamCampo = strlen(c.le); } while (tamCampo>5); completaEspacos(c.le, 6); do { printf("\nFísica (máx:4): "); gets(c.fis); tamCampo = strlen(c.fis); } while (tamCampo>4); completaEspacos(c.fis, 5); do { printf("\nQuímica (máx:4): "); gets(c.qui); tamCampo = strlen(c.qui); } while (tamCampo>4); completaEspacos(c.qui, 5); do { printf("\nEscore Final (máx:6): "); gets(c.final); tamCampo = strlen(c.final); } while (tamCampo>6); completaEspacos(c.final, 7); do { printf("\nClassificação (máx:3): "); gets(c.clas); tamCampo = strlen(c.clas); } while (tamCampo>3); completaEspacos(c.clas, 4); do { printf("\nObservação (máx:3): "); gets(c.obs); tamCampo = strlen(c.obs); } while (tamCampo>3); completaEspacos(c.obs, 4); FILE *fd; fd = fopen(DADOS, "a"); rrn = ftell(fd); fprintf(fd, "|%s|%s|%s|%s|%s|%s|%s|%s|%s|%s|%s|%s|%s|%s|%s|#", c.inscricao, c.nome, c.nascimento, c.red, c.geo, c.his, c.bio, c.mat, c.port, c.le, c.fis, c.qui, c.final, c.clas, c.obs); //Inclusão de registros nos índices primário e secundário. nodePk *p; p = inserirPk(c.inscricao, rrn, &pkFirst, &pkLast); inserirSk(c.nome, p, &skNomeFirst, &skNomeLast); inserirSk(c.red, p, &skRedFirst, &skRedLast); fclose(fd); } /* Percorre o arquivo de dados com base no rrn e adiciona uma marca de exclusão (*), além de desativar o respectivo nó; Recebe como parâmetro: - o ponteiro para o nó do registro a ser excluído; */ void excluir(nodePk *node) { node->ativo = 0; FILE *file; file = fopen(DADOS, "r+b"); fseek(file, node->rrn, SEEK_SET); fputc('*', file); fclose(file); } /* Exibe na tela o registro contido no arquivo de dados, indicado pelo RRN; */ void imprimirRegistro(int rrn) { char registro[150], c; int x = 0; FILE *file; file = fopen(DADOS, "rb"); fseek(file, rrn+1, SEEK_SET); while ((c=fgetc(file))!='#') { registro[x] = c; x++; } registro[x] = 0; printf("\n\nNúmero de Inscrição: %s", strtok(registro, "|*")); printf("\nNome: %s", strtok(NULL, "|*")); printf("\nData de nascimento: %s", strtok(NULL, "|*")); printf("\n:::::::::::::::::::::::::::NOTAS::::::::::::::\ :::::::::::::\nRedação: %s; ", strtok(NULL, "|*")); printf("Geografia: %s; ", strtok(NULL, "|*")); printf("História: %s; ", strtok(NULL, "|*")); printf("\nBiologia: %s; ", strtok(NULL, "|*")); printf("Matemática: %s; ", strtok(NULL, "|*")); printf("Português: %s; ", strtok(NULL, "|*")); printf("\nLíngua Estrangeira: %s; ", strtok(NULL, "|*")); printf("Física: %s; ", strtok(NULL, "|*")); printf("Química: %s; ", strtok(NULL, "|*")); printf("\n:::::::::::::::::::::::::RESULTADOS:::::::::::\ :::::::::::::\nEscore Final: %s; ", strtok(NULL, "|*")); printf("Classificação: %s; ", strtok(NULL, "|*")); printf("Observação: %s; \n", strtok(NULL, "|*")); printf("-----------------------------------------------------------\n"); fclose(file); } /* Exibe para o usuário todos os itens dos índices secundários */ void mostrarSk(nodeSk *first) { getchar(); nodeInvertida *inv; while (first) { inv = first->first; while(inv) { if (inv->pk->ativo) { imprimirRegistro(inv->pk->rrn); printf("Pressione ENTER para próximo registro (ESC + ENTER para voltar)..."); if (getchar()==27) return; } inv = inv->prox; } first = first->prox; } } /* Exibe para o usuário todos os itens dos índices primários */ void mostrarPk(nodePk *first) { getchar(); while (first) { if (first->ativo) { imprimirRegistro(first->rrn); printf("Pressione ENTER para próximo registro (ESC + ENTER para voltar)..."); if (getchar()==27) return; } first = first->prox; } } /* Busca no vetor construído a partir do índice primário o valor informado; Usa o método de busca binária; Recebe como parâmetro: - a chave a ser pesquisada; - vetor onde deve ser pesquisado; - o tamanho do vetor onde deve ser pesquisado; */ void buscaPk(char *elemento, nodePk **vetor, int tamVetor) { int inf = 0, sup = tamVetor-1, x, encontrado = 0; while (inf <= sup) { x = (inf+sup)/2; if (strcmp((vetor[x])->key, elemento)==0) { encontrado = 1; break; } else if (strcmp((vetor[x])->key, elemento)<0) { inf = x + 1; } else { sup = x - 1; } } system(LIMPAR); printf("RESULTADOS DA BUSCA POR: \"%s\"\n\n", elemento); if (encontrado) { char opcao; char *op = &opcao; getchar(); if ((vetor[x])->ativo) { opcao = 'N'; imprimirRegistro((vetor[x])->rrn); if (excluirBusca) { printf("\nDESEJA EXCLUIR ESSE REGISTRO? (S/N)\n"); gets(op); if (opcao == 'S' || opcao == 's') { excluir((vetor[x])); atualizaVetores(); } } } } else { printf("Não foi encontrado o item"); } } /* Busca no vetor construído a partir de um dos índices secundários o valor informado; Usa o método de busca binária; Recebe como parâmetro: - a chave a ser pesquisada; - vetor onde deve ser pesquisado; - o tamanho do vetor onde deve ser pesquisado; */ void buscaBinaria(char *elemento, nodeSk **vetor, int tamVetor) { int inf = 0, sup = tamVetor-1, x, encontrado = 0; while (inf <= sup) { x = (inf+sup)/2; if (strcmp((vetor[x])->key, elemento)==0) { encontrado = 1; break; } else if (strcmp((vetor[x])->key, elemento)<0) { inf = x + 1; } else { sup = x - 1; } } system(LIMPAR); printf("RESULTADOS DA BUSCA POR: \"%s\"\n", elemento); if (encontrado) { nodeInvertida *inv; inv = (vetor[x])->first; char opcao; char *op = &opcao; // Percurso da lista e opção para exclusão de registro while(inv) { opcao = 'N'; if (inv->pk->ativo) { imprimirRegistro(inv->pk->rrn); if (excluirBusca) { printf("\nDESEJA EXCLUIR ESSE REGISTRO? (S/N)\n"); gets(op); if (opcao == 'S' || opcao == 's') { excluir(inv->pk); atualizaVetores(); } } printf("Pressione ENTER para próximo registro (ESC + ENTER para voltar)..."); if (getchar()==27) return; } inv = inv->prox; } } else { printf("Não foi encontrado o item"); } } /* MENU DE PESQUISA */ void menuPesquisar() { char opcao = ' '; char valor[33]; while (opcao!='4') { getchar(); system(LIMPAR); if (excluirBusca) { printf("EXCLUSÃO DE REGISTROS\n"); } printf("PESQUISAR REGISTROS POR: \n\n"); printf("1. Número de Inscrição\n"); printf("2. Nome\n"); printf("3. Nota da Redação\n"); printf("4. Voltar\n"); printf("\nEscolha uma opção: "); opcao = getchar(); if (opcao=='1') { printf("\nEntre com a chave primária: "); scanf("%s", valor); completaEspacos(valor, 8); buscaPk(valor, vetorPk, tamPk); printf("\nFim de busca, pressione ENTER para continuar...\n"); } if (opcao=='2') { getchar(); printf("\nEntre com o nome: "); gets(valor); buscaBinaria(valor, vetorSkNome, tamSkNome); printf("\nFim de busca, pressione ENTER para continuar...\n"); } if (opcao=='3') { printf("\nEntre com a nota de redação: "); scanf("%s", valor); completaEspacos(valor, 4); getchar(); buscaBinaria(valor, vetorSkRed, tamSkRed); printf("\nFim de busca, pressione ENTER para continuar...\n"); } } } /* Desaloca todos os dados utilizados pelos índices mantidos em memória */ void limparIndices() { nodeInvertida *inv, *anteInv; nodeSk *sk, *anteSk; sk = skNomeFirst; while (sk) { inv = sk->first; anteInv = NULL; while (inv) { anteInv = inv; inv = inv->prox; free(anteInv->pk); free(anteInv); } anteSk = sk; sk = sk->prox; free(anteSk); } sk = skRedFirst; while (sk) { inv = sk->first; anteInv = NULL; while (inv) { anteInv = inv; inv = inv->prox; free(anteInv); } anteSk = sk; sk = sk->prox; free(anteSk); } pkFirst = NULL; skNomeFirst = NULL; skRedFirst = NULL; } /* Efetua a gravação das listas de índices primário e secundário em arquivos */ void salvarIndices() { nodeInvertida *inv; nodePk *pk; nodeSk *skn, *skr; FILE *fn, *fr; fn = fopen(IDXNOME, "wb"); fr = fopen(IDXRED, "wb"); skn = skNomeFirst; while (skn) { inv = skn->first; while (inv) { if (inv->pk->ativo) { fprintf(fn, "%s|%s|%d|\n", inv->pk->key, skn->key, inv->pk->rrn); } inv = inv->prox; } skn = skn->prox; } skr = skRedFirst; while (skr) { inv = skr->first; while (inv) { if (inv->pk->ativo) { fprintf(fr, "%s|%s|%d|\n", inv->pk->key, skr->key, inv->pk->rrn); } inv = inv->prox; } skr = skr->prox; } fclose(fn); fclose(fr); } /* Caso os índices sejam apagados, reconstroi os mesmos; O parâmetro "recupera" pode ser valorado como: - 0 : efetua reconstrução sem recuperar registro excluídos - 1 : efetua reconstrução recuperando registro excluídos */ void reconstruirIndices(int recupera) { limparIndices(); nodePk *p; char registro[150], c, *pk, *nome, *red; int x, rrn = 0; FILE *file; file = fopen(DADOS, "rb"); if (!file) { printf("\nNão foi possível abrir o arquivo de dados..."); return; } while (1) { x = 0; while (((c=fgetc(file))!='#')) { if (feof(file)) { fclose(file); salvarIndices(); printf("\nOs índices foram reconstruídos com sucesso..."); getchar(); return; } registro[x] = c; x++; } registro[x] = 0; if (recupera==1||(recupera==0 && registro[0]!='*')) { pk = strtok(registro, "|*"); nome = strtok(NULL, "|*"); strtok(NULL, "|*"); red = strtok(NULL, "|*"); completaEspacos(red, 4); p = inserirPk(pk, rrn, &pkFirst, &pkLast); inserirSk(nome, p, &skNomeFirst, &skNomeLast); inserirSk(red, p, &skRedFirst, &skRedLast); } rrn = ftell(file); } } /* Carrega para memória todos os índices gravados em arquivo; */ void carregarIndices() { limparIndices(); FILE *nome, *red; nome = fopen(IDXNOME, "rb"); red = fopen(IDXRED, "rb"); if (nome&&red) { char linha[100], *key, *pk, *rrn; nodePk *p; while (fgets(linha, 100, nome)) { pk = strtok(linha, "|*"); key = strtok(NULL, "|*"); rrn = strtok(NULL, "|*"); p = inserirPk(pk, atoi(rrn), &pkFirst, &pkLast); inserirSk(key, p, &skNomeFirst, &skNomeLast); } while (fgets(linha, 100, red)) { pk = strtok(linha, "|*"); key = strtok(NULL, "|*"); rrn = strtok(NULL, "|*"); p = inserirPk(pk, atoi(rrn), &pkFirst, &pkLast); inserirSk(key, p, &skRedFirst, &skRedLast); } } else { printf("\nNão foi possível carregar os índices, pressione ENTER\ para iniciar a reconstrução dos índices..."); getchar(); reconstruirIndices(0); } } /* Realiza a abertura e importação do arquivo "arqdad.txt" */ void importar() { FILE *file; file = fopen(HEADER, "rb"); char l[4]; fscanf(file, "%s", l); fclose(file); if (l[2] == 's') { printf("\n\nO arquivo arqdad.txt já foi importado."); getchar(); return; } cand candidato; char linha[150]; int rrn, i, x=0; FILE *saida, *fd; fd = fopen(IMPORTACAO, "rb"); saida = fopen(DADOS, "ab"); if (!fd) { printf("ARQUIVO DE IMPORTAÇÃO NÃO ENCONTRADO..."); getchar(); return; } for (i=0; i<7; i++) { fgets(linha, 150, fd); } rrn = 0; while (fgets(linha, 150, fd)) { fseek(saida, 0, SEEK_END); rrn = ftell(saida); for (i=1; i<8; i++) { candidato.inscricao[x]=linha[i]; x++; } candidato.inscricao[x] = 0; x = 0; fprintf(saida, "|%s|", candidato.inscricao); for (i=10; i<43; i++) { if ((linha[i]==' ')&&(linha[i+1]==' ')) break; candidato.nome[x]=linha[i]; x++; } candidato.nome[x] = 0; x = 0; fprintf(saida, "%s|", candidato.nome); for (i=43; i<49; i++) { candidato.nascimento[x]=linha[i]; x++; } candidato.nascimento[x] = 0; x = 0; fprintf(saida, "%s|", candidato.nascimento); for (i=52; i<56; i++) { candidato.red[x]=linha[i]; x++; } candidato.red[x] = 0; x = 0; fprintf(saida, "%s|", candidato.red); for (i=57; i<61; i++) { candidato.geo[x]=linha[i]; x++; } candidato.geo[x] = 0; x = 0; fprintf(saida, "%s|", candidato.geo); for (i=62; i<67; i++) { candidato.his[x]=linha[i]; x++; } candidato.his[x] = 0; x = 0; fprintf(saida, "%s|", candidato.his); for (i=68; i<73; i++) { candidato.bio[x]=linha[i]; x++; } candidato.bio[x] = 0; x = 0; fprintf(saida, "%s|", candidato.bio); for (i=73; i<78; i++) { candidato.mat[x]=linha[i]; x++; } candidato.mat[x] = 0; x = 0; fprintf(saida, "%s|", candidato.mat); for (i=80; i<85; i++) { candidato.port[x]=linha[i]; x++; } candidato.port[x] = 0; x = 0; fprintf(saida, "%s|", candidato.port); for (i=85; i<91; i++) { candidato.le[x]=linha[i]; x++; } candidato.le[x] = 0; x = 0; fprintf(saida, "%s|", candidato.le); for (i=92; i<97; i++) { candidato.fis[x]=linha[i]; x++; } candidato.fis[x] = 0; x = 0; fprintf(saida, "%s|", candidato.fis); for (i=97; i<102; i++) { candidato.qui[x]=linha[i]; x++; } candidato.qui[x] = 0; x = 0; fprintf(saida, "%s|", candidato.qui); for (i=103; i<109; i++) { candidato.final[x]=linha[i]; x++; } candidato.final[x] = 0; x = 0; fprintf(saida, "%s|", candidato.final); for (i=112; i<116; i++) { candidato.clas[x]=linha[i]; x++; } candidato.clas[x] = 0; x = 0; fprintf(saida, "%s|", candidato.clas); for (i=117; i<120; i++) { candidato.obs[x]=linha[i]; x++; } candidato.obs[x] = 0; x = 0; fprintf(saida, "%s|#", candidato.obs); candidato.inscricao[7] = 0; candidato.nome[32] = 0; candidato.red[3] = 0; nodePk *p; p = inserirPk(candidato.inscricao, rrn, &pkFirst, &pkLast); inserirSk(candidato.nome, p, &skNomeFirst, &skNomeLast); inserirSk(candidato.red, p, &skRedFirst, &skRedLast); } file = fopen(HEADER, "wb"); l[2] = 's'; fprintf(file, "%s", l); fclose(file); } /* Cria um novo arquivo de dados, excluindo definitivamente os registros outrora somente removidos logicamente. */ void removerDefinitivo() { int x; char c, registro[150]; FILE *file, *tmp; file = fopen(DADOS, "rb"); tmp = fopen("tmp", "wb"); if (!file) { printf("\nNão foi possível abrir o arquivo de dados..."); return; } while (1) { x = 0; while (((c=fgetc(file))!='#')) { if (feof(file)) { fclose(file); fclose(tmp); remove(DADOS); rename("tmp", DADOS); reconstruirIndices(1); printf("\nTodos os registros removidos logicamente foram definitivamente removidos..."); return; } registro[x] = c; x++; } registro[x] = '#'; registro[x+1] = 0; if (registro[0]!='*') { fprintf(tmp, "%s", registro); } } } /* MENU DE LISTAGEM DE REGISTROS */ void menuListar() { char opcao = ' '; char valor[33]; getchar(); while (opcao!='4') { system(LIMPAR); printf("LISTAR REGISTROS POR: \n\n"); printf("1. Número de Inscrição\n"); printf("2. Nome\n"); printf("3. Nota da Redação\n"); printf("4. Voltar\n"); printf("\nEscolha uma opção: "); scanf("%c", &opcao); if (opcao=='1') { mostrarPk(pkFirst); } if (opcao=='2') { mostrarSk(skNomeFirst); } if (opcao=='3') { mostrarSk(skRedFirst); } } } /* MENU DE INSERCAO DE REGISTROS */ void menuInserir() { char opcao = ' '; getchar(); while (opcao!='2') { system(LIMPAR); printf("INSERIR NOVO REGISTRO\n"); printf("1. Iniciar inserção de dados\n"); printf("2. Voltar\n"); printf("\nEscolha uma opção: "); scanf("%c", &opcao); if (opcao=='1') { inserir(); } } } /* MENU PRINCIPAL */ int menuPrincipal() { char opcao[] = ""; system(LIMPAR); printf("Pressione ENTER..."); while (opcao[0] != '1' && (opcao[1] != '1' || opcao[1] != '0')) { getchar(); system(LIMPAR); printf("MANIPULAÇÃO DE ARQUIVOS DE DADOS COM USO DE ÍNDICES"); printf("\n\n1. Inserir"); printf("\n2. Excluir"); printf("\n3. Listar"); printf("\n4. Buscar"); printf("\n5. Importar arquivo \"arqdad.txt\""); printf("\n6. Restaurar registros removidos logicamente"); printf("\n7. Reconstruir índices"); printf("\n8. Remover registros definitivamente"); printf("\n9. Salvar alterações"); printf("\n10. Cancelar alterações e sair"); printf("\n11. Salvar alterações e sair"); printf("\n\nEscolha uma opção válida: "); scanf("%s", opcao); if (opcao[0] == '1' && opcao[1] == '0') { return 0; } if (opcao[0] == '1' && opcao[1] == '1') { return 1; } if (opcao[0] == '1') { menuInserir(); } if (opcao[0] == '2') { atualizaVetores(); excluirBusca = 1; menuPesquisar(); } if (opcao[0] == '3') { excluirBusca = 0; menuListar(); } if (opcao[0] == '4') { atualizaVetores(); excluirBusca = 0; menuPesquisar(); } if (opcao[0] == '5') { importar(); } if (opcao[0] == '6') { limparIndices(); reconstruirIndices(1); salvarIndices(); printf("\n\nOs registros excluídos foram restaurados!"); } if (opcao[0] == '7') { reconstruirIndices(0); } if (opcao[0] == '8') { removerDefinitivo(); } if (opcao[0] == '9') { salvarIndices(); printf("\n\nAs alterações foram gravadas nos arquivos de índices..."); getchar(); } } } /* Programa principal */ int main() { //Verifica se os arquivos já existem e os cria, caso negativo; criarArquivos(); //Carrega os índices do arquivo para a memória; carregarIndices(); //Salva índices se for a opção escolhida pelo usuário; if (menuPrincipal()) { salvarIndices(); } }
ORDENACAO PELO METODO SHELLSORT
dog - semelhante ao cat do Linux
Cadastro de arquivo usando ncurses como menu
Nenhum comentrio foi encontrado.
Enviar mensagem ao usuário trabalhando com as opções do php.ini
Meu Fork do Plugin de Integração do CVS para o KDevelop
Compartilhando a tela do Computador no Celular via Deskreen
Como Configurar um Tnel SSH Reverso para Acessar Sua Mquina Local a Partir de uma Mquina Remota
Configuração para desligamento automatizado de Computadores em um Ambiente Comercial
Compartilhamento de Rede com samba em modo Pblico/Annimo de forma simples, rpido e fcil
Cups: Mapear/listar todas as impressoras de outro Servidor CUPS de forma rpida e fcil
Criando uma VPC na AWS via CLI
Tem como instalar o gerenciador AMD Adrenalin no Ubuntu 24.04? (15)
Tenho dois Link's ( IP VLIDOS ), estou tentando fazer o failover... (0)
Pendrive no formata de jeito nenhum (4)