Buscar

3390-pdfestruturadados

Faça como milhares de estudantes: teste grátis o Passei Direto

Esse e outros conteúdos desbloqueados

16 milhões de materiais de várias disciplinas

Impressão de materiais

Agora você pode testar o

Passei Direto grátis

Você também pode ser Premium ajudando estudantes

Faça como milhares de estudantes: teste grátis o Passei Direto

Esse e outros conteúdos desbloqueados

16 milhões de materiais de várias disciplinas

Impressão de materiais

Agora você pode testar o

Passei Direto grátis

Você também pode ser Premium ajudando estudantes

Faça como milhares de estudantes: teste grátis o Passei Direto

Esse e outros conteúdos desbloqueados

16 milhões de materiais de várias disciplinas

Impressão de materiais

Agora você pode testar o

Passei Direto grátis

Você também pode ser Premium ajudando estudantes
Você viu 3, do total de 416 páginas

Faça como milhares de estudantes: teste grátis o Passei Direto

Esse e outros conteúdos desbloqueados

16 milhões de materiais de várias disciplinas

Impressão de materiais

Agora você pode testar o

Passei Direto grátis

Você também pode ser Premium ajudando estudantes

Faça como milhares de estudantes: teste grátis o Passei Direto

Esse e outros conteúdos desbloqueados

16 milhões de materiais de várias disciplinas

Impressão de materiais

Agora você pode testar o

Passei Direto grátis

Você também pode ser Premium ajudando estudantes

Faça como milhares de estudantes: teste grátis o Passei Direto

Esse e outros conteúdos desbloqueados

16 milhões de materiais de várias disciplinas

Impressão de materiais

Agora você pode testar o

Passei Direto grátis

Você também pode ser Premium ajudando estudantes
Você viu 6, do total de 416 páginas

Faça como milhares de estudantes: teste grátis o Passei Direto

Esse e outros conteúdos desbloqueados

16 milhões de materiais de várias disciplinas

Impressão de materiais

Agora você pode testar o

Passei Direto grátis

Você também pode ser Premium ajudando estudantes

Faça como milhares de estudantes: teste grátis o Passei Direto

Esse e outros conteúdos desbloqueados

16 milhões de materiais de várias disciplinas

Impressão de materiais

Agora você pode testar o

Passei Direto grátis

Você também pode ser Premium ajudando estudantes

Faça como milhares de estudantes: teste grátis o Passei Direto

Esse e outros conteúdos desbloqueados

16 milhões de materiais de várias disciplinas

Impressão de materiais

Agora você pode testar o

Passei Direto grátis

Você também pode ser Premium ajudando estudantes
Você viu 9, do total de 416 páginas

Faça como milhares de estudantes: teste grátis o Passei Direto

Esse e outros conteúdos desbloqueados

16 milhões de materiais de várias disciplinas

Impressão de materiais

Agora você pode testar o

Passei Direto grátis

Você também pode ser Premium ajudando estudantes

Prévia do material em texto

