E
STRUTURAS DED
ADOSBruno Almeida de Jesus
E
MENTA Introdução à programação orientada a objetos.
Classes containers: arrays, arrays ordenados, listas
e suas variantes (alocação dinâmica). Tipos
E
STRUTURAS DED
ADOS TIPOS DE DADOS ETIPOS ABSTRATOS DE DADOS
Bruno Almeida de Jesus
S
UMÁRIO Motivação
Tipos de Dados
Operações
Tipos Primitivos ou
Escalares
Tipos Inteiros Tipos Reais Tipos Lógicos Tipo Caracter
Funções Para Conversão
Tipos Coleções ou
Não-Escalares
Tipo Vetor Tipo Registro Tipo Conjunto
Tipos Abstratos de Dados
Alocação de Memória
Vantagens e
M
OTIVAÇÃO Por que estudar os tipos de dados?
Duas são as principais preocupações em um
projeto de software
Os procedimentos a serem executados;
M
OTIVAÇÃO “Estruturas de Dados” busca descrever modelos de
estruturas de dados e procedimentos
Exemplos: Arrays, Registros, Listas, Pilhas, Filas e
M
OTIVAÇÃO Os tipos de dados e operações determinam as
estruturas de dados
Exemplo: em uma pilha ou fila você possui operações
push e pop para colocar e retirar elementos dela;
A forma como os dados são inseridos ou removidos é que
T
IPOS DED
ADOS Define a forma como um dado deve ser
armazenado ou recuperado, bem como os
possíveis valores que ele pode assumir ou as operações que podem ser efetuadas sobre os mesmos
Exemplo em Pascal:
integer permite valores inteiros e operações de adição,
multiplicação, subtração e divisão;
T
IPOS DED
ADOS Primitivos, derivados ou coleções;
Os principais tipos primitivos são: inteiro, real, lógico,
caracter, ponteiro;
Estáticos ou dinâmicos (instanciados em tempo de
O
PERAÇÕES Um conjunto de instruções a fim de manipular um
determinado tipo de dado a fim algum objetivo;
Criação (declaração) Percurso
Busca Alteração Retirada
T
IPOSP
RIMITIVOS OUE
SCALARES Inteiro (integer, longint, etc.);
Real (real, double, etc.);
Lógico (boolean);
T
IPOSI
NTEIROS Operações numéricas contidas no conjunto dos
números inteiros:
Soma, subtração, multiplicação, divisão inteira, resto da
divisão;
Permitem comparações de igualdade e/ou de
T
IPOSR
EAIS Satisfaz as operações e comparações possíveis
com tipos inteiros;
Operações numéricas contidas no conjunto dos
números reais:
T
IPOSL
ÓGICOS Permite operações lógicas (booleanas):
E, OU, NÃO;
Deve-se ter muito cuidado na construção de
expressões lógicas
Quanto maiores elas são, maiores as chances de
T
IPOC
ARACTER Permite a representação de um único caracter;
Operações de igualdade e desigualdade;
Por ser armazenado internamente como um valor
inteiro, podemos fazer um “casting” e efetuar outras
F
UNÇÕES PARA CONVERSÃO De real para inteiro:
Trunc, Floor, Ceil, Round;
De caracter para inteiro:
Ord;
De inteiro para caracter:
Char;
Obs: Dependendo de quais os tipos/classes envolvidos,
T
IPOSC
OLEÇÕES OUN
ÃO-E
SCALARES Vetor;
Registro;
T
IPOV
ETOR Coleção de dados homogênea indexada que pode
ser acessada por meio de um índice numérico;
var v = array [1..5] of integer;
T
IPOR
EGISTRO Coleção de dados heterogênea cujas informações
podem ser acessadas por meio de um campo;
var r = record
c1: integer; c2: boolean; end;
T
IPOC
ONJUNTO Coleção de objetos (ou informações) correlatos que
podem estar presentes ou não em um dado momento;
var c = set of (V1, V2, V3);
c := [V1, V2];
T
IPOSA
BSTRATOS DED
ADOS Segundo a Wikipédia:
Especificação de um conjunto de dados e operações
que podem ser executadas sobre esses dados;
Exemplo:
Quando usamos arrays e registros para criar uma
T
IPOSA
BSTRATOS DED
ADOS Vetores, registros e conjuntos são interessantes...
... Mas há um problema, são estáticos!
O que acontece se eu tiver um vetor de 5 posições e
precisar de outras 1000?
E se meu vetor tiver 100000 posições e eu somente
A
LOCAÇÃO DEM
EMÓRIA Alocação estática Variável alocada ocupa
espaço fixo e contíguo na memória;
Alocação dinâmica Variável alocada ocupa
V
ANTAGENS ED
ESVANTAGENS DAA
LOCAÇÃOD
INÂMICA Se alocamos dinamicamente, podemos aumentar e
diminuir o tamanho de nossa estrutura quando quisermos!
Entretanto, necessitaremos de mais algumas operações
para buscar, inserir e/ou remover informações;
Além disso, um array (estático) de vinte posições
Arrays
Slides do prof. Rodrigo de Barros Paes
P
ROBLEMA Calcule a média de n números dados e depois de imprimir
a média, devemos imprimir todos os números dados novamente.
A
RRAY::
SINTAXE<tipo de dado> <identificador>[<quantidade máxima de elementos>]
Exemplo:
FLOAT VALORES
[1000];
R
ESOLVENDO O PROBLEMA DA MÉDIAQ
UANTAS VEZES X APARECEU? (
LIVRO10.1)
E
XERCÍCIOS(
LIVRO10.2)
Usando o programa https://github.com/r0drigopaes/livro/blob/master/10_3.c, imprima
também o índice do elemento que contém o maior valor. Caso existam mais de um maior valor, imprima o primeiro.
Leia um array com 10 números inteiros e imprima todos os números pares de trás pra
frente. Por exemplo, se os números forem: 2 4 6 5 3 2 5 8 9 1, você deve imprimir: 8 2 6 4 2.
Leia um array com 10 números inteiros e substitua todos os valores pares por 1 e os
ímpares por -1
Leia um array com 10 números reais e imprima somente aqueles cujo índice são pares.
O
UTRAS FORMAS DE INICIALIZAÇÃOint meu_array[100] = {0}; // todas as posições com zero
int meu_array[100] = {5}; // apenas a primeira posição é inicializada
PROBLEMA: CALCULAR O DESVIO PADRÃO DE UM CONJUNTO DE VALORES (LIVRO 10.5)
Medida muito utilizada na estatística para medir o quão
distante da média uma população ou amostra se encontra.
A raiz quadrada da variância.
A variância é definida como sendo a média das distâncias
E
XEMPLO8, 6, 7, 8, 7, 6, 6, 10 Média: 7.25 Variância:
(8 –7.25)2= 0.5625
(6 - 7.25)2=1.5625
(7 - 7.25)2= 0.0625
(8 - 7.25)2= 0.5625
(7 - 7.25)2= 0.0625
(6 - 7.25)2= 1.5625
(6 - 7.25)2= 1.5625
(10 - 7.25)2= 7.5625
C
ONT.
Desvio padrão:
M
ISSÃOFunção que recebe um array de números como parâmero e retorna o desvio padrão desses números.
Como?
D
ECOMPONDOFunções:
media(float n[], int tam)
variância(float n[], int tam) : aqui vamos usar a função média desvio_padrao(float n[], int tam) : aqui vamos usar a função
variância
Vou fazer a média e a variância … e deixar você tentar a
M
ÉDIAfloat media(float n[], int tam) {
int i;
float soma = 0;
for (i=0; i< tam ; ++i) {
soma += n[i]; }
V
ARIÂNCIAfloat variancia(float n[], int tam) {
int i;
float var = 0;
// chama a função média que criamos
float m = media(n,tam);
for (i=0; i< tam ; ++i) {
var += (n[i] - m)*(n[i] - m); }
S
OLUÇÃO COMPLETAE
XERCÍCIOS(
LIVRO10.6)
Escreva uma função que recebe dois parâmetros: um array de inteiros
e um inteiro indicando o tamanho do array e imprime todos os números pares desse array
Escreva uma função que recebe um array de caracteres e também um
inteiro indicando o seu tamanho e retorna a quantidade de vogais que existem no array.
Escreva uma função que recebe um array de caracteres e o seu
S
E USARMOS ARRAY COM UMA DIMENSÃOfloat joao[4]; float julia[4]; float maria[4];
float ambrosio[4]; float taise[4];
A
RRAY BIDIMENSIONAL<tipo de dado> <identificador>[<linhas>][<colunas>]; Exemplo:
float notas[5][4];
0 1 2 3
0
1
2
3
A
TRIBUINDOnotas[0][0] = 5.5;
0 1 2 3
0
5.5
1
2
3
S
EGUNDA NOTA DAT
AÍSEnotas[4][1] = 8.0;
0 1 2 3
0
5.5
1
2
3
4
O
U TODA A MATRIZSCANF NA MATRIZ
notas[0][0] = 5.5 ; //atribuição fixa no código
S
OLUÇÃOhttps://github.com/r0drigopaes/livro/blob/master/10_10.c
E
XERCÍCIOS(
LIVRO10.9)
No código anterior, lemos os elementos da matriz a partir do teclado.
Depois de ler os valores, percorra a matriz e imprima-os, linha por linha.
Imprima todos os valores da matriz anterior só que agora coluna por
coluna.
Imprima todos os valores de baixo pra cima, linha a linha, da direita pra
esquerda.
Imprima todos os valores de baixo pra cima, linha a linha, da esquerda
para a direita.
E
XERCÍCIO::
FAZENDO JUNTOS(
LIVRO10.10)
E
XERCÍCIO::
FAZENDO JUNTOS Vamos fazer um programa que lê duas matrizes de inteiros
e preenche uma terceira matriz com o resultado da soma das duas. As matrizes possuem dimensões N x M, onde N e M serão dados pelo usuário. Sabe-se que 1 <= N,M
S
OLUÇÃOM
ATRIZ TRANSPOSTA(
LIVRO10.11)
F
AZENDO JUNTOSS
OLUÇÃOE
XERCÍCIO(
LIVRO10.12)
int main() {
int quadrado[5][5] = {0};
int tabela[5][6] = {{1, 2, 3, 4, 5}, {2, 4, 6, 8, 10},
{20, 10, 5, 3, 1}, {3, 6, 9, 12, 15} };
return 0; }
a) Complete o código ao lado(mas não altere a inicialização das variáveis) para que o conteúdo do
array “quadrado” fique como mostrado a seguir.
E
XERCÍCIO(
LIVRO10.12)
int main() {
int quadrado[5][5] = {0};
int tabela[5][6] = {{1, 2, 3, 4, 5}, {2, 4, 6, 8, 10},
{20, 10, 5, 3, 1}, {3, 6, 9, 12, 15} };
return 0; }
b) Complete o código ao lado para que o conteúdo
E
XERCÍCIO(
LIVRO10.12)
int main() {
int quadrado[5][5] = {0};
int tabela[5][6] = {{1, 2, 3, 4, 5}, {2, 4, 6, 8, 10},
{20, 10, 5, 3, 1}, {3, 6, 9, 12, 15} };
return 0; }
c) Complete o código ao lado para que o conteúdo
E
XERCÍCIO(
LIVRO10.12)
int main() {
int quadrado[5][5] = {0};
int tabela[5][6] = {{1, 2, 3, 4, 5}, {2, 4, 6, 8, 10},
{20, 10, 5, 3, 1}, {3, 6, 9, 12, 15} };
return 0; }
d) O array “tabela” foi parcialmente inicializado.
Strings
Slides do prof. Rodrigo de Barros Paes
M
AS EM MUITOS CASOS,
PRECISAMOS MANIPULARFRASES
!
Problema: Faça um programa para ler uma frase e indicar o seu tamanho!
Exemplo de entrada: o rato
V
AMOS APRENDER A:
Como representar uma string Como declarar
S
TRINGS SÃO ARRAYS DE CARACTERESchar c[8];
c[0] = 'p'; c[1] = 'r'; c[2] = 'o'; c[3] = 'g'; c[4] = 'r'; c[5] = 'a'; c[6] = 'm'; c[7] = 'a';
M
AS SÃO ESPECIAISInicialização pode ser diferente:
char c[9] = "programa";
\0
Indica o final de string
char c[9] = "casa";
L
EITURA VIA SCANFchar c[9];
T
ENTE DIGITAR “Tudo vale a pena”GETS
I
MPRESSÃOprintf("A frase lida foi: %s\n",frase);
E
XERCÍCIOS Modifique o código do exercício anterior para imprimir a quantidade de vogais
que aparecem na frase e não a quantidade de caracteres.
Faça um programa para ler uma string e um caractere qualquer e imprima o
número de ocorrências desse caractere na string. Por exemplo, se a string for
“abacate” e o caractere for: ‘a’, então a resposta deve ser 3.
Leia uma string e copie o seu conteúdo invertido em um outro array. Por exemplo, se a string for “PROGRAMAR”, então a outra string será:
“RAMARGORP”
Diferentemente do exercício anterior, leia uma string e inverta o seu conteúdo
Ponteiros
Slides do prof. Rodrigo de Barros Paes
T
IPOUm tipo define o conjunto de valores válidos para aquela variável.
Exemplos:
int : números inteiros float : números reais char : caractere
P
ONTEIROUm tipo capaz de armazenar endereços e memória
A
MEMÓRIACódigo: área onde o programa compilado
reside;
Global: variáveis globais
Pilha: parâmetros de funções e variáveis
locais
P
ONTEIROSSe um ponteiro guarda o endereço de memória, como saber o endereço de memória de uma variável?
OPERADOR &
Endereço da variável x:
D
ECLARAÇÃOD
ESAFIOEscreva uma função que troque o conteúdo de duas variáveis. #include <stdio.h>
void troca(int x, int y) {
// implementar }
int main() {
int a, b; a = 5; b = 3; troca(a,b);
printf("a=%d, b=%d\n", a, b);
R
OTEIROE
XERCÍCIO:
ORDENAR TRÊS VARIÁVEIS INTEIRASS
OLUÇÃOP
ONTEIROS Ponteiros guardam endereços de memória.
Um ponteiro também tem tipo. No C quando declaramos ponteiros nós
informamos ao compilador para que tipo de variável vamos apontá-lo.
Por exemplo, um ponteiro int aponta para um inteiro, isto é, guarda o endereço de
P
ONTEIROS Para declarar um ponteiro temos a seguinte forma geral:
tipo_do_ponteiro *nome_da_variável;
É o asterisco (*) que faz o compilador saber que aquela variável não vai guardar
um valor mas sim um endereço para aquele tipo especificado.
Exemplos:
int *pt;
char *temp, *pt2;
Ponteiros não inicializados apontam para um lugar indefinido.
Os ponteiros devem ser inicializados (apontado para algum lugar conhecido)
P
ONTEIROS Para atribuir um valor a um ponteiro recém-criado poderíamos igualá-lo a um valor
de memória.
Mas, como saber a posição na memória de uma variável do nosso programa?
Podemos então deixar que o compilador faça este trabalho por nós. Para saber o
endereço de uma variável basta usar o operador &. Veja o exemplo:
int count=10; int*pt;
P
ONTEIROS Para alterar o valor de uma variável apontado por um ponteiro, basta usar o
operador *.
Resumindo:
*pt: o conteúdo da posição de memória apontado por pt;
&count: o endereço onde armazena a variável count.
int count=10; int*pt;
pt = &count; *pt = 12;
P
ONTEIROSE
XEMPLO1
#include <stdio.h>
void main (){
int num, valor; int*p;
num = 55;
p = # /* Pega o endereco de num */ valor = *p;
/* Valor e igualado a num de uma maneira indireta */ printf ("\n\n%d\n", valor);
printf ("Endereco para onde o ponteiro aponta: %p\n", p); printf ("Valor da variavel apontada: %d\n", *p);
P
ONTEIROS–
E
XEMPLO2
#include <stdio.h>
void main (){ int num, *p;
num = 55;
p = # /* Pega o endereco de num */ printf ("\n Valor inicial: %d\n", num);
*p = 100; /* Muda o valor de num de uma maneira indireta */ printf ("\n Valor final: %d\n", num);
O
PERAÇÕES ARITMÉTICAS COM PONTEIROS p1 = p2; p1 aponte para o mesmo lugar que p2;
*p1 = *p2; a variável apontada por p1 tenha o mesmo conteúdo da
variável apontada por p2;
p++; passa a apontar para o próximo valor do mesmo tipo para o
qual o ponteiro aponta. Isto é, se temos um ponteiro para um inteiro e o incrementamos ele passa a apontar para o próximo inteiro;
p--; funciona semelhantemente;
(*p)++; incrementar o conteúdo da variável apontada pelo ponteiro
O
PERAÇÕES ARITMÉTICAS COM PONTEIROS p = p+15; ou p+=15; incrementar um ponteiro de 15;
*(p +15); usar o conteúdo do ponteiro 15 posições adiante;
== e != para saber se dois ponteiros são iguais ou diferentes;
>, <, >= e <= estamos comparando qual ponteiro aponta para uma posição mais
alta na memória. Então uma comparação entre ponteiros pode nos dizer qual dos dois está "mais adiante" na memória.
Há entretanto operações que você não pode efetuar num ponteiro. Você não pode dividir ou multiplicar ponteiros, adicionar dois
P
ONTEIROSG
ENÉRICOS Um ponteiro genérico e um ponteiro que pode apontar para qualquer tipo de dado.
Define-se um ponteiro genérico utilizando-se o tipo void:
O tipo de dado apontado por um void pointerdeve ser controlado pelo usuário
Usando um type cast (conversão de tipo) o programa pode tratar adequadamente
o ponteiro
void *pv; int x=10; float f=3.5;
P
ONTEIROS EV
ETORES Há uma diferença entre o nome de um vetor e um ponteiro que deve ser frisada:
um ponteiro é uma variável, mas o nome de um vetor não é uma variável. Isto significa, que não se consegue alterar o endereço que é apontado pelo "nome do vetor".
/* as operações abaixo são válidas */
int vetor[10]; int *ponteiro, i;
ponteiro = &i;
/* as operações a seguir são inválidas */
vetor = vetor + 2; /* ERRADO: vetor não e' variável */ vetor++; /* ERRADO: vetor não e' variável */
vetor = ponteiro; /* ERRADO: vetor não e' variável */ /* as operações abaixo são válidas */
P
ONTEIROS EV
ETORESExemplo
Podemos ver que p[2] equivale a *(p+2)
#include <stdio.h>
voidmain ()
{
int matrx [10] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 }; int *p;
p = matrx;
P
ONTEIROS ES
TRINGS strings são arrays de caracteres e podem ser acessados através de char *
abcdef
O incremento de pc o posiciona sobre o próximo caracter (byte a byte) void main ()
{
char str[]=“abcdef”, *pc;
for (pc = str; *pc != ‘\0’; pc++)
P
ONTEIROS ES
TRINGS Operações sobre strings com ponteiros
void StrCpy (char *destino, char *origem)
{
while(*origem) /* *origem==‘\0’ encerra while */
P
ONTEIROS ES
TRINGS Variação de strcpy:
void strcpy (char *destino, char *origem)
{
while((*destino = *origem) != ‘\0’)
V
ETORES DEC
ARACTERES Percorrendo vetores com ponteiro:
void main () {
char matriz[5][10]; char *pc;
int i;
for (i=0, pc=matriz[0]; i < 50; i++, pc++)
*pc = ‘ ‘; }
void main () {
char matriz[5][10]; int i, j;
for (i=0; i<5; i++) for (j=0; j<10; j++)
matriz[i][j] = ‘ ‘;
V
ETOR DES
TRINGS Cada elemento do vetor é um ponteiro para um
caracter.
Declaração:
char *arstr[] = {“Joao”, “Maria”, “Antonio”, “Zacarias”, “Carlos”};
arstr e um vetor de ponteiros para char, iniciado
V
ETOR DES
TRINGS Comparando vetor de string com matriz de char
char *as[]=
{“Joao”,“Maria”,“Antonio”,“Zacarias”,“Carlos”};
char ma[5][10]=
C
UIDADO COMS
TRINGS E comum esquecer de alocar uma área para
armazenamento de caracteres
void main() {
char *pc; char str[] = “Um string”;
strcpy(pc, str); /* erro! pc indeterminado */
V
ETORES DE PONTEIROS Podemos construir vetores de ponteiros como declaramos vetores de qualquer
outro tipo. Uma declaração de um vetor de ponteiros inteiros poderia ser:
int*pmatrx [10];
V
ETORES MULTIDIMENSIONAIS Vetores podem ter diversas dimensões, cada uma
identificada por um par de colchetes n declaração
Ex:
char matriz[5][10];
Declara uma matriz de 5 linhas e 10 colunas; Na memória, entretanto, os caracteres são
P
ONTEIROS PARAP
ONTEIROS Um ponteiro para um ponteiro é como se você anotasse o endereço de um papel
que tem o endereço da casa do seu amigo.
Podemos declarar um ponteiro para um ponteiro com a seguinte notação:
tipo_da_variável **nome_da_variável;
**nome_da_variável é o conteúdo final da variável apontada; *nome_da_variável é
P
ONTEIROS PARAP
ONTEIROS Para acessar o valor desejado apontado por um ponteiro para ponteiro, o
operador asterisco deve ser aplicado duas vezes, como mostrado no exemplo abaixo:
#include <stdio.h>
void main()
{
floatfpi = 3.1415, *pf, **ppf;
pf = &fpi; /* pf armazena o endereco de fpi */ ppf = &pf; /* ppf armazena o endereco de pf */ printf("%f", **ppf); /* Imprime o valor de fpi */
C
UIDADO!!!
O principal cuidado ao se usar um ponteiro deve
ser:
saiba sempre para onde o ponteiro está apontando.
void main () /* Errado -Nao Execute */ {
Q
UIZvoid exemplo2() {
int firstvalue, secondvalue;
int * mypointer; mypointer = &firstvalue;
*mypointer = 10; mypointer = &secondvalue;
*mypointer = 20; printf("%d\n", firstvalue);
printf("%d\n", secondvalue);
Alocação Dinâmica
Slides do prof. Mário Dantas
A
LOCAÇÃO DEM
EMÓRIA Alocação Estática
Espaço de memória é reservado previamente;
Área de Tamanho FIXO e de Endereço FIXO (estática); Declarado e reservado em tempo de compilação
Exemplo: variáveis globais - declaradas fora do main/funções
Alocação Dinâmica:
Espaço de memória é alocado em tempo de execução
usando as funções “calloc” e “malloc” (dinâmica); Áreas de Tamanho VARIÁVEL e de Endereço VARIÁVEL
são criadas (reserva memória) e destruídas (libera memória);
Acesso usualmente através de Endereços e Ponteiros Exemplo: ponteiros+calloc/malloc ou variáveis locais
ALOCAÇÃO
DINÂMICA DE
MEMÓRIA
Ponteiros fornecem o suporte necessário para o poderoso sistema de alocação dinâmica.
Alocação dinâmica é o meio pelo qual um programa
pode obter memória enquanto está em execução.
ALOCAÇÃO
DINÂMICA DE
MEMÓRIA
Por exemplo, um processador de texto ou um banco de dados aproveita toda a RAM de um sistema. Porém, como a
quantidade de RAM varia entre computadores esses programas não podem usar variáveis normais.
ALOCAÇÃO
DINÂMICA DE
MEMÓRIA
A memória alocada pelas funções de alocação dinâmica é obtida do heap – a região de memória livre do seu
computador.
Embora o tamanho do heap seja desconhecido, ele
ALOCAÇÃO
DINÂMICA DE
MEMÓRIA
No padrão C ANSI existem 4 funções para alocações dinâmica pertencentes a biblioteca stdlib.h. São elas malloc(), calloc(), realloc() e free(). Sendo que as mais utilizadas são as funções
malloc() e free().
malloc() aloca memória
ALOCAÇÃO
DINÂMICA DE
MEMÓRIA
MALLOC()
A sintaxe da função malloc() é dada por:
numero_de_bytes é o número de bytes da memória que você quer alocar.
O tipo size_t é definido em stdlib.h como sendo um inteiro sem sinal.
O interessante é que esta função retorna um ponteiro do tipo void podendo assim ser atribuído a qualquer tipo de ponteiro.
MALLOC()
O fragmento de código mostrado abaixo aloca 1000 bytes de memória:
MALLOC()
Para garantir portabilidade é interessante então efetuar o cast para o tipo de ponteiro que você deseja:
MALLOC()
O próximo exemplo aloca espaço para 50 inteiros.
MALLOC()
Como o heap não é infinito, sempre que alocar memória, você deve testar o valor devolvido por malloc(), antes de usar o ponteiro, para estar certo de que não é nulo.
FREE()
A função free() é o oposto de malloc(), visto que ela devolve memória previamente alocada ao sistema.
Uma vez que a memória tenha sido liberada, ela pode ser realocada por uma nova chamada a malloc().
Aqui, pont é um ponteiro para a memória alocada
anteriormente por malloc(). É muito importante que você nunca use free() com um argumento inválido, isso destruiria a lista de memória livre.
ESTRUTURA DE
DADOS
A
LOCAÇÃOD
INÂMICA DEM
EMÓRIA Alocação de memória:
calloc - Aloca memória, zerando os dados
malloc - Aloca memória, sem inicializar os dados
free - Libera um bloco de memória alocada previamente
void *calloc ( <quantidade_elementos>, <tamanho_elemento> )
Exemplo: tabela_inteiros = calloc( 10, sizeof ( int ) );
void *malloc( <quantidade_elementos>, <tamanho_elemento> )
Exemplo: tabela_inteiros = malloc( 10, sizeof ( int ) );
void free ( void *ponteiro)
Exemplo: free ( tabela_inteiros );
A
LOCAÇÃOD
INÂMICA DEM
EMÓRIAExemplos:
int *ptr_int; double *ptr_pf;
ptr_int = (int*)calloc(10,sizeof(int)); /* Aloca 10 inteiros em seqüência */
ptr_pf = (double*)calloc(10,sizeof(double)); /* Aloca 10 n. tipo double */ free (ptr_int); /* Libera a área de memória alocada */
Fazendo a criação de um vetor de duas formas equivalentes:
int tabela[10]; /* Aloca memória: tabela aponta para o início do vetor */ ou
int *tabela; tabela = (int *) calloc (10, sizeof(int));
E
XEMPLOS 131 #include <stdio.h> #include <stdlib.h> double Tabela[10]; main () { int i;for (i=0; i < 10; i++) {
printf("Dado %d = ",i); scanf ("%lf",&(Tabela[i])); }
printf("\nDados Lidos:\n"); for (i=0; i < 10; i++)
printf("Dado %d = %.2lf \n",i, Tabela[i]);
system(“pause”);
}
#include <stdio.h>
#include <stdlib.h> /* Inclui a lib do "calloc" */ double *Tabela; /* Cria somente o
ponteiro (não aloca)*/ main () {
int i;
Tabela=(double*)calloc(10,sizeof(double)); for (i=0; i < 10; i++) {
printf("Dado %d = ",i); scanf ("%lf",&(Tabela[i])); }
printf("\nDados Lidos:\n"); for (i=0; i < 10; i++)
printf("Dado %d = %.2lf \n",i, Tabela[i]);
system(“pause”);
}
Estruturas
Slides do prof. Rodrigo de Barros Paes
D
ESAFIO Fazer o sistema de controle de uma locadora online de
filmes.
Módulo de cadastro de clientes:
Código
Nome
Data de nascimento
Sexo (masculino ou feminino)
O
PÇÃO1
int codigo;
char nome[500];
int dia_nascimento; int mes_nascimento; int ano_nascimento;
D
ESSA FORMA…
PARA IMPRIMIRNome e data de nascimento do cliente 30:
printf("%s %d\n",nome[30],ano_nascimento[30]);
Imprimir tudo:
void imprimir(int codigo, char nome[500], int dia_nascimento, int mes_nascimento, int
ano_nascimento, int sexo) {
STRUCT
Com o struct podemos criar um novo tipo de dados Composto por tipos já existentes
E também por outras estruturas que criamos antes
struct <identificador do tipo> {
D
ECLARANDO VARIÁVEISstruct <identificador do tipo> <identificador da variável>;
struct cliente um_cliente;
M
ODIFICANDO A FUNÇÃO DE IMPRIMIRDe:
void imprimir(int codigo, char nome[500], int dia_nascimento, int mes_nascimento, int ano_nascimento, int sexo)
{ }
Para:
void imprimir(struct cliente c) {
P
OR DENTRO DA FUNÇÃO IMPRIMIRComo acessar os campos?
T
UDO JUNTODeclaração do tipo
Declaração da variável Passagem de parâmetro Acessando valores
Modificando valores
A
RRAYSarrays de inteiros
int a[5];
arrays de floats
float a[5];
arrays de estruturas
E
XEMPLO COMPLETOE
XERCÍCIOSModifique o código anterior para que o cliente também tenha CPF. Lembre de ler e imprimir.
Implemente a função: