Mudanças entre as edições de "AULA 15 - Programação 1 - Engenharia"

De MediaWiki do Campus São José
Ir para navegação Ir para pesquisar
(Criou página com '===Objetivos=== ===Referências=== [http://pw1.netcom.com/~tjensen/ptr/ch1x.htm] [http://eternallyconfuzzled.com/tuts/languages/jsw_tut_pointers.aspx] [http://duramecho.com/Co...')
 
(Limpou toda a página)
 
Linha 1: Linha 1:
===Objetivos===
 
  
===Referências===
 
[http://pw1.netcom.com/~tjensen/ptr/ch1x.htm]
 
 
[http://eternallyconfuzzled.com/tuts/languages/jsw_tut_pointers.aspx]
 
 
[http://duramecho.com/ComputerInformation/WhyCPointers.html]
 
 
[http://boredzo.org/pointers/]
 
 
 
===Ponteiros===
 
 
A memória de um computador pode ser vista como um vetor de bytes.
 
 
Cada byte possui um endereço. O tamanho da memória é definido pelo tamanho do barramento de endereços usado para acessá-la.
 
 
Uma variável ocupa uma área da memória. Tipicamente uma variável to tipo ''char'' se utiliza de um ''byte''. Já uma variável do tipo ''int'' pode (dependendo do sistema) usar 4 ''bytes'' contíguos.
 
 
  Uma variável possui um endereço e um conteúdo (dados).
 
 
 
Uma variável ponteiro tem como conteúdo um endereço. Portanto a variável ponteiro possui um endereço e contém um endereço como conteúdo.
 
 
===Ponteiro para inteiro===
 
 
Observe o programa abaixo. A variável ''p'' é um ponteiro para inteiro. Isto significa que ela pode armazenar um endereço
 
de um inteiro.
 
 
 
<syntaxhighlight lang=c>
 
#include <stdio.h>
 
 
main()
 
{
 
  int x;
 
  int *p;
 
 
  x=5;
 
  printf("Valor de x antes = %d\n", x);
 
 
 
  p = &x;
 
  *p=10;
 
 
  printf("Valor de x depois = %d\n", x);
 
  printf("Valor de p = %p\n", p);
 
}
 
</syntaxhighlight>
 
 
Observe que para se referenciar o conteúdo da posição de memória apontada por ''p'' deve-se usar o asterisco: ''*p''
 
 
EXERCÍCIO 1: Considere o programa:
 
<syntaxhighlight lang=c>
 
main()
 
{
 
  int x=10;
 
  int y, *p, *w;
 
 
}
 
</syntaxhighlight>
 
Faça um código para copiar o conteúdo de x para y, sem que estas variáveis apareçam no lado esquerdo de um sinal de atribuição.
 
 
EXERCÍCIO 2: Tente inferir qual seria o valor da variável y no final do programa abaixo.
 
<syntaxhighlight lang=c>
 
main()
 
{
 
  int x,y,w,*p1,*p2;
 
  x = 20;
 
  w = 30;
 
  p1 = &x;
 
  p2 = &w;
 
  y = *p1 + *p2;
 
}
 
</syntaxhighlight>
 
 
EXERCÍCIO 3: Tente inferir qual seria o valor da variável y no final do programa abaixo.
 
<syntaxhighlight lang=c>
 
main()
 
{
 
  int x,y,w,*p1,*p2, *p3;
 
  x = 20;
 
  w = 30;
 
  p1 = &x;
 
  p2 = &w;
 
  y = *p1 + w;
 
  p3 = &y;
 
  *p3 = *p3 + 10;
 
  y = *p1 + *p2 + *p3;
 
}
 
</syntaxhighlight>
 
 
===Ponteiro para ''char''===
 
 
Os ponteiro para ''char'' são muito utilizados pois permitem apontar para ''strings''. A ideia é que ele aponte para o primeiro caracter da ''string''. Veja o exemplo abaixo.
 
 
<syntaxhighlight lang=c>
 
#include <stdio.h>
 
 
main()
 
{
 
  char x[10]="ifsc";
 
  char *p;
 
 
  p = &x[2];
 
 
  printf("x[2] = %c\n", *p);
 
 
  p = x;
 
 
  printf("string %s\n", p);
 
 
  while (*p!=0) {
 
      printf("Endereco %p conteúdo %c\n", p,*p);
 
      p++;
 
  }
 
}
 
</syntaxhighlight>
 
 
Neste foi usado o incremento de um ponteiro, o que implica em adicionar ao endereço armazenado em ''p'' uma quantidade relativa ao tamanho do tipo apontado.
 
No caso é 1 (tamanho de um ''char'' é um byte).
 
 
EXERCÍCIO: Sem executar o programa abaixo, determine o valor de y no final do programa:
 
<syntaxhighlight lang=c>
 
main()
 
{
 
  char x[10]="ifsc";
 
  char *p, y;
 
 
 
  p = x + 2;
 
  y= *p;
 
}
 
</syntaxhighlight>
 
 
===Apontando para um vetor de inteiros===
 
 
Da mesma forma que usamos um ponteiro para char para apontar uma ''string'', podemos fazer um ponteiro para ''int'' apontar para para um elemento de um vetor de inteiros.
 
 
<syntaxhighlight lang=c>
 
#include <stdio.h>
 
 
main()
 
{
 
  int x[10]= {0,1,2,3,4,5,6,7,8,9};
 
  int *p;
 
  int i;
 
 
 
  p = x;
 
 
  i=0;
 
  while (i<10) {
 
      printf(" endereco %p e conteudo %d\n", p, *p);
 
      p++;
 
      i++;     
 
  }
 
}
 
</syntaxhighlight>
 
 
 
OBSERVE que p++ incrementa em 4 unidades.
 
 
===Usando ponteiro na passagem de parâmetros===
 
 
Observe como podemos usar ponteiros na passagem de parâmetros.
 
 
 
<syntaxhighlight lang=c>
 
#include <stdio.h>
 
 
void str_cpy(char *pdest, char *pfonte)
 
{
 
  while (*pfonte!=0) {
 
        *pdest++ = *pfonte++;
 
  }
 
  *pdest = 0;
 
}
 
 
 
int str_len (char *p)
 
{
 
  int i=0;
 
  while (*p++!=0)
 
i++;
 
  return i;
 
}
 
 
main()
 
{
 
  char fonte[10]="ifsc";
 
  char destino[10];
 
 
  str_cpy(destino, fonte);
 
  printf("string destino = %s\n", destino);
 
 
  printf("tamanho de dest = %d\n", str_len(destino));
 
}
 
</syntaxhighlight>
 
 
Um ponto interessante é que ponteiros permitem, na chamada de uma função, passar valores por referência:
 
 
<syntaxhighlight lang=c>
 
 
void alfa(int *p)
 
{
 
  *p=10;
 
}
 
 
main()
 
{
 
  int x;
 
  x =5;
 
  printf("Valor de x antes da chamada de alfa = %d\n", x);
 
  alfa(&x);
 
  printf("Valor de x depois da chamada de alfa = %d\n", x);
 
}
 
</syntaxhighlight>
 
 
EXERCíCIO 1: Implementar a função ''str_cat'' que concatena duas ''strings'' usando ponteiros.
 
 
 
{{collapse bottom}}
 
 
[http://www.mtm.ufsc.br/~azeredo/cursoC/aulas/c600.html Link Aula Ponteiros UFMG]
 
 
{{collapse top | Aula dia 22/05/2014}}
 
 
Viagem para Porto Alegre
 
 
{{collapse bottom}}
 
 
{{collapse top | Aula dia 23/05/2014}}
 
 
Viagem para Porto Alegre
 
 
Exercícios Adicionais ponteiros
 
 
1.Implementar um programa para ler dados para dentro das variáveis x e y e somar o conteúdo das mesmas colocando o resultado em x SEM
 
referenciar estas variáveis no scanf ou na expressão de soma.
 
 
<syntaxhighlight lang=c>
 
#include <stdio.h>
 
main()
 
{
 
  float x,y;
 
}
 
</syntaxhighlight>
 
 
2.Implementar uma função que compara duas strings passadas como parâmetro. A função retorna 0 se as strings forem iguais e 1 se diferentes.
 
Usar ponteiros.
 
 
3.Implementar uma função que recebe como parâmetro o endereço de duas variáveis float que contêm a parte real e imaginária de um número complexo no formato polar (ângulo em radianos). A função deve converter do formato polar retangular colocando a coordenada x no primeira variável cujo endereço foi fornecido como parâmetro e a coordenada y na segunda variável.
 
 
<syntaxhighlight lang=c>
 
 
void converte_polar_retang(float *parte1, float parte2)
 
{
 
}
 
 
main()
 
{
 
  float num1=1.5, num2=10.6;
 
 
  /*chamar a função aqui */
 
 
  /* imprimir os valores de num1 e num2 aqui */
 
}
 
</syntaxhighlight>
 
 
4.Implemantar uma funçao que recebe como parâmetro o endereço de duas variáveis do tipo char e
 
após a chamada da função os valores das variáveis devem estar maiúsculos(caso elas contenham letras minúsculas).
 
 
<syntaxhighlight lang=c>
 
main()
 
{
 
  char alfa='a', beta='b';
 
 
  capitaliza(&alfa, &beta);
 
 
 
  /* aqui os valores de alfa e beta deverão ser A e B */
 
}
 
 
</syntaxhighlight>
 
 
5.Implementar uma função que recebe uma string contendo uma cadeia de caracteres com dígitos numéricos e retorna o valor inteiro da string. Usar ponteiros.
 
 
<syntaxhighlight lang=c>
 
 
int a_toi(char *p)
 
{
 
}
 
 
main()
 
{
 
  char *p="123";
 
  int x;
 
 
  x = a_toi(p);
 
 
 
  /* neste ponto x deve conter 123 */
 
}
 
</syntaxhighlight>
 

Edição atual tal como às 20h50min de 28 de outubro de 2014