Programação de Computadores I Aula 09 Programação: Vetores José Romildo Malaquias Departamento de Computação Universidade Federal de Ouro Preto 2011-1 1/62 Motivação Problema Faça um programa que leia as notas dos alunos de uma turma de 5 alunos, determine e mostre a média aritmética das notas, e o número de alunos com notas inferiores à média. 2/62 Motivação (cont.) # include < stdio .h > int main ( void ) { double nota ; double soma = 0.0; for ( int i = 0; i < 5; i ++) { printf ( " nota % d : " , i +1); scanf ( " % lf " , & nota ); soma = soma + nota ; } double media = soma / 5; printf ( " média : %2 f \ n " , media ); // e agora ... como acessar as notas já digitadas ? return 0; } 3/62 Motivação (cont.) I Este programa utiliza uma única variável para armazenar a nota digitada pelo usuário. I Toda vez que o usuário digita uma nova nota, o valor anteriormente digitado é perdido. I Após ler todas as notas e calcular a média, não é mais possı́vel comparar cada nota com a média. I Solução? Usar uma variável diferente para armazenar cada nota. 4/62 Motivação (cont.) # include < stdio .h > int main ( void ) { double n1 , n2 , n3 , n4 , n5 ; printf ( " nota 1: " ); scanf ( " % lf " , & n1 ); printf ( " nota 2: " ); scanf ( " % lf " , & n2 ); printf ( " nota 3: " ); scanf ( " % lf " , & n3 ); printf ( " nota 4: " ); scanf ( " % lf " , & n4 ); printf ( " nota 5: " ); scanf ( " % lf " , & n5 ); double media = ( n1 + n2 + n3 + n4 + n5 ) / 5; printf ( " média : %2 f \ n " , media ); int cont = 0; if ( n1 < media ) cont ++; if ( n2 < media ) cont ++; if ( n3 < media ) cont ++; if ( n4 < media ) cont ++; if ( n5 < media ) cont ++; printf ( " abaixo da média : % d \ n " , cont ); return 0; } 5/62 Motivação (cont.) I O problema foi resolvido. I Porém o fato de usarmos uma variável diferente para cada nota impossibilita o uso de comando de repetição. I Assim foi necessáro escrever scanf 5 vezes, e if 5 vezes. 6/62 Motivação (cont.) I Estenda o problema para trabalhar com uma turma de 100 alunos. É possı́vel, porém esta será uma tarefa enfadonha e sujeita a erros, pois serão necessários: 100 variáveis distintas, cada uma com um nome diferente. 100 comandos scanf 100 comandos if I Pergunta: Existe outra maneira de trabalhar com as 100 variáveis sem usar 100 nomes diferentes? I Resposta: Sim, utilizando vetor. 7/62 Motivação (cont.) I Estenda o problema para trabalhar com um número de alunos que somente será conhecido em tempo de execução. Com este esquema não é possı́vel. I Pergunta: Existe uma maneira de trabalhar com um número desconhecido (pelo programador) de variáveis? I Resposta: Sim, utilizando vetor. 8/62 Vetor I Vetor é uma variável composta homogênea unidimensional. I Um vetor é formado por uma sequência de variáveis, todas do mesmo tipo de dados. I Dizemos que cada variável componente é um elemento do vetor. I As variáveis que compõem um vetor são todas identificadas por um mesmo nome. I Estas variáveis são alocadas sequencialmente na memória. 9/62 Vetor (cont.) 10/62 Declaração de uma variável vetor tipo identificador [tamanho]; I Primeiro o tipo de dado dos componentes do vetor: int, float, double, char, . . . I Segundo o nome da variável vetor: usando as mesmas convenções de um identificador comum: array, vetor, variavelDeNumeros, vet, . . . I E por fim, o tamanho do vetor (isto é, a quantidade de elementos que formam o vetor) escrito entre colchetes: [5], [10], [3], . . . 11/62 Declaração de uma variável vetor (cont.) Exemplos: int vet [6]; double notas [100]; char texto [256]; double medias [2* n ]; // // // // um um um um vetor vetor vetor vetor de de de de 6 inteiros 100 doubles 256 caracteres 2* n doubles 12/62 Declaração de uma variável vetor (cont.) I Todo vetor é um espaço linear na memória dividido em várias variáveis componentes de acordo com o tamanho declarado. I Ao declaramos int vet [4] é alocado na memória um espaço linear para 4 variáveis inteiras, representadas da seguinte forma: I Assim vet é uma variável vetor formada por 4 espaços de memória. 13/62 Acessando elementos de um vetor I Os componentes de um vetor são numerados sequencialmente começando com zero. I Para identificar cada componente usamos o nome do vetor juntamente com o número que indica a posição do componente na sequência. I A posição de um componente é chamada de ı́ndice. I Exemplo: double Notas [10]; 14/62 Acessando elementos de um vetor (cont.) I Sintaxe: vetor[ı́ndice] I Primeiramente escreve-se o vetor. I Depois escreve-se o ı́ndice (uma expressão inteira) entre colchetes. 15/62 Acessando elementos de um vetor (cont.) I Exemplo: double Notas [10]; Notas [1] = 9.35; printf ( " % f " , Notas [1]); Notas[1] refere-se ao componente na posição 1 do vetor Notas, ou seja, o segundo elemento do vetor. 16/62 Acessando elementos de um vetor (cont.) I Uma vez que as variáveis que compõem o vetor têm o mesmo nome, o que distingue cada uma delas é o seu ı́ndice, que referencia sua localização dentro da estrutura. 17/62 Acessando elementos de um vetor (cont.) 18/62 Acessando elementos de um vetor (cont.) I A primeira posição de um vetor tem ı́ndice 0. I A última posição de um vetor tem ı́ndice tamanho - 1 . I Importante: O sistema de execução não verifica se o ı́ndice usado para acessar um componente do vetor é válido. É responsabilidade do programador garantir que o ı́ndice usado para acessar um elemento de um vetor é válido. 19/62 Acessando elementos de um vetor (cont.) Não esqueça: I Para acessar uma posição especı́fica de um vetor basta indicar a posição desejada entre colchetes I A posição é chamada de ı́ndice. I A faixa de ı́ndices válidos inicia em 0 e termina com o tamanho - 1. I Exemplo: os ı́ndices válidos para um vetor de tamanho 4 são 0, 1, 2 e 3. 20/62 Acessando elementos de um vetor (cont.) Exemplo: Declarar um vetor de tamanho 4 e atribuir o valor 540 na posição 1 e o valor 8456 na posição 3. int vetor [4]; vetor [1] = 540; vetor [3] = 8456; 21/62 Acessando elementos de um vetor (cont.) I O limite do vetor é sempre o seu tamanho menos 1. I No exemplo anterior o vetor é de tamanho 4, a posição máxima é 3, pois 4 − 1 = 3. I Se um valor for atribuı́do fora dos limites do vetor ocorrerá um erro muito grave, pois o valor estará sendo armazenado em um espaço de memória que não pertence ao vetor. I Ainda no exemplo anterior, não se deve fazer vetor [4] = 200; 22/62 Exemplo: ler e mostrar um vetor Inserir 5 notas em um vetor, depois disso visualizar as notas inseridas. 23/62 Exemplo: ler e mostrar um vetor (cont.) # include < stdio .h > int main ( void ) { double notas [5]; // um vetor de 5 elementos int j ; // ı́ndice no vetor // entrada dos dados for ( j = 0; j < 5; j ++) { printf ( " Inserir nota % d : " , j +1); scanf ( " % d " , & notas [ j ]); } // visualizaç~ a o dos dados for ( j = 0; j < 5; j ++) printf ( " % d " , notas [ j ]); return 0; } 24/62 Exemplo: ler e mostrar um vetor (cont.) 25/62 Exemplo: ler e mostrar um vetor (cont.) 26/62 Exemplo: ler e mostrar um vetor (cont.) 27/62 Exemplo: ler e mostrar um vetor (cont.) 28/62 Exemplo: ler e mostrar um vetor (cont.) 29/62 Exemplo: ler e mostrar um vetor (cont.) 30/62 Exemplo: ler e mostrar um vetor (cont.) 31/62 Exemplo: ler e mostrar um vetor (cont.) 32/62 Exemplo: ler e mostrar um vetor (cont.) 33/62 Exemplo: ler e mostrar um vetor (cont.) 34/62 Exemplo: ler e mostrar um vetor (cont.) 35/62 Exemplo: ler e mostrar um vetor (cont.) 36/62 Exemplo: ler e mostrar um vetor (cont.) 37/62 Exemplo: ler e mostrar um vetor (cont.) 38/62 Exemplo: ler e mostrar um vetor (cont.) 39/62 Exemplo: ler e mostrar um vetor (cont.) 40/62 Exemplo: ler e mostrar um vetor (cont.) 41/62 Exemplo: ler e mostrar um vetor (cont.) 42/62 Exemplo: média de 5 notas Faça um programa que leia as notas dos alunos de uma turma de 5 alunos, determine e mostre a média aritmética das notas, e o número de alunos com notas inferiores à média. 43/62 Exemplo: média de 5 notas (cont.) # include < stdio .h > int main ( void ) { double notas [5]; int indice ; // leitura dos dados for ( indice = 0; indice < 5; indice ++) { printf ( " nota % d : " , indice + 1); scanf ( " % lf " , & notas [ indice ]); } // cálculo e exibiç~ a o da média double soma = 0; for ( indice = 0; indice < 5; indice ++) soma = soma + notas [ indice ]; 44/62 Exemplo: média de 5 notas (cont.) double media = soma /5; printf ( " média : %2 f \ n " , media ); // cálculo e exibiç~ a o da quantidade // de notas abaixo da média int cont = 0; for ( indice = 0; indice < 5; indice ++) if ( notas [ indice ] < media ) cont = cont + 1; printf ( " abaixo da média : % d \ n " , cont ); return 0; } 45/62 Exemplo: preenchendo um vetor I Colocar os números de 1 a 5 em Vetor. 46/62 Exemplo: preenchendo um vetor I Colocar os números de 1 a 5 em Vetor. for ( int i = 0; i < 5; i ++) Vetor [ i ] = i + 1; 46/62 Exemplo: preenchendo um vetor I Colocar os números de 1 a 5 em Vetor. for ( int i = 0; i < 5; i ++) Vetor [ i ] = i + 1; I Colocar os números de 5 a 1 em Vetor. 46/62 Exemplo: preenchendo um vetor I Colocar os números de 1 a 5 em Vetor. for ( int i = 0; i < 5; i ++) Vetor [ i ] = i + 1; I Colocar os números de 5 a 1 em Vetor. for ( int i = 0; i < 5; i ++) Vetor [ i ] = 5 - i ; 46/62 Uso de constantes com vetores I Geralmente é melhor usar um nome representando um valor constante do que usar a própria constante em um programa. I Para tanto define-se a constante no inı́cio do programa, e no restante do programa usa-se o nome definido. I Se for necessário redefinir o valor da constante no texto do programa, o local a ser alterado é somente na declaração da constante. I Além disto, o uso de um nome pode ser uma dica do significado da constante. 47/62 Uso de constantes com vetores (cont.) I Geralmente é melhor definir e usar uma constante para representar o tamanho de um vetor do que escrever o valor do tamanho explicitamente em todas os locais que precisamos do tamanho. 48/62 Uso de constantes com vetores (cont.) I Uma constante pode ser definida como uma macro do pré-processador usando a diretiva #define. I No inı́cio da compilação, o pré-processador substitui todas as ocorrências no nome da macro pela definição dada. I Este procedimento é apenas manipulação do texto do programa. I Não é feita nenhuma checagem de tipo com o nome da macro. I Exemplo: # define TAMANHO 5 double VetReais [ TAMANHO ]; // coloca 5 ,4 ,3 ,2 ,1 no vetor for ( i = 0; i < TAMANHO ; i ++) VetReais [ i ] = TAMANHO + i ; 49/62 Uso de constantes com vetores (cont.) I Uma constante pode ser definida no nı́vel da linguagem através do especificador const colocado em uma declaração de variável, antes no nome do tipo. I A variável assim definida é similar às outras variáveis, exceto pelo fato de que o seu valor não pode ser alterado. Portanto não é possı́vel fazer uma atribuição a ela. I Exemplo: const int TAMANHO = 20 double VetReais [ TAMANHO ] , VetCopia [ TAMANHO ]; // copia os dados de um vetor para outro for ( i = 0; i < TAMANHO ; i ++) VetCopia [ i ] = VetReais [ i ]; 50/62 Exemplo: ordem inversa Construa um algoritmo que leia 300 números inteiros e imprima esses números na ordem inversa de entrada. 51/62 Exemplo: ordem inversa (cont.) # include < stdio .h > # define QUANTIDADE 300 // definiç~ a o de macro int main ( void ) { int vet [ QUANTIDADE ]; int i ; // leitura dos dados for ( i = 0; i < QUANTIDADE ; i ++) { printf ( " número % d : " , i + 1); scanf ( " % d " , & vet [ i ]); } // impress~ a o na ordem inversa printf ( " \ nordem inversa :\ n " ); for ( i = QUANTIDADE - 1; i >= 0; i - -) printf ( " número % d : % d \ n " , i + 1 , vet [ i ]); return 0; } 52/62 Inicialização de vetores I Quando declaramos um vetor, os seus elementos não são inicializados. I Neste caso os seus elementos são desconhecidos (lixo) e só deverão ser utilizados após atribuição. I Porém é possı́vel fazer a inicialização de um vetor com os valores iniciais desejados. I Os valores inicias são colocados entre chaves {}. I Exemplo: int v [5] = { 16 , 36 , 3 , 8 , 26 }; 53/62 Inicialização de vetores (cont.) I A quantidade de valores entre chaves não deve ser maior que o tamanho do vetor. I A fim de facilitar a inicialização, C permite omitir o número de elementos (tamanho): []. I Neste caso, o compilador assume que o tamanho do vetor é igual ao número de valores especificados na inicialização (entre chaves). I Exemplo: int v [] = { 16 , 36 , 3 , 8 , 26 }; 54/62 Busca I Dada uma coleção de n elementos, pretende-se saber se um determinado valor x está presente nessa coleção. I Para efeitos práticos, vamos supor que essa coleção é implementada como sendo um vetor de n elementos inteiros: v[0]..v[n-1]. 55/62 Pesquisa seqüêncial I I Utilizamos uma variável encontrado para sinalizar se o valor já foi encontrado. Inicialmente o seu valor é falso (representando como 0 no C). Percorremos o vetor desde a primeira posição até a última, ou até o valor ser encontrado: Para cada posição i, comparamos v[i] com o valor x: se forem iguais sinalizamos que o valor foi encontrado atribuindo verdadeiro (representado como 1 no C) à variável encontrado se chegarmos ao fim do vetor sem sucesso concluı́mos que o valor não existe no vetor 56/62 Pesquisa seqüêncial (cont.) Passos: 1. Inicialização int i = 0; int encontrado = 0; /* falso */ 57/62 Pesquisa seqüêncial (cont.) 2. Pesquisa while ( i < TAMANHO && ! encontrado ) { if ( vetor [ i ] == x ) encontrado = 1; /* verdadeiro */ else i ++; } 58/62 Pesquisa seqüêncial (cont.) 3. Tratamento do resultado if ( encontrado ) printf ( " Valor % d encontrado na posiç~ ao %d\n" , vetor [ i ] , i ); else printf ( " Valor % d n~ a o encontrado \ n " , vetor [ i ]); 59/62 Pesquisa seqüêncial (cont.) Exemplo: # include < stdio .h > # define TAMANHO 4 int main ( void ) { int vet [ TAMANHO ]; int i ; // leitura dos dados printf ( " Digite % d números :\ n " , TAMANHO ); for ( i = 0; i < TAMANHO ; i ++) scanf ( " % d " , & vet [ i ]); // leitura do valor a ser pesquisado int valor ; printf ( " Valor procurado :\ n " ); scanf ( " % d " , & valor ); 60/62 Pesquisa seqüêncial (cont.) // realiza a pesquisa int encontrado = 0; /* falso */ for ( i = 0; i < TAMANHO && ! encontrado ; i ++) encontrado = ( vet [ i ] == valor ); // exibe resultado if ( encontrado ) printf ( " encontrado na posiç~ a o % d \ n " , i - 1); else printf ( " n~ a o encontrado \ n " ); return 0; } 61/62 FIM Créditos: Baseado no material preparado pelo Prof. Guillermo Cámara-Chávez. 62/62