Linguagem C_Exercicios Propostos Solucao_11

Page 1


11.1

Linguagem C 25.ª Edição Atualizada e Aumentada

FCA Editora (c) 2025

EXERCÍCIOS PROPOSTOS – SOLUÇÃO

1: #include <stdio.h>

2: #include <string.h>

3: #include <stdlib.h> /* Função exit */

4: #include <ctype.h> /* Função toupper */

5:

6: #define FICH "dados.dat" /* Ficheiro com os Dados */

7:

8: #define OP_INSERIR '1'

9: #define OP_ALTERAR '2'

10: #define OP_APAGAR '3'

11: #define OP_LISTAR '4'

12: #define OP_PESQUISAR '5'

13:

14: #define OP_SAIR '0'

15:

16: #define OP_PESQ_IDADE '1'

17: #define OP_PESQ_NOME '2'

18:

19: char *mainMenu[]={

20: "1. Inserir Registo", 21: "2. Alterar Registo", 22: "3. Apagar Registo", 23: "4. Listar Registos", 24: "5. Pesquisas", 25: "0. Sair",

26: NULL /* Acabaram as Opções */

27: };

28:

29: char *searchMenu[]={

30: "1. Pesquisar por Intervalo de Idades",

31: "2. Pesquisar por Nome",

32: "0. Voltar",

33: NULL /* Acabaram as Opções */

34: };

35:

36: typedef struct

37: {

38: char nome[30+1];

39: int idade;

40: float salario;

41: char status; /* '*' Indica que o registo esta apagado */

42: } PESSOA;

43:

44: void mensagem(char *msg);

45:

46: /* Lê os dados de um registo introduzidos pelo utilizador */

47: void ler_pessoa(PESSOA *p)

48: {

49: printf("Nome : "); gets(p->nome);

50: printf("Idade : "); scanf("%d", &p->idade);

51: printf("Salario : "); scanf("%f", &p->salario); 52: p->status=' ';

53: }

54:

55: /* Mostra no ecrã, os dados existente no registo */

56:

57: void mostrar_pessoa(PESSOA p)

58: {

59: printf("%-30s %3d %10.2f\n", p.nome, p.idade, p.salario);

60: }

61:

62: /* Limpar o buffer do teclado */

63: void limpar_buffer()

64: {

65: while (scanf("%*c")==1)

66: ;

67: }

68:

69: /* Grava os dados de uma pessoa no Ficheiro */

70: void gravar_pessoa(FILE*fp, PESSOA p)

71: {

72: fseek(fp, 0L, SEEK_END);

73: if (fwrite(&p, sizeof(p), 1L, fp)!=1)

74: mensagem("Adicionar Pessoa: Falhou a escrita do Registo");

75: else

76: mensagem("Registo gravado com sucesso.");

77: }

78:

79: /* Coloca um mensagem no ecrã */

80: void mensagem(char *msg)

81: {

82: printf("%s", msg); 83: printf("Prima <ENTER> para continuar");

84: limpar_buffer();

85: getchar();

86: }

87:

88: /* Devolve a referência para o ficheiro de dados */ 89: FILE *obter_ficheiro()

90: {

91: FILE *fp=fopen(FICH, "r+b"); /* Tentar Abrir */ 92:

93: if (fp==NULL) /* Ficheiro não existe */ 94: fp=fopen(FICH, "w+b"); /* Tentar Criar */ 95:

96: if (fp==NULL)

97: {

98: fprintf(stderr, "ERRO FATAL: Ficheiro de Dados\n"); 99: exit(1); 100: }

101: return fp; 102: }

103:

104: /*

105: * Faz um Menu Simples com as opções do array de strings. 106: * Selecciona a Opção, usando o 1º caráter de cada string.

107: * Devolve o primeiro caráter da opção

108: */

109: char menu(char *opcoes[])

110: { 111: char op; 112:

113: while (1) 114: { 115:

116: printf("\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n");

117: for(int i=0; opcoes[i]!=NULL; i++)

118: printf("\t\t%s\n", opcoes[i]);

119: 120: printf("\n\n\t\tOpção: ");

121: scanf(" %c", &op); 122: limpar_buffer();

123:

124: for (int i=0; opcoes[i]!=NULL; i++)

125: if (opcoes[i][0]==op)

126: return op; 127: }

128: }

129:

130: void inserir_pessoa(FILE *fp)

131: { PESSOA x; 132: ler_pessoa(&x); 133: gravar_pessoa(fp, x); 134: }

135:

136: void alterar_pessoa(FILE*fp)

137: { PESSOA x; 138: long int n_reg; 139:

140: printf("Qual o nº do registo: ");

141: scanf("%ld", &n_reg);

142: if (fseek(fp, (n_reg-1)*sizeof(PESSOA), SEEK_SET)!=0)

143: { 144: mensagem("Registo inexistente ou problemas no posicionamento!!!");

145: return;

146: }

147:

148: if (fread(&x, sizeof(PESSOA), 1L, fp)!=1)

149: { 150: mensagem("Problemas na leitura do registo!!!"); 151: return;

152: }

153:

154: if (x.status=='*')

155: { 156: mensagem("Um registo apagado não pode ser alterado!!!\n\n"); 157: return; 158: } 159:

160: printf("\n\nDados Actuais\n\n"); 161: mostrar_pessoa(x); 162: printf("\n\nNovos Dados\n\n"); 163: ler_pessoa(&x); 164:

165: // Recuar um Registo no Ficheiro

166: fseek(fp, -(long) sizeof(PESSOA), SEEK_CUR); 167: // Reescrever o Registo; 168: fwrite(&x, sizeof(PESSOA), 1L, fp); 169: fflush(fp); 170: }

171:

172: void apagar_pessoa(FILE*fp)

173: { PESSOA x; 174: long int n_reg; 175: char resp;

176:

177: printf("Qual o nº do Registo: "); 178: scanf("%ld", & n_reg);fflush(stdin); 179:

180: if (fseek(fp, (n_reg-1)*sizeof(PESSOA), SEEK_SET)!=0)

181: { 182: mensagem("Registo inexistente ou problemas no posicionamento!!!");

183: return; 184: }

185:

186: if (fread(&x, sizeof(PESSOA), 1L, fp)!=1)

187: { 188: mensagem("Problemas na leitura do registo!!!");

189: return ; 190: }

191:

192: if (x.status=='*')

193: {

194: mensagem("Registo já está apagado!!!\n\n"); 195: return; 196: }

197:

198: printf("\n\nDados Actuais\n\n"); 199: mostrar_pessoa(x);

200:

201: printf("\n\nApagar o registo (s/n)???: "); scanf(" %c", &resp); 202: if (toupper(resp)!='S') return;

203:

204: x.status='*';

205:

206: // Recuar um registo no ficheiro

207: fseek(fp, -(long) sizeof(PESSOA), SEEK_CUR);

208:

209: // Reescrever o fegisto; 210: fwrite(&x, sizeof(PESSOA), 1L, fp); 211: fflush(fp); 212: }

213:

214:

215: void listar(FILE*fp)

216: { long int n_linhas =0; 217: PESSOA reg; 218:

219: rewind(fp);

220: while(1)

221: {

222: if (fread(&reg, sizeof(reg), 1L, fp)!=1)

223: break;/* Sair do Ciclo */

224:

225: if (reg.status=='*')

226: continue ; /* Passa ao próximo */

227: mostrar_pessoa(reg);

228: n_linhas++;

229: if (n_linhas%20==0)

230: mensagem("");

231: }

232: mensagem("\n\nFim da listagem "); /* No fim da Listagem */ 233: }

234:

235: void pesquisar_idades(FILE*fp, int ini, int fim)

236: { PESSOA reg; 237: rewind(fp);

238:

239: while (fread(&reg, sizeof(PESSOA), 1L, fp))

240: if (reg.status!='*' && reg.idade>=ini && reg.idade<=fim)

241: mostrar_pessoa(reg);

242:

243: mensagem("\n\nFim da listagem "); /* No fim da Listagem */ 244: }

245:

246: void pesquisar_nome(FILE*fp, char *s)

247: { PESSOA reg; 248: rewind(fp);

249:

250: while (fread(&reg, sizeof(PESSOA), 1L, fp))

251: if (reg.status!='*' && strstr(reg.nome, s))

252: mostrar_pessoa(reg);

253: mensagem("\n\nFim da listagem "); /* No fim da Listagem */ 254: }

255:

256: int main(void)

11.2

257: {

258: char opcao;

259: FILE *fp = obter_ficheiro();

260:

261: while ((opcao=menu(mainMenu))!=OP_SAIR)

262: switch(opcao)

263: {

264: case OP_INSERIR: inserir_pessoa(fp); break; 265: case OP_ALTERAR: alterar_pessoa(fp); break; 266: case OP_APAGAR: apagar_pessoa(fp); break; 267: case OP_LISTAR: listar(fp); break;

268:

269: case OP_PESQUISAR:

270: while((opcao=menu(searchMenu))!=OP_SAIR)

271: switch (opcao)

272: {

273: case OP_PESQ_IDADE:

274: {

275: int n1, n2;

276: printf("Qual o intervalo de Idades: "); 277: scanf("%d%d", &n1, &n2);

278: pesquisar_idades(fp, n1, n2);

279: break;

280: }

281: case OP_PESQ_NOME:

282: { 283: char string[BUFSIZ+1];

284: printf("Qual o nome a procurar: "); 285: gets(string); 286: pesquisar_nome(fp, string);

287: }

288: }

289: }

290: return 0;

291: }

a)

#define MAX 10 #define MAX_NOME 40

typedef struct { unsigned n; char nome[MAX_NOME+1]; } REGISTO;

b)

typedef struct { REGISTO arr[MAX]; int conta; } LISTA;

c) int main(void) { LISTA lista; return 0; }

GEST.C

d)

void inic(LISTA * ptr)

{ ptr->conta=0; }

e)

int lista_cheia(LISTA lst)

{ return lst.conta>=MAX; }

f)

int inserir(LISTA *ptr, REGISTO reg)

{ if (lista_cheia(*ptr)) return -1; ptr->arr[ptr->conta] = reg; return ptr->conta++; }

g)

h)

int gravar(LISTA lst, char *filename) /* Versão 1 */ { FILE *fp=fopen(filename, "wb"); if (fp==NULL) return 0;

for (int i=0 ; i<lst.conta; i++) if (fwrite(&lst.arr[i], sizeof(REGISTO), 1L, fp)!=1) return 0; fclose(fp); return 1; }

int gravar_v2(LISTA lst, char *filename) /* Versão 2 */ { FILE *fp=fopen(filename, "wb"); if (fp==NULL) return 0;

if (fwrite(lst.arr, sizeof(REGISTO), (long) lst.conta, fp)!= lst.conta) return 0; fclose(fp); return 1; }

int carregar_lista(LISTA *ptr, FILE *fp) { REGISTO reg; rewind(fp); /* Ir para o principio do ficheiro */ while (fread(&reg, sizeof(reg), 1L, fp)==1) if (inserir(ptr, reg)==-1) return 0; return 1; }

i)

void listar(LISTA lst)

{ puts("---- LISTA (inicio) ----"); for (int i=0; i<lst.conta; i++) printf("%2d: %d %s\n", i+1, lst.arr[i].n, lst.arr[i].nome); puts("---- LISTA (fim) -------"); }

j)

1: #include <stdio.h>

2: #include <string.h>

3:

4: #define MAX 10

5: #define MAX_NOME 40

6:

7: typedef struct

8: { 9: unsigned n; 10: char nome[MAX_NOME+1];

11: } REGISTO;

12:

13: typedef struct

14: { 15: REGISTO arr[MAX];

16: int conta; 17: } LISTA;

18:

19: void inic(LISTA * ptr)

20: { 21: ptr->conta=0; 22: }

23:

24: int lista_cheia(LISTA lst)

25: { 26: return lst.conta>=MAX;

27: }

28:

29: int inserir(LISTA *ptr, REGISTO reg)

30: { 31: if (lista_cheia(*ptr))

32: return -1;

33: ptr->arr[ptr->conta] = reg; 34: return ptr->conta++;

35: }

