TrabalhosGratuitos.com - Trabalhos, Monografias, Artigos, Exames, Resumos de livros, Dissertações
Pesquisar

Variável Ponteiro

Resenha: Variável Ponteiro. Pesquise 862.000+ trabalhos acadêmicos

Por:   •  2/10/2013  •  Resenha  •  1.869 Palavras (8 Páginas)  •  429 Visualizações

Página 1 de 8

Variável Ponteiro

Uma variável ponteiro é uma variável que guarda um endereço de memória suficiente para armazenar um conteúdo do tipo especificado na sua declaração. Assim, uma variável ponteiro para inteiro é declarada da seguinte forma:

int *pi; //que significa uma variável ponteiro para inteiro

Isto significa que pi serve para armazenar o endereço de memória de uma variável inteira.

Quando colocamos o asterisco na frente do nome da variável, *pi, significa que estamos nos referindo ao conteúdo armazenado no endereço de memória apontado por pi.

Exemplo:

int a=3, b=5; //duas variáveis inteiras contendo respectivamente o valor 3 e 5.

int *pa, *pb; //dois ponteiros para variáveis inteiras

pa=&a; // o ponteiro pa recebe o endereço da variável a

pb=&b; // o ponteiro pb recebe o endereço da variável b

printf(“Valor de a =%d Valor apontado por *pa =%d\n”, a,*pa); //fará aparecer o valor 3 em ambos os casos

printf(“Endereço de b=%d Valor armazenado por pb=%d\n”, &b, pb);// fará aparecer em ambos os casos o endereço de memória da variável b)

Alocação Estática e Dinâmica de Memória

Quando se declara um vetor, o nome do vetor já é, por si só, um ponteiro (que armazena o endereço do primeiro elemento do vetor). Então, se um programa declara:

int lista[10];

o nome lista é um ponteiro, conforme figura abaixo:

lista

Escrever *lista (valor apontado por lista) é equivalente a escrever lista[0] ( valor do primeiro elemento da lista). Da mesma forma *(lista+i) é equivalente a lista[i], ou seja, o valor do elemento que ocupa a posição i no vetor lista é o valor apontado pelo ponteiro lista avançado de i posições.

Observe que (lista+i) é equivalente a &(lista[i]). Portanto, uma outra forma de declarar o vetor é: int *lista;

A única diferença entre declarar o vetor lista como um ponteiro para int (int *lista) ou como um vetor de elementos do tipo int (int lista[10]) está na alocação de memória.

Ao declarar lista como um vetor de elementos do tipo int, o compilador aloca automaticamente o espaço de memória necessário (que é determinado pela constante que aparece entre colchetes). Para o caso citado, por exemplo, serão alocados 10 * sizeof(int) bytes de memória para o vetor lista. Para compiladores que usam sizeof(int)=4, serão alocados 40 bytes de memória para o vetor lista. Quando o programador define a quantidade de elementos de um vetor, o compilador pode alocar memória suficiente para a quantidade de elementos estipulada. Isto é conhecido como alocação estática de memória, pois é realizada pelo compilador, isto é, antes que o programa esteja rodando.

A função sizeof requer como parâmetro o nome de um tipo de dado e retorna uma constante correspondente ao número de bytes necessários para armazenar um valor deste tipo. Ao calcular o espaço de memória de um vetor é interessante usar a função sizeof ao invés da constante, porque o valor da constante pode variar de um compilador para outro. Alguns compiladores alocam 2 bytes para o tipo int e outros 4 para o mesmo tipo. Então, o mais correto é informar que serão necessários, por exemplo, 10 * sizeof(int) bytes para alocar um vetor de inteiros de 10 elementos, do que alocar um espaço de 20 ou 40 bytes com a mesma finalidade.

Ao declarar lista como um ponteiro, a alocação de memória não pode ser feita pelo compilador, já que a declaração não especifica o número de elementos do vetor. Deste modo a alocação de memória não pode ser estática. É preciso que a alocação seja feita com o programa já em funcionamento, o que corresponde a uma alocação dinâmica de memória.

Para fazer a alocação dinâmica podem ser usadas duas funções: malloc ou calloc.

A função calloc requer 2 parâmetros: a quantidade de elementos e o tamanho de cada elemento (dado pela função sizeof). A função malloc, por outro lado, requer apenas um parâmetro que corresponde ao espaço total em bytes a ser alocado (que é dado pela multiplicação do número de elementos pelo tamanho de cada elemento). As duas funções retornam um ponteiro do tipo void para o inicio da área de memória alocada (ou NULL se a alocação de memória não for possível). O ponteiro retornado precisa ser convertido para o tipo de dado desejado através de uma operação cast.

Exemplificando: para fazer com que lista aponte para um espaço de memória suficiente para acomodar 10 elementos do tipo int podemos escrever:

int *lista;

lista=(int *) calloc(10,sizeof(int));

ou,

int *lista;

lista=(int *) malloc(10*sizeof(int));

Note que a conversão explicita do tipo void retornado pelas funções malloc e calloc é realizada pelo operador cast (int*).

A vantagem em se definir um vetor como ponteiro está no fato de que a quantidade de elementos não precisa ser fixa, podendo variar de uma execução para outra.

Entretanto, seria possível declarar o vetor como:

int lista[MAX]; para uma constante MAX previamente definida. Mas por ser um valor estimado, poderia levar a situações de desperdício ou de falta de espaço, o que não é conveniente.

Outra vantagem da alocação dinâmica é a possibilidade de aumentar ou reduzir a quantidade de memória alocada anteriormente. Isto pode ser feito através da função realloc, que recebe como parâmetros: um ponteiro para o inicio da área de memória previamente alocada, e o novo espaço requerido, retornando um ponteiro para o novo bloco de memória alocado. O ponteiro retornado pela função realloc pode ser igual ou diferente do ponteiro para o bloco de memória original. Se for diferente, a função realloc copia os dados originais para um novo bloco, liberando o anterior.

...

Baixar como (para membros premium)  txt (11.6 Kb)  
Continuar por mais 7 páginas »
Disponível apenas no TrabalhosGratuitos.com