www.esab.edu.br
Estrutura de DadosSISTEMAS DE INFORMAÇÃO
Estrutura de Dados
Vila Velha (ES)
2014
Escola Superior Aberta do Brasil
Diretor Geral 
Nildo Ferreira
Diretora Acadêmica
Beatriz Christo Gobbi
Coordenadora do Núcleo de Educação a Distância
Beatriz Christo Gobbi
Coordenadora do Curso de Administração EAD
Rosemary Riguetti
Coordenador do Curso de Pedagogia EAD
Claudio David Cari
Coordenador do Curso de Sistemas de Informação EAD
David Gomes Barboza
Produção do Material Didático-Pedagógico
Delinea Tecnologia Educacional / Escola Superior Aberta do Brasil
Diretoria Executiva
Charlie Anderson Olsen
Larissa Kleis Pereira
Margarete Lazzaris Kleis
Conteudista
Marcelo Medeiros
Coordenação de Projeto
Andreza Regina Lopes da Silva
Supervisão de conteúdo
Renata Oltramari
Liderança Técnica Design Gráfico
Fernando Andrade
Liderança Técnica Revisão Gramatical
Tiago Costa Pereira
Laís Gonçalves Natalino
Designer Educacional
Aline Batista
Revisão Gramatical
Bárbara Seger Zeni
Érica Valduga
Laís Gonçalves Natalino
Designer Gráfico
Laura Rodrigues
Neri Gonçalves Ribeiro
Diagramação
Dilsonir José Martins Junior
Karina Silveira
Equipe Acadêmica da ESAB
Coordenadores dos Cursos
Docentes dos Cursos
Copyright © Todos os direitos desta obra são da Escola Superior Aberta do Brasil.
www.esab.edu.br
Av. Santa Leopoldina, nº 840
Coqueiral de Itaparica - Vila Velha, ES
CEP 29102-040
Apresentação
Caro estudante,
Seja bem-vindo à disciplina de Estrutura de Dados, um complemento aos 
conceitos fundamentais de programação vistos nas disciplinas que envolvem 
lógica de programação, aliado à discussão e apresentação de novas técnicas para o 
desenvolvimento de programas de computadores mais eficientes no uso de memória 
principal e tempo de processamento.
Adotaremos como base para validação das técnicas apresentadas a linguagem de 
programação C, porém, os conceitos e técnicas desenvolvidas nesta disciplina podem 
ser codificados em qualquer linguagem de programação atual, como Java.
Hoje é fundamental para o profissional que deseja ser um especialista em Tecnologia 
da Informação ter habilidades e competências que lhe permitam maximizar o uso dos 
recursos do computador.
E você, como nosso aluno, deve estar interessado nessa área, em saber como planejar 
e desenvolver rotinas computacionais que aperfeiçoem os resultados dos algoritmos, 
evitando o desperdício de memória principal criando rotinas de alocação, pesquisa e 
classificação dos dados.
Nesta disciplina, tendo como base os autores Forbellone et al.(2005), Cerqueira, Celes 
e Rangel Netto (2004), Ascencio e Araújo (2010) e Guimarães (1994), você conhecerá 
os conceitos e as técnicas de como implementar os tipos de alocação de memória, os 
algoritmos de classificação e pesquisa de dados, as estruturas de dados avançadas, 
como: Filas, Pilhas, Listas e Árvores.
Assim, esta disciplina possibilitará que você entenda, projete, desenvolva e valide 
o uso de estruturas de dados mais eficientes e que possibilitem o aproveitamento 
máximo dos recursos do computador.
Bom estudo!
Objetivo
Analisar, avaliar e implementar as principais técnicas de representação e 
manipulação de dados, possibilitando aos alunos a capacidade de escolher as 
estruturas de dados mais adequadas aos problemas que envolvam a ordenação e 
recuperação de informações por meio de algoritmos de organização e busca.
Habilidades e competências
• Analisar e implementar estruturas de dados para solução de problemas 
computacionais.
• Projetar estruturas de dados para resolução de problemas complexos.
• Avaliar as melhores estruturas de dados para cada tipo de problema 
computacional.
• Codificar estruturas de dados.
• Analisar as diferentes estruturas de dados.
• Aplicar adequadamente estruturas de dados.
Ementa
Conceitos básicos e apontadores. Representação de estruturas simples e 
encadeadas (listas lineares, pilhas, filas, árvores). Procedimentos e funções de 
acesso, remoção e inserção de nós nas estruturas. Métodos de classificação e 
ordenação de dados. Pesquisa de dados.
Sumário
1. Introduzir o aluno aos conceitos de Estruturas de Dados .................................................7
2. Funções – parte I ..........................................................................................................15
3. Funções – parte II .........................................................................................................22
4. Variáveis compostas homogêneas: vetores ...................................................................33
5. Alocação dinâmica de memória ....................................................................................40
6. Alocação dinâmica em C ...............................................................................................49
7. Tipos de passagens de parâmetros ................................................................................58
8. Tipos estruturados – parte I ..........................................................................................68
9. Tipos estruturados – parte II .........................................................................................80
10. Matrizes – conceituação ...............................................................................................92
11. Matrizes – codificação ................................................................................................101
12. Matrizes – exercícios ...................................................................................................109
13. Tipos abstratos de dados – parte I ..............................................................................120
14. Tipos abstratos de dados – parte II .............................................................................126
15. Listas encadeadas .......................................................................................................133
16. Listas encadeadas simples – conceituação .................................................................141
17. Listas encadeadas simples – codificação ....................................................................154
18. Lista encadeada simples – exercícios ..........................................................................166
19. Listas circulares – conceituação ..................................................................................175
20. Listas circulares – codificação .....................................................................................182
21. Listas circulares – exercícios ........................................................................................190
22. Listas duplamente encadeadas – conceituação ..........................................................197
23. Listas duplamente encadeadas – codificação .............................................................206
24. Listas circulares duplamente encadeadas – conceituação ...........................................214
25. Listas circulares duplamente encadeadas − codificação .............................................226
26. Pilhas – conceituação .................................................................................................237
27. Pilhas – codificação – parte I ......................................................................................244
28. Pilhas – codificação – parte II .....................................................................................253
29. Filas – conceituação ....................................................................................................258
30. Filas – codificação .......................................................................................................264
31. Filas – exercícios .........................................................................................................27132. Fila dupla ....................................................................................................................277
33. Árvores – parte I .........................................................................................................284
34. Árvores – parte II ........................................................................................................292
35. Árvores – parte III .......................................................................................................300
36. Árvores – parte IV .......................................................................................................308
37. Árvores – parte V ........................................................................................................316
38. Métodos de pesquisa e ordenação: conceituação ........................................................324
39. Métodos de ordenação: bubble sort – parte 1 ............................................................331
40. Métodos de ordenação: bubble sort – parte 2 ............................................................338
41. Métodos de ordenação: quick sort – parte 1 ...............................................................345
42. Métodos de ordenação: quick sort – parte 2 ...............................................................352
43. Métodos de ordenação: merge sort .............................................................................361
44. Métodos de ordenação: merge sort .............................................................................368
45. Métodos de pesquisa: busca em vetor .........................................................................375
46. Métodos de pesquisa: árvore binária de pesquisa .......................................................382
47. Métodos de pesquisa: árvore balanceada ....................................................................388
48. Exercícios de fixação ....................................................................................................395
Glossário ............................................................................................................................405
Referências ........................................................................................................................414
www.esab.edu.br 7
1 Introduzir o aluno aos conceitos de Estruturas de Dados
Objetivo
Introduzir o aluno aos conceitos de estruturas de dados.
Nesta unidade serão apresentados os conceitos fundamentais da estrutura 
de dados: o que é estrutura de dados, a diferença entre informações e 
dados e as áreas de aplicação da estrutura de dados e seus benefícios. 
Inicialmente podemos entender a estrutura de dados como qualquer 
forma de armazenamento e manipulação de dados no computador, como 
variáveis, vetores, matrizes e arquivos. Tal pensamento não está errado, 
porém, nesta unidade, você estudará que a estrutura de dados é muito 
mais do que armazenamento de informações, há um gerenciamento de 
memória associado ao processo de criação e destruição dessas estruturas, 
assim como normas e procedimentos para seu uso.
Para elaboração desta unidade foram utilizadas as referências de 
Guimarães (1994) e Ascencio e Araújo (2010).
1.1 O que é estrutura de dados?
A definição de estrutura de dados é um conceito amplo e requer um 
conjunto de conhecimentos que a fundamentam. Vamos começar pela 
compreensão da abstração de dados, que consiste na análise de um 
problema identificando os processos finitos que devem ser realizados para 
se chegar ao resultado desejado. 
Por exemplo, no desenvolvimento de um sistema acadêmico durante 
a etapa de análise do problema pode-se chegar à conclusão que as 
informações a serem armazenadas para cada aluno são: matrícula, o 
nome e o sexo. Já em outro contexto, um sistema acadêmico durante a 
mesma etapa de análise do problema pode especificar que cada aluno 
www.esab.edu.br 8
será identificado pela matrícula, nome, idade, sexo, data de nascimento, 
nome do pai e da mãe. Nos dois casos os requisitos avaliados foram os 
dados cadastrais de um aluno, porém no processo de abstração do que é 
um “aluno”, os dois sistemas a serem desenvolvidos possuem definições 
diferentes, mesmo se tratando de um aluno, e cabe ao analista fazer o 
levantamento de acordo com o cenário que lhe é apresentado. Assim 
como os dados cadastrais, as funcionalidades de cada sistema, as regras de 
negócio e uso do sistema também dependerão da abstração de cada um 
dos contextos apresentados. 
A Figura 1 representa a abstração de dados.
Entrada Processamento Saída
Figura 1 – Abstração de Dados.
Fonte: Elaborada pelo autor (2013).
A entrada refere-se aos dados que são colhidos no mundo real, ou seja, 
externo ao computador, e a saída à sua transformação na informação 
desejada. O processamento representa uma sequência finita de operações 
a serem realizadas a partir dos dados de entrada, a fim de transformá-
los em informações. A abstração de dados se constitui pela análise dos 
valores manipulados, os métodos e os procedimentos que devem ser 
aplicados aos dados de entrada com a finalidade de resolver determinados 
problemas, representados pela saída desejada.
Por exemplo, um sistema que deve converter uma medida em metros para 
centímetros requer uma sequência ordenada de procedimentos e operações 
que possibilitam ao computador realizar essa tarefa. Para tanto, é necessário 
avaliar o problema e abstrair as regras importantes a serem transferidas 
para o algoritmo, como a definição dos valores de entrada e saída como 
números reais, já que as medidas manipuladas pelo sistema (metros e 
centímetros) são números que podem conter casas decimais. Para conversão 
da medida, será necessária a operação de divisão da medida em metros por 
100, já que cada um metro corresponde a 100 centímetros. Por fim, será 
necessária a utilização de procedimentos para interagir com o usuário para 
que ele informe os dados que serão processados (entrada de dados) e para a 
apresentação do resultado final da operação de conversão (saída de dados).
www.esab.edu.br 9
Para sua reflexão
A definição de quais métodos e procedimentos 
serão utilizados para resolução de um problema 
na forma de um sistema computacional não é 
imediata, é construída a partir de testes e validação 
dos resultados, por meio de uma técnica de 
análise e refinamento dos processos. Requerem 
também técnicas de representação do problema, 
como fluxogramas, diagramas, algoritmos, todos 
como uma documentação formal e roteiros de 
validação da solução, aliados à expertise de cada 
executor. Por isso, deve-se ter em mente que há 
diversas estratégias para se chegar à solução de um 
determinado problema, apresentando vantagens 
e desvantagens em relação a cada uma delas, mas 
todas devem garantir a resolução do problema.
Note que mesmo que seja apresentado um problema, como o problema 
anterior de conversão de metros para centímetros para um conjunto de 
programadores e analistas de sistemas, cada um apresentará uma lógica 
e estratégia que pode não ser a mesma para todos já que a abstração 
do problema e de como resolvê-la é uma visão subjetiva de cada um, 
mas todos devem garantir que o resultado da conversão será o mesmo 
independentemente da solução, já que somente essa condição garante 
que o sistema funcionará de acordo com o esperado.
O executor ou analista deve ser capaz de escolher aquela estratégia que 
melhor se adéqua para resolução do problema, levando em consideração 
a eficiência da solução, as necessidades de armazenamento dos dados e o 
tempo de processamento.
Note que as características de armazenamento de dados, de 
processamento e de eficiência da solução determinam o processo de 
informatização da solução, que é a transferência para o computador de 
uma tarefaque era realizada no mundo real, a partir de uma sequência 
www.esab.edu.br 10
finita de processamentos. Estes, por sua vez, são fundamentados nas 
definições de como o sistema deverá funcionar, requisitos, testes e 
validações especificadas pelos especialistas em tecnologia da informação. 
Por exemplo, no desenvolvimento de um sistema computacional que 
deverá controlar a temperatura de uma caldeira, é fundamental que o 
processamento das informações aconteça de forma rápida e eficiente. 
Pois, além de monitorar os dados, é preciso que a resposta em caso de 
temperaturas elevadas ou situações de riscos seja rápida, e o sistema possa 
garantir em tempo hábil a tomada de decisões por parte dos envolvidos. 
Esses requisitos e especificações fazem parte do processo de abstração dos 
dados realizados pelos especialistas em tecnologia da informação.
A elaboração de um algoritmo, que representa a solução de um 
problema, a partir de uma linguagem de programação chama-se 
implementação. Sua finalidade é transformar uma abstração de dados 
em um processo concreto, formal, com a execução de métodos e 
procedimentos já projetados na forma de algoritmos. 
Para Ascencio e Araújo (2010, p. 1), 
Durante o processo de computação de sua saída, um algoritmo manipula dados 
obtidos de sua entrada. Quando dados são dispostos e manipulados de forma 
homogênea, constituem um tipo abstrato de dados.
Nesse processo de abstração de dados, quando uma série finita de 
instruções é manipulada de forma homogênea, a sua formatação em 
algoritmos e a sua posterior execução pelos computadores representa a 
aplicação da estrutura de dados e da sua conceituação.
Podemos entender a estrutura de dados como um recurso que vai 
além do armazenamento de dados, pois exige a identificação e 
desenvolvimento de procedimentos, métodos e técnicas que permitem a 
solução do problema, utilizando o espaço de armazenamento de forma 
otimizada, com processamento eficiente e garantia de integridade das 
informações. Ou seja, mais do que armazenar os dados em memória, o 
www.esab.edu.br 11
acesso e processamento dos dados devem ocorrer de forma a atender às 
necessidades da solução em tempo hábil e com garantia que os resultados 
processados estão corretos. 
Portanto, uma estrutura permite que os dados se mantenham 
organizados por alguma lógica. Além disso, o usuário pode manipular os 
dados disponibilizados pelas operações. 
Ou seja, a estrutura de dados, por meio de sequências finitas de operações, 
gerencia os dados que podemos entender por informações armazenadas. 
Por exemplo, no desenvolvimento de um sistema que realize a busca 
dos dados de um funcionário, por meio de um vetor pelo valor da 
sua matrícula (que é única, dois funcionários não podem ter a mesma 
matrícula), é importante que quando acontecer a localização dessa 
matrícula, o sistema encerre a busca, pois não haverá outro funcionário 
com essa matrícula. Caso isso não seja definido como uma regra da 
aplicação, o sistema continuará a pesquisa desnecessariamente. Ao 
final o resultado será o mesmo, a matrícula será localizada, porém o 
tempo de processamento será maior devido à pesquisa em toda a tabela 
de matrículas. Portanto, a estrutura de dados não se limita apenas ao 
armazenamento de dados, mas permite também otimizar os processos de 
armazenamento , organização e acesso aos dados.
Para Guimarães (1994, p. 2), as estruturas de dados “[...] são usadas nos 
algoritmos para representar as informações do problema a ser resolvido”. 
Ainda, para Ascencio e Araújo (2010, p. 2), 
[...] na representação do tipo abstrato de dados, emprega-se uma estrutura de dados. 
[...] uma estrutura de dados é um meio para armazenar e organizar dados com o 
objetivo de facilitar o acesso às modificações.” Diz ainda que “[...] as estruturas de dados 
diferem-se uma das outras pela disposição ou manipulação de seus dados, de modo que 
não se pode separar as estruturas de dados e os algoritmos associados a elas.
Segundo Guimarães (1994, p. 2), “[...] o processo de construção de 
programas, a formulação do algoritmo e a definição das estruturas de 
dados a serem usadas estão intimamente ligadas”.
www.esab.edu.br 12
Observe que a definição de estrutura de dados está associada 
ao armazenamento dos dados, mas não apenas isso. A forma de 
armazenamento dos dados, como serão manipulados e sua organização 
estão relacionados com as atividades e problemas do mundo real. 
Portanto, levá-la com suas regras de negócios e formas de manipulação 
para o computador requer do especialista a habilidade de avaliar, 
compreender e modelar todo esse universo por meio da estrutura de 
dados mais adequada. 
Então podemos entender a estrutura de dados como a forma pela qual os 
dados serão armazenados, organizados e manipulados no computador; 
associada às operações, pode ser executada com esses dados, visando 
sempre evitar o desperdício de memória alocada e otimizando o 
processamento dos dados.
1.2 Dados versus Informação
Observe que na seção anterior em alguns momentos os conceitos de 
dados e informação se confundem, e essa é uma dúvida comum, mas 
fácil de ser resolvida.
De forma geral, podem-se entender dados como a informação pura, não 
processada, no seu estado inicial, que pode representar vários significados 
e isoladamente não transmite conhecimento.
Já a informação pode ser compreendida como o dado já processado, útil, 
com alguma finalidade.
Por exemplo, o conjunto de letras a seguir pode ser entendido como 
dados, pois ele não transmite conhecimento ou informação útil: BESA. 
Mas, se processarmos esse conjunto de dados de forma a organizá-los, 
obtemos a informação: ESAB.
www.esab.edu.br 13
1.3 Utilização e benefícios
Como visto nas seções anteriores, a conceituação de estrutura de dados 
está diretamente relacionada ao desenvolvimento de algoritmos e sua 
posterior implementação. Para criar e utilizar um algoritmo, é necessário 
avaliar seu desempenho e a utilização dos recursos disponibilizados, 
como alocação de espaços na memória principal ou secundária, e tempo 
gasto para execução de determinada rotina.
Nesse sentido, a estrutura de dados pode ser aplicada em algoritmos 
simples, de entrada, processamento e saída de dados, ou mais complexos, 
como algoritmos de busca e classificação de dados.
Em muitos casos as estruturas de dados devem ser utilizadas para a construção 
de conjunto de dados, ou coleções, na forma de vetores estáticos ou dinâmicos. 
Os vetores estáticos são utilizados para o armazenamento de dados em que se 
conhece a quantidade de dados a serem processados. Já os vetores dinâmicos 
não possuem uma quantidade de elementos predefinidos, alocando memória 
à medida que cada elemento é inserido na estrutura de dados, e liberando 
memória, à medida que um elemento é removido, tornado o uso mais eficiente.
Para sua reflexão
Para o desenvolvimento de programas de 
computadores é muito commum que o 
programador não conheça o número de dados 
que serão manipulados pelo sistema, sendo uma 
informação dinâmica e muito variável.Por isso a 
importância em conhecer as estruturas de dados.
Vamos refletir sobre, por exemplo, um sistema que precisa gerar um relatório 
de produtos comercializados num determinado período. Os dados da 
pesquisa precisam ser armazenados em uma estrutura de dados para depois 
serem apresentados ao usuário. Porém, não se sabe previamente a quantidade 
de elementos que serão armazenados, o tamanho da estrutura para esse 
armazenamento, e que se pode variar de período para período. Uma solução 
www.esab.edu.br 14
seria criar uma estrutura de dados com um tamanho absurdamente grande 
que garantiria o armazenamento dos dados, mas haveria um desperdício de 
memória do computador caso a quantidade de elementos do relatório fosse 
muito baixa. Dessa forma, a melhorsolução é a criação de uma tabela com a 
quantidade exata de elementos que a pesquisa retornou, mas isto só poderá 
ocorrer em tempo de execução do programa, pois somente no momento em 
que a rotina que realiza a pesquisa dos produtos é executada é que se terá a 
quantidade de elementos da tabela.
Em alguns casos as estruturas de dados são utilizadas para solução de problemas 
bem específicos como a implementação de filas de atendimento em bancos, 
nas quais cada cliente é identificado por uma senha, e que devem garantir que 
o indivíduo que chegou mais cedo tenha prioridades nos atendimentos. Ou 
para elaboração de um programa de computadores que possa calcular e mostrar 
o menor caminho entre dois pontos de uma cidade, a fim de diminuir o custo 
de combustível e o tempo para realizar o deslocamento.
A escolha da estrutura de dados mais adequada deve analisar algumas 
características do problema a ser solucionado. Conforme Guimarães 
(1994), essas características são:
• as propriedades relevantes do objeto real que queremos representar;
• as operações a serem efetuadas sobre elas;
• os resultados de acordo com os fenômenos do mundo real.
Em resumo, as estruturas de dados devem ser definidas de forma a 
atender as operações que serão realizadas e das características (abstração) 
do mundo real que ela deverá representar. 
Nesta unidade você pôde conhecer o conceito de estrutura de dados e 
sua relação com a abstração de dados, passando pela contextualização 
de tipos abstratos de dados. Vimos também a diferenciação entre dados 
e informações. Além desses tópicos iniciais, foi discutida a forte relação 
entre algoritmos e estrutura de dados. Por fim, foram apresentadas 
algumas aplicações para a estrutura de dados na elaboração de métodos 
de pesquisa, ordenação e construção de estruturas específicas.
Na próxima unidade serão apresentadas aplicações da estrutura de 
dados, começando pela construção de funções, suas propriedades e 
características de funcionamento.
www.esab.edu.br 15
2 Funções – parte I
Objetivo
Apresentar a definição de funções, funcionamento da pilha de 
execução e visibilidade de variáveis.
Na unidade anterior você pôde se familiarizar com o conceito de 
estrutura de dados e abstração de dados e as vantagens e benefícios da 
sua aplicação. Nesta unidade será apresentada a técnica de refinamentos 
sucessivos na forma de módulos ou funções, destacando seu papel na 
redução da complexidade dos algoritmos e a consequente facilidade 
da manutenção e validação. Para tanto, serão abordados temas como a 
decomposição de problemas, a construção e parametrização de módulos 
e a aplicação da estrutura de dados responsável pelo gerenciamento da 
execução dos módulos em um programa de computador. 
Esta unidade está fundamentada nos trabalhos de Guimarães (1994) e 
Forbellone et al. (2005).
A resolução de um problema na forma de algoritmos com uso das 
estruturas de dados é uma tarefa complexa, que exige a análise do 
problema, das possíveis soluções e dos requisitos que precisam ser 
atendidos, a fim de garantir a plenitude da solução. Diante disso, uma 
técnica muito eficiente para estruturação de um algoritmo é dividir o 
problema complexo em problemas menores (FORBELLONE et al., 
2005). Essa estratégia possibilita uma visão mais específica de cada rotina 
a ser construída e validada. Já Guimarães (1994, p. 155), sobre o mesmo 
tema, afirma que “[...] a metodologia de refinamentos sucessivos parte 
do princípio de que resolver um problema complexo é mais fácil se não 
precisarmos considerar todos os aspectos do problema simultaneamente”. 
Portanto, a decomposição de um problema, a partir de um refinamento 
sucessivo, em problemas menores e mais simples, resulta na redução da 
sua complexidade. Essa ideia vem ao encontro de Forbellone et al. (2005, 
p. 127) quando nos diz que 
www.esab.edu.br 16
[...] a decomposição de um problema é fator determinante para a redução da 
complexidade. [...] quando decompomos um problema em subproblemas, 
estamos invariavelmente dividindo também a complexidade e, por consequência, 
simplificando a resolução. 
Na prática, a decomposição ou modularização se dá na codificação e 
no uso de funções. Forbellone et al. (2005, p.128) citam a relação de 
modularização e algoritmos com o seguinte discurso: “[...] depois de 
decompor um problema complexo em subproblemas, podemos construir 
subalgoritmos ou módulo para cada subproblema”. Esses subalgoritmos 
são conhecidos como funções ou métodos.
2.1 Definição
As funções são subprogramas que decompõem as grandes tarefas em 
subtarefas. Um programa de computador geralmente consiste de várias 
funções. A criação de funções visa à redução do código e à consequente 
simplificação dos processos de validação e testes, uma vez que rotinas que 
se repetem no código devem ser transformadas em funções que, então, 
serão chamadas diversas vezes. 
As funções uniformizam “[...] determinado conjunto de ações afins, que 
obedecem à mesma estruturação de um algoritmo, com o objetivo de 
representar um bloco lógico em especial” (FORBELLONE et al., 2005, 
p. 130-131). 
As funções são executadas quando chamadas no programa ou em outras 
funções, resultando em um desvio na execução do programa. Para que esse 
procedimento seja executado de forma organizada, é necessária uma estrutura 
de dados que gerencie as chamadas e encerramentos de cada função em 
execução. Essa estrutura de dados é conhecida como pilha de execução.
www.esab.edu.br 17
2.2 Pilha de execução
Como estudado na seção anterior, a modularização transforma um problema 
em um conjunto de soluções, então, o próximo passo é compreender como 
esses módulos são interligados, manipulados e executados.
A execução ou ativação de um módulo ocorre quando em algum ponto 
do algoritmo há uma chamada para a função, pelo nome definido na 
declaração da função. A execução do módulo se dá por um desvio no fluxo 
de execução do algoritmo para a função chamada, retornando somente 
após a execução de todas as instruções da função, sempre para a próxima 
linha após a chamada. A Figura 2 representa um algoritmo fazendo a 
chamada para duas funções hipotéticas, Função A e Função B, observe:
Linhas
1
2
3
4
5
6
7
 