36:

37: int gravar(LISTA lst, char *filename) /* Versão 1 */

38: {

39: FILE *fp=fopen(filename, "wb");

40: if (fp==NULL) return 0;

41:

42: for (int i=0 ; i<lst.conta; i++)

43: if (fwrite(&lst.arr[i], sizeof(REGISTO), 1L, fp)!=1)

44: return 0;

45: fclose(fp);

46: return 1;

47: }

48:

49: int gravar_v2(LISTA lst, char *filename) /* Versão 2 */

50: {

51: FILE *fp=fopen(filename, "wb");

52: if (fp==NULL) return 0;

53:

54: if (fwrite(lst.arr, sizeof(REGISTO), (long) lst.conta, fp)!= lst.conta)

55: return 0;

56: fclose(fp);

57: return 1;

58: }

59:

60: int carregar_lista(LISTA *ptr, FILE *fp)

61: { REGISTO reg; 62: rewind(fp); /* Ir para o principio do ficheiro */ 63: while (fread(&reg, sizeof(reg), 1L, fp)==1)

64: if (inserir(ptr, reg)==-1)

65: return 0;

66: return 1;

67: }

68:

69: void listar(LISTA lst)

70: {

71: puts("---- LISTA (inicio) ----");

72: for (int i=0; i<lst.conta; i++)

73: printf("%2d: %d %s\n", i+1, lst.arr[i].n, lst.arr[i].nome);

74: puts("---- LISTA (fim) -------\n");

75: }

76:

77:

78: int main(void)

79: {

80: REGISTO regs[] = {{50, "Rui"}, {22, "Ana"}, 81: {77, "Isabel"}, {99, "Carlos"}

82: };

83: LISTA lista;

84:

85: inic(&lista); 86: listar(lista);

87:

88: // Adicionar os registos à lista

89: for (int i=0; i<sizeof(regs)/sizeof(regs[0]); i++)

90: inserir(&lista, regs[i]);

91: listar(lista);

92:

93: if (gravar(lista, "lista.dat"))

94: puts("Registos gravados com sucesso.");

95: else

96: puts("Problemas na gravação dos registos."); 97:

98: // Carregar os registos existentes em ficheiro 99: // ja lista já existente, adicionando-os ao fim 100:

101: FILE *fp = fopen("lista.dat", "rb"); 102: if (fp==NULL)

103: { 104: printf("Não foi possível abrir o ficheiro de dados"); 105: return 1; 106: }

107:

108: carregar_lista(&lista, fp); 109: puts("Depois de adicionados os registos à lista 1x"); 110: listar(lista); 111:

112: // Voltar a carregar os registos para ver se os limites 113: // não são violados

114:

115: carregar_lista(&lista, fp); 116: fclose(fp);

117: puts("Depois de adicionados os registos à lista 2x"); 118: listar(lista); 119:

120: return 0; 121: } PROG1104.C (PROGRAMA COMPLETO)

$ pro1104 ---- LISTA (inicio) ------- LISTA (fim) -------

---- LISTA (inicio) ----

1: 50 Rui

2: 22 Ana

3: 77 Isabel

4: 99 Carlos ---- LISTA (fim) -------

Registos gravados com sucesso.

Depois de adicionados os registos à lista 1x

---- LISTA (inicio) ----

1: 50 Rui

2: 22 Ana

3: 77 Isabel

4: 99 Carlos

5: 50 Rui

6: 22 Ana

7: 77 Isabel

8: 99 Carlos ---- LISTA (fim) -------

Depois de adicionados os registos à lista 2x

---- LISTA (inicio) ----

1: 50 Rui

2: 22 Ana

3: 77 Isabel

4: 99 Carlos

5: 50 Rui

6: 22 Ana

7: 77 Isabel

8: 99 Carlos

9: 50 Rui

10: 22 Ana ---- LISTA (fim) -------

Turn static files into dynamic content formats.

Create a flipbook
Issuu converts static files into: digital portfolios, online yearbooks, online catalogs, digital photo albums and more. Sign up and create your flipbook.