Baixe o app para aproveitar ainda mais
Prévia do material em texto
UNIVERSIDADE FEDERAL DO ESPÍRITO SANTO CENTRO DE CIÊNCIAS AGRÁRIAS DEPARTAMENTO DE ENGENHARIA RURAL ENG06842 PROGRAMAÇÃO I PARTE 2 Prof. Geraldo Regis Mauri CCA-UFES Agosto - 2009 ENG06842 – Programação I Sumário 7.Linguagens de programação e execução de programas ........................................................... 3 7.1.Introdução ............................................................................................................................. 3 7.2.Tradutores: compiladores e interpretadores .......................................................................... 5 7.3.Compilador PASCAL ........................................................................................................... 6 7.4.Exercícios ............................................................................................................................ 14 8.A Linguagem Pascal .............................................................................................................. 16 8.1.Introdução ........................................................................................................................... 16 8.2.Tipos de dados simples ....................................................................................................... 16 8.3.Mapeamento Portugol x Pascal ........................................................................................... 18 8.4.Unidades pré-definidas ....................................................................................................... 21 8.5.Palavras reservadas ............................................................................................................. 22 8.6.Funções pré-definidas ......................................................................................................... 22 8.7.Tipos definidos pelo usuário ............................................................................................... 29 8.8.Exercícios ............................................................................................................................ 31 9.Estruturas de dados ................................................................................................................ 33 9.1.Introdução ........................................................................................................................... 33 9.2.Variáveis compostas homogêneas ...................................................................................... 33 9.3.Variáveis compostas heterogêneas ..................................................................................... 39 9.4.Algoritmos de classificação e busca ................................................................................... 46 9.5.Exercícios ............................................................................................................................ 48 10.Modularização ...................................................................................................................... 51 10.1.Introdução ......................................................................................................................... 51 10.2.Procedimentos ................................................................................................................... 52 10.3.Funções ............................................................................................................................. 53 10.4.Escopo de variáveis ........................................................................................................... 56 10.5.Parâmetros ......................................................................................................................... 56 10.6.Recursividade .................................................................................................................... 60 10.7.Exercícios .......................................................................................................................... 60 11.Armazenamento de dados .................................................................................................... 67 11.1.Arquivos ............................................................................................................................ 67 11.2.Exercícios ..........................................................................................................................76 Referências ................................................................................................................................ 78 Apêndice A – Mensagens de erro do Turbo Pascal .................................................................. 79 Apêndice B – Tabela de códigos ASCII ................................................................................... 82 2 ENG06842 – Programação I 7. Linguagens de programação e execução de programas 7.1. Introdução A linguagem de programação é o meio pelo qual se pode indicar os “passos” que devem ser realizados pelo computador para resolver problemas. Utilizando as linguagens de programação, pode-se colocar os algoritmos numa forma que o computador possa interpretá-los, ou seja, na forma de programas computacionais. Para que o computador execute o algoritmo proposto, as operações devem ser transcritas para uma linguagem que a máquina consiga compreender. Na realidade, os computadores só podem executar algoritmos expressos em linguagem de máquina, que se constitui de um conjunto de instruções capazes de ativar diretamente os dispositivos eletrônicos do computador. Características da Linguagem de Máquina: • diferente para cada tipo de computador, dependendo de sua arquitetura; • extremamente rudimentar, onde até as operações mais simples têm que ser expressas em termos de registros, acumuladores e outros dispositivos de máquina; • totalmente expressa em forma numérica - sistema de numeração binário (0s e 1s) ou hexadecimal. Conseqüentemente, é uma linguagem de difícil aprendizado e pouco expressiva para as pessoas. Para tornar a atividade de programação mais acessível, foram desenvolvidas outras linguagens, denominadas de “Linguagens de Programação”, que funcionam como uma forma alternativa de se comunicar com o computador. 3 ENG06842 – Programação I As linguagens de programação são compostas por um grupo de elementos e regras que permitem a construção das instruções utilizadas para resolver os problemas computacionais. Com elas, pode-se construir programas que devem ser, posteriormente, transformados em instruções em Linguagem de Máquina. Para realizar a transformação, cada linguagem de programação possui um programa-suporte denominado, genericamente, de tradutor. Linguagem de Programação de Baixo Nível: Conhecida como Linguagem Assembler ou Linguagem de Montagem, ou ainda, Linguagem Simbólica. Utiliza números binários, hexadecimais, alguns símbolos e letras para compor os programas. Está muito próxima da Linguagem de Máquina, onde cada instrução simbólica corresponde, praticamente, a uma instrução de máquina. Para transformar o programa escrito em Linguagem Assembler em código de máquina executável, é utilizado um programa- suporte denominado de MONTADOR. Linguagens de Programação de Alto Nível: São linguagens de programação que utilizam notações matemáticas e grupos de palavras para representar as instruções de máquina, tornando o processo de programação mais próximo do entendimento humano. Muitas destas linguagens foram desenvolvidas para atender os problemas de áreas de aplicação específicas, como, por exemplo, linguagens para aplicações comerciais, científicas, administrativas, de ensino, etc. A primeira linguagem de alto nível foi desenvolvida em 1957 - denominada de FORTRAN (Formula Translator) - e destina-se a aplicações científicas e de engenharia. Principais vantagens das linguagens de Alto Nível: • facilidade de entendimento e uso; • independência de máquina (é praticamente a mesma, não importando o computador utilizado). 4 ENG06842 – Programação I Para transformar os programas escritos com Linguagens de Alto Nível em códigos de máquina, é usado um programa-suporte denominado TRADUTOR (Compilador ou Interpretador). 7.2. Tradutores: compiladores e interpretadores Para executar um programa escrito numa linguagem de alto nível é preciso primeiro traduzir o código-fonte para código-objeto. O processo de tradução pode dar-se em tempo de execução caso a linguagem use um interpretador (traduz e executa instrução a instrução), ou todas as instruções podem ser traduzidas antes que se inicie a execução do programa, o que ocorre no caso de linguagens que usam tradutores do tipo compilador. Código-fonte: não é executável diretamente pelo processador - permite apenas que o programador consiga definir o programa em uma forma legível aos humanos. Código-objeto: é o código produzido pelo compilador; é uma forma intermediária, similar a linguagem de máquina do computador. Apesar de estar representado em binário, não é executável diretamente pelo processador, pois normalmente, o código-objeto referencia partes de programa que não estão necessariamente definidas no mesmo arquivo que o gerou, por exemplo, arquivos de bibliotecas de sub-rotinas. Editores de ligação (ou linkeditores ) : Um programa que reúne módulos compilados e arquivos de dados para criar um programa executável. Os linkeditores têm também outras funções, como a criação de bibliotecas. Compilador: No sentido mais geral, qualquer programa que transforme um conjunto de símbolos em outro obedecendo a uma série de regras sintáticas e semânticas; no sentido mais comum, um programa que traduz 5 ENG06842 – Programação I todo o código-fonte de programas escritos numa linguagem de alto nível em código-objeto antes da execução do programa. Ou seja, traduz o programa escrito em linguagem de alto nível (código-fonte) para um programa equivalente escrito em linguagem de máquina (código-objeto). Interpretador: traduz e envia para execução, instrução por instrução e o programa permanece na forma fonte. 7.3. Compilador PASCAL O Turbo Pascal é um programa que contém, além do compilador PASCAL, um ambiente completo de programação, com editor de programa, depurador de erros, sistema de ajuda, etc. Existem diversos compiladores para a linguagem Pascal, porém para esse curso, será utilizado como padrão o compilador Borland Turbo Pascal 7.0, pois este é um programa gratuito e de simples utilização. Algumas dicas para aquisição e instalação deste programa são apresentadas no Erro: Origem da referência não encontrada. O ambiente de desenvolvimento do Turbo Pascal (ver figura abaixo) é composto de um editor de texto, um compilador, um programa ligador (linkeditor) e um depurador (debugger), harmonicamente integrados. 6 ENG06842 – Programação I Após editar um arquivo, é natural compilá-lo e rodá-lo, para ver os resultados do programa. Durante esse processo, o Turbo Pascal irá procurar erros em tempo de compilação. Senão houver erros, o programa rodará normalmente. Caso contrário, o processo de compilação será interrompido e o compilador indicará o erro e a sua posição. Os programas podem conter três tipos de erros: Erro de sintaxe: ocorre quando se viola uma regra da linguagem. Ao encontrar um destes erros, o Turbo Pascal interrompe a compilação do programa, dá uma mensagem com o número e a descrição do erro, e deixa o cursor piscando no item do programa que permitiu a detecção do erro. Deve-se observar que este item pode não estar errado, mas apenas permitiu detectaro erro. O Turbo Pascal não executa um programa enquanto houver erros de sintaxe. Erro de semântica: é um erro que o programa detecta durante a sua execução, interrompendo-a; por exemplo, quando o programa é levado a ler um arquivo inexistente, a tirar a raiz quadrada de um número negativo, a dividir por zero, etc. Ocorrendo um erro de semântica, o Turbo Pascal interrompe a execução do programa e mostra a descrição do erro, com o cursor piscando no início da linha em que ele foi detectado. 7 ENG06842 – Programação I Erro de lógica: aparece em programas, sintática e semanticamente corretos, que, apesar disso, não produzem os resultados desejados. São devidos a instruções corretas, para o computador, mas que não são apropriadas para a solução lógica do problema que motivou o programa. A correção dos erros de lógica é muitas vezes trabalhosa e demorada. Para ajudar a depuração de erros de lógica, o Turbo Pascal oferece diversos recursos que permitem ver e acompanhar o que ocorre durante a execução de um programa. Erros de sintaxe e semântica não são preocupantes, pois o próprio computador os localiza e os identifica. Uma lista com os principais erros apresentados no Turbo Pascal são descritos no Apêndice A – Mensagens de erro do Turbo Pascal. Para compilar um programa, deve-se utilizar a opção COMPILE (compilar) do Menu COMPILE ou pressione Alt+F9. Caso seja detectado algum erro (de sintaxe), este será exibido na tela, caso contrário, será exibida uma mensagem dizendo que o programa foi compilado com sucesso. A partir daí, basta pressionar qualquer tecla para fechar essa mensagem e executar o programa. Para executar um programa, deve-se utilizar a opção RUN (executar) do Menu RUN ou pressione Ctrl+F9. Ao terminar a execução, o Pascal volta para a janela de edição. Para ver os resultados do programa, basta pressionar Alt+F5. O Turbo Pascal 7.0 também oferece alguns recursos para depuração do programa. Um desses recursos é a utilização de break points (pontos de parada). Para sua utilização, basta clicar com o botão direito do mouse sobre a linha onde a execução do programa deverá parar, e selecionar a opção Toogle breakpoint (ou pressionar Ctrl+F8). A linha ficará vermelha, e quando o programa for executado, assim que seu fluxo de execução chegar nessa linha, será possível acompanhar passo-a-passo o restante da execução do programa. Para isso, basta pressionar a tecla F8, que cada instrução subseqüente será executada uma a uma. Para verificar o 8 ENG06842 – Programação I conteúdo das variáveis presentes na instrução atual, basta pressionar Ctrl+F4, ou clicar com o botão direito e selecionar a opção Evaluate/Modify. A seguir são descritos os menus do Turbo Pascal 7.0. File – esta opção possibilita executar operações de controle com arquivos. o New – criar um novo programa. o Open – abrir um programa existente. o Save – salvar um programa em disco. o Save as – salvar um programa em disco com outro nome. o Save all – salvar todos os programas modificados. o Change dir – mudar o diretório de trabalho. o Print – imprimir o programa da janela ativa. o Print setup – configurar o uso de outra impressora. o DOS shell – sair temporariamente para o sistema operacional (DOS). o Exit – finalizar a execução do Turbo Pascal. Edit – esta opção possibilita executar operações do editor do programa, sendo possível remover, movimentar e copiar textos que estejam selecionados. o Undo – desfazer uma operação com texto. o Redo – refazer uma operação com texto. 9 ENG06842 – Programação I o Cut – remover um texto previamente selecionado, enviando-o para área de transferência. o Copy – copiar um texto selecionado do editor para uma área de transferência. o Paste – copiar um texto da área de transferência para o editor. o Clear – remover o texto selecionado sem transferi-lo para a área de transferência. o Show Clipboard – apresentar o conteúdo existente na área de transferência. Search – esta opção possibilita executar operações de busca, troca e deslocamento dentro de um programa. o Find – localizar uma seqüência de caracteres em um programa. o Replace – substituir uma seqüência de caracteres por outra. o Search again – repetir a última busca. o Go to line number – posicionar-se em uma determinada linha do programa. o Show last compiler error – mostrar o último erro de compilação, quando ocorrer. o Find error – posicionar-se na última posição de erro encontrada pelo compilador. o Find procedure – localizar uma sub-rotina dentro do programa no momento de depuração de um programa. Run – esta opção possibilita colocar em execução o programa da janela ativa. 10 ENG06842 – Programação I o Run – compilar e executar o programa. o Step over – rodar o programa passo a passo com exceção das sub-rotinas existentes. o Trace into – rodar o programa passo a passo inclusive as suas sub-rotinas. o Go to cursor – rodar o programa até a posição em que está o cursor. o Program reset – interromper a execução de um programa durante sua depuração. o Parameters – efetuar a passagem de parâmetros. Compile – esta opção possibilita compilar o programa. o Compile – compilar o programa da janela ativa. o Make – recompilar apenas os programas alterados. o Build – recompilar todos os programas. o Destination – determinar se o programa será compilado somente em memória ou disco. o Primary file – determinar numa lista de arquivos qual será o arquivo principal que será carregado primeiro no processo de compilação. o Clear primary file – limpar o arquivo anteriormente configurado como o arquivo primário. o Information – obter informações a respeito da última compilação executada. 11 ENG06842 – Programação I Debug – esta opção possibilita depurar o programa para facilitar a localização de erros lógicos. o Breakpoint – colocar ou retirar um ponto de parada (exame) na depuração de um programa. o Call stack – apresentar uma janela com a seqüência de chamadas efetuadas de sub-rotinas. o Register – visualizar a janela de registradores da CPU. o Watch – abrir a janela de acompanhamento de valores nas variáveis do programa. o Output – abrir uma janela para apresentar as telas de saída do programa em execução ou depuração. o User Screen – exibir na sua totalidade a tela do usuário. o Evaluate/modify – permite efetuar a avaliação de expressões, constantes ou variáveis. o Add watch – possibilidade de incluir expressões na tela de vigia. o Add breakpoint – permite a inclusão de um ponto de parada quando for executado o programa. Tools – esta opção possibilita a utilização de ferramentas configuradas pelo usuário. o Messagens – abrir uma janela para a apresentação de mensagens. o Go to next – visualizar a próxima mensagem da janela de mensagens. 12 ENG06842 – Programação I o Go to previous – visualizar a mensagem anterior da janela de mensagens. o Grep – efetuar a busca de seqüências de caracteres em programas gravados através do utilitário GREP.EXE. Options – esta opção permite configurar a forma de trabalho do ambiente do Turbo Pascal. o Compiler – alterar o estado das diretivas de compilação. o Memory sizes – definir o tamanho de memória. o Linker – a possibilidade de usar ou não o recurso de link. o Debugger – estabelecer critérios de depuração. o Directories – determinar os diretórios de trabalho. o Browser – especifica configurações globais do visualizador.o Tools – efetuar a manutenção do menu de ferramentas. o Environment – efetuar mudanças no ambiente de trabalho (Preferências, Editor, Mouse, Inicialização e Cores) do Turbo Pascal conforme necessidade do usuário. o Open – a abertura do arquivo de configuração. o Save – gravar o arquivo de configuração. o Save as – gravar o arquivo de configuração com outro nome. Window – esta opção possibilita o controle das janelas que estejam abertas. o Tile – ordenar as janelas lado a lado. o Cascade – ordenar as janelas em cascata. 13 ENG06842 – Programação I o Close all – fechar todas as janelas. o Refresh display – redesenhar a janela ativa. o Size/Move – movimentar ou alterar o tamanho de uma janela. o Zoom – alterar o tamanho de uma janela para o tamanho máximo ou para o tamanho preestabelecido. o Next – selecionar a próxima janela como ativa. o Previous – selecionar a janela anterior como ativa. o Close – fechar a janela ativa. o List – apresentar a listagem das janelas que estejam abertas. Help – esta opção permite executar o modo de ajuda do Turbo Pascal. O modo de ajuda poderá ser executado de qualquer parte do programa com a tecla de função F1 ou Ctrl+F1 para visualizar explicações de instruções que estejam marcadas com o posicionamento do cursor sobre elas. o Contents – apresenta o sumário. o Index – apresenta todas as instruções em ordem alfabética. o Error messages – apresenta uma lista de erros de execução e de compilação. o About – informações sobre o Turbo Pascal 7.0. 7.4. Exercícios 1. Defina, com suas palavras, os seguintes termos: a) programa b) linguagem de programação 14 ENG06842 – Programação I c) tradutor 2. Qual a diferença entre linguagem de baixo nível e linguagem de alto nível? 3. Qual a diferença entre código-fonte e código-objeto? 4. Explique a diferença entre compilador e interpretador. 5. Diferencie com suas palavras os três tipos de erros encontrados em programas. 15 ENG06842 – Programação I 8. A Linguagem Pascal 8.1. Introdução A linguagem de programação PASCAL foi criada para ser uma ferramenta educacional, isto no início da década de 70 pelo Prof. Niklaus Wirth da Universidade de Zurique. Foi batizada pelo seu idealizador em homenagem ao grande matemático Blaise Pascal, inventor de uma das primeiras máquinas lógicas conhecidas. Foi baseada em algumas linguagens estruturadas existentes na época, ALGOL e PLI. O próprio Niklaus Wirth diz que esta linguagem foi criada simultaneamente para ensinar programação estruturada e para ser utilizada em sua fábrica de software. A linguagem é extremamente bem estruturada e muito adequada para ensino de linguagens de programação. É provavelmente uma das linguagens mais bem resolvidas entre as linguagens estruturadas, e certamente um dos exemplos de como uma linguagem especificada por uma pessoa pode ser bem melhor do que uma linguagem especificada por um comitê. Apesar de seu propósito inicial, o PASCAL começou a ser utilizado por programadores de outras linguagens, tornando-se, para surpresa do próprio Niklaus, um produto comercial. Comercialmente, a linguagem foi sucedida pela criação da linguagem Object Pascal, atualmente utilizada nas IDEs Borland Delphi, Kylix e Lazarus. Academicamente, seus sucessores são as linguagens subseqüentes de Niklaus Wirth: Modula-2 e Oberon. 8.2. Tipos de dados simples integer - Envolve os números inteiros. A partir da versão 5.0 do Turbo Pascal passaram a existir também outros tipos de números inteiros: shortint, byte, word e longint. 16 ENG06842 – Programação I Exemplos: -45, 1, 138, 0, -2. Tipo Valor mínimo Valor máximo Bytes ocupados shortint -128 127 1 byte 0 255 1 integer -32768 32767 2 word 0 65535 2 longint -2147483648 2147483647 4 real - abrange os números reais. A partir da versão 5.0 passaram a existir também outros tipos de números reais: single, double, extended e comp. Exemplos: 4.5, -32.0, .5, 7.8E3, 21E+3, -315E-3. Tipo Valor mínimo Valor máximo Bytes ocupados Dígitos significativo s real +-2.9 x 10-39 -+1.7 x 1038 6 11-12 single +-1.5 x 10-45 +-3.4 x 1038 4 7-8 double +-5.0 x 10-324 +-1.7 x 10308 8 15-16 extended +-3.4 x 10- 4932 +-1.1 x 104932 10 19-20 comp -263 + 1 263 - 1 8 19-20 boolean - representa um valor lógico (booleano). Utiliza apenas duas constantes lógicas: true (verdadeiro) e false (falso). char - representa um único caractere, escrito entre apóstrofos ( ‘ ’ ). A maioria dos computadores utiliza a tabela de códigos ASCII (ver Apêndice B – Tabela de códigos ASCII) para representar todos os caracteres disponíveis. Qualquer caractere poderá ser representado pelo seu código ASCII em decimal, precedido por #, ou em hexadecimal, precedidos por # e $. Exemplos: ‘A’, ‘B’, ‘a’, ‘1’, ‘@’, ‘ ’, #65 (é o caractere A). 17 ENG06842 – Programação I string - formado por um conjunto de elementos do tipo char. O tamanho máximo é de 255 caracteres. Também pode apresentar um tamanho pré- definido: string[5], por exemplo (máximo de 5 caracteres). Exemplos: ‘CPU’, ‘Processamento de Dados’, ‘123’. 8.3. Mapeamento Portugol x Pascal A passagem de um código em Portugol para a linguagem Pascal é praticamente direta, como se fosse uma simples tradução de português para inglês. Entretanto, algumas estruturas devem ser cuidadosamente observadas. A seguir são apresentadas as principais regras para realizar o mapeamento de Portugol para Pascal. PORTUGOL PASCAL algoritmo CALCULA_MEDIA; var P1, P2, P3, P4, MEDIA: real; in icio leia (P1); leia (P2); leia (P3); leia (P4); MEDIA (P1 + P2 + P3 + p4) / 4; escreva (MEDIA); se MEDIA ≥ 7,0 então escreva (APROVADO); senão escreva (REPROVADO); fim-se; fim. program CALCULA_MEDIA; var P1, P2, P3, P4, MEDIA: real; begin read (P1); read (P2); read (P3); read (P4); MEDIA := (P1 + P2 + P3 + p4) / 4; write (MEDIA); if MEDIA ≥ 7,0 then write (‘APROVADO’) else write (‘REPROVADO’); end. No exemplo acima, nota-se claramente que é feita um tradução português-inglês do algoritmo. Entretanto, deve-se observar as equivalências definidas na tabela abaixo: PORTUGOL PASCAL algoritmo program inicio begin fim end leia read escreva write 18 ENG06842 – Programação I := se if então then senão else caso case enquanto ... faça while ... do repita ... até repeat ... until para ... até ... faça for ... to ... do Como pode ser observado no exemplo anterior, a palavra fim-se não é usada em Pascal, pois deve-se entender que apenas uma instrução será executada após o if e o else. Caso seja necessária a execução de mais de uma instrução dentro do if, por exemplo, deve-se definir um “bloco” (conjunto de comandos delimitados pelas palavras begin e end) através dos comandos begin e end. Exemplos: if condição1 then begin comando 1; if condição2 then comando 2; end else comando 3; Obs.: O comando anterior ao “else” nunca terminará com “;”. No caso acima o “end” anterior ao “else” não termina com “;”. Exemplos: if condição then comando 1 else comando 2; if condição then begin comando 1; comando 2; ... end else begin comando 3; comando 4; ... end; 19 ENG06842 – Programação I Resumindo então, utiliza-se a definição de blocos apenas nos casos onde mais de uma instrução deverá ser executada. Esse conceito de blocos também é usado nas estruturas de repetição. Os comandos read e write podem ser substituídos pelos comandos readln e writeln, respectivamente.Esses novos comandos saltam uma linha após sua execução. Ex: writeln(‘teste’); Esse comando escreve teste e pula para a linha abaixo na tela. No comando write, pode-se definir o formato de saída das variáveis numéricas (casas decimais, com arredondamento), pois no seu modo padrão, os valores aparecerão em notação científica. Ex: Seja a variável a = 2.36780984. write(a); { Será mostrado o valor: 2.3678098400E+00 } write(a:3:2); { Será mostrado o valor: 2.37 } No caso do comando for (para), o contador é atualizado, por padrão, de 1 em 1. Entretanto, esse comando pode ser usado com TO, onde a variável de controle assume valores crescentes e com DOWNTO, onde a variável assume valores decrescentes. Exemplos: for identificador := valor1 to/downto valor2 do { escolher entre to e downto } comando ; { ou bloco de comandos, usando begin e end } Exemplo: fatorial de N (inteiro maior que 1). … readln(N); fat := 1; for I := N downto 1 do fat := fat * I; writeln(‘O fatorial de ’, N:5, ‘ é ’, fat:5); ... 20 ENG06842 – Programação I 8.4. Unidades pré-definidas O Turbo Pascal possui diversas unidades predefinidas: system, printer, crt, dos, overlay e graph são as principais. Os identificadores usados nestas unidades geralmente são formados por palavras compostas em inglês que lembram seu significado. Uma unidade (unit) nada mais é que um conjunto de procedimentos e funções que trabalham sob um mesmo objetivo. É uma coleção de declarações de constantes, tipos, variáveis, funções e procedimentos, compilada separadamente. Algumas destas declarações são de uso interno da unidade, enquanto outras são visíveis, isto é, podem ser usadas por programas ou outras unidades. Por exemplo, a unit graph possui comandos para criação de desenhos, figuras, barras, entre outros; a unit crt possui os procedimentos básicos de entrada e saída de dados e comandos de controle do monitor. Dessa forma, para utilizar uma função criada dentro de uma unidade, deve-se declarar o uso dessa unidade no início do código-fonte (após a definição do nome do programa). Ex: uses crt; A cláusula uses permite que uma unidade faça uso de outras unidades. Para usar uma ou mais unidades, um programa deve conter a cláusula uses antes das declarações de variáveis. A seguir são apresentadas algumas das principais unidades disponíveis no Pascal. system – é a única unidade que não necessita estar na cláusula uses dos programas ou das outras unidades que a utilizarem. Ex.: tipos de constantes e variáveis; comentários; expressões aritméticas, lógicas e literais; funções numéricas predefinidas; funções literais predefinidas; comandos de entrada e saída; comandos de estrutura condicional e de repetição. printer – define um arquivo lst do tipo texto, associado à impressora do computador, permitindo a sua utilização com os comandos write(lst, ...) e writeln (lst, ...). 21 ENG06842 – Programação I crt – oferece diversos recursos para utilizar o vídeo no modo texto, o teclado e o som do computador. Essa unidade é usada em praticamente todos os programas escritos em Pascal. dos – contém constantes, tipos, variáveis, funções e procedimentos relacionados com o sistema operacional. Ex.: obter data e hora; espaço no disco rígido; espaço livre no disco rígido, etc. graph – permite utilizar o vídeo em modo gráfico, define um grande número de constantes, tipos, variáveis, funções e procedimentos. 8.5. Palavras reservadas São palavras que fazem parte da estrutura da linguagem e têm significados pré-determinados. Elas não podem ser redefinidas e não podem ser utilizadas como identificadores. A tabela a seguir apresenta as palavras reservada da linguagem Pascal. absolute end inline procedure type and external interface program unit array file interrupt record until begin for label repeat uses case forward mod set var const function nil shl while div goto not shr with do if of string xor downto implementati on or then else in packed to 8.6. Funções pré-definidas A seguir, são apresentadas algumas funções matemáticas pré-definidas na linguagem Pascal. Função Finalidade Tipo do argumento Tipo do resultado abs(X) valor absoluto integer, real o mesmo do argumento frac(X) parte fracionária real real trunc(X) parte inteira real integer round(X) valor arredondado real integer 22 ENG06842 – Programação I sqr(X) eleva ao quadrado integer, real o mesmo do argumento sqrt(X) raiz quadrada integer, real real ln(X) logaritmo natural real real exp(X) exponencial real real Como não existe em Pascal um operador nem uma função específica para a operação de potenciação, pode-se consegui-la utilizando as funções ln(X) e exp(X). Para calcular o valor de XN é suficiente usar: exp(ln(X)*N) Exemplos: Expressão Resultado abs(-2.5) 2.5 abs(8) 8 frac(5.234) 0.234 trunc(2.78) 2 round(2.78) 3 sqr(2) 4 sqr(1.5) 2.25 sqrt(4) 2 sqrt(2.25) 1.5 exp(ln(2)*3) 8 A seguir, são apresentadas outras funções interessantes disponíveis na linguagem Pascal. val(atr,num,code): a função val tentará converter a string informada na variável atr em um valor numérico (que será armazenado na variável num), seja real ou integer. Caso não seja possível, a variável inteira code retornará a posição de erro encontrada. Exemplo: val(str_idade,val_idade,code); { se str_idade tiver “12a”, code terá 3, ou seja, erro } val(str_idade,val_idade,code); { se str_idade tiver “12”, code terá 0, ou seja, sem erros } str(num,str): a função str converterá o valor numérico informado em uma string. Exemplo: str(val_idade,str_idade); 23 ENG06842 – Programação I keypressed: a função keypressed retornará true caso haja alguma informação no buffer do teclado, ou seja, caso alguma tecla seja pressionada. Caso contrário retornará false. Exemplo: repeat until keypressed; {dará uma pausa no programa até que se pressione alguma tecla} readkey: a função readkey pára a execução do programa até que alguma tecla seja pressionada. É muito utilizada como última instrução de um programa, pois assim o usuário pode ler o que está escrito na tela com calma, e quando terminar, pressiona uma tecla e o programa é encerrado. Exemplo: readkey; odd(num): a função odd retornará true se o valor informado for ímpar (inteiro). Caso contrário retornará false. Exemplo: if odd(num) then write(‘é ímpar’); inc(num,val): a função inc irá incrementar o número informado em 1 (um), caso o segundo parâmetro não seja informado. Se o mesmo for informado, o incremento será de seu valor. Exemplos: inc(x); {o mesmo que x := x+1;} inc(y,5); {o mesmo que y:=y+5;} dec(num,val): a função dec irá decrementar o número informado em 1 (um), caso o segundo parâmetro não seja informado. Se o mesmo for informado, o decremento será de seu valor. Exemplos: dec(x); {o mesmo que x:=x-1;} dec(y,5); {o mesmo que y:=y-5;} ord(car): a função ord retornará o código ASCII (em decimal) da variável car (do tipo char). Exemplo: write(ord(‘a’),ord(‘A’)); {mostrará 97 65, os respectivos códigos ASCII} 24 ENG06842 – Programação I upcase(char): a função upcase retornará o caractere informado em formato maiúsculo. Caso o caractere informado não seja alfabético, o mesmo será retornado como foi informado. Exemplo: write(upcase(‘a’)); {mostrará A} Obs.: para converter um caractere em maiúsculo basta diminuir 32 de seu código ASCII. Exemplo: … write(letra); {‘a’} dec(letra,32); write(letra); {‘A’} … chr(code): a função chr retornará o caractere correspondente ao código ASCII informado.Exemplo: write(chr(97)); {mostrará ‘a’} insert(str,str_destino,pos_inicio): a função insert irá inserir a string str na string str_destino a partir da posição pos_inicio. Somente a variável str_destino será alterada. Exemplo: msg := ‘O Brasil foi penta!’; adic := ‘não’#32; insert(adic,msg,10); write(msg); {‘O Brasil não foi penta!’} delete(str,pos_inicio,quant): a função delete irá eliminar uma string interna a outra string. O primeiro parâmetro é a string, o segundo é a posição inicial, e o terceiro e último a quantidade de caracteres a remover. Somente o primeiro parâmetro será alterado. Exemplo: msg := ‘O Brasil não foi penta!’; delete(msg,10,4); write(msg); {‘O Brasil foi penta!’} concat(str1,str2,...,strN): a função concat retornará a concatenação (união) de todas as strings informadas como parâmetros. O resultado da 25 ENG06842 – Programação I concatenação não pode ultrapassar os 255 caracteres permitidos. Utilize o operador “+” ao invés de concat, pois “+” é mais veloz. Exemplo: msg1:= ‘Linguagem’; msg2:=#32; msg3:= ‘Pascal’; write(concat(msg1,msg2,msg3)); {‘Linguagem Pascal’} É mais rápido usar: write(msg1 + msg2 + msg3); copy(str,pos_inicio,quant): a função copy retornará uma substring a partir de uma string original. A string original é o primeiro parâmetro, a posição inicial de cópia é o segundo e a quantidade de caracteres a serem copiados é o terceiro. Exemplo: msg := ‘A Linguagem Pascal’; write(copy(msg,13,6)); {Pascal} length(str): a função length retornará o comprimento da string, ou seja, seu número de caracteres. Exemplo: msg := ‘A Linguagem Pascal’; write(length(msg)); {18} clrscr: a função clrscr limpará toda a tela; Exemplo: clrscr; textbackground(c): altera a cor de fundo da tela. O parâmetro c pode variar de 0 a 7, e também pode-se usar o nome da cor em inglês. Para alterar a cor de toda a tela deve-se usar o comando clrscr em seguida. Exemplo: textbackground(1); clrscr; { toda a tela ficará azul } textcolor(c): altera a cor do texto. O parâmetro c pode variar de 0 a 15, e também pode-se usar o nome da cor em inglês.. Exemplo: textcolor(10); 26 ENG06842 – Programação I clreol: a função clreol limpará parte da tela, apenas da posição do cursor até o final da mesma linha. Exemplo: clreol; delline: a função delline limpará toda a linha onde estiver o cursor, sem movê-lo. Exemplo: delline; insline: a função insline irá inserir uma linha onde estiver o cursor, sem movê-lo. Todos os dados que estiverem abaixo da posição do cursor serão deslocados para baixo. Caso se queira inserir mais de uma linha, basta colocar essa função dentro de um laço (loop). Exemplo: for x := 1 to 10 do insline; {irá inserir10 linhas a partir da posição do cursor} sound(freq): a função sound irá ativar o auto-falante do micro, bastando apenas informar no parâmetro a freqüência do som desejado. Normalmente utiliza-se esse procedimento com os procedimentos delay e nosound, já que sound sozinho irá ativar o som e o mesmo ficará tocando o tempo todo. Exemplo: sound(200); nosound: a função nosound irá desligar o som do auto-falante do micro. Exemplo: nosound; delay(ms): O procedimento delay irá dar uma pausa na execução do programa, só que diferentemente dos procedimentos já citados, essa pausa se dará por um tempo informado no parâmetro em milisegundos (10-3s). Exemplo: sound(240); delay(1000); {equivale a 1s} nosound; random(num): a função random retornará um valor randômico (aleatório) a partir do número informado. Esse número randômico será um número qualquer na faixa de 0 <= a < num. Caso não seja informado um número, o valor randômico estará na faixa 0 <= a < 1. Normalmente esta função é utilizada com o procedimento randomize. Exemplo: 27 ENG06842 – Programação I random(300); {através de fórmulas internas, será gerado um número entre 0 e 300} randomize: a função randomize irá fazer apenas um pequeno diferencial no uso da função random. Toda vez que se utiliza random, o valor inicial das fórmulas é o mesmo. Portanto, os valores randômicos sempre serão os mesmos. Para que isto não aconteça, basta utilizar o procedimento randomize, o mesmo irá fazer com que o valor inicial das fórmulas de randomização seja baseado na hora do sistema, o que sabemos que muda constantemente. Exemplo: randomize; repeat write(random(500)); delay(50); until keypressed; exit: a função exit irá fazer com que a execução do programa saia do procedimento atual e vá para o seu chamador. Caso o procedimento atual seja o programa principal, exit terminará a execução do programa. Exemplo: if tecla = #27 then exit; { Pressionou ESC, fim } Exemplo: Um programa para ler um número e mostrar se é igual a zero, positivo ou negativo. O fundo de tela deve estar em azul e as letras em amarelo. program teste; uses crt; var num: real; begin textbackground (blue); clrscr; 28 ENG06842 – Programação I textcolor (yellow); write (‘Digite um numero: ’); readln (num); if num = 0 then writeln (‘Igual a zero.’) else if num > 0 then writeln (‘Numero positivo.’) else writeln (‘Numero negativo.’); readkey; end. 8.7. Tipos definidos pelo usuário Os tipos byte, integer, real, boolean, char, etc são pré-definidos em Pascal e constituem conjunto de valores inteiros, reais, lógicos, caractere, etc. O Pascal permite a criação de novos tipos. Um novo tipo é criado através de uma definição que determina um conjunto de valores associados a um identificador. Uma vez definido, o tipo passa a ser referenciado pelo seu identificador. O novo tipo criado pelo usuário também é denominado tipo enumerado. Os identificadores que criamos para um tipo enumerado não representam mais nenhum valor, exceto seus próprios. Os tipos enumerados constituem ferramentas extremamente úteis na criação de programas limpos e auto-documentados, podendo ser referenciados em qualquer parte do programa. Um tipo enumerado é uma seqüência ordenada de identificadores definidos pelo usuário, que forma um tipo ordinal. A palavra reservada para criação de tipos enumerados é type. Exemplo: type semana = (segunda, terça, quarta, quinta, sexta, sábado, domingo); 29 ENG06842 – Programação I Uma das mais importantes características de um tipo enumerado é a ordem na qual os valores são ordenados. Além de estabelecer os próprios identificadores, a declaração do mesmo define a ordem dos identificadores no tipo. Diversas operações são válidas usando os tipos enumerados. Exemplo: program cores; uses crt; type cores = (preto, azul, vermelho, amarelo, verde, rosa, branco, roxo, lilas); var uma_cor: cores; begin clrscr; uma_cor := roxo; {atribuir um identificador a variável de tipo} uma_cor := succ(uma_cor); {receber lilás, o sucessor} uma_cor := pred(uma_cor); {receber roxo novamente, o antecessor} uma_cor := succ(azul); {receber vermelho, sucessor de azul} if succ(uma_cor)>=lilas then uma_cor := preto; writeln(ord(uma_cor)); {escrever 2, a ordem do vermelho} uma_cor := preto; writeln(ord(uma_cor)); {escrever 0, a ordem do preto} for uma_cor := preto to rosa do writeln(ord(uma_cor)); {escrever as posições, do preto ao rosa} end. As variáveis de tipos enumerados não podem ser lidas ou escritas. Não é válida nenhuma operação aritmética com os elementos de um tipo enumerado, como somar 1, diminuir 2 ou somar duas constantes ou mais constantes do tipo. 30 ENG06842 – Programação I Pode-se usar as constantes dos tipos enumerados para servir de índice de vetores/matrizes e também no laço (loop) for. A ordem do primeiro elemento do tipo tem valor0. Um tipo pode ser definido como uma parte de um dado tipo escalar. Esta parte ou faixa define o domínio de um tipo escalar que está associado a um novo tipo, que é chamado de tipo escalar. A definição de uma faixa (subrange) indica quais os valores mínimo e máximo que podem ser assumidos. A descrição de uma faixa se faz com a indicação dos seus limites separados por dois pontos (..), onde o limite inferior deve ser menor que o limite superior. Exemplo: program dias; uses crt; type semana = (seg, ter, qua, qui, sex, sab, dom); {tipo enumerado} coluna = 1..80; {tipo escalar associado: byte} maius = ‘A’..’Z’; {tipo escalar associado: char} d_util = seg..sex; {tipo escalar associado: semana} num = -128..130; {tipo escalar associado: integer} var letra: maius; dia: d_util; begin clrscr; for letra := ‘J’ to ‘P’ do write(letra:2); for dia := seg to sex do case dia of seg: writeln(‘Segunda’); ter: writeln(‘Terça’); qua: writeln(‘Quarta’); qui: writeln(‘Quinta’); other writeln(‘Sexta’); end; readkey; end. 8.8. Exercícios 1. Transforme os algoritmos elaborados nas questões 24 e 25 do Capítulo 4 para a linguagem Pascal. Execute esses algoritmos no computador. 31 ENG06842 – Programação I 2. Transforme os algoritmos elaborados nas questões 1, 2, 5, 6, 10, 11, 12, 13, 14, 15, 16, 17, 24, 25, 26, 27, 28, 29, 30 e 31 do Capítulo 5 para a linguagem Pascal. Execute esses algoritmos no computador. 3. Transforme os algoritmos apresentados ou elaborados nas questões 1, 2 e 3 do Capítulo 6 para a linguagem Pascal. Execute esses algoritmos no computador. 32 ENG06842 – Programação I 9. Estruturas de dados 9.1. Introdução Os tipos estruturados são compostos por múltiplos elementos relacionados entre si. Cada grupo de elementos está relacionado a um identificador. Os elementos do grupo podem estar também relacionados a identificadores individuais, representando vários locais de memória que guardam vários valores, e que podem ser acessados em conjunto ou individualmente. 9.2. Variáveis compostas homogêneas Correspondem a posições de memória, identificadas por um mesmo nome, individualizadas por índices e cujo conteúdo é de mesmo tipo. O conjunto de 10 notas dos alunos de uma disciplina pode constituir uma variável composta. A este conjunto, associa-se o identificador NOTA, que passará a identificar não uma única posição de memória, mas 10. A referência ao conteúdo do n-ésimo elemento do conjunto será indicada pela notação NOTA[n] onde n é um número inteiro ou uma variável numérica contendo um valor inteiro. Exemplo: Supondo que a variável composta NOTA contivesse os seguintes valores: 6 0 7 0 9 0 6 0 5 5 9 1 10 0 4 7 7 4 8 6 1 2 3 4 5 6 7 8 9 10 NOTA[3] estaria referenciando o terceiro elemento do conjunto cujo conteúdo é 90. Vetores (array): definem conjuntos de dados homogêneos (todos os elementos são do mesmo tipo). Cada elemento ocupa uma posição definida no conjunto e pode ser referenciado através dela. Esses conjuntos 33 ENG06842 – Programação I necessitam de apenas um índice para endereçar seus elementos. São conhecidos como Variáveis Compostas Unidimensionais. Declaração de vetores: <identificador>: array [tipo_índice] of tipo_elemento; tipo_índice: é um tipo simples ordenado (inteiro, caractere, booleano, enumerado). É formado por: [li..ls] , onde li: limite inferior e ls: limite superior. Este tipo pode ser utilizado tanto na declaração de variáveis como também na definição de novos tipos. Ex1: var lista: array [1..100] of real; { o identificador do vetor é lista e ele poderá conter 100 elementos do tipo real } Ex2: type indice = 1..100; { tipo definido pelo usuário - tipo subrange } var lista: array [indice] of real; Ex3: type max = 300; vetor = array[1..max] of string[20]; var endereco: vetor; { a variável endereço está associada ao tipo vetor } Ex4: var dados: array[‘A’..’Z’] of integer; Definição de Vetores como constantes: sintaxe geral: 34 ENG06842 – Programação I <identificador_constante>: tipo_array = (lista de valores); Ex1: const vetconst: array [1..3] of integer = (0, 1, 2); Ex2: type vetsemana = array [1..7] of string [3]; const dias_semana: vetsemana = (‘DOM’, ‘SEG’, ‘TER’, ‘QUA’, ‘QUI’, ‘SEX’, ‘SAB’); Obs: Os valores das constantes array de tipo char podem ser especificados ou como valores de caracteres simples ou como um string. Ex: const digito: array [0..9] of char = (‘0’, ‘1’, ‘2’, ‘3’, ‘4’, ‘5’, ‘6’, ‘7’, ‘8’, ‘9’); ou const digito: array [0..9] of char = ‘0123456789’; A manipulação de vetores nos programas Pascal pode ser expressa com uma constante, variável ou expressão, devendo ser do tipo correto (correspondente à definição do array) e estar dentro do intervalo pré- definido. Ex: lista[5] lista[i], onde i é uma variável inteira com valores variando de 1 a 100. lista[i+j], onde i e j são variáveis inteiras cuja soma não ultrapassa 100. Os elementos do ARRAY podem ser usados em expressões, instruções de atribuição, instruções read e write, etc. Exemplo: program exVetor; type vetorNotas = array [1..40] of real; 35 ENG06842 – Programação I var nota: vetorNotas; i: integer; begin i := 1; media := 0; repeat begin write (‘Digite a nota :’); read(nota[i]); media:= media + nota[i]; i:= succ(i); { função que incrementa a variável ⇒ i := i + 1 } end; until i > 40; writeln (‘Notas dos alunos ’); for i:= 1 to 40 do writeln (nota[i]); writeln (‘Media da turma:’, media/40:5:2); end. Matrizes (vetores multidimensionais): também definem conjuntos de dados homogêneos (todos os elementos são do mesmo tipo), entretanto, esses conjuntos necessitam de mais de um índice para endereçar seus elementos. São conhecidos como Variáveis Compostas Multidimensionais (matrizes). Exemplo de matriz bidimensional: 1 2 3 1 1 0 4 7 9 4 2 6 7 9 8 7 4 3 1 6 2 1 3 2 Declaração de matrizes: 36 ENG06842 – Programação I <identificador>: array [dim1,dim2,...] of tipo_elemento; As dimensões são definidas como: dim1 = li1..ls1, dim2 = li2..ls2, etc. Exemplo de declaração de uma matriz TRIDIMENSIONAL: mat3D: array [1..10, 1..20, 1..40] of real; A 1ª dimensão tem 10 elementos, a 2ª tem 20 elementos e a 3ª tem 40 elementos. Todos os elementos são números reais. Matriz BIDIMENSIONAL: mat2D: array [1..5,1..9] of char; É uma matriz bidimensional com 5 elementos do tipo char na 1ª dimensão e 9 na 2ª dimensão. A manipulação de matrizes nos programas em Pascal pode ser expressa com constantes, variáveis ou expressões, devendo ser do tipo correto (correspondente à definição do array) e estar dentro do intervalo pré- definido. Exemplo: mat3D[5,4,8], mat2D[i,9], onde i é uma variável inteira com valores variando de 1 a 5. Os elementos da matriz podem ser usados em expressões, instruções de atribuição, instruções read e write, etc. Exemplo: program Matrizes; var matriz: array [1..20, 1..10] of integer; lin, col: integer; begin for lin := 1 to 20 do for col := 1 to 10 do read (matriz[lin,col]); ... 37 ENG06842 – Programação I Uma matriz também pode ser definida como uma constante, e nesse caso, essa matriz deve ser definida da seguinte forma: type apart = array[1..5,1..2] of string[3]; const num: apart = ((‘101’,’102’), (‘103’,’104’), (‘105’,’106’), (‘107’,’108’), (‘109’,’110’)); { 1ª linha 2ª linha 3ª linha 4ª linha 5ª linha } ... write(num[3,2]); {106} write(num[1,1]);{101} Exemplo: program matriz; uses crt; const alunos: array[1..3,101..103] of string[10] = ((‘Cenira’,’Joana’,’Marcia’), {primeira linha} (‘Lourdes’,’Nágyla’,’Luciana’), {segunda linha} (‘Patrícia’,’Marcos’,’Angélica’)); {terceira linha} var i,j: integer; begin clrscr; for i:=1 to 3 do for j:=101 to 103 do writeln(‘Aluno(a)’,I,’ da turma ‘,j,’: ‘,alunos[i,,j]); {listará por linha} writeln; 38 ENG06842 – Programação I for j:=101 to 103 do for i:=1 to 3 do writeln(‘Aluno(a)’,I,’ da turma ‘,j,’: ‘,alunos[i,,j]); {listará por coluna} readkey; end. Cuidados ao utilizar arrays: Caso o seu limite seja ultrapassado, o programa pode travar e junto com ele o sistema. O Pascal só acusará erro se você tentar atribuir a um vetor um dado qualquer com índice fora da faixa escrita no programa. Mas isso não acontecerá se a origem do índice for alguma expressão. Os tipos array em Pascal são estáticos, ou seja, o comprimento e as dimensões alocadas são fixas em tempo de compilação e não podem ser redefinidas durante a execução do programa. 9.3. Variáveis compostas heterogêneas O principal tipo de variáveis compostas heterogêneas é o registro, que consiste em conjuntos de dados logicamente relacionados, mas de tipos diferentes (numéricos, lógicos, literais, etc). Pode-se definir registros em Pascal na sessão type ou diretamente declarar variáveis do tipo record. a) Declaração na sessão TYPE: type <nome_novo_tipo> = record campo 1: tipo 1; campo 2: tipo 2; … campo n: tipo n; end; 39 ENG06842 – Programação I var <identificador_variavel>: <nome_novo_tipo>; Exemplo: type { Atencao para a indentacao dos campos do registro} funcionario = record nome: string[40]; idade: integer; funcao: string[30]; salario: real; end; var funcionarioUFES: funcionario; b) Declaração na sessão VAR: var <identificador_registro>: record campo 1: tipo 1; campo 2: tipo 2; … campo n: tipo n; end; Ex emplo : var funcionarioUFES: record nome: string[40]; idade: integer; funcao: string[30]; salario: real; end; 40 ENG06842 – Programação I Os campos dos registros podem ser por sua vez de tipos simples ou estruturados (array, registros, etc.). Ex emplo : type estadosBrasil = (AC,AL,AM,AP,BA,CE,DF,ES,GO,MA,MG,MS,MT,PA,PB,PE, PI,PR,RJ,RN,RO,RR,RS,SC,SE,SP,TO); var cliente: record nome: string[50]; endereco: record rua: string [30]; numero: integer; complemento: string [40]; cep: string [10]; cidade: string[20]; estado: estadosBrasil; end; valoresUltimasCompras: array [1..10] of real; end; O acesso aos campos de um registro pode ocorrer de duas formas: a) uso da notação <identifRegistro>.<campo>. Ex: write(‘Digite o nome do funcionario: ’); readln(funcionarioUFES.nome); {acesso ao campo nome } write(‘Digite a funcao do funcionario: ’); readln(funcionarioUFES.funcao); {acesso ao campo funcao } ... b) uso da estrutura with <identif_Registro> do. Ex: with funcionarioUFES do 41 ENG06842 – Programação I begin writeln(‘Dados do funcionario cadastrado’); writeln(‘Nome: ’, nome); writeln(‘Idade: ’, idade); writeln(‘Funcao: ’, funcao); writeln(‘Salario: ’, salario:5:2); end; Exemplo: program exRegistro; var aluno : record { variável aluno do tipo registro } matricula: string[6]; {definição dos campos do registro } nome: string[15]; serie: integer; turma: char; { cada campo tem um nome e um tipo } end; begin write('Numero de matricula: '); readln(aluno.matricula); write('Nome: '); readln(aluno.nome); {acesso ao campo nome do registro aluno} write('Serie: '); readln (aluno.serie); write ('Turma: '); readln (aluno.turma); { comando with indica o registro que será usado - não há necessidade de se colocar begin e end quando se tem apenas um comando na estrutura with } with aluno do write (‘O aluno ’, nome , ‘ estuda na ’, serie, ‘serie!’); 42 ENG06842 – Programação I end. Conjunto de registros: utilizado para armazenar n informações referentes ao mesmo tipo de registro, como, por exemplo, informações de vários funcionários ou vários alunos. Em Pascal, esse tipo de conjunto é definido por um array unidimensional (vetor) de registros. A declaração é dada da seguinte forma: type <tipo_registro> = record campo 1: tipo 1; … campo n: tipo n; end; var <identif_vetor>: array[n..m] of <tipo_registro>; Exemplo: type aluno = record matricula: string[6]; nome: string[15]; serie: integer; end; var vetAlunos: array [1..45] of aluno; A manipulação de conjuntos de registros é dada da seguinte forma: <identif_vetor>[posicao].campo. Ex: for i:= 1 to 45 do begin readln(vetAlunos[i].matricula); readln(vetAlunos [i].nome); readln(vetAlunos [i].serie); 43 ENG06842 – Programação I end; Também pode-se usar a estrutura with. Ex: for i:=1 to 45 do with vetAlunos[i] do begin readln(matricula); readln(nome); readln(serie) end; Exemplo: 44 ENG06842 – Programação I program produtos; uses crt; type produto = record ident: string[3]; descr: string[10]; preco: real; quant: integer; end; var vet_prod: array [1..3] of produto; i: integer; begin clrscr; writeln (‘*** CADASTRO DE PRODUTOS ***’); for i:=1 to 3 do with vet_prod[i] do { vet_prod[i] representa cada elemento do vetor } begin write(‘identificação: ’); readln(ident) ; write(‘descrição: ’); readln(descr) ; write(‘preco: ’); readln(preco) ; write(‘quantidade: ’); readln(quant) end; writeln (‘***** Produtos no Estoque *****’) ; writeln (‘---Identif.----Descricao----Preco----Quantidade---’) ; for i:=1 to 3 do with vet_prod[i] do if quant > 0 then 45 ENG06842 – Programação I write(‘ ’, ident, ‘ ’, descr, ‘ ’, preco:6:2, ‘ ’, quant); end. 9.4. Algoritmos de classificação e busca Algoritmos de classificação : existem diversos métodos para classificar (ou ordenar) uma estrutura de dados. Os mais conhecidos são o “Método da Bolha”, o “Método da Seleção Direta” e o “Método Quick Sort”, porém o mais comum desses é o Método da bolha (Bubble Sort). Exemplo: Método da Bolha para ordenação de um vetor de “nomes de objetos”. program BubbleS; uses crt; const N=5; type letras = string[10]; vet_letras = array[1..N] of letras; var objetos: vet_letras; aux: letras; i, j, cont: integer; begin clrscr; write('>>> Exercicio - Ordenacao de Vetores com metodo da Bolha<<<'); write('Digite ',N,' nomes de objetos para compor o conjunto'); for i:=1 to N do begin write ('Digite o elemento objetos(',i,'): '); readln(objetos[i]); write(' '); end; 46 ENG06842 – Programação I { ***************** Ordenação do Vetor ******************* } for i:= 2 to N do for j:= N downto i do if objetos[j] < objetos[j-1] then begin aux := objetos[j]; objetos[j] := objetos[j-1]; objetos[j-1] := aux end; { ********************* Saida Ordenada ****************** } writeln ('Vetor Ordenado: '); for i:=1 to N do writeln(objetos[i]); end. Algoritmos de busca : também existem diversos métodos para procurar (ou buscar) um valor dentro de uma estrutura de dados. Os mais conhecidos são o “Busca Seqüencial” e o “Busca Binária”, porém o mais comum desses é o Seqüencial. Exemplo: Considere um vetor A com 50 elementos. Verificar se existe um elemento igual a K no vetor. Se existir mostrar a posição em que se encontra, senão imprimir “não encontrei K no vetor”. program Procura_K; uses crt; const max = 10; { Indica onumero maximo de elementos do array num } var i, k: integer; achou: boolean; num: array[1..max] of integer; begin clrscr; writeln('Digite ',max,' numeros inteiros!'); for i:=1 to max do begin write('Digite o elemento (',i,'): '); readln(NUM[i]); 47 ENG06842 – Programação I end; write('Digite o numero que deseja procurar no conjunto: '); readln(k); achou := false; i:=1; while (not achou) and (i<=max) do if num[i]=k then achou := true else i := i+1; if achou then write('Achei o numero ',k,' na posicao (',i,') do vetor !!!') else write('Nao achei o numero ',k,' no vetor !!!'); end. 9.5. Exercícios 1. Elabore um programa que leia dois vetores inteiros de 20 elementos cada, depois some seus elementos, gerando um terceiro vetor. Ao final, mostre o novo vetor gerado. 2. Considere um vetor VET com 30 elementos. Verificar se existe um elemento igual a K no vetor. Se existir mostrar a posição em que se encontra, senão imprimir “não encontrei K no vetor”. 3. Faça um programa para ler um conjunto de 10 inteiros e escreve-los na ordem inversa à ordem de leitura. 4. Faça um programa para ler um conjunto de 10 inteiros e escreve-los na ordem crescente. 5. Elabore um programa que leia um conjunto A com 50 números reais e construa um conjunto B, onde os elementos de ordem (posição) par são os elementos correspondentes de A divididos por 2, e os de ordem (posição) ímpar correspondem aos elementos de A multiplicados por 3. Ao final, mostre os dois conjuntos de números. 6. Fazer um programa Pascal que, ao ser fornecida uma data no formato DD/MM/AA, mostre-a por extenso. Ex: Entrada: 12/06/95; Saída: 12 de junho de 1995. 48 ENG06842 – Programação I 7. Elabore um programa que utilize dois vetores V1 e V2, formados de números reais com 20 posições cada um, e efetue neles as operações indicadas no vetor OP, cujos elementos são caracteres que indicam as quatro operações aritméticas básicas (+, -, *, /) . O resultado obtido das operações devem ser colocados num vetor resultante VR e mostrado ao final do programa. 8. Escreva um programa que leia duas matrizes bidimensionais reais MAT1 e MAT2 de dimensões 3x5 cada, calcule e imprima a matriz soma MSOMA. 9. Calcule e imprima a soma dos elementos situados abaixo da diagonal principal da matriz A (dimensões 10x10), incluindo os elementos da própria diagonal. 10. Escreva um programa que leia duas matrizes reais A e B de dimensões 3x5 e 5x3, respectivamente, calcule e imprima o produto delas. 11. Dada uma matriz A de dimensões 5x4 formada de elementos numéricos reais, calcule e mostre sua matriz transposta T. 12. Dada uma matriz B formada por números inteiros com 10 linhas por 15 colunas, determinar o elemento de maior valor algébrico. Mostre tal elemento e sua posição na matriz (linha e coluna). 13. Faça um programa para ler 2 vetores a e b, de inteiros, e montar o vetor soma = a + b. 14. Faça um programa para multiplicação de matrizes: leia a e b (4x4), crie C = A*B, escreva C. 15. Loteria esportiva. Faça um programa para ler um "gabarito" com os resultados dos jogos da loteria esportiva (coluna 1, coluna2, coluna do meio, 13 jogos), armazenando em um vetor. Depois leia um conjunto indeterminado de jogos e verifique se ganhou o prêmio. Ao final da 49 ENG06842 – Programação I verificação, pergunte se o usuário quer entrar mais jogos. Ao final do programa, informe quantos ganharam o prêmio. 50 ENG06842 – Programação I 10. Modularização 10.1. Introdução Dentre as técnicas de programação estruturada, encontra-se a modularização. Esta técnica consiste em decompor um programa em uma série de subprogramas individuais. A modularização é um método utilizado para facilitar a construção de grandes programas, através de sua divisão em pequenas etapas (dividir para conquistar), que são os módulos ou subprogramas. A primeira delas, por onde começa a execução do trabalho, recebe o nome de programa principal, e as outras são os subprogramas propriamente ditos, que são executados sempre que ocorre uma chamada dos mesmos, o que é feito através da especificação de seus nomes. A modularização permite o reuso de partes do programa num mesmo programa ou mesmo em novos programas, exemplo: imagine um trecho de programa que verifica se uma data é valida ou não. Este módulo pode ser usado várias vezes num mesmo programa que leia várias datas diferentes e pode ser reaproveitado em novos programas que serão escritos. Outras conseqüências positivas do uso de modularização é o aumento de clareza e concisão do programa, pois o comprimento do programa diminui com o uso de módulos. Em Pascal existem dois tipos de módulos de programas: Procedimentos e Funções. Vantagens da utilização de subprogramas: Economia de código: escreve-se menos; Desenvolvimento modularizado: pensa-se no algoritmo por partes; Facilidade de depuração (correção/acompanhamento): é mais fácil corrigir/detectar um erro apenas uma vez do que dez vezes; Facilidade de alteração do código: se é preciso alterar, altera-se apenas uma vez; 51 ENG06842 – Programação I Generalidade de código com o uso de parâmetros: escreve-se algoritmos para situações genéricas. 10.2. Procedimentos Um subprograma do tipo PROCEDIMENTO é, na realidade, um programa com vida própria, mas que, para ser processado, tem que ser solicitado pelo programa principal que o contém, ou por outro subprograma, ou por ele mesmo. Declaração: procedure nome; declaração dos objetos (constantes, variáveis, etc.) locais ao procedimento begin comandos do procedimento; end; Onde: nome é o identificador associado ao procedimento. Exemplo: O programa abaixo calcula a média aritmética entre duas notas, sem o uso de procedimentos. program CALCULA_MEDIA; {sem o uso de procedimentos} var NOTA1,NOTA2,MEDIA : real; begin {lê as notas} write('Digite a primeira nota: '); readln(NOTA1); write('Digite a segunda nota: '); readln(NOTA2); {calcula a media} MEDIA := (NOTA1 + NOTA2) / 2; {escreve o resultado} 52 ENG06842 – Programação I writeln('Media = ',MEDIA,4:1) end. Agora, o mesmo programa, utilizando um procedimento. program CALCULA_MEDIA; {usando procedimento} var NOTA1,NOTA2,MEDIA : real; { declaração do procedimento } procedure LER_NOTAS; begin write('Digite a primeira nota: '); readln(NOTA1); write('Digite a segunda nota: '); readln(NOTA2); end; { programa principal } begin LER_NOTAS; {ativação do procedimento LER_NOTAS} MEDIA := (NOTA1 + NOTA2) / 2; {calcula a media} Writeln('Media = ',MEDIA,4:1) {escreve o resultado} end. 10.3. Funções As funções, embora bastante semelhantes aos procedimentos, têm a característica especial de retornar ao programa que as chamou um valor associado ao nome da função. Esta característica permite uma analogia com o conceito de função da Matemática. Declaração: function nome: tipo; 53 ENG06842 – Programação I declaração dos objetos locais à função begin comandos da função; end; Onde: nome é o identificador associado à função; e tipo é o tipo da função, ou seja, o tipo do valor de retorno. Exemplo: O programa abaixo calcula a média dos elementos de um vetor, sem uso de procedimentos ou funções. program SOMA_VETOR; {sem o uso de procedimentos ou funções} const N = 30; var VETOR: array[1..N] of integer; I,SOMA,MEDIA: integer; begin {lê os valores do vetor} for I:=1 to N do readln(VETOR[I]); {calcula a media} SOMA := 0; for I:=1 to N do SOMA := SOMA + VETOR[I]; MEDIA := SOMA div N; {escreve o resultado} writeln(MEDIA);end. Agora, o mesmo programa, porém utilizando um procedimento para ler os valores do vetor e uma função para efetuar o cálculo da média. program SOMA_VETOR; {usando uma função e um procedimento} 54 ENG06842 – Programação I const N = 30; var VETOR: array[1..N] of integer; { declaração do procedimento } procedure LER_DADOS; var I: integer; begin for I := 1 to N do readln(VETOR[I]); end; { declaração da função } function MEDIA: integer; var I, SOMA: integer; begin SOMA := 0; for I := 1 to N do SOMA := SOMA + VETOR[I]; MEDIA := SOMA div N; end; { programa principal } begin LER_DADOS; {ativa o procedimento LER_DADOS} writeln(MEDIA); {escreve o resultado, chamando a função MEDIA} end. 55 ENG06842 – Programação I 10.4. Escopo de variáveis Observe que, no exemplo anterior, foi declarada uma variável no programa principal e outras nos subprogramas. Pode-se dizer que a variável VETOR, que foi declarada no programa principal é uma variável global aos subprogramas, enquanto que a variável I é dita variável local ao procedimento LER_DADOS e as variáveis I e SOMA são locais à função MEDIA. É importante ressaltar que a variável I do procedimento LER_DADOS é diferente da variável I da função MEDIA, embora possuam o mesmo identificador. O uso de variáveis globais dentro de procedimentos e funções serve para implementar um mecanismo de transmissão de informações de um nível mais externo para um mais interno. As variáveis locais dos procedimentos e funções são criadas e alocadas quando da sua ativação e automaticamente liberadas quando do seu término. A utilização de variáveis globais não constitui, no entanto, uma boa prática de programação. Assim, todos os subprogramas devem apenas utilizar as variáveis locais, conhecidas dentro dos mesmos, e a transmissão de informações para dentro e fora dos subprogramas deve ser feita através dos parâmetros de transmissão, que serão apresentados a seguir. 10.5. Parâmetros Quando se deseja escrever um subprograma que seja o mais genérico possível, deve-se usar a passagem de parâmetros. A passagem de parâmetros formaliza a comunicação entre os módulos. Além disto, permite que um módulo seja utilizado com operandos diferentes, dependendo do que se deseja do mesmo. Dá-se a designação de parâmetro real ou de chamada ao objeto utilizado na unidade chamadora/ativadora, e de parâmetro formal ou de definição ao recebido como parâmetro no subprograma. Dentre os modos de passagem de parâmetros, destaca-se a passagem por valor e a passagem por referência. 56 ENG06842 – Programação I P assagem de parâmetros por valor : as alterações feitas nos parâmetros formais, dentro do subprograma, não se refletem nos parâmetros reais. O valor do parâmetro real é copiado no parâmetro formal, na chamada do subprograma. Assim, quando a passagem é por valor, isto significa que o parâmetro é de entrada. P assagem de parâmetros por referência : toda alteração feita num parâmetro formal corresponde a mesma alteração feita no seu parâmetro real associado. Assim, quando a passagem é por referência, isto significa que o parâmetro é de entrada-saída. Na linguagem Pascal, a declaração dos procedimentos e funções com parâmetros se diferencia da forma já apresentada apenas pela inclusão da lista de parâmetros formais no cabeçalho. Esta deve vir entre parênteses e cada parâmetro deve ter o seu tipo especificado. A forma geral é: procedure nome (lista de parâmetros formais) function nome (lista de parâmetros formais): tipo A lista de parâmetros formais tem a seguinte forma: parâmetro1: tipo; parâmetro2: tipo; ...; parâmetro n: tipo Exemplos da lista de parâmetros: procedure PROC (X, Y, Z: integer; K: real); function FUNC (A, B: real; C: string): integer; Na forma apresentada, a passagem dos parâmetros será por valor. Para se utilizar a passagem por referência, deve-se acrescentar a palavra VAR antes do nome do parâmetro. Exemplo: procedure PROC(A: integer; var B, C: integer); 57 ENG06842 – Programação I Na chamada de procedimentos ou funções utilizando parâmetros, devemos acrescentar após o nome do procedimento ou função uma lista de parâmetros reais (de chamada), os quais devem ser do mesmo tipo e quantidade dos parâmetros formais declarados. O exemplo a seguir demonstra a diferença entre a passagem de parâmetros por referência e a passagem de parâmetros por valor. program EXEMPLO_PASSAGEM_PARAMETROS; var N1, N2 : integer; procedure PROC(X: integer; var Y: integer); begin X := 1; Y := 1; end; begin N1:=0; N2:=0; PROC(N1,N2); writeln(N1); {será exibido o valor 0} writeln(N2); (será exibido o valor 1} end. Exemplo: Escrever um procedimento chamado DOBRA que multiplique um número inteiro (recebido como parâmetro) por 2. Escrever um programa para ler um valor inteiro e, utilizando o procedimento DOBRA, calcular e exibir o dobro do mesmo. program CALCULA_DOBRO; var X: integer; 58 ENG06842 – Programação I procedure DOBRA (var NUM: integer); begin NUM := NUM * 2 end; begin readln(X); DOBRA(X); writeln(X); end. Exemplo: Escrever uma função chamada MAIOR que receba dois números inteiros e retorne o maior deles. Escrever um programa para ler dois números inteiros e, utilizando a função MAIOR, calcular e exibir o maior valor entre os números lidos. program CALCULA_MAIOR; var X, Y, M: integer; function MAIOR (NUM1, NUM2: integer): integer; begin if NUM1 > NUM2 then MAIOR := NUM1 else MAIOR := NUM2; end; begin readln(X,Y); M := MAIOR(X,Y); writeln(M); end. 59 ENG06842 – Programação I Exemplo: Escreva um procedimento que receba uma string S e converta o mesmo para letras maiúsculas. procedure MAIUSC (var S: string); var I, TAM: byte; begin TAM := length(S); for I := 1 to TAM do S[I] := upcase(S[I]); end; 10.6. Recursividade 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. Por exemplo, o fatorial de um número n pode ser definido recursivamente, ou seja: = >− = 0 n se1 0 n se1)!(nn !n Dessa forma, pode-se escrever uma função recursiva em Pascal que traduz esta definição matemática: function FAT(n: integer): integer; begin if n = 0 then FAT := 1 else FAT := N * FAT(N-1); end; 10.7.Exercícios 1. Cite as principais vantagens da utilização de subprogramas. 60 ENG06842 – Programação I 2. Conceitue procedimento e função. Em que eles são semelhantes e em que eles são diferentes? 3. Que tipo de informação deve ser incluído na declaração de um procedimento? E na declaração de uma função? Se houver diferenças, explique o motivo. 4. Qual a diferença entre variável global e variável local? 5. Como deve ser feita a transmissão de informações entre um subprograma e o programa principal? 6. Qual a diferença entre parâmetro real e parâmetro formal? 7. Cite os modos de passagem de parâmetros, explicando como funciona cada um deles. 8. Escreva um procedimento que limpe a tela do micro e exiba o seu nome. 9. Escreva um procedimento que receba uma string S e um inteiro positivo N e exiba a string S por N vezes seguidas na tela. 10. Escreva uma função chamada CUBO que receba um valor do tipo real e retorne a potência elevado a 3 do mesmo. 11. Escreva um procedimento chamado TROCA que receba duas variáveis inteiras (X e Y) e troque o conteúdo entre elas; 12. Escreva uma função que receba uma string S e retorne o número de espaços existentes na mesma.
Compartilhar