A
B
Algoritmo
Linhas
1
2
3
4
5
Função B
Linhas
1
2
3
Função A
Figura 2 – Ativação de Funções.
Fonte: Elaborada pelo autor (2013).
O algoritmo principal possui 7 linhas com comandos quaisquer, e sua 
execução começa na linha 1 e se encerra na linha 7. Durante a execução, 
como na linha 2, há uma chamada para a função “Função A”, por meio da 
instrução “A”, que é o nome da função, haverá um desvio para a primeira 
linha dessa função, que será executada da linha 1 até a linha 3, que encerra 
a função. Após o encerramento da função, o fluxo retorna para a próxima 
linha após a chamada, linha 3 do algoritmo principal, e segue a execução 
normalmente. Como na linha 6 do algoritmo há uma chamada para a 
www.esab.edu.br 18
“Função B”, novamente haverá um desvio, executando todas as instruções 
da linha 1 a 5 da função B, e retornando para o algoritmo na linha 7, 
dando sequência na execução até o seu encerramento.
Todo esse processo é possível devido a uma estrutura de dados que 
gerencia todos os desvios entre o algoritmo e as funções, chamada de 
pilha de execução.
A cada execução de um método ou função, a sua chamada é inserida 
no topo de uma estrutura de dados chamada de pilha, que possui duas 
operações, a inserção no topo e a remoção do topo, de forma que o 
último elemento inserido será o primeiro a ser removido. A Figura 3 
representa a pilha de execução para o exemplo anterior em que um 
algoritmo chama as funções A e B, observe:
Antes da
execução
1
Algo
Algoritmo
inserido
no topo 
da linha.
Algoritmo
em execução
2
Algo
Execuçãoretorna
para o
algoritmo.
5
Algo
Execução
retorna
para o
algoritmo.
8
Fim da
execução do
algoritmo.
9
Algo
A
Função A
em execução.
Método
inserido
na pilha.
3
Variáveis e
parâmetros
Algo
Função A
terminou.
Método
removido
da pilha.
4
A
Função B é 
chamada e
entra em
execução.
Algo
B
Método B
inserido
no topo
da pilha.
6
Algo
Função B
terminou.
Método é
removido
da pilha.
7
B
Figura 3 – Pilha de execução.
Fonte: Elaborada pelo autor (2013).
www.esab.edu.br 19
Observe que no passo 1 a pilha estava vazia, não havia função em 
execução. No passo 2 o algoritmo entrou em execução, sendo inserido na 
pilha de execução. Assim que a “função A” foi chamada no algoritmo, ela 
foi inserida no topo da pilha (passo 3) de execuções, mantendo-se ali até 
que a função se encerre. No passo 4 a “Função A” foi encerrada, sendo 
retirada da pilha e devolvendo a execução para o algoritmo (passo 5). 
No momento em que a “Função B” é chamada e entra em execução, esta 
é inserida no topo da pilha (passo 6), mantendo-se até que sua execução 
se encerre. No encerramento da “Função B”, ela é retirada da pilha 
(passo 7), devolvendo a execução para o algoritmo (passo 8) até que ele 
termine sua execução e seja retirado da pilha (passo 9).
Durante a execução das funções, as variáveis declaradas e utilizadas 
nelas passam a ser criadas à medida que a função entra em execução e 
destruídas quando a função se encerra. O acesso às variáveis a partir do 
seu local de declaração é chamado de Visibilidade de Variáveis.
2.3 Visibilidade de variáveis
Observando a pilha de execução pode-se notar que apenas uma função é 
executada por vez, sendo que a função anterior só retorna à sua execução 
quando a função que está no topo da pilha é encerrada (apenas a função 
do topo está em execução naquele instante), e consequentemente, 
retirada da pilha. Portanto, a cada execução a função é inserida no 
topo da pilha. Se já existe alguma função em execução, esta não será 
mais executada até que a função que está no topo da pilha se encerre, 
retornando o processamento para a função que estava logo abaixo, e 
assim sucessivamente para todas as funções empilhadas, inclusive o 
algoritmo que chamou as funções.
Nesse contexto, quando são declaradas variáveis dentro dessas funções, chamadas de 
variáveis locais (FORBELLONE et al., 2005), elas passam a existir somente no momento 
em que a função é executada. 
www.esab.edu.br 20
Por isso essas variáveis não podem ser acessadas por outras funções, uma 
vez que a execução das outras funções só terá sequência quando a função 
no topo da pilha se encerrar. No momento em que isso ocorre, as variáveis 
locais também saem da pilha, assim como a função, e deixam de existir.
Quando uma função ou procedimento é chamado, as variáveis locais e 
parâmetros são copiados para a pilha com a função. Quando a função 
termina, as variáveis e parâmetros são desalocados da memória, no 
mesmo momento em que a função se encerra. Por essa razão, as variáveis 
locais fora das funções não podem ser acessadas por outras funções ou 
pelo programa principal (algoritmo). 
Guimarães (1994, p. 133) destaca: “[...] uma variável declarada dentro 
de um bloco só é conhecida dentro deste bloco”. Para que os dados 
armazenados no algoritmo possam ser acessados por qualquer método 
ou função, esta deve ser declarada no algoritmo, por isso chamada de 
variáveis globais (FORBELLONE et al., 2005). 
No caso da linguagem de programação C, as variáveis globais são 
declaradas fora das funções, inclusive da função main() que é obrigatória 
e responsável pela execução do programa, é a primeira função executada 
por um programa em C. Caso uma variável seja declarada na função 
main() ela não estará acessível as outras funções.
A Figura 4 apresenta um programa escrito em C com duas variáveis, observe:
www.esab.edu.br 21
Figura 4 – Declaração de variáveis em C.
Fonte: Elaborada pelo autor (2013).
A variável sexo foi declarada fora das funções teste() e main(). Sendo assim, 
se trata de uma variável global, acessível às duas funções. Já a variável idade 
foi declarada dentro da função main(), dessa forma sendo visível apenas a 
essa função. Na função teste(), na linha 9, foi indicado um erro (quadrado 
em vermelho), indicando que a variável idade não existe. Todas as 
instruções, da linha 1 a linha 18 correspondem ao algoritmo em C, assim 
temos nesse algoritmo as bibliotecas stdio e stdlib, a variável global sexo, as 
funções teste() e main(), que possui a variável local idade.
O escopo de abrangência de uma variável é chamado de visibilidade da 
variável. Forbellone et al. (2005, p. 136) destaca que 
[...] em alguns casos, uma determinada variável é utilizada apenas por um módulo 
específico, o que não justifica uma definição global, pois somente se fazem necessários o 
conhecimento e a utilização dessa variável dentro dos limites deste bloco lógico.
As variáveis locais devem ser utilizadas para a definição de dados que 
serão manipulados somente naquele método, garantindo que o espaço 
de memória seja alocado dinamicamente, pois ocorre durante a execução 
da função, e após a sua execução seja liberado, otimizando o uso de 
www.esab.edu.br 22
memória principal para criação e armazenamento de variáveis. Por outro 
lado, caso os dados devam ser acessados pelas funções desenvolvidas 
pelo programador e pelo método main(), que é o método principal e 
obrigatório em todo programa desenvolvido em C, as variáveis devem ser 
declaradas fora das funções, tornando-se assim globais e visíveis a todas as 
estruturas de dados do algoritmo. Porém, mesmo que não sejam utilizadas, 
ocupam espaço de memória enquanto o programa estiver em execução.
Estudo complementar
Para saber mais sobre os conceitos e exemplos de 
funções em C, acesse aqui. 
Nesta unidade estudamos sobre a modularização de algoritmos com o uso 
de funções e como se dá o funcionamento e gerenciamento dos blocos 
de instruções quando chamados pelo algoritmo, por meio da pilha de 
execução que interfere diretamente na visibilidade e escopo das variáveis.
Na próxima unidade daremos sequência ao estudo das funções com foco 
na recursividade e endereçamento de variáveis.
www.esab.edu.br 23
3 Funções – parte II
Objetivo
Apresentar a definição de ponteiros e conhecer a técnica de 
recursividade e como utilizar variáveis estáticas dentro das funções.
Caro aluno, na unidade anterior você pôde estudar sobre a pilha de 
execução das funções e a sua relação com a visibilidade das variáveis. 
Nesta unidade serão apresentados os conceitos de endereçamento de 
memória na forma de ponteiros, o uso da recursividade, que consiste em 
uma função que faz uma chamada para ela mesma e o uso de variáveis 
estáticas, que utilizam um único endereçamento no seu armazenamento 
na memória principal. Para abordar esses assuntos, foram utilizadas as 
referências de Guimarães (1994) e Forbellone et al. (2005).
Nos estudos anteriores você conheceu o conceito e forma de 
funcionamento da pilha de execução que armazena as chamadas das 
funções e suas variáveis. Esse armazenamento se dá na memória principal 
do computador, em endereços específicos, conhecidos como ponteiros.
3.1 Ponteiro de variáveis
Pode-se entender a variável como uma caixa que armazenará algum 
conteúdo definido pelo programador, no momento de sua inicialização 
ou em uma atribuição. A variável possui quatro importantes 
propriedades: o nome, também conhecido como identificador; o tipo 
de dados; o valor armazenado; e a sua localização na memória principal, 
chamado de endereçamento. Para Guimarães (1994, p. 20), “[...] 
podemos imaginar uma variável como o nome de um local onde se 
pode colocar qualquer valor do conjunto de valores possíveis do tipo 
básico associado”.O nome da variável é utilizado pelo programador 
para identificar no algoritmo a variável que será manipulada, por isso 
chamada de identificador. O valor da variável pode ser alterado durante 
a execução do programa, sempre respeitando a definição do tipo de 
www.esab.edu.br 24
dados que podem ser: números (inteiros e reais), caracteres (símbolo ou 
conjunto de símbolos) e lógicos (verdadeiro ou falso). A criação de uma 
variável se dá pela instrução de declaração da variável, que na linguagem 
de programa C/C++ possui a semântica apresentada na Figura 5, observe:
Tipo de Dado Identi�cador ;
;
Figura 5 – Declaração de Variável em C/C++.
Fonte: Elaborada pelo autor (2013).
Observe que a variável em C pode ter apenas um tipo de dados, e mais 
de uma variável podem ser declaradas para o mesmo tipo, desde que os 
nomes (identificadores) sejam separados por vírgula. São exemplos de 
declaração de variáveis em C. 
• int idade;
• float peso, altura, media;
• char nome[30], cidade[30];
A declaração tem como finalidade criar as variáveis que serão utilizadas 
no programa de computador, mas na prática o resultado é a alocação de 
espaço na memória principal, na área chamada de Heap. Cada variável 
declarada será alocada em um bloco de memória com endereço único. 
Mesmo que a variável não seja utilizada, esse espaço não será liberado até 
que o programa se encerre. O código a seguir apresenta a declaração de 
variáveis em C/C++, observe:
Algoritmo 1 – Exemplo de declaração de variáveis em C
01 int idade;
02 float media;
03 char sexo;
Fonte: Elaborado pelo autor (2013).
www.esab.edu.br 25
No algoritmo declaram-se três variáveis: idade como inteiro, na linha 
1, media como float, na linha 2, e sexo como char na linha 3. Antes da 
execução do programa, essas instruções solicitam ao sistema operacional 
um espaço de memória para cada variável. Essa ação é chamada de 
alocação de memória e resulta na criação física da variável e da associação 
a um endereço. A Figura 6 representa a alocação das variáveis do 
algoritmo 1 na memória principal, veja:
Emq1
idade
Memória
Heap
Memória Principal
Emq3
sexo
Emq2
media
endereço valor
identi�cador
Figura 6 – Alocação de variáveis do algoritmo 1.
Fonte: Elaborada pelo autor (2013).
Observe que na memória Heap, um espaço da memória principal, foram 
alocados espaços para cada variável. Além de alocar o espaço, associa-
se um endereço à variável, representado pelo termo Emq (endereço 
de memória qualquer), sendo que cada variável possui o seu endereço 
exclusivo, ou seja, duas variáveis não podem utilizar o mesmo endereço. 
Note que cada variável é representada pelo seu nome, um valor e um 
endereçamento de memória. Assim, na Figura 6, Emq1, Emq2 e Emq3 
são os endereços de memória de cada variável.
Na Figura 7 está representada uma atribuição à variável idade, observe. 
www.esab.edu.br 26
Emq1
idade
Memória
Heap
Memória Principal
Emq3
sexo
Emq2
media
idade = 43;
Emq1 43
43
Figura 7 – Atribuição de valor à variável.
Fonte: Elaborada pelo autor (2013).
Note que foi realizada uma atribuição utilizando o identificador da 
variável “idade”, usando a sintaxe: idade = 43; Para a linguagem de 
programação a variável idade corresponde ao ponteiro Emq1, que é o 
seu endereço na memória Heap, e para que a atribuição ocorra há um 
desvio para esse endereço, localizando a variável na memória e gravando 
o valor 43 nesse endereço. Caso o identificador referenciado não exista 
na memória Heap, a linguagem de programação indicará um erro de 
compilação informando que o identificador não foi declarado.
Observe que de acordo com o que foi estudado até aqui, toda variável 
possui um identificador, um valor, um endereço de memória e um tipo 
de dado. Mas há um tipo diferenciado de variável que é chamado de 
ponteiro cuja finalidade é armazenar o endereço de uma variável na 
memória do computador. A Figura 8 representa uma variável do tipo 
ponteiro, observe:
endXYZ
idade
Endereço:endXYZ
nome
Figura 8 – Variável do tipo ponteiro.
Fonte: Elaborada pelo autor (2013).
www.esab.edu.br 27
A variável nome possui um endereço hipotético endXYZ, que por sua 
vez está sendo atribuído à variável ponteiro que o armazenará. Caso 
seja executada a instrução para imprimir o valor da variável ponteiro, 
o resultado será a impressão do endereço armazenado, porém, caso seja 
solicitada a impressão do valor nesse endereço, o resultado impresso será 
o mesmo valor que está armazenado na variável nome.
Para Cerqueira, Celes e Rangel (2004, p. 46), “[...] os ponteiros servem 
para armazenamento e manipulação de valores de endereços de memória”. 
Assim como a Heap gerencia a criação de cada variável declarada no programa, 
as chamadas das funções também são monitoradas por essa estrutura, 
armazenando o endereço de cada função chamada, das variáveis locais e 
globais. Mas há um tipo específico de chamada de funções na qual uma função 
faz uma chamada a ela mesma no código, e a Heap precisa gerenciar cada 
endereço dessas chamadas, garantindo a execução correta do programa.
3.2 Recursividade
A recursividade consiste em uma função fazer a chamada dela mesma 
em seu código, e a sua finalidade é tornar algoritmos mais complexos em 
rotinas mais simples e com menos linhas de codificação. Para Guimarães 
(1994, p. 141): “[...] existem casos em que um procedimento ou função 
chama a si próprio. Diz-se então que o procedimento ou função é 
recursivo”. O código do Algoritmo 2 apresenta uma função recursiva de 
pesquisa de um determinado valor inteiro em um vetor. 
Algoritmo 2 – Pesquisa recursiva
01 int pesquisar(int chave, int posicao,int 
tamanho){
02 if(posicao == tamanho) return 0; //não existe
03 else{
04 if(dados[posicao] == chave) return 1;//achou
05 else{
06 posicao++;
07 return pesquisar(chave,posicao,tamanho);
08 }
09 }
}
Fonte: Elaborado pelo autor (2013).
www.esab.edu.br 28
As regras de funcionamento do processo recursivo são: se a posição 
visitada do vetor for igual ao tamanho do vetor, instrução da linha 2, 
então todas as posições já foram visitadas e o valor não existe no vetor, 
não há mais posições a serem pesquisadas e o método retornará um 0 
(falso). Na regra da linha 4, compara-se o vetor na posição de pesquisa 
com a chave, que é o valor procurado, e se for igual a função retornará 
o valor 1 (verdadeiro), indicando que o valor existe. Caso o vetor não 
tenha todas as posições visitadas e o valor não tenha sido achado, na 
linha 7 a função é chamada recursivamente recebendo como parâmetro 
o valor a ser pesquisado (chave), a nova posição de pesquisa, pois esta foi 
incrementada na linha 6, e o tamanho do vetor.
O código a seguir implementa a pesquisa no vetor com valores 
predefinidos. 
Algoritmo 3 – Pesquisa recursiva no vetor
01 #include <stdio.h>
02 #include <stdlib.h>
03 int dados[] = {1,3,15,70,19,101,2,20,23,4,127,88};
04 int pesquisar(int chave, int posicao,int tamanho){
05 if(posicao == tamanho) return 0; //não existe
06 else{
07 if(dados[posicao] == chave) return 1;//achou
08 else{
09 posicao++;
10 return pesquisar(chave,posicao,tamanho);
11 }
12 }
13 }
14 int main (void){
15 int valor,resultado;
16 puts("Informe um Valor para Pesquisa:");
17 scanf("%d",&valor);
18 resultado = pesquisar(valor,0,12);
19 if(resultado == 1) puts("Valor existe no vetor");
20 else puts("Valor não existe no vetor");
21 system("pause");
22 return 0;
23 }
Fonte: Elaborado pelo autor (2013).
www.esab.edu.br 29
O algoritmo solicita ao usuário um valor a ser pesquisado. Como o vetor 
possui 12 elementos, na linha 18 é chamada a função pesquisar com os 
parâmetros valor (valor a ser localizado no vetor), 0 (primeira posição de 
pesquisa) e 12 (tamanho do vetor). A cada interação da função, caso o 
valor não sejalocalizado e o vetor não tenha sido todo visitado, a função 
pesquisar é reexecutada com o mesmo valor de pesquisa, o mesmo 
tamanho de vetor, porém com a próxima posição de pesquisa.
O Quadro 1 apresenta a sequência de pesquisa do valor 70 no vetor:
Número de 
Chamadas 
do Método
Valor Posição Tamanho
Valor do 
vetor Dados 
[posição]
Linhas Executadas 
do Método
Primeira - 1 70 0 12 1 6, 7, 8, 9, 10, 11,12
2 70 1 12 3 6, 7, 8, 9, 10, 11,12
3 70 2 12 15 6, 7, 8, 9, 10, 11,12
4 70 3 12 70 6, 7, 8,9 retorna 1
Quadro 1 – Simulação da Função Pesquisar. 
Fonte: Elaborado pelo autor (2013).
Observe que as três primeiras chamadas executam do início da função até 
a linha 10 quando a função é reexecutada com o mesmo valor de pesquisa, 
mesmo tamanho e a próxima posição do vetor que foi incrementada na 
linha 9. Na quarta execução da função, na linha 7, o valor do vetor será 
igual ao valor pesquisado e, portanto, a função executará o comando 
return 1, e se encerrará, já que o comando return termina a execução de 
uma função. A Figura 9 apresenta a sequência de execução de cada uma 
das chamadas função pesquisar buscando o valor 70.
4 3 2 1
Figura 9 – Sequência de execução do método pesquisar buscando o valor 70.
Fonte: Elaborada pelo autor (2013).
www.esab.edu.br 30
Observe que a chamada número 1 da função fará uma nova chamada 
para a mesma função, assim como a chamada número 2, chamada 
número 3 e chamada número 4. Todas as chamadas recursivas serão 
executadas no comando return pesquisar (chave, posição, tamanho).
Cada chamada é inserida na pilha de execução e fica aguardando para 
retornar à execução normal quando a chamada acima encerrar. Dessa 
forma, a chamada 1 aguarda a chamada 2, que por sua vez aguarda a 
chamada 3, que aguarda a chamada 4. Como a chamada 4 retornará 1, 
pois a condição if(vetor[posicao] == chave) será verdadeira, essa chamada 
será encerrada, dando a vez da execução da chamada 3, que parou na 
instrução return pesquisar (). Assim, a chamada 3 retornará o valor 1 
devolvido pela chamada 4, e será encerrada, transferindo a execução para 
chamada 2, que também aguarda o return pesquisar(). Devolverá então o 
valor 1 retornado pela chamada 3 e portanto se encerrará, passando a vez 
para chamada 1 que está aguardando no return pesquisar(), que retornará 
1 da chamada 2 e se encerrará.
Saiba mais
Para se aprofundar no conhecimento de métodos 
recursivos, você pode acessar um conjunto de 
endereços com blogs que tratam do assunto 
clicando aqui.
Bem, até agora estudamos as funções, as chamadas recursivas e a 
visibilidade das variáveis. Em princípio as variáveis locais têm seus dados 
perdidos com o encerramento da função na qual foram declaradas. 
Digo em princípio, pois é possível implementar variáveis locais que não 
perdem os dados após a execução das funções. Essa técnica é chamada de 
variáveis estáticas.
www.esab.edu.br 31
3.3 Variáveis estáticas
O uso das variáveis estáticas está associado ao contexto de visibilidade 
das variáveis, que podem ser locais e globais. Como estudado na unidade 
anterior na seção de visibilidade das variáveis, as variáveis locais só podem 
ser acessadas durante a execução do método, sendo visível somente nesse 
método e que no seu encerramento todas as variáveis são desalocadas e 
os dados são perdidos. Já as variáveis globais podem ser acessadas por 
qualquer método do programa e é destruída somente ao final da sua 
execução. O papel das variáveis estáticas declaradas nas funções é garantir 
que o valor da variável seja mantido mesmo após o encerramento da 
execução do método.
O código a seguir apresenta o método chamado contar que declara e 
usa a variável contador de forma estática. O método main() faz duas 
chamadas a esse método, observe:
Algoritmo 4 – Função com variável estática
01 #include <stdio.h>
02 #include <stdlib.h>
03 void contar(){
04 static int contador =0; //declara uma variável 
como estática
05 contador++; //incrementa a variável contador em 1
06 printf("Contador vale:%d",contador); //imprime a 
variável na tela
07 }
08 int main()
09 {
10 system("cls");
11 printf("\nExecutando a Funcao Contar\n");
12 contar();
13 printf("\nExecutando a Funcao Contar\n");
14 contar();
15 system(“pause”);
16 return 0;
17 }
Fonte: Elaborado pelo autor (2013).
www.esab.edu.br 32
Note que a cláusula static, utilizada na linha 4, é que define uma variável 
como estática, e deve ser usada na sua declaração. Cada vez que o 
método contar() é executado, a variável contador é incrementada em 1 
e impressa na tela. No método main() a função contar é chamada duas 
vezes, a primeira chamada na linha 12 e outra na linha 14. Na chamada 
da linha 12, a variável contador começará em 0, será incrementada em 1, 
portanto, seu valor atual será 1. Mesmo após o encerramento do método, 
o valor da variável não será perdido, e na segunda chamada do método, 
na linha 14, a variável contador, por ser estática, iniciará de 1, não mais 
de 0, depois será incrementada em 1, mudando seu valor atual para 2 e 
posteriormente será impresso na tela.
A Figura 10 apresenta o resultado do programa após a sua execução:
Figura 10 – Resultado da execução do Algoritmo 4.
Fonte: Elaborada pelo autor (2013).
Observe que a variável contador não perdeu seus dados após a primeira 
execução, isso só é possível porque as variáveis estáticas são armazenadas 
na memória principal em blocos de memória diferentes do espaço 
utilizado pelas funções, e no encerramento da função todas as variáveis 
são desalocadas com o método. Mas as variáveis estáticas não, pois estão 
em outro endereçamento de memória.
A Figura 11 apresenta a alocação de funções com variáveis locais e 
variáveis estáticas, veja:
www.esab.edu.br 33
variáveis
locais
Função / Método
variáveis
estáticas
Função / Método
Figura 11 – Alocação de variáveis locais e variáveis estáticas.
Fonte: Elaborada pelo autor (2013).
Note que a Figura 11 representa que as variáveis locais ficam no mesmo 
bloco de memória da função que as cria, por isso, quando uma função é 
encerrada, as variáveis são perdidas. Já as variáveis estáticas são alocadas 
em outro bloco de memória, por isso quando a função se encerra, a 
variável se mantém alocada.
Nesta unidade foi apresentado o conceito de ponteiros, que é o endereço 
da variável na memória principal, na área chamada de Heap. Esse 
endereçamento é resultado da instrução de declaração da variável. Duas 
variáveis não podem ter o mesmo endereço, pois se trata da forma pela 
qual a linguagem identifica a variável que está sendo manipulada no 
programa. Vimos também que a recursividade consiste na técnica de 
criar funções que chamam a si própria. Por fim, você pôde estudar o uso 
de variáveis estáticas declaradas em funções e como possibilitam o acesso 
aos seus dados mesmo após o encerramento da função.
Na próxima unidade estudaremos as variáveis compostas homogêneas, 
conhecidas como vetores.
www.esab.edu.br 34
4 Variáveis compostas homogêneas: vetores
Objetivo
Apresentar o conceito, a aplicação e a manipulação de vetores.
Nesta unidade será apresentada a estrutura de dados vetor com ênfase no 
seu funcionamento e armazenamento na memória principal. Para isso, 
vamos utilizar as principais ideias dos trabalhos de Cerqueira, Celes e 
Rangel Netto (2004).
Na unidade anterior você pôde estudar a declaração de variáveis e pôde 
verificar que a variável é formada por um nome ou identificador, valor, 
endereço de memória e o tipo de dados. Mas existem casos em que há 
a necessidade de um armazenamento de vários dados do mesmo tipo, 
porém, a declaração de inúmeras variáveis torna a solução do problema 
mais complexa do que realmente é. Por exemplo, uma empresa necessita 
cadastrar a média de vendas de um determinado produto nos doze 
mesesdo ano. Uma solução seria criar 12 variáveis do tipo real para 
armazenamento dessas médias e posterior processamento no algoritmo. 
Note que a solução é bem simples, entretanto, utilizar 12 variáveis torna o 
processo mais complexo, pois gerenciar 12 variáveis de forma correta não 
é tarefa fácil, o que pode gerar inconsistências na solução do problema. 
A estrutura de dados que pode ser utilizada para facilitar a solução do 
problema é o uso de vetores.
4.1 Conceito de vetores
O vetor permite criar uma variável dividida em inúmeras posições, todas do 
mesmo tipo de dados. Para Cerqueira, Celes e Rangel Netto (2004, p. 59), 
“[...] o vetor é a forma mais simples de estruturar um conjunto de dados”. 
www.esab.edu.br 35
Para contextualizar, vamos analisar o problema de armazenamento das 
médias de vendas de um determinado produto nos 12 meses do ano. Em 
vez de declarar 12 variáveis, é possível a criação de uma variável com 12 
posições. A declaração de vetor em C é realizada utilizando-se a seguinte 
sintaxe: tipo de dado identificador[n], em que n se refere à quantidade de 
posições do vetor, começando em 0 e terminando na posição n-1.
A instrução a seguir apresenta a declaração da variável “vendas”, como 
um vetor de reais com 12 posições, veja: float vendas[12]. A instrução 
criará a variável “vendas”, com um único endereço de memória, porém 
com 12 posições para serem manipuladas. Observe na Figura 12 a 
estrutura do vetor vendas:
vendas
0
Emq1
1 2 3 4 5 6 7 8 9 10 11
Figura 12 – Vetor de Vendas.
Fonte: Elaborada pelo autor (2013).
Note que o vetor “vendas” possui um único endereço de memória, 
representado pela expressão (Emq1 – endereço de memória qualquer), 
e um conjunto de 12 posições para armazenamento e manipulação dos 
dados, começando na posição 0 e terminando na posição 11. Como o 
tipo de dados float ocupa 4 bytes, e o vetor possui 12 posições, serão 
alocados na memória 48 bytes contíguos para esse vetor, conforme 
representado na Figura 13 a seguir, observe:
vendas
Emq1
12 X 4 = 48 bytes
Figura 13 – Alocação de Memória para o vetor de vendas.
Fonte: Elaborada pelo autor (2013).
Analisando a Figura 13 pode-se notar que o bloco de memória não 
possui as posições ou a divisão. E isso é verdade: na memória será alocado 
um bloco único de 48 bytes, resultante do cálculo da quantidade de 
elementos do vetor multiplicado pelo espaço ocupado pelo tipo de dados 
www.esab.edu.br 36
do vetor. Porém no uso do vetor para armazenamento ou leitura dos 
dados, o programador deverá informar qual a posição a ser utilizada. Mas 
como isso é possível?
Como a variável possui um único endereço de memória, e o vetor armazena 
o tipo float (real), e cada real ocupa 4 bytes, para que seja possível gravar na 
posição indexada no vetor, basta multiplicar a posição por 4.
Por exemplo, para atribuir o valor 128.99 na posição 3 do vetor, a 
instrução em C é: vendas [3] = 128.99, mas na execução do programa, 
como será realizada essa operação pelo sistema operacional de forma que 
na posição 3 seja realmente armazenado o valor 128.99?
A Figura 14 representa o processo para se chegar à posição 3 do vetor:
vendas
0
Emq1
Ponto de partida
Endereço da variável
Deslocamento: quantidade de posições X 4 bytes
1 2 3
128.99
4 5 6 7 8 9 10 11
Posições deslocadas
ponteiro
Bloco de memória ocupado pelo tipo de dados
Figura 14 – Localizando a posição no vetor.
Fonte: Elaborada pelo autor (2013).
Como a variável possui um endereço de memória, esse ponto representa 
o início do bloco que foi alocado contiguamente, ou seja, cada bloco 
de 4 bytes do tipo float foi alocado um ao lado do outro. Para chegar à 
posição desejada é preciso calcular em quanto será o deslocamento na 
estrutura, cujo resultado é multiplicar o tamanho do bloco pelo número 
de posições. Nesse caso, a posição 3 resulta em um deslocamento de 12 
bytes a partir do endereço inicial do vetor. Esse deslocamento posicionará 
o ponteiro do vetor 12 bytes à frente do endereço de memória de todo 
o bloco. Como cada bloco possui 4 bytes, os próximos quatro bytes a 
partir do ponteiro se refere à posição indexada pela instrução vendas[3] = 
128.99. Nesse bloco será gravado o valor informado.
www.esab.edu.br 37
Saiba mais
Para aprofundar os estudos sobre os tipos de 
dados em C e o espaço ocupado por cada um deles, 
acesse o endereço clicando aqui. Agora que vimos 
que os vetores nos permitem criar uma variável 
dividida em inúmeras posições, veremos a seguir 
como os vetores são aplicados e manipulados.
4.2 Aplicação e manipulação
A aplicação de vetores está muito associada à necessidade de 
armazenamento de vários dados na forma de uma tabela. Para tanto, 
na sua declaração é necessário que seja explicitamente informada a 
quantidade de elementos dessa tabela, que é formada por uma única 
linha e “N” colunas.
Para inserir, alterar ou consultar um determinado valor do vetor 
é necessária a referência da posição do vetor que se deseja acessar, 
utilizando a seguinte sintaxe: identificador[p], em que “p” se refere à 
posição que varia de 0 ao tamanho do vetor -1. Caso a posição informada 
seja maior ou igual ao tamanho do vetor, ocorrerá um erro fatal que 
encerrará a execução do algoritmo, já que a posição não pertence ao 
bloco previamente alocado.
A Figura 15 representa o vetor de vendas com 12 posições e o resultado 
da instrução que intenciona gravar na posição 12 do vetor, observe:
vendas
12 X 4 = 48 bytes
0 1 2 3 4 5 6 7 8 9 10 11
12
Figura 15 – Manipulando a posição fora do vetor.
Fonte: Elaborada pelo autor (2013).
www.esab.edu.br 38
Note que a posição 12 do vetor é um bloco de memória que não lhe 
pertence, por isso quando acessada pelo programa de computador resultará 
em um erro fatal, grave, que resultará no encerramento da aplicação.
Para atribuição de um valor no vetor, a sintaxe é: identificador[p] = valor. 
Caso nessa posição já exista um valor, este será sobrescrito, uma vez que 
em cada posição do vetor somente um valor pode ser armazenado. Dessa 
forma essa instrução possibilita tanto a inserção de um valor no vetor 
quanto a sua alteração. Para consulta de um valor, basta referenciar o 
vetor e a posição de acesso por meio da sintaxe: identificador[p].
O algoritmo a seguir apresenta as instruções de inserção, alteração e 
consulta no vetor.
Algoritmo 5 – Manipulação de vetores
01 #include <stdio.h>
02 #include <stdlib.h>
03 float vendas[12];
04 int main(){
05 puts("Informe a media de vendas do Primeiro Mes:");
06 scanf("%f",&vendas[0]); //inserção de dados
07 printf(" A venda do primeiro mes 
foi:%.2f",vendas[0]);//consulta
08 puts("\nInforme NOVAMENTE a media de vendas do 
Primeiro Mes:");
09 scanf("%f",&vendas[0]); //alteração de dados
10 printf(" A venda do primeiro mes 
foi:%.2f",vendas[0]);//consulta
11 system(“pause”);
12 return 0;
13 }
Fonte: Elaborado pelo autor (2013).
Observe no algoritmo que na linha 4 será gravado um valor informado 
pelo usuário na primeira posição do vetor. Na linha 5 será mostrado o valor 
informado na entrada de dados da instrução da linha 4. Na linha 7 será 
cadastrado um novo valor na primeira posição do vetor, alterando o antigo 
valor para esse novo valor que será informado pelo usuário do sistema. Na 
linha 8 será mostrado o valor atual da primeira posição do vetor.
www.esab.edu.br 39
Uma característica importante do vetor é que uma vez definida a sua 
dimensão (quantidade de elementos) na declaração do vetor, durante 
a execução do programa o bloco de memória alocado não poderá ser 
gerenciado, independentemente da inserção ou não de itens no vetor. 
Cerqueira, Celes e Rangel Netto (2004) destacam o uso da alocação 
dinâmica para os casos em que a dimensão do vetor é desconhecida. 
Quando sabemos a dimensão, é preferível ouso de vetores.
Mesmo que dados não sejam armazenados no vetor, o espaço é pré-
alocado a fim de garantir que o bloco de memória esteja disponível 
durante a execução do programa, sendo liberado após o seu 
encerramento. Tal contexto pode representar um grande problema no 
uso dessa estrutura de dados, uma vez que havendo necessidade de 
mais ou menos posições, não há como modificá-lo, pois se trata de uma 
alocação estática, aquela que ocorre antes da execução do programa.
No caso do vetor de vendas, por exemplo, caso o usuário deseje cadastrar 
as vendas de um período superior a 12 meses, não será possível, pois o 
vetor durante a execução do programa permitirá somente 12 posições de 
armazenamento. Caso o usuário do sistema cadastre apenas as vendas dos 
seis primeiros meses, o vetor ocupará o espaço referente às 12 posições, 
independentemente de quantas já foram cadastradas, sendo que as 
demais posições serão preenchidas com zero. 
Dessa forma, o uso de vetores deve estar associado a casos em que se 
conhece exatamente quantos dados serão cadastrados, sem a possibilidade 
de variações nesse número de informações a serem gerenciadas.
Nesta unidade estudamos sobre a estrutura de dados vetor que possui 
como principal característica o uso de índices ou posições para 
referenciar o local de inserção ou busca dos dados. Por se tratar de uma 
estrutura de dados de alocação estática, que não permite a otimização e 
gerenciamento da sua dimensão, é recomendado para os casos em que 
o número de dados a serem gerenciados é conhecido e não se modifica 
durante a execução do programa.
Na próxima unidade você estudará o conceito de alocação dinâmica, uma 
técnica que possibilita a criação de estruturas de dados com tamanhos 
alterados durante a execução do programa.
www.esab.edu.br 40
5 Alocação dinâmica de memória
Objetivo
Apresentar o conceito de alocação dinâmica de memória.
Vimos na unidade anterior o conceito de vetores, também como 
são aplicados e manipulados. Já nas unidades anteriores, em especial 
a unidade 3 estudamos sobre a definição de ponteiros, o uso da 
recursividade e variáveis estáticas. Nesta unidade, vamos apresentar a 
alocação dinâmica de memória, por meio do aporte teórico de Cerqueira, 
Celes e Rangel Netto (2004) que se fundamenta nos conceitos de 
vetores, recursividade e variáveis estáticas.
Conforme estudamos na unidade 3, as variáveis são formadas por 
um nome, um tipo de dado, os valores que são armazenados e um 
endereço de memória. O ciclo de vida de uma variável começa no 
momento em que é declarada. Sem a sua declaração uma variável não 
pode ser reconhecida pelo compilador em uso e, consequentemente, 
não pode ser alocada na memória principal. Entretanto, a instrução 
de declaração da variável não representa a sua criação. A alocação de 
memória para a variável pode ocorrer antes da execução do programa, 
quando o programa é carregado na memória do computador, na Heap, 
de forma que o espaço de memória para variável é alocado e não pode 
ser gerenciado. Mesmo que não seja atribuído valor algum à variável, esse 
espaço de memória se manterá reservado até que o programa se encerre. 
Esse processo de alocação de memória no carregamento do programa 
ocorre, por exemplo, na declaração das variáveis globais, aquelas visíveis a 
todas as funções implementadas no programa. Esse processo de alocação 
de memória no carregamento do programa é chamado de alocação 
estática. Cerqueira, Celes e Rangel Netto (2004, p. 12), destacam: 
“[...] a declaração de uma variável reserva um espaço na memória para 
armazenar um dado do tipo da variável e associa o nome da variável a 
esse espaço de memória”. 
www.esab.edu.br 41
O Quadro 2 a seguir apresenta as vantagens e desvantagens da alocação 
estática, observe:
Vantagens Desvantagens
O gerenciamento da memória é realizado 
exclusivamente pelo sistema operacional 
que é responsável por alocar e desalocar o 
espaço de memória solicitado.
O espaço de memória alocado não pode ser 
alterado durante a execução do programa. 
Caso a definição do espaço solicitado não 
atenda às necessidades do programa de 
computador, não há como gerenciá-lo de 
forma a corrigir o problema.
A definição de alocação de memória 
é simples, realizada pela instrução de 
declaração de variável.
Caso o espaço solicitado na declaração 
das variáveis seja maior que o espaço 
disponibilizado pelo sistema operacional, o 
programa de computador não será iniciado, 
indicando um problema de Overflow.
A sua implementação é simples e atende 
aos problemas triviais de armazenamento 
de dados que exigem pouco espaço de 
armazenamento, principalmente quando 
se conhece a quantidade de dados a serem 
armazenados e manipulados.
É inviável para solução de problemas 
em que não se conhece a quantidade de 
dados que serão armazenados ou o espaço 
a ser alocado é muito maior do que o 
disponibilizado pelo sistema operacional. 
Quadro 2 – Vantagens e desvantagens da alocação estática.
Fonte: Elaborado pelo autor (2013).
Note que um grande problema da alocação estática está na definição de 
quanto de espaço de memória será alocado e reservado para a execução 
do programa no que se refere às variáveis. Essa é uma realidade no 
desenvolvimento de softwares no dia a dia. Por exemplo, uma escola que 
possui um cadastro de alunos e deseja gerar um relatório com os que 
moram em determinado bairro: quantos alunos atendem a essa condição? 
Haverá necessidade de criação de uma estrutura de dados para armazenar 
e listar esses dados: como dimensioná-la?
Para resolver esse problema da alocação estática, em que o espaço de 
memória é alocado sem a possibilidade de gerenciamento por parte 
do programa, por exemplo, aumentando ou diminuindo esse espaço 
à medida que se faz necessário, com criação de novas posições num 
vetor, ou diminuição de posições do vetor com a remoção de dados não 
serão mais utilizadas é que a maioria das linguagens de programação 
disponibiliza a alocação dinâmica.
www.esab.edu.br 42
5.1 Definição
Na alocação dinâmica as variáveis são declaradas, porém, o espaço de 
memória será alocado durante a execução do programa por meio de 
instruções específicas por parte do programador, garantindo que ele possa 
alocar e liberar espaço de memória a qualquer momento. Isso possibilita 
ao programador a construção de estruturas de dados que tenham 
tamanhos variados, de acordo com a necessidade de momento, evitando-
se o desperdício de memória. 
Um exemplo clássico de desperdício de memória é quando declaramos 
variáveis globais no programa que não são utilizadas. Esse procedimento 
não gerará erro algum de compilação e o programa será executado sem 
restrições. Entretanto, todas as variáveis globais ocupam um espaço 
de memória no carregamento do programa, e mesmo que não sejam 
utilizadas, o espaço alocado não é liberado até que o programa se encerre. 
Por isso é muito importante uma revisão do programa verificando se 
variáveis globais foram declaras e não foram utilizadas.
Outra técnica muito comum é a criação de vetores com quantidade de 
elementos muito alta, pois não se conhece previamente essa quantidade 
em tempo de execução do programa. Por exemplo, para armazenar 
os nomes dos alunos de uma sala é criado um vetor com 60 posições, 
estimando-se que uma turma possa ter no máximo essa quantidade de 
alunos, entretanto, caso a turma tenha 20 alunos, as outras 40 posições 
foram previamente alocadas e não usadas, representando um desperdício 
de memória considerável. Se cada nome no vetor for definido com 35 
caracteres, estamos desperdiçando 1.400 bytes de memória (40 posições 
vezes 35 bytes de cada nome).
Para Cerqueira, Celes e Rangel Netto (2004, p. 64), “[...] a alocação 
dinâmica é um meio de requisitar espaços de memória em tempo de 
execução. [...] a principal vantagem daalocação dinâmica é fazer a 
alocação sem desperdício de memória”. 
www.esab.edu.br 43
O Quadro 3 apresenta as vantagens e desvantagens da alocação dinâmica, 
observe:
Vantagens Desvantagens
O espaço de memória é definido em tempo 
de execução sem desperdiço de memória, já 
que o espaço pode ser alocado e liberado em 
tempo de execução.
Pode ser aplicado em soluções triviais ou 
em problemas complexos que exigem um 
espaço de memória considerável.
É implementado a partir de ponteiros, 
que são variáveis que apontam para um 
endereço de memória.
Como se trata de um bloco de memória 
criado em tempo de execução, toda a 
responsabilidade em alocar e liberar o 
espaço de memória é do programador. 
Caso ele libere um espaço de memória em 
um momento inadequado, todos os dados 
serão perdidos. Cabe ao programador saber 
o momento de executar a instrução que 
aloca o espaço de memória, bem como o 
momento em que o espaço é liberado.
Quadro 3 – Vantagens e desvantagens da alocação dinâmica.
Fonte: Elaborado pelo autor (2013).
Note que no caso da alocação dinâmica, a principal vantagem é alocar 
e liberar espaço de memória a qualquer momento da execução do 
programa, porém, cabe ao programador saber o momento exato em que 
essas operações devem ser realizadas. Enquanto a alocação estática era 
gerenciada pelo sistema operacional e o programador “usava” as variáveis, 
na alocação dinâmica cabe ao programador declarar, alocar e liberar as 
variáveis, aumentando a complexidade dos algoritmos.
A alocação dinâmica é a base para implementação de estruturas de dados 
mais avançadas como Pilhas, Filas, Listas e Árvores, que são basicamente 
estruturas de armazenamento em que não se conhece previamente o 
número de elementos que serão manipulados.
Para sua reflexão
O espaço de memória alocado para um programa 
de computador ou funções é gerenciado pelo 
sistema operacional do computador, porém, não 
podemos imaginar que todo o espaço de memória do 
computador está disponível. Uma grande parte dessa 
memória é utilizada pelo próprio sistema operacional 
para execução e gerenciamento de suas tarefas.
www.esab.edu.br 44
5.2 Uso da memória
Basicamente o uso da memória pode ocorrer de forma estática ou 
dinâmica. A forma mais comum de definição do espaço de memória se 
dá pela declaração de variáveis globais, sendo uma alocação estática, e o 
espaço alocado se mantém o mesmo durante toda execução do programa. 
As variáveis globais são declaradas no programa e acessíveis a todos os 
demais blocos de programas, sejam eles funções ou procedimentos. Outra 
forma muito utilizada são as variáveis locais, declaradas dentro dos blocos 
de memória e visíveis somente a esses blocos. Nesse caso, as demais funções 
e procedimentos, bem como o próprio programa de computador, não 
têm acesso a essas variáveis já que são criadas durante a execução do bloco 
e liberadas após seu encerramento. Como essas variáveis são criadas em 
tempo de execução do método, são alocações dinâmicas.
Uma nova forma de alocação e uso de memória é definida pelo 
próprio programador por meio de instruções específicas que alocam ou 
liberam um espaço de memória, existente na maioria das linguagens de 
programação. Assim como as variáveis locais e globais usam do espaço 
de memória, todos os comandos, funções, procedimentos, ou seja, 
as estruturas de dados utilizadas no programa também ocupam um 
espaço da memória principal do computador. Quando um programa de 
computador é executado, um espaço de memória é alocado para o código 
do programa, para as variáveis globais e variáveis que serão alocadas 
dinamicamente. Caso o programa necessite de mais espaço do que há 
disponível pelo sistema operacional, o programa é encerrado.
A Figura 16 representa a distribuição de memória principal por parte do 
sistema operacional para que seja possível a execução do programa, observe:
www.esab.edu.br 45
Variáveis
alocadas
dinamicamente
Variáveis globais
Código do programa
Figura 16 – Uso da memória.
Fonte: Elaborada pelo autor (2013).
É possível notar na Figura 16 que o espaço de memória destinado às 
variáveis locais e código do programa é fixo, uma vez alocado, não é mais 
disponibilizado até que o programa se encerre. Já o espaço de memória 
para alocações dinâmicas é flexível, seu espaço pode aumentar ou diminuir 
em função das variáveis que são criadas ou destruídas durante a execução 
do programa. A estrutura de dados representada na Figura 16 representa 
uma pilha, as variáveis são inseridas e removidas pelo topo, de forma que o 
último elemento inserido é sempre o primeiro a ser removido.
A alocação da memória para armazenamento do código do programa e 
variáveis globais é estática, o tamanho não varia durante a execução do 
programa, já o espaço ocupado pelas variáveis globais é flexível. Depende 
das operações de alocação e liberação de memória que serão executadas 
durante o programa, na chamada de funções e procedimentos com 
variáveis locais e procedimentos ou nas instruções explícitas definidas 
pelo programador requisitando ou liberando espaços de memória.
Observe que as variáveis estáticas são alocadas antes da execução do programa 
durante a carga do programa na memória principal, por isso sua alocação 
é mais simples, em blocos de memória contíguos e únicos. Já as variáveis 
dinâmicas são alocadas em tempo de execução à medida que o programa 
requisita mais espaço ou as desaloca. Quando um espaço de memória é 
requisitado dinamicamente, o sistema operacional procura por um espaço 
disponível no tamanho do bloco requisitado em toda a memória.
www.esab.edu.br 46
5.3 Alocação contígua e alocação dispersa
Quando uma variável estática é alocada na memória pelo sistema 
operacional os blocos são alocados contiguamente, ou seja, um bloco 
do lado do outro, de forma organizada. Um vetor com oito posições, 
por exemplo, terá os oito blocos de memória que o constituem alocados 
um ao lado do outro, facilitando dessa forma o acesso e manipulação da 
informação. A Figura 17 apresenta a alocação do vetor de dez posições, 
sendo uma alocação estática, veja:
Memória
vendas
Figura 17 – Alocação estática de vetor.
Fonte: Elaborada pelo autor (2013).
Isso é possível, pois o sistema operacional pode alocar o espaço todo antes 
mesmo da execução do programa, já que cada item do vetor possui o 
mesmo espaço de memória. Por exemplo, se for um vetor de “char”, cada 
posição do vetor ocupa 1 byte, resultando em um bloco total de 8 bytes.
Na alocação dinâmica, o espaço só é conhecido em tempo de execução 
quando, explicitamente ou por uso de variáveis locais, as variáveis são 
criadas e liberadas, e cada bloco é alocado dispersamente, como pode ser 
observado na Figura 18. 
www.esab.edu.br 47
Memória
Figura 18 – Alocação dinâmica de vetor.
Fonte: Elaborada pelo autor (2013).
Observe que cada posição do vetor está sendo alocada à medida que 
uma nova posição se faz necessária. Caso se desejasse alocar todo o vetor 
dinamicamente, ou seja, alocar todas as posições no mesmo momento, 
o resultado seria o mesmo da Figura 17, um único bloco de memória 
alocado durante a execução do programa, com a vantagem que a 
quantidade de posições é conhecida em tempo de execução. 
Como se trata de uma alocação dinâmica, de cada posição do vetor, e 
não da estrutura toda, o vetor alocou quatro elementos, podendo ter 
mais ou menos elementos em tempo de execução. Como a alocação não 
é contígua, exige que cada elemento alocado saiba qual o seu próximo 
elemento, pelo seu endereço na memória, observe na Figura 19. 
Memória
e1
e5
e10
e15
Figura 19 – Alocação Dinâmica de Estruturas de Dados com encadeamento.
Fonte: Elaborada pelo autor (2013).
www.esab.edu.br 48
Cada elemento possui um endereço de alocação na memória, além 
disso, é armazenado

Continue navegando

Outros materiais