Logo Passei Direto
Buscar
Material
details

Libere esse material sem enrolação!

Craque NetoCraque Neto

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

details

Libere esse material sem enrolação!

Craque NetoCraque Neto

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

details

Libere esse material sem enrolação!

Craque NetoCraque Neto

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

details

Libere esse material sem enrolação!

Craque NetoCraque Neto

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

details

Libere esse material sem enrolação!

Craque NetoCraque Neto

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

details

Libere esse material sem enrolação!

Craque NetoCraque Neto

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

details

Libere esse material sem enrolação!

Craque NetoCraque Neto

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

details

Libere esse material sem enrolação!

Craque NetoCraque Neto

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

details

Libere esse material sem enrolação!

Craque NetoCraque Neto

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

details

Libere esse material sem enrolação!

Craque NetoCraque Neto

Ao continuar, você aceita os Termos de Uso e Política de Privacidade

Prévia do material em texto

Introdução à Programação com Python 
 
 
 
 
 
 
 
 
(Versão 2.0 - Revisada para uso no Semestre 2024-2. O texto não passou por nenhuma 
revisão profissional. 
Assim, correções serão muito bem vindas!!! 
 
Envie as correções/sugestões para: goulart@ufv.br 
 
Meus agradecimentos antecipados!!!) 
 
 
 
 
 
 
 
 
 
 
 
 
 
Carlos de Castro Goulart 
Departamento de Informática 
Universidade Federal de Viçosa 
2023 
 
 
mailto:goulart@ufv.br
 Introdução à Programação com Python 
 
 
 
 
 
 
 
Licença de uso: este texto pode ser copiado e distribuído livremente para uso não 
comercial, mantendo sempre a informação sobre a autoria. 
 
 
 
 
 
 
1 
 Introdução à Programação com Python 
 
Introdução à Programação com Python 0 
Prefácio 4 
Capítulo 1 - Introdução 6 
1.1. Motivação - por que aprender programação? 6 
1.2. Arquitetura do computador e o Sistema Operacional 7 
1.3. Algoritmos e linguagens de programação 11 
1.4. O ambiente de programação no LBI 15 
1.4.1 - Home Python 23 
1.5. Exercícios 24 
Capítulo 2 - Algoritmos 26 
2.1 Definição de Algoritmo 26 
2.2 Algoritmo computacional e não computacional 26 
2.3. Propriedades de um algoritmo 27 
2.4. Refinamento sucessivo e estruturas de programação 28 
2.4.1 Eliminando ambiguidades 29 
2.4.2. Refinamento do Algoritmo 30 
2.5 - Estrutura de comando condicional 32 
2.6 - Estrutura de comando repetitivo 34 
2.7. Comandos aninhados e rastreio do algoritmo 37 
2.8. Viva a diferença 42 
2.9. Exercícios 43 
Capítulo 3 - Variáveis e Operadores 45 
3.1 - Variáveis 45 
3.1.1. Comando de Atribuição 48 
3.1.2. Tipos de Variáveis 50 
3.2 Operadores e Expressões 54 
3.2.1. Operadores e Expressões aritméticas 54 
3.2.2. Operadores e Expressões Lógicos 58 
3.2.2.1 - Operador não (not) 58 
3.2.2.2 - Operador e (and) 59 
3.2.2.3 - Operador ou (or) 59 
3.2.2.4 - Expressões lógicas 60 
3.2.2.5 Equivalência de Expressões Lógicas 62 
3.3. Exercícios 65 
Capítulo 4 - Comandos de Entrada e Saída 68 
4.1 - Comando de Saída 68 
4.1.1 - Forma básica do comando de saída 68 
4.1.2. Comando print() com separador e terminador 70 
4.1.3. Comando print() com apenas um parâmetro de texto 72 
2 
 Introdução à Programação com Python 
4.1.4. Formatação de dados no comando print() 74 
4.2 - Comando de Entrada 77 
4.3 - Usando os comandos de entrada e saída em programas simples 79 
4.3.1. Cálculo da área de um triângulo 79 
4.3.2. Cálculo das raízes de uma equação do segundo grau 82 
4.4. Exercícios 83 
Capítulo 5 - Comandos Condicionais 89 
5.1. Comando if 89 
5.2 Comando if-else 92 
5.3 Comando if-elif-else 94 
5.4 Cálculo de raízes de uma equação do 2⁰ grau 98 
5.5. Exercícios 100 
Capítulo 6 - Comandos Repetitivos 105 
6.1. Comando while 105 
6.1.1. Cuidado com o loop infinito 107 
6.1.2. Número determinado de repetições com o while 109 
6.1.3. Usando while-True 111 
6.2. Comando for 112 
6.2.1. Comando for 113 
6.2.2. Comando for com incremento não unitário 114 
6.2.3. Comando for-break 117 
6.3. Alguns exemplos de uso de comandos repetitivos 118 
6.3.1. Cálculo de média 118 
6.3.2. Números Primos 122 
6.3.3. Cálculo de raiz quadrada 124 
6.4. Exercícios 126 
Capítulo 7 - Arranjos 132 
7.1. Arranjo unidimensional 133 
7.1.1 Arranjos em Python 135 
7.1.2 Percorrendo Arranjos 137 
7.1.3. Alguns Exemplos 139 
7.1.3.1. Cálculo do desvio-padrão 139 
7.1.3.2. Relação entre vizinho 141 
7.2. Arranjos multidimensionais 143 
7.2.1. Definição de arranjos bidimensionais em Python 145 
7.2.2. Exemplos usando matrizes 146 
7.2.2.1. Pesquisa em matriz 146 
7.2.2.2. Verificação de propriedades de uma matriz 149 
7.2.3. Arranjos e Processamento de Imagens 153 
7.3. Exercícios 158 
3 
 Introdução à Programação com Python 
Capítulo 8 - Funções 164 
8.1. Motivação 164 
8.2. Funções em Python 165 
8.2.1. Identificando candidato a virar função 166 
8.2.2. Função que retorna dois (ou mais) parâmetros 169 
8.3. Escopo de Variáveis 170 
8.4. Passagem de arranjos como parâmetro 173 
8.5. De volta aos algoritmos 173 
8.6. Exercícios 176 
 
 
4 
 Introdução à Programação com Python 
Prefácio 
Este material tem o objetivo de servir de apoio para os estudantes matriculados na 
disciplina de Introdução à Programação I, oferecida pelo Departamento de Informática da 
UFV, e sua primeira versão foi gerada nos primeiros meses de interrupção das aulas, em 
função da pandemia da Covid-19, no ano de 2020. A ideia de elaboração deste material 
surgiu a partir da constatação de haver pouquíssimos livros sobre a linguagem de 
programação Python em nossas bibliotecas. 
De fato, com a grande quantidade de material sobre a linguagem de programação 
Python disponível na Internet, talvez a melhor opção seja não gastar recursos públicos para 
a aquisição de livros. Porém, os estudantes muitas vezes tem dificuldade de “pinçar” a parte 
que interessa, por estar sendo apresentada na disciplina. Muitos livros e materiais 
disponíveis na Internet partem do pressuposto de que o leitor já possui noções de 
programação. Ou apresentam de início assuntos mais avançados que serão abordados 
apenas na disciplina INF 101 - Introdução à Programação II, como a estrutura de dados de 
listas. 
Assim, este material foi elaborado para seguir exatamente a sequência de assuntos 
apresentados em sala de aula. Por isso, este material terá uma versão eletrônica 
disponibilizada no PVANet no espaço reservado para a disciplina INF 100 - Introdução à 
Programação I, sem custos para os estudantes da UFV. O objetivo é ter um material de 
apoio com texto mais detalhado do que o dos slides exibidos em sala de aula. 
O texto está organizado da seguinte forma: o capítulo 1 apresenta uma breve 
introdução sobre a programação de computadores e motivação para o seu aprendizado, 
uma vez que a programação está cada vez mais presente na vida profissional; no capítulo 2 
é apresentado o conceito de algoritmo e alguns exemplos não computacionais, para, 
posteriormente, ser apresentado em pseudo-linguagem já com o intuito de tradução para a 
linguagem de programação Python; o conceito de variável e os principais operadores da 
linguagem Python são apresentados no capítulo 3; o capítulo 4 apresenta os comandos de 
entrada e saída; a estrutura dos comandos condicionais é apresentada no capítulo 5; o 
capítulo 6 apresenta as primeiras estruturas de comandos repetitivos; no capítulo 7 a 
estrutura de dados de arranjos unidimensionais e arranjos bidimensionais (matrizes) com 
ênfase em algoritmos para manipulação de imagens; como últimos tópicos abordados na 
disciplina, as funções e escopo de variáveis são apresentados no capítulo 8. 
Para ajudar no aprendizado de qualquer linguagem é fundamental a prática pois 
muitos erros são identificados de forma automática pela ferramenta de programação, como 
é o caso do interpretador da linguagem Python. Além disso, a implementação de uma 
solução usando uma ferramenta permitirá a visualização da solução, permitindo conferir sua 
correção e, eventualmente, sua eficiência. Fica como sugestão uma visita à página do 
projeto Python Brasil (https://python.org.br) onde você poderá encontrar informações sobre 
diferentes ambientes de programação para a linguagem Python. Para os alunos 
matriculados na disciplina INF 100 - Introdução à Programação I, haverá links para 
5 
https://python.org.br/onde
 Introdução à Programação com Python 
materiais de apoio como interpretadores Python para instalar em seu computador, páginas 
de programação onde você pode enviar ea um e alternado com o queijo. Como na 
receita são dois ovos, o acréscimo de queijo ralado será feito em duas partes de 200g. 
 
Modo de Preparo 
1. Coloque 500g de polvilho em uma tigela grande. 
2.1 Misture em uma panela 10g de sal, 300ml de leite e 150ml de óleo. 
2.2. Aqueça a mistura até ferver 
3.1. Jogue a mistura fervendo sobre o polvilho 
3.2. Mexa até desfazer as pelotinhas. 
4. Deixe esfriar por 20 minutos. 
5.1. Acrescente um ovo 
5.2. Acrescente 200g de queijo ralado 
5.3. Bata até a mistura ficar homogênea 
5.4. Acrescente um ovo 
5.5. Acrescente 200g de queijo ralado 
5.6. Bata até a mistura ficar homogênea 
6. Unte as mãos com óleo, se necessário. 
7. Enrole bolinhos de 2 cm de diâmetro e coloque-os em uma assadeira untada. 
8. Leve ao forno médio (180º C), preaquecido. 
9. Asse até ficarem douradinhos. 
Figura 2.1 - Algoritmo versão 2 
 
 Note que a versão 2 já está mais detalhada com o refinamento das ações 2, 3 e 5 e, 
como consequência, o número de ações quase dobrou. Entretanto, algumas ações ainda 
não estão definidas como ações únicas, o que dificultaria a execução do algoritmo por parte 
de um robô. Por exemplo, a ação 2 que já foi desmembrada nas ações 2.1 e 2.2 poderia ser 
mais refinada ainda, nas seguintes ações mostradas na Figura 2.2. 
 
 
2.1.1. Coloque 300ml de leite na panela 
2.1.2. Acrescente 150ml de óleo na panela. 
2.1.3. Acrescente 10g de sal 
2.1.4.. Misture os ingredientes na panela 
2.2.1. Acenda uma das trempes do fogão 
2.2.2. Coloque a panela com a mistura na trempe acesa 
2.2.3. Aqueça a mistura até ferver 
Figura 2.2 - Algoritmo versão 2 
 
A versão 3 do algoritmo apresenta todas as ações refinadas, explicitando ações que 
antes estavam implícitas, como acender uma das trempes no passo 2 e ligar o forno para 
que ele esteja pré-aquecido no momento de executar a ação 8. Está sendo suposto que o 
tempo de pré-aquecimento é o tempo que se gastaria para enrolar os pães de queijo e 
colocá-los no tabuleiro. Acender o forno para o pré-aquecimento foi inserida como a 
34 
 Introdução à Programação com Python 
operação de número 6 e, consequentemente, forçou a renumeração das ações seguintes. A 
Figura 2.3 apresenta a versão 3 do algoritmo. 
 
Modo de Preparo 
1. Coloque 500g de polvilho em uma tigela grande. 
2.1.1. Coloque 300ml de leite na panela 
2.1.2. Acrescente 150ml de óleo na panela. 
2.1.3. Acrescente 10g de sal 
2.1.4.. Misture os ingredientes na panela 
2.2.1. Acenda uma das trempes do fogão 
2.2.2. Coloque a panela com a mistura na trempe acesa 
2.2.3. Aqueça a mistura até ferver 
3.1. Jogue a mistura fervendo sobre o polvilho 
3.2. Mexa até desfazer as pelotinhas. 
4. Deixe esfriar por 20 minutos. 
5.1. Acrescente um ovo 
5.2. Acrescente 200g de queijo ralado 
5.3. Bata até a mistura ficar homogênea 
5.4. Acrescente um ovo 
5.5. Acrescente 200g de queijo ralado 
5.6. Bata até a mistura ficar homogênea 
6. Acenda o forno para pré-aquecimento 
7. Unte as mãos com óleo, se necessário. 
8.1 Untar uma assadeira 
8.2 Enrole bolinhos de 2 cm de diâmetro 
8.3 Coloque-os em uma assadeira untada. 
9. Leve a assadeira ao forno médio (180º C). 
10. Asse até ficarem douradinhos. 
Figura 2.3 - Algoritmo versão 3 
 
 Embora esteja sendo usada a numeração, ela é dispensável. Como se está 
tratando de estrutura de comandos sequenciais, é suposto que os comandos serão 
executados na sequência em que eles foram escritos, linha após linha, uma linha de cada 
vez. Porém, será mantida a numeração por mais algum tempo. 
 
2.5 - Estrutura de comando condicional 
 
 A versão 3 do algoritmo apresentado na Figura 2.3 possui apenas comandos 
sequenciais. Entretanto, existe pelo menos um comando que implicitamente é uma estrutura 
condicional: “7. Unte as mãos com óleo, se necessário”. Note que existe uma condição para 
que o operador humano unte as mãos. A pessoa só deve untar as mãos se necessário. 
Note que na lista de ingredientes, a quantidade de óleo é de 200ml e para a mistura são 
necessários 150 ml. Desta forma, os 50 ml restantes poderiam ser usados para untar as 
35 
 Introdução à Programação com Python 
mãos. Mas somente, se necessário. Portanto, é preciso ter uma estrutura que permita 
executar condicionalmente uma ação. 
 
 Um comando condicional é uma estrutura das linguagens de programação na qual 
existe um teste de uma condição que é feito antes de executar o comando. O comando 
somente será executado no caso da condição testada ser verdadeira. A forma geral de um 
comando condicional é a mostrada na Figura 2.4. 
 
se 
 
Figura 2.4 - Estrutura do comando condicional 
 
 A representa a condição a ser verificada ou o teste a ser feito. O 
resultado do teste da condição só pode ter dois valores: verdadeiro ou falso. 
representa o comando que será executado somente no caso do resultado do teste ter sido 
verdadeiro. Note que está deslocado para a direita indicando que sua 
execução está vinculada à cláusula “se”, que corresponde ao caso da condição testada ser 
verdadeira. Este deslocamento é chamado de indentação. 
 
O pode ser, na verdade, um bloco com um ou mais comandos, onde 
todos os comandos do bloco seriam executados somente quando o teste for verdadeiro. 
 
 De acordo com a regra de indentação, o próximo comando, após o comando 
condicional, deve ser escrito alinhado com o “se”. Isso indica a sequência de execução do 
programa. Desta forma, um comando condicional nada mais seria do que um comando 
sequencial, mas que só será executado quando a condição avaliada for verdadeira. Em 
outras palavras, a condição sempre é testada (característica de comando sequencial), mas 
o bloco de comandos condicionais será executado apenas quando o resultado do teste for 
verdadeiro. 
 
 No caso do algoritmo em discussão, o teste a ser feito é verificar se a massa do pão 
de queijo ficou grudenta (ou não). Se a massa estiver grudenta (resultado verdadeiro), é 
necessário que a mão seja untada de óleo para a massa não ficar agarrando na palma da 
mão, enquanto cada pão de queijo vai sendo enrolado. No caso do teste ser falso (massa 
não ficou grudenta), a ação de untar a mão não será executada, pois não é necessária. A 
Figura 2.4 mostra como ficaria o comando 7 da versão 3 do algoritmo. 
 
 
7. se “massa está grudenta”: 
 7.1. Unte as mãos com óleo 
Figura 2.5 - Exemplo de comando condicional 
 
Em alguns casos é desejado executar uma ação no caso da condição ser verdadeira 
ou uma ação diferente no caso da ação ser falsa. Isto não é possível com a estrutura da 
36 
 Introdução à Programação com Python 
Figura 2.3 onde existe apenas um comando (ou bloco de comandos) que só é executado no 
caso do teste ser verdadeiro. Quando o teste é falso, passa-se para a execução do próximo 
comando sequencial (comando 8, no caso do algoritmo da Figura 2.3). 
 
A Figura 2.6 apresenta a estrutura do comando condicional que também permite a 
especificação de um comando (ou bloco de comandos) associados ao resultado negativo do 
teste. 
 se 
 
 senão 
 
Figura 2.6 - Estrutura de comando condicional com cláusula “senão” 
 
Para este tipo de comando condicional, se a condição for verdadeira apenas o 
 será executado e se a condição for falsa apenas o será 
executado. Como o resultado do teste só pode assumir estes dois valores (verdadeiro ou 
falso), e nunca serão executados juntos. Ou será 
executado (se condição for verdadeira) ou será executado (caso contrário ou 
se condição for falsa). 
 
A cláusula “senão” deixa explícito que o está associado ao casoda 
condição ser falsa. Note que tanto o comando (ou bloco de comandos) vinculados ao caso 
do teste verdadeiro (cláusula “se”), como o comando (ou bloco de comandos) do teste falso 
(cláusula “senão”) ficam deslocados para a direita, indicando a vinculação ao respectivo 
resultado do teste (verdadeiro ou falso). 
 
Este deslocamento (indentação) aparecerá também nos comandos repetitivos que 
serão vistos na próxima seção. A indentação é importante para deixar claro quais são os 
comandos que pertencem a cada bloco. Algumas linguagens de programação são mais 
exigentes com a indentação, como é o caso da linguagem Python, conforme será visto a 
partir do capítulo 3. 
 
No algoritmo versão 3 ainda há uma ambiguidade que será resolvida para 
exemplificar o uso da estrutura de comando condicional da Figura 2.6. A ação “5.1. Adicione 
um ovo” para ser executada por um robô não estaria suficientemente detalhada e poderia 
resultar em uma massa com fragmentos de casca de ovo. Além disso, para quem costuma 
fazer ovo frito ou omelete, já pode ter passado pela experiência de quebrar um ovo choco. 
Desta forma um refinamento necessário seria incluir uma condição para testar se o ovo 
pode ser usado ou não, como mostrado na Figura 2.7. 
 
 No exemplo da Figura 2.7, se o teste for verdadeiro o bloco de dois comandos 
(“Jogue o ovo na lixeira” e “Lave a tigela pequena”) será executado. Se o teste for falso, 
apenas o comando “Adicione o ovo da tigela pequena” será executado. Note que a 
numeração do primeiro comando de cada bloco é a mesma (5.1.3.1.), exatamente porque 
um dos dois será executado logo após o teste feito (5.1.3). Cada teste realizado na cláusula 
37 
 Introdução à Programação com Python 
“se”, na verdade, é uma execução de operação feita pelo processador, quando se trata de 
um programa. 
 
5.1.1. Quebre um ovo em uma tigela pequena 
5.1.2. Jogue a casca do ovo na lixeira 
5.1.3. se “ovo está choco” 
 5.1.3.1. Jogue o ovo na lixeira 
 5.1.3.2. Lave a tigela pequena 
 senão 
 5.1.3.1. Adicione o ovo da tigela pequena 
Figura 2.7 - Exemplo de comando condicional com cláusula “senão” 
 
 Importante chamar a atenção, mais uma vez, que a sequência de ações sempre é 
importante para se chegar à solução correta do problema. Quebrar o ovo na tigela e jogar a 
casca fora são tarefas que sempre tem que ser feitas. Portanto são comandos sequenciais. 
E devem ser executadas na ordem em que foram escritas! Se inverter a ordem… a massa 
não terá ovos. 
 
 Também é importante distinguir tarefas (ou ações) que são sequenciais das tarefas 
condicionais. Escrever uma mesma ação no bloco “se” e também no bloco “senão” é um 
erro do ponto de vista lógico. Considere, por exemplo, que o trecho de algoritmo mostrado 
na figura 2.7 fosse reescrito assim: 
 
5.1.1. Quebre um ovo em uma tigela pequena 
5.1.2. se “ovo está choco” 
 5.1.2.1. Jogue a casca do ovo na lixeira 
 5.1.2.2. Jogue o ovo na lixeira 
 5.1.2.2. Lave a tigela pequena 
 senão 
 5.1.2.1 Jogue a casca do ovo na lixeira 
 5.1.2.2. Adicione o ovo da tigela pequena 
Figura 2.8 - Erro de uso de ação sequencial em comando condicional 
 
A ação “Jogue a casca do ovo na lixeira” será executada sempre, independente do 
resultado da condição testada. E, de fato, a casca do ovo sempre deve ser descartada. 
Logo, é uma ação sequencial e não deve estar em um comando condicional. Muitos 
programadores inexperientes costumam cometer este tipo de erro, replicando blocos de 
comandos, às vezes enormes, nas duas cláusulas (se/senão) de um comando condicional. 
 
As estruturas de comando condicional podem ser mais poderosas, permitindo a 
inclusão de outras cláusulas de teste. Porém, para solucionar o problema de gerar um 
algoritmo para a receita de pão de queijo, as duas estruturas apresentadas são suficientes. 
Algumas linguagens de programação implementam essas estruturas de comando 
38 
 Introdução à Programação com Python 
condicional compostas, como é o caso da linguagem Python. Essas estruturas serão 
apresentadas no Capítulo 5. 
 
2.6 - Estrutura de comando repetitivo 
 
No algoritmo, versões 2 e 3 existe uma sequência de 3 ações que é repetida duas 
vezes, relacionada com a adição do ovo na receita: “Acrescente um ovo”; “Acrescente 200g 
de queijo ralado”; e “Bata até a mistura ficar homogênea”. Imagine se a receita precisasse 
de 10 ovos ao invés de 2 ovos. Ou, em outro problema, em que uma tarefa tivesse que ser 
executada 1.000 vezes. O algoritmo ficaria imenso. 
 
Para resolver este problema utiliza-se a estrutura do comando repetitivo Enquanto, 
mostrada na Figura 2.9. Apesar de ter sido utilizada uma marcação de final do comando 
repetitivo, o deve ser deslocado à direita, seguindo a regra de indentação de 
blocos. 
 
Enquanto 
 
Fim_Enquanto 
Figura 2.9 - Estrutura de comando repetitivo Enquanto 
 
A é avaliada antes da execução do comando e, assim como no caso do 
comando condicional, o resultado da avaliação só pode ser verdadeiro ou falso. No caso do 
resultado ser verdadeiro, o (ou bloco de comandos) é executado uma vez. 
Após a execução, chegando ao fim do comando repetitivo (marcado pelo “Fim_Enquanto), 
volta-se ao teste da condição que é feito novamente. No caso do resultado do teste ser 
verdadeiro, novamente, o comando repetitivo será executado pela segunda vez. Esta 
execução se repetirá enquanto a condição testada continuar dando resultado verdadeiro. 
 
Quando o resultado da condição testada é falso, o comando repetitivo termina, 
passando para a execução do próximo comando sequencial. Caso o teste da condição dê 
resultado falso na primeira vez, o comando repetitivo não será executado. Portanto, esta 
estrutura fará com que o comando repetitivo seja executado zero ou mais vezes. 
 
 Muitas vezes é necessário definir (ou inicializar) uma informação de controle para 
forçar a entrada no comando repetitivo e, dentro do bloco de comandos repetitivos modificar 
a condição de controle para que o número de repetições do comando seja o desejado. 
 
 Considerando as 3 ações (“Acrescente um ovo”; “Acrescente 200g de queijo ralado”; 
e “Bata até a mistura ficar homogênea”) que tem que ser executadas 2 vezes, a informação 
de controle será o número de ovos adicionados na receita. Inicialmente, o número de ovos 
na receita é igual a zero e a cada vez que um ovo for acrescentado, o número de ovos da 
39 
 Introdução à Programação com Python 
receita deve ser incrementado. A Figura 2.10 mostra um exemplo com um comando 
repetitivo para o caso do algoritmo do pão de queijo. 
 
NumeroDeOvosNaReceita = 0 
Enquanto NumeroDeOvosNaReceitaassumindo o valor 2. Com este valor, agora o teste “NumeroDeOvosNaReceita até 
 
fim_para 
Figura 2.11 - Estrutura de comando repetitivo para 
 
 Para o exemplo do algoritmo do pão de queijo, o comando repetitivo da Figura 2.10 
pode ser reescrito usando a estrutura do comando repetitivo “para”. 
 
para NumeroDeOvosNaReceita = 0 até 2 
 Acrescente um ovo 
 Acrescente 200g de queijo ralado 
 Bata até a mistura ficar homogênea 
fim_para 
Figura 2.12 - Exemplo de uso do comando repetitivo para 
 
 Neste tipo de estrutura o valor inicial da variável de controle “NumeroDeOvosNa 
Receita” terá valor inicial igual a zero e será incrementado automaticamente ao final do 
bloco de comandos repetitivos. Quanto o valor chegar a 2, o comando repetitivo termina. 
Nesta notação se supõe que para o valor final, o comando não será executado. Assim, o 
comando será repetido 2 vezes, para os valores da variável de controle iguais a 0 e 1. 
Dependendo da linguagem de programação, esta suposição pode não ser válida. 
Entretanto, para a linguagem Python que será usada nos capítulos seguintes, o significado 
do comando repetitivo no estilo “para” é exatamente a descrita aqui. 
 
 
2.7. Comandos aninhados e rastreio do algoritmo 
 
 Conforme foi dito anteriormente, as três estruturas de comando vistas nas seções 
anteriores (sequencial, condicional e repetitiva) são suficientes para escrever qualquer 
programa. Em geral, uma descrição de alto nível (ou primeira versão) do algoritmo poderia 
conter apenas comandos sequenciais. Entretanto, ao detalhar a solução, alguns comandos 
que pareciam ser sequenciais são quebrados em dois ou mais comandos e, eventualmente, 
em comandos condicionais ou comandos repetitivos. 
 
 Neste ponto, é importante ressaltar que é possível utilizar comandos condicionais e 
repetitivos aninhados, ou seja, um dentro do outro. Para exemplificar esta utilização, 
considere a estrutura definida na Figura 2.10 que utilizou a forma do comando repetitivo 
“Enquanto”. Note que a operação de acrescentar um ovo não considera a possibilidade de 
ter um ovo choco, como o refinamento apresentado na Figura 2.7. Note que para este caso, 
a estrutura do comando repetitivo “Enquanto” é mais adequada do que a estrutura do 
comando repetitivo “para”, pois não se sabe a priori se há algum ovo choco. 
41 
 Introdução à Programação com Python 
 
Há também, na Figura 2.10, um comando repetitivo implícito, ou que não foi refinado 
ainda: “Bata até a mistura ficar homogêneo”. A operação que é possível executar é bater a 
massa usando uma batedeira, enquanto que o “até a mistura ficar homogênea” nada mais é 
do que um teste visual para aferir se a operação bater deve prosseguir ou não. A Figura 
2.13 apresenta o trecho do algoritmo com os refinamentos discutidos nesta seção. 
 
NumeroDeOvosNaReceita = 0 
Enquanto NumeroDeOvosNaReceitaBata a mistura 
 Fim_Enquanto 
Fim_Enquanto 
 
a) “ovo choco” é verdadeiro 
 
b) “ovo choco” é falso. 
Figura 2.14 - Possíveis fluxos de execução dependendo da condição “ovo está choco” 
 
Para verificar se o algoritmo está correto ou apresentando o comportamento 
esperado podemos simular a sua execução. Para tanto, será necessário supor o 
fornecimento de valores de entrada para a execução de cada operação do algoritmo e a 
verificação das eventuais modificações no estado de cada objeto do algoritmo. A esta 
simulação da execução é dado o nome de rastreio. O rastreio pode ser aplicado para um 
algoritmo ou para um programa. 
 
Suponha que no momento de adicionar os ovos na receita, o primeiro ovo estará 
bom, mas o segundo estará choco. Isso demandará um terceiro ovo que, em nossa 
simulação, estará bom. Além dos ovos, as porções de queijo ralado estarão também à 
disposição. Os ovos e as porções de queijo são as entradas necessárias para a execução 
do trecho do algoritmo da figura 2.13. Para realizar o rastreio vamos analisar a sequência 
de comandos que serão executados para os nossos dados de entrada. 
 
Observe que o primeiro comando (NumeroDeOvosNaReceita = 0) será sempre 
executado pois trata-se de um comando sequencial e atribui o valor zero para o número de 
ovos já adicionados à receita. 
 
O segundo comando é um comando repetitivo que será executado enquanto o 
número de ovos na receita for menor do que 2. No estado atual, no qual o número de ovos 
na receita é zero, o bloco de comandos repetitivos será executado. 
 
Os dois primeiros comandos, dentro do bloco repetitivo, são sequenciais. Portanto, 
eles sempre serão executados, para quebrar o ovo e colocá-lo em uma tigela para testá-lo, 
no comando seguinte. 
 
43 
 Introdução à Programação com Python 
Na nossa simulação o primeiro ovo está bom (não choco) e o bloco a ser executado 
no comando condicional é o bloco “senão”, no qual o ovo será adicionado juntamente com 
uma porção de queijo ralado e misturados até que a mistura fique homogênea, conforme 
detalhado na Figura 2.14.b. Porém, o comando mais importante do ponto de vista do 
rastreio é o que faz o incremento do número de ovos na receita que passará de 0 (zero) 
para 1. Este comando é o que poderá, em algum momento, tornar a condição do comando 
repetitivo principal (NumeroDeOvosNaReceita ), ficando “Enquanto NumeroDeOvosNaReceita > 2”, o que 
aconteceria com a execução do algoritmo? Neste caso, como a condição seria falsa já no 
primeiro teste, o bloco de comandos repetitivos não seria executado e teríamos uma receita 
sem os 2 ovos e sem queijo. 
 
E o que aconteceria para o caso da condição estar correta, como na figura 2.14, 
mas o programador se esquecesse do comando “Incremente(NumeroDeOvosNaReceita)” 
no bloco “senão” do comando condicional? Neste segundo caso, o valor da variável 
“NumeroDeOvosNaReceita” ficaria sempre com o valor 0 (zero) e o comando repetitivo não 
terminaria (loop infinito). Teríamos que ter infinitos ovos e uma quantidade infinita de queijo. 
 
Considere, ainda, uma terceira situação na qual o programador pensasse em contar 
todos os ovos, tirando o comando “Incremente(NumeroDeOvosNaReceita)” do bloco 
“senão” do comando condicional e o colocasse no bloco de comandos sequenciais, antes 
do comando condicional, conforme detalhado no exercício 5 deste capítulo. O que poderia 
acontecer com o algoritmo? Faça as suas considerações resolvendo o exercício proposto. 
 
2.8. Viva a diferença 
 
 Um aspecto final a ser ressaltado é que há maneiras diferentes de se analisar o 
problema que leva a algoritmos diferentes, mas que não estão necessariamente errados. 
Aliás, uma das belezas da programação é permitir diferentes soluções para um mesmo 
problema. 
 
Para NumeroDeOvosNaReceita = 0 até 2 
 Quebre um ovo em uma tigela pequena 
 Jogue a casca do ovo na lixeira 
 Enquanto “ovo estiver choco” 
 Jogue o ovo na lixeira 
 Lave a tigela pequena 
 Quebre um ovo em uma tigela pequena 
 Jogue a casca do ovo na lixeira 
 Fim_Enquanto 
 Adicione o ovo da tigela pequena 
 Acrescente 200g de queijo ralado 
 Enquanto “mistura não estiver homogênea” 
 Bata a mistura 
 Fim_Enquanto 
Fim_Para 
Figura 2.15 - Outra versão para o algoritmo com comandos aninhados 
 
45 
 Introdução à Programação com Python 
Neste formato, o comando principal é um comando repetitivo no estilo “para” que 
será executado 2 vezes, de acordo com os valores inicial e final da variável de controle 
“NumeroDeOvosNaReceita”. Porém, no primeiro comando repetitivo “enquanto”, aninhado 
no comando “para”, seu teste verifica se o ovo está choco. 
 
No caso do resultado do teste ser positivo, os dois primeiros comandos do bloco 
repetitivo tratam do descarte do ovo choco (“Jogue o ovo na lixeira” e “Lave a tigela 
pequena”) e os dois seguintes repetem a ação de pegar um novo ovo (“Quebre um ovo em 
uma tigela pequena”e “Jogue a casca do ovo na lixeira”), que foi executada antes de entrar 
no comando repetitivo “enquanto”. Ao terminar o bloco de comando repetitivo, volta-se ao 
teste da condição (Enquanto “ovo estiver choco”). Ou seja, enquanto não for obtido um ovo 
bom, o algoritmo continuará executando o bloco de comandos repetitivos, descartando o 
ovo choco e pegando outro ovo. 
 
2.9. Uma ferramenta de rastreio de programas 
 
A tarefa de rastreio é tão importante que alguns ambientes de desenvolvimento de 
código trazem opções para ajudar a realizar esta tarefa. Como na disciplina INF 100 o 
nosso ambiente de programação é muito simples, recomendamos o uso de uma ferramenta 
que ajuda a verificar a execução de código Python. 
 
A página do “Python Tutor” disponível em https://pythontutor.com/ permite escrever 
(ou copiar) um código Python e simular a sua execução passo a passo. Na verdade, é 
possível trabalhar com diferentes linguagens de programação, dentre elas a linguagem 
Python. O uso do Python Tutor é bem intuitivo para quem já aprendeu os primeiros 
comandos da linguagem Python. 
 
2.10. Exercícios 
 
1. Identifique os comandos no Algoritmo do pão de queijo que ainda não estão refinados e 
refine-os. 
 
2. Escreva o algoritmo completo e refinado para fazer pão de queijo. 
 
3. Escreva um algoritmo para trocar um pneu de um carro. 
 
4. Escreva um algoritmo para escolher entre três opções possíveis qual o melhor 
apartamento para ser alugado para uma república de 5 pessoas, considerando as 
características descritas a seguir. 
 
46 
https://pythontutor.com/
 Introdução à Programação com Python 
Características Apartamento 1 Apartamento 2 Apartamento 3 
Quartos (incluindo as suítes) 3 3 4 
Suites 1 1 2 
Vaga Garagem 1 0 1 
Andar 1 4 8 
Banheiros (incluindo os da suíte) 2 2 3 
Elevador Não Sim Sim 
Frente p/ rua Sim Não Não 
Valor aluguel (R$) 1.200,00 1.350,00 1.700,00 
Valor Condomínio (R$) 400,00 590,00 550,00 
5. Considere o trecho de algoritmo mostrado a seguir, correspondendo à modificação 
proposta no último parágrafo deste capítulo: 
 
NumeroDeOvosNaReceita = 0 
Enquanto NumeroDeOvosNaReceitavalor durante toda a execução do programa. 
 
O uso das variáveis lembram um pouco dos conceitos matemáticos, mas possuem 
também algumas diferenças bastante significativas, conforme serão expostas na sequência. 
Suponha, por exemplo, uma equação do segundo grau: . Na 𝑎𝑥² + 𝑏𝑥 + 𝑐 = 0
matemática a equação possui apenas uma variável: x. E os valores a, b e c não são vistos 
como variáveis, mas sim como parâmetros ou coeficientes quaisquer de uma equação de 
segundo grau. 
 
Na programação de computadores, x, a, b e c são vistos como variáveis, pois podem 
representar um valor numérico que pode variar dependendo da equação que se deseja 
resolver. Como regra, é sempre desejável que o programa resolva não apenas um problema 
mas uma classe de problemas similares. Por exemplo, se for feito um programa para 
encontrar as raízes de equação de segundo grau, uma boa solução seria aquela que 
informasse a resposta para qualquer equação. Neste caso, o programa deveria receber os 
valores dos coeficientes (a, b e c), atribuindo-os às respectivas variáveis e efetuar o cálculo 
das raízes. O valor de x não é necessário para este cálculo. 
 
Na matemática, podemos usar letras gregas ou outros símbolos para representar 
constantes ou variáveis em equações. Podem ser usadas expressões para calcular o 
discriminante de uma equação do segundo grau e a área de um círculo seriam, 
respectivamente: 
 
● Δ = 𝑏² − 4𝑎𝑐
● á𝑟𝑒𝑎 𝑐í𝑟𝑐𝑢𝑙𝑜 = π. 𝑟²
 
Na programação os nomes de variáveis tem que seguir regras muito mais restritas. 
Só podem ser usados um conjunto restrito dos símbolos definidos na linguagem. Por 
exemplo, as letras gregas Δ e π usadas nos exemplos não fazem parte dos símbolos da 
linguagem Python. Em geral, os nomes de variáveis devem ser iniciados com uma letra 
A..Z, a..z, ou _, podendo conter depois os caracteres A..Z, a..z, 0..9, _. Não são permitidos 
símbolos como +, -, *, /, =, (, ), [, ], {, }, espaços em branco, caracteres acentuados, dentre 
outros. Uma possibilidade de definição de nomes de variáveis e as respectivas expressões 
em um programa, similares às dos exemplos acima seriam: 
 
● 𝑑𝑒𝑙𝑡𝑎 = 𝑏 * 𝑏 − 4 * 𝑎 * 𝑐
● 𝐴𝑟𝑒𝑎𝐶𝑖𝑟𝑐𝑢𝑙𝑜 = 𝑝𝑖 * 𝑟 * 𝑟
 
Nos exemplos acima os caracteres ‘*’ e ‘-’ são operadores de multiplicação e 
subtração e serão explicados com mais detalhes na próxima seção. Algumas palavras são 
“reservadas” na linguagem e também não podem ser usadas como nomes de variáveis. Em 
50 
 Introdução à Programação com Python 
Python, a lista de palavras reservadas pode ser obtida no Shell com o comandos ‘import 
keyword’ e ‘keyword.kwlist’, como mostrado na Figura 3.2. 
 
Figura 3.2 - Comandos do Shell para visualizar lista de palavras reservadas 
 
 Alguns exemplos de nomes ou identificadores válidos para variáveis: x, nome, x7, 
y_max e NomeGrande. Alguns exemplos de identificadores não válidos para variáveis, com 
a razão explicitada entre parênteses: 8y (não pode começar com número), and (palavra 
reservada - vide Figura 3.2), for (palavra reservada) e Nome Grande (não pode ter espaço). 
 
3.1.1. Comando de Atribuição 
 
 Conforme dito anteriormente a definição do tipo de uma variável, na linguagem 
Python, é feita no momento da execução do código, de acordo com o tipo do valor que será 
atribuído à variável. O valor pode ser atribuído diretamente ou ser resultante da avaliação 
de uma expressão. 
 
O comando de atribuição é representado pelo caractere ‘=’ e significa que a 
expressão (ou valor) que se encontra à esquerda do comando de atribuição será atribuído 
para o nome (identificador) que está à sua esquerda. Sua forma geral é: 
 
● = 
 
onde: é um nome válido para variável 
 é uma expressão lógica ou aritmética ou um valor de um 
tipo definido na linguagem. 
 
Os comandos de atribuição para definir o conteúdo da memória como mostrado na 
Figura 3.1 seriam os seguintes: 
● nome = ‘MARIA’ 
● idade = 40 
 
Cabe ao interpertador Python entender que serão necessários 5 bytes para 
armazenar o valor da variável ‘nome’ e quatro bytes para armazenar o valor da variável 
idade. E, de fato, a forma e o espaço gasto no armazenamento podem variar dependendo 
da linguagem de programação e do tipo de processador. É importante ter a noção de que 
cada variável ou estrutura de dados ocuparão espaço na memória. 
 
Importante ressaltar que comando de atribuição não deve ser confundido com uma 
equação da matemática. Suponha, por exemplo, que seja necessário atualizar a ‘idade’ 
51 
 Introdução à Programação com Python 
passando o valor de 40 para 41. Uma possibilidade seria simplesmente executar um novo 
comando de atribuição: 
● idade = 41 
 
 Como o comando de atribuição tem o efeito de armazenar o valor na posição de 
memória associada ao nome da variável que se encontra à esquerda do operador de 
atribuição (=). O efeito deste comando seria escrever o valor 41 na posição onde, antes, 
havia o valor 40. Ou seja, o valor anterior é sobrescrito. Uma outra forma de alterar a idade 
seria escrevendo um outro comando de atribuição da seguinte forma: 
● idade = idade + 1 
 
Note que na matemática tal equação não faria sentido. Mas, como se trata de um 
comando de atribuição, o seu funcionamento se dá da em três etapas, conforme mostrado 
na Figura 3.3, supondo que o valor da variável ‘idade’, anterior à execução do comando, 
seja 41. Para avaliação da expressão ‘idade + 1’ é necessário, primeiramente, obter o valor 
da variável ‘idade’. Para isso, uma operação de busca na memória será feita, na posição 
apontada pelo identificador ‘idade’, com o valor do seu conteúdo (41) sendo armazenado 
em um registrador do processador. O segundo operando da expressão, o valor 1, será 
carregado em um segundo registrador. O processador realizará a operação de soma dos 
dois operandos e o valor resultante (42) será colocado em algum registrador do 
processador. Com o término da avaliação da expressão, o seu resultado será atribuído para 
a posição de memória associada ao identificador ‘idade’. 
 
 
 
 
 
 
 
 
 
 
Figura 3.3 - Etapas do comando de atribuição 
 
 Importante chamar a atenção, mais uma vez, que o efeito final de um comando de 
atribuição é escrever um valor em uma determinada posição de memória. Portanto, o valor 
anterior se perde. Supondo que os três comandos de atribuição foram executados na ordem 
apresentada, a variável ‘idade’ foi criada com valor 40 pelo primeiro comando (idade = 40). 
O segundo comando (idade = 41) alterou seu valor para 41 e o terceiro comando (idade = 
idade + 1) o modificou para 42. 
 
 Suponha que um novo comando para modificar o valor da variável ‘idade’ seja 
escrito para indicar qual será a idade de uma pessoa daqui a uma década, usando a 
seguinte forma: 
● idade = idade + uma_decada 
52 
 Introdução à Programação com Python 
 O interpretador Python, para executar o comando irá fazer a primeira parte da tarefa 
que é buscar os operandos (‘idade’ e ‘uma_decada’). A busca do primeiro operando ‘idade’ 
seria feita com sucesso e o seu valor (42) carregado em algum registrador do processador, 
pois a suposição é a de que os 3 comandos de atribuição para a variável ‘idade’ 
apresentados anteriormente foram executados. Porém, ao tentar buscar o segundo 
operando, o interpretador Python apontará um erro de sintaxe, informando que 
‘uma_decada’ é um nome desconhecido. E, de fato, esta variável não havia aparecido 
anteriormente neste texto. 
 
 Na linguagem Python, toda variável precisa ser definida antes de ser usada em uma 
expressão. A definição implica em atribuir um valor inicial no momento da criação. Por 
exemplo, a variável ‘idade’ foi criada com valor inicial 40, como primeiro comando de 
atribuição (idade = 40). Para corrigir, o erro de sintaxe, o código poderia ser reescrito da 
seguinte forma: 
● uma_decada = 10 # cria a variável uma_decada com valor 10 
● idade = idade + uma_decada # utiliza a variável uma_decada 
 
 Note que os dois comandos acima não podem ser invertidos, pois se isso 
acontecesse, a mesma situação de erro de sintaxe seria apontada pelo interpretador 
Python. Novamente, estaria ocorrendo uma tentativa de utilizar no primeiro comando, uma 
variável que só seria criada no segundo comando. Lembre que a sequência correta de 
eventos é fundamental para se chegar em uma solução correta de qualquer problema. 
 
 Um comentário final sobre o comando de atribuição é que na linguagem Python é 
possível atribuir um mesmo valor para duas ou mais variáveis em um comando de 
atribuição composto, como por exemplo: 
● a = b = c = d = 0 
 
 Este comando irá atribuir, ao final de sua execução, o valor zero para as quatro 
variáveis. A ordem de atribuição é da direita para a esquerda, com a variável d sendo a 
primeira a ter o valor definido e a variável a sendo a quarta. Mas, para a lógica da 
programação de alto nível pode-se enxergar como as 4 variáveis tendo seus valores 
definidos “ao mesmo tempo”. 
 
3.1.2. Tipos de Variáveis 
 
Os tipos primitivos de variáveis da linguagem Python podem ser classificados em 
variáveis numéricas, lógicas e de texto. O tipo numérico possui dois subtipos básicos que 
são os números inteiros e os números reais ou números de ponto flutuante. A faixa de 
valores (menor valor negativo, maior valor positivo) depende do interpretador da linguagem 
Python e do processador que a máquina possui. 
 
Os valores lógicos ou booleanos são apenas dois verdadeiro (True) e (False). Um 
resultado de uma comparação, como aquelas feitas no algoritmo do pão de queijo, vão 
53 
 Introdução à Programação com Python 
resultar sempre em um destes dois valores. Da mesma forma, comparar se uma variável é 
maior do que outra, também resultará em valor verdadeiro ou falso. 
 
Já as variáveis do tipo texto (ou strings) podem ter tamanho variável em função do 
número de caracteres do texto. Em algumas linguagens, é feita uma distinção para variável 
de apenas um caractere. Mas este não é o caso da linguagem Python, que admite até uma 
string vazia, ou seja, um texto de zero caracteres. 
 
Conforme já observado, a linguagem Python define o tipo da variável no momento 
da execução do programa, ao analisar o comando de criação de cada variável no código. 
Por exemplo, uma variável tipo texto (string) é definida pela expressão do lado direito do 
comando de atribuição ser colocada entre aspas simples (' ') ou duplas (" "). Já a definição 
de uma variável numérica do tipo ponto flutuante ou inteiro pode se dar pela colocação ou 
não de um ponto, respectivamente. 
 
 Em outras linguagens de programação, o programador deve definir explicitamente o 
tipo de cada variável. A abordagem da linguagem Python torna a tipagem mais flexível 
permitindo, inclusive, que uma variável que tenha sido criada como sendo do tipo inteiro, 
possa ser alterada durante a execução do programa para armazenar um número de ponto 
flutuante. A grande vantagem é que o programador não precisa redefinir nada. O 
interpretador se encarrega de fazer todas as tarefas necessárias, inclusive com alocação de 
mais memória, pois a representação na memória de um número de ponto flutuante gasta 
mais espaço (bytes) do que um número inteiro. 
A Figura 3.4 apresenta alguns exemplos de criação de variáveis de tipos diferentes e 
o uso em algumas operações simples, pois os operadores da linguagem Python serão 
formalmente apresentados apenas na próxima seção. Neste capítulo, será utilizado o Shell 
para exibição dos valores das variáveis, até que seja apresentado o comando de saída no 
próximo capítulo. 
 
 
Figura 3.4 - Exemplo de definição de variáveis usando o Shell 
 
Note que no Shell do Python algumas informações aparecem com cores diferentes. 
O valor False atribuído para a variável ‘terminou’ está na cor laranja. As strings estão na cor 
verde e os comentários na cor vermelha. O comentário é iniciado com o caractere # e 
aparece na cor vermelha. Um comentário não tem nenhum significado para o interpretador 
54 
 Introdução à Programação com Python 
Python, ou seja, tudo o que aparece após o caractere #, na mesma linha, é ignorado pelo 
interpretador Python. 
 
A forma de criação e atribuição do valor inicial define implicitamente o tipo de cada 
variável na Figura 3.4. As duas primeiras variáveis n e idade são inteiras, as duas variáveis 
seguintes fator e k são reais (ou de ponto flutuante), sexo e nome são variáveis do tipo 
string (texto) e a variável terminou é do tipo booleana (ou lógica). A notação ‘1.37e-8’ usada 
para atribuir o valor para a variável k significa . Note que na linguagem de 1, 37𝑥10⁻⁸
programação Python (e em todas as outras mais populares) utiliza-se o ponto (.) ao invés 
da vírgula (,) para representação de números não inteiros. Como foi feito também na 
atribuição do valor da variável fator. 
 
No Shell do Python, para exibir o valor atual de uma variável basta digitar o seu 
nome e depois a tecla “Enter”. Caso deseje imprimir o valor de mais de uma variável, basta 
digitar a lista de nomes de variáveis separando-as com vírgula. Os valores, neste caso, 
aparecerão entre parênteses e separadas por vírgulas. No próximo capítulo será 
apresentado o comando de impressão, mas até lá as impressões de valores no Shell serão 
feitas da forma descrita anteriormente. A Figura 3.5 apresenta um comando para imprimir o 
valor de cada variável, na ordem em que foram definidas. Note que a saída deste comando 
de impressão é feita na cor azul. 
 
 
Figura 3.5 - Exibindo o valor das variáveis 
 
A seguir, na Figura 3.6, são mostradas algumas alterações de valor feitas com a 
utilização de comandos de atribuição e algumas expressões bem simples. Na próxima 
seção serão vistos com detalhes os operadores da linguagem Python e alguns exemplos de 
expressão um pouco mais elaboradas. Os comandos estão na sequência dos comandos já 
apresentados na Figura 3.6, ou seja, com os valores iniciais das variáveis já definidos. Para 
maior clareza, o último comando da figura anterior será sempre exibido na figura seguinte. 
 
55 
 Introdução à Programação com Python 
 
Figura 3.6 - Alguns comandos de atribuição para alterar o valor de variáveis 
 
Na Figura 3.6, após um ou mais comandos de atribuição, o comando que imprime o 
valor de todas as variáveis foi repetido para que seja possível visualizar o efeito do(s) 
comando(s) sobre a variável à esquerda do operador de atribuição (variável que recebe o 
valor definido pela expressão à direita do operador de atribuição). 
 
Os dois primeiros comandos de atribuição são exatamente aqueles usados na seção 
3.1.1 para explicar o funcionamento do comando de atribuição. O primeiro levou o valor da 
variável idade para 41 e o segundo para 42. Note que nenhuma outra variável teve seu 
valor alterado até este ponto, pois até ali apenas a variável idade apareceu recebendo o 
resultado dos dois comandos de atribuição (idade = 41 e idade = idade + 1). 
 
O comando seguinte (k = k + idade) tem uma expressão que soma um valor inteiro 
com um valor de ponto flutuante, o que resultará em um valor de ponto flutuante. Portanto, o 
resultado ao ser atribuído para a variável k não vai alterar o seu tipo. Entretanto, a forma de 
exibição do valor que antes utilizada a notação científica tem que ser alterada para que não 
se omita o valor fracionário. 
 
No comando n = n + k também soma um valor inteiro com um valor de ponto 
flutuante e oresultado está sendo atribuído para a variável n que foi criada como do tipo 
inteiro. Em algumas linguagens de programação esta atribuição seria considerada como um 
erro. Mas não é o caso da linguagem Python, que altera dinamicamente o tipo da variável n 
para que o valor seja armazenado corretamente na memória. Note, que na impressão 
seguinte o valor de n passa a ter várias casas decimais. Note também que o valor de n e k 
passaram a ser iguais, pois no momento da avaliação da expressão o valor de n era zero, 
logo n + k foi igual a k. 
 
Os comandos seguintes que alteram o valor das variáveis sexo e nome mostram 
outra característica dinâmica da linguagem Python. Uma variável do tipo string pode 
aumentar ou diminuir de tamanho dinamicamente durante a execução do programa. O texto 
56 
 Introdução à Programação com Python 
‘Maria das Dores’ tem um caractere a mais do que ‘Carlos Alberto’, portanto, o espaço na 
memória reservado para esta variável teve de aumentar (o interpretador Python faz isso de 
forma transparente para o programador). A variável sexo também cresceu de forma mais 
fácil de se notar. O comentário no comando de criação indicava que ela era do tipo 
caractere, na verdade, não está correto. De fato, sexo é uma variável do tipo string que 
recebeu, inicialmente, um texto de apenas 1 caractere (‘M’). 
 
Finalmente, os dois últimos comandos de atribuição da Figura 3.6 atribuem valore 
diretamente para as variáveis n e terminou. A variável n volta a ter o valor zero e a variável 
terminou passa a valer True (verdadeiro). É importante entender que após um comando de 
atribuição, o valor anterior é perdido. Esta foi a razão da inserção dos comandos de 
exibição dos valores das variáveis entre os comandos de atribuição. 
 
 
 
3.2 Operadores e Expressões 
 
Os operadores da linguagem de programação são utilizados para permitir a escrita 
de expressões para o cálculo de valores para a realização da computação desejada 
 
3.2.1. Operadores e Expressões aritméticas 
 
Os principais operadores para a realização de cálculos e criação de expressões 
aritméticas são apresentados na Tabela 3.2: 
 
Tabela 3.2 - Principais operadores aritméticos 
Operador Nome / Papel do operador 
( ) Parênteses / permite alterar a prioridade de execução das operações 
+ Soma 
- Subtração 
* Multiplicação 
/ Divisão 
% Módulo / Resto da divisão inteira 
// Quociente / Quociente da divisão inteira 
** Potenciação 
 
57 
 Introdução à Programação com Python 
Considere os exemplos de expressões aritméticas mostradas na Figura 3.7. 
Supondo que cada linha corresponda a uma linha de um código de Programa Python 
poderia ser perguntado: qual o valor final de cada variável do Programa? 
 
Num. do 
comando 
Código Pyton 
1 
2 
3 
4 
5 
6 
7 
resultado = 2+6 
x = 2*resultado 
pi = 3.14159 
UmMega = 1024 * 1024 
y = (x+3)*x/3 
y = x+y 
x = y = 0 
Figura 3.7 - Alguns exemplos simples de expressões aritméticas 
 
Para responder a esta pergunta pode-se utilizar uma tabela de rastreio para simular 
a execução do código. A tabela terá o nome de cada variável e uma coluna indicando qual 
comando foi o mais recentemente executado. A cada comando, as variáveis vão sendo 
criadas e os valores atribuídos. Uma variável que ainda não foi criada terá seu valor 
representado na tabela de rastreio com um traço ‘-’. Por exemplo, na primeira linha está 
sendo suposto que nenhum comando foi executado e, portanto, todos os valores são ‘-’. 
 
Tabela 3.3 - Tabela de Rastreio para o trecho de código da Figura 3.7 
resultado x pi UmMega y Número do último 
comando executado 
- - - - - Nenhum 
8 - - - - 1 
8 16 - - - 2 
8 16 3.14159 - - 3 
8 16 3.14159 1048576 - 4 
8 16 3.14159 1048576 101.33333 5 
8 16 3.14159 1048576 117.33333 6 
8 0 3.14159 1048576 0 7 
 
 
 A tabela de rastreio é sempre útil para ajudar a entender o fluxo de execução e o 
que acontece com as variáveis do programa, à medida que os comandos vão sendo 
executados. Entretanto, como é um método manual e, por isso, sujeito a erros, a melhor 
alternativa para verificar o que acontece com um programa é utilizar alguma ferramenta de 
desenvolvimento, como é o caso IDLE. Nas aulas práticas da disciplina INF 100 - 
Introdução à Programação I este será o ambiente utilizado. A página do Python Tutor 
58 
 Introdução à Programação com Python 
(https://pythontutor.com/), conforme falado no final do capítulo 2, é um excelente ambiente 
para automatizar a tarefa de rastreio para código Python. 
 
Até aqui foi utilizado apenas o Shell do ambiente de desenvolvimento IDLE. Se o 
Shell fosse utilizado para responder à pergunta sobre o valor final das variáveis para o 
trecho de código da Figura 3.7 poderia ser feito da forma mostrada na Figura 3.8, a seguir: 
 
 
Figura 3.8 - Uso do Shell para verificar valor final de variáveis 
 
Suponha, agora, que se deseja usar o Shell para calcular a área de um círculo. A 
fórmula para cálculo da área de um círculo é , onde r é o raio do círculo e π é um valor π. 𝑟²
constante igual a 3.14159 na representação com 5 casas decimais de precisão. 
 
 
Figura 3.9 - Exemplo de uso do Shell para cálculo de área de um círculo 
 
Nos 3 primeiros comando da Figura 3.9 são usados para: definir o valor da 
constante pi; definir o valor do raio; e calcular a área. O valor 12.56636 é exibido, como 
resultado do quarto comando, como sendo o valor da área de um círculo de raio 2. A área 
depende da unidade do raio. Se o raio fornecido significar 2 cm, a área seria de 12.56636 
cm². Porém, se o raio estivesse em metros, a área seria de 12.56636 m². 
 
59 
https://pythontutor.com/
 Introdução à Programação com Python 
Na sequência existe um comando que altera o valor da variável r (que representa o 
raio) para 10 e no comando seguinte utiliza-se o comando para exibir o conteúdo da 
variável area. Note que o valor da variável area continua o mesmo, pois não houve nenhum 
comando de atribuição para a variável area, após a redefinição do valor do raio. Para que 
isto ocorra, o sétimo comando calcula novamente a expressão aritmética com o valor da 
variável r (raio) com o valor atual (10). No comando seguinte, o novo valor da área 
(314.159) é exibido. 
 
Nos comandos seguintes, o valor da variável pi é redefinido, passando a valer -1. 
Novamente, o valor da variável area é exibida e repete a exibição do último valor que lhe foi 
atribuído (314.159). Finalmente, a expressão de cálculo da área é novamente avaliado e o 
seu resultado é atribuído para a variável area. E, no último comando, o valor -100 é 
informado como a área do círculo!!! 
 
Um absurdo do ponto de vista lógico, pois não existe área negativa. Note que este 
valor absurdo, deriva do erro absurdo de definir o valor da constante pi como -1, ao invés de 
3.14159. Mas, do ponto de vista da execução do código, para o computador está tudo certo. 
O nome pi, para o computador, não tem nenhum significado especial, logo, qualquer valor 
atribuído para a variável será aceito. Não há erro na definição das variáveis e nem nas 
expressões aritméticas. Importante frisar que o computador não erra. O que ele pode fazer 
é executar comandos que contém erro na sua definição e que ele não consegue identificar. 
 
Portanto, os programadores devem garantir que os comandos não contenham erros, 
absurdos ou não, conhecendo o problema que se pretende resolver e observando se as 
respostas fazem sentido, em cada caso. 
 
Existe uma precedência entre os operadoresaritméticos na linguagem Python. 
Conhecer esta ordem é fundamental para que as expressões sejam escritas corretamente 
e, consequentemente, processem as informações de maneira correta, para produzir o 
resultado desejado. A Tabela 3.4 apresenta a ordem de precedência dos operadores 
aritméticos, sendo 1 a mais prioritária.. 
 
Tabela 3.4 - Ordem de prioridade dos operadores aritméticos 
Ordem Operador Nome 
1 ( ) Parênteses 
2 ** Potenciação 
3 - Negação 
4 * / // % Multiplicação, Divisão, Divisão inteira e Resto da Divisão Inteira 
5 + - Soma e Subtração 
 
Em uma expressão, quando existirem operadores de mesma prioridade, as 
operações são executadas na ordem de aparição (da esquerda para a direita). A seguir, são 
apresentados alguns exemplos de expressões e suas avaliações passo a passo: 
60 
 Introdução à Programação com Python 
● -1**2 = -1 
● (-1)**2 = 1 
● 8+3*2 = 8+6 = 14 
● (8+3)*2 = 11*2 = 22 
● 2+4%3 = 2+1 = 3 
● (2+4)%3 = 6%3 = 0 
● 5-3+1 = 2+1 = 3 
● 5-(3+1) = 5-4 = 1 
● 1+4/2+2*2 = 1 + 2 + 2*2 = 1 + 2 + 4 = 3 + 4 = 7 
 
Em caso de dúvida, a utilização de parênteses é sempre uma boa alternativa a ser 
adotada. Outra observação importante é que ao utilizar parênteses o número de caracteres 
‘(‘ tem que ser igual ao número de caracteres ‘)’. E, obviamente, um caractere ‘(‘ sempre 
deve vir antes do caractere ‘)’ correspondente. Ao encontrar um caractere ‘(‘, o interpretador 
entende que foi aberto um bloco, que deverá ser fechado, necessariamente, com um 
caractere ‘)’. 
 
3.2.2. Operadores e Expressões Lógicos 
 
Os operadores lógicos ou booleanos são utilizados para ajudar a escrever 
expressões lógicas. O resultado de uma expressão lógica poderá assumir apenas dois 
valores: verdadeiro (True) ou falso (False). Os operadores lógicos costumam ser 
apresentados juntamente com os comandos condicional e repetitivo, pois ambos utilizam 
um teste para verificar o fluxo a ser seguido. O resultado do teste será sempre verdadeiro 
ou falso, ou seja, um valor booleano (ou lógico). 
 
A maioria dos operadores aritméticos são de conhecimento de todos, desde o 
ensino fundamental. O mesmo não se aplica aos operadores lógicos, mesmo que no dia a 
dia, eventualmente, já tenhamos aplicado alguma destas operações lógicas de maneira 
intuitiva. A seguir são descritas as três operações lógicas primitivas: não (not), e (and) e ou 
(or). Com estes três operadores é possível escrever qualquer função lógica. 
3.2.2.1 - Operador não (not) 
O operador not é um operador unário, ou seja, necessita apenas de um operando e 
o resultado da operação é a negação ou a inversão do valor lógico. A tabela verdade da 
função not para uma entrada A é mostrada a seguir: 
 
A not A 
False True 
True False 
 
A tabela verdade lista todas as combinações de entradas possíveis e, para cada 
combinação, informa o valor da saída. No caso da função not a tabela verdade terá apenas 
61 
 Introdução à Programação com Python 
2 linhas. A aplicação da função not, portanto, inverte o valor da entrada fornecida, conforme 
indicado em sua tabela verdade. 
3.2.2.2 - Operador e (and) 
O operador and é um operador que necessita de pelo menos duas entradas e o seu 
resultado será Falso se pelo menos uma das entradas for Falsa. O resultado da função and 
será verdadeiro somente se todas as suas entradas forem verdadeiras. A tabela verdade da 
função and para duas entradas A e B é mostrada a seguir: 
 
A B not(A) 
False False False 
False True False 
True False False 
True True True 
 
A tabela verdade para duas entradas, como é o caso da função and mostrada acima 
terá 4 linhas. O número de linhas de uma tabela verdade será sempre , onde n 2𝑛
corresponde ao número de entradas da função booleana. 
3.2.2.3 - Operador ou (or) 
O operador or é um operador que também necessita de pelo menos duas entradas e 
o seu resultado será Falso somente quando todas as entradas forem falsas. O resultado da 
função or será verdadeiro se pelo menos uma de suas entradas for verdadeira. A tabela 
verdade da função or para duas entradas A e B é mostrada a seguir: 
 
A B not(A) 
False False False 
False True True 
True False True 
True True True 
 
A Tabela 3.5 apresenta os três operadores lógicos com a respectiva notação utilizada na 
linguagem Python. 
 
Tabela 3.5 - Operadores lógicos (booleanos) 
Operador Equivalente em Python 
não (not) not 
e (and) and 
ou (or) or 
62 
 Introdução à Programação com Python 
3.2.2.4 - Expressões lógicas 
Tendo visto, então, os três operadores lógicos (booleanos) primitivos é hora de 
apresentar as expressões lógicas. Uma expressão lógica pode usar apenas os operadores 
booleanos, mas pode conter também expressões aritméticas e fazer uso dos operadores 
relacionais (ou de comparação). Os operadores relacionais são apresentados na Tabela 3.6: 
 
Tabela 3.6 - Operadores relacionais 
Operador Significado 
 maior 
>= maior ou igual 
== igual 
!= diferente 
 
 O uso de um operador relacional resultará em um valor booleano (verdadeiro ou 
falso), pois o resultado de uma comparação (relação) só pode ser verdadeira ou falsa. 
Considere o trecho de código mostrado na imagem do Shell na Figura 3.10. O código define 
duas variáveis inteiras x e y com valores iniciais 1 e 2, respectivamente. Depois são usados 
operadores relacionais e lógicos para atribuir valor para 3 variáveis a, b e c, que vão 
assumir valor verdadeiro ou falso, dependendo do resultado da avaliação da expressão 
relacional/booleana. 
 
 Para atribuição do valor para a variável a, a expressão “ytipo modificado durante a 
execução do programa. Isso não acontece em linguagens como C++, Java, dentre outras. 
 
Por isso, é muito importante ter bastante atenção no momento de escrever as 
expressões aritméticas, relacionais e lógicas em seus programas. É necessário considerar 
também a ordem de execução das operações ou a prioridade entre as operações. A Tabela 
3.7 apresenta todos os operadores vistos até aqui com a ordem de prioridade, sendo o 
número 1, a operação mais prioritária. 
 
Tabela 3.7 - Ordem de prioridade dos operadores aritméticos 
P Operador Nome 
1 - negação aritmética 
2 ** Potenciação 
3 * / // % Multiplicação, Divisão, Divisão inteira e Resto da Divisão Inteira 
4 + - Soma e Subtração 
5 >= == != Operadores relacionais 
6 not Não lógico 
7 and E lógico 
8 or OU lógico 
9 = Atribuição 
 
64 
 Introdução à Programação com Python 
3.2.2.5 Equivalência de Expressões Lógicas 
 
Conforme já destacado na seção 2.8, algumas vezes os algoritmos são diferentes, 
mas levam à mesma solução correta de um problema. O mesmo se aplica às expressões 
booleanas. Muitas vezes a forma de desenvolver um raciocínio lógico pode levar 
expressões lógicas distintas, mas com resultados idênticos ao serem avaliadas. 
 
Para exemplificar tal situação, imagine um programa que precisa verificar se um 
número está dentro do intervalo qualquer, por exemplo, representados por duas variáveis a 
e b. Desta forma, podemos definir diferentes intervalos, simplesmente atribuindo valores 
diferentes para a e b. Por exemplo, a = 0 e b = 100, para verificar se o valor de uma nota (n) 
final está na faixa de valores usados na UFV. A hipótese que se assume aqui é que sempre 
o valor de a será menor que o valor de b. Graficamente, podemos representar o nosso 
intervalo como mostrado na Figura 3.11. 
 
 
Figura 3.11 - Intervalo fechado [a, b] 
 
A representação [a, b] indica que os valores das extremidades, a e b, pertencem ao 
intervalo. Uma forma de representar este intervalo é como sendo a interseção de dois 
intervalos: qualquer número maior ou igual ao limite inferior ([a, +∞)) e qualquer número 
menor ou igual ao limite superior ((-∞, b]). A Figura 3.12 representa a definição do intervalo 
como a interseção descrita. 
 
 
 
Figura 3.12 - Intervalo fechado [a..b] 
 
A operação de interseção define o que é comum em dois conjuntos. No caso 
dos intervalos a interseção pegará todos os números que atendem às duas 
condições simultaneamente: ser maior ou igual a zero e ser menor ou igual a 100. 
Supondo que o valor (nota) a ser verificada esteja armazenada na em uma variável 
n, a condição lógica que verifica se n pertence ao intervalo pode ser descrita como: 
 
65 
 Introdução à Programação com Python 
 𝑛 >= 𝑎 𝐸 𝑛 = 𝑎 𝑎𝑛𝑑 𝑛 𝑏
 
Mas esta expressão representa os números que estão fora do intervalo. Assim, 
devemos negá-la para que seja representado os números que pertencem ao intervalo: 
 
 𝑛ã𝑜(𝑛 𝑏)
 
Ou escrevendo na linguagem Python: 
 
 (expressão 2) 𝑛𝑜𝑡(𝑛 𝑏)
 
 Uma forma de demonstrar que as expressões 1 e 2 são equivalentes seria definir os 
limites do intervalo e testar para valores conhecidos. Vamos supor que o intervalo seja [0, 
100] e testar as expressões 1 e 2 para valores que estão no intervalo (ex: 0, 93 e 100) e 
66 
 Introdução à Programação com Python 
outros que estão fora (ex: -1 e 230). A Tabela 3.8 apresenta o detalhamento do resultado de 
todas as operações relacionais e booleanas, com o valor final das expressões 1 e 2 nas 
colunas em negrito, mostrando que são equivalentes. 
 
Tabela 3.8 - Comparação entre (n>=a and nb) para a=0 e b=100 
 A B n>=0 and n100) 
n n >= 0 n 100 C or D not E 
-1 False True False True F alse True False 
0 True True True False False False True 
93 True True True False False False True 
100 True True True False False False True 
230 True False False False True True False 
 
Outra forma de demonstrar a equivalência das duas expressões é utilizando o 
Teorema de Boole. Por este teorema as seguintes equivalências são válidas: 
 
 𝑛𝑜𝑡(𝑝 𝑜𝑟 𝑞) = 𝑛𝑜𝑡(𝑝) 𝑎𝑛𝑑 𝑛𝑜𝑡(𝑞)
 𝑛𝑜𝑡(𝑝 𝑎𝑛𝑑 𝑞) = 𝑛𝑜𝑡(𝑝) 𝑜𝑟 𝑛𝑜𝑡(𝑞)
 
 Para a sequência, vai ser considerado o intervalo [0, 100], substituindo, então, a por 
0 e b por 100. Considere a primeira equivalência do Teorema de Boole que possui a sua 
primeira parte escrita com a mesma estrutura da expressão 2, deduzida anteriormente: 
 
 𝑛𝑜𝑡(𝑛 100)
 
Neste caso, corresponde ao operando p e corresponde ao operando 𝑛 100
q da equivalência no Teorema de Boole, reescrita a seguir: 
 
 𝑛𝑜𝑡(𝑛 100) = 𝑛𝑜𝑡(𝑛 100)
 
Mas o que seriam e ? Ora, negar a comparação é 𝑛𝑜𝑡(𝑛 100) 𝑛 = 0
vai tornar a segunda comparação falsa e, vice-versa. Em Português pode-se dizer que “o 
que não é menor do que zero”, só pode “ser maior ou igual a zero”. Usando o operador 
booleano not pode-se escrever . Analogamente, para 𝑛𝑜𝑡(𝑛 = 0
negar a comparação deve-se utilizar a comparação . Usando o operador 𝑛 > 100 𝑛 100) "𝑒𝑞𝑢𝑖𝑣𝑎𝑙𝑒 𝑎" 𝑛 100) = 𝑛 >= 0 𝑎𝑛𝑑 𝑛testar seus códigos Python, etc. 
Estudar e conhecer os fundamentos teóricos é muito importante. Principalmente 
para saber se adaptar às mudanças muito comuns na área de programação. Mudar de 
Python para Java, C++ ou Matlab para quem sabe os fundamentos de programação é uma 
tarefa relativamente tranquila. 
Mas, deve ser lembrado que a prática é fundamental para o aprendizado de 
qualquer linguagem de programação. Assim como para ser considerado um piloto é 
necessário ter horas de voo, para se tornar um bom programador vai ser preciso muitas 
horas de programação. 
Então, mãos à obra! 
 
 
 
6 
 Introdução à Programação com Python 
Capítulo 1 - Introdução 
 
 
1.1. Motivação - por que aprender programação? 
 
 
Uma pergunta comum dos estudantes é: onde este assunto da disciplina vai ser 
importante na minha vida pós universidade? No caso do assunto de noções de 
programação para estudantes de cursos da área de Ciências Exatas é possível afirmar, sem 
medo de errar, que o tema tem se tornado cada vez mais importante. 
 
Vivemos a chamada era da informação, na sociedade da informação, onde a 
criação, distribuição, uso, integração e manipulação da informação é uma atividade 
econômica, política e cultural cada vez mais significativa. A evolução das tecnologias 
digitais de informação e comunicação propiciaram um crescimento exponencial das 
informações e estão mudando profundamente todos os aspectos da organização social, 
incluindo a economia, educação, saúde, guerra, governo e democracia. 
 
A cada dia, mais e mais produtos são lançados com capacidade de conexão às 
redes de computadores. Desde as já consagradas Smart TVs até eletrodomésticos como 
geladeiras e fornos de microondas, passando pelos automóveis com computadores e 
softwares cada vez mais sofisticados, incluindo os protótipos de carros autônomos, que 
dispensam o motorista. 
 
Associados a cada tipo de dispositivo com capacidade de se conectar à Internet, 
novas aplicações e serviços vão sendo disponibilizados. Hoje estamos entrando na fase em 
que a Internet ganha um “sobrenome” e passa a ser chamada de Internet das Coisas (IoT - 
Internet of Things), onde a principal característica é que o usuário precisa conhecer cada 
vez menos a tecnologia que está cada vez mais presente nas aplicações do dia-a-dia. 
 
Supermercados inteligentes nos quais o usuário coloca os produtos em seu carrinho 
de compras e não precisa passar pelo caixa antes de ir para o estacionamento estão se 
popularizando em alguns países. Todo o processamento é feito por softwares de 
identificação facial ou leitura de dados de um cartão inteligente (smart card) para identificar 
o comprador e sistema de identificação por rádio frequência (RFId) nas etiquetas de cada 
produto e sensores RFId espalhados pelo supermercado. 
 
Aplicações nas mais diversas áreas tais como agricultura de precisão, controle de 
frota de veículos, monitoramento ambiental, rastreabilidade de produtos para a segurança 
alimentar, controle de tráfego em tempo real, controle de distanciamento social em tempos 
de pandemia e muitas outras que vão demandar profissionais com diferentes formações, 
7 
 Introdução à Programação com Python 
mas que irão precisar de uma característica comum: saber analisar um problema e propor 
uma solução descrita utilizando um raciocínio lógico. 
 
E mesmo para quem não irá trabalhar com soluções computacionais, pode 
economizar um dinheirinho usando raciocínio lógico. Foi o que aconteceu com o João da 
Silva, que na infância era chamado de Joãozinho, quando ligou, no final da tarde, para 
cancelar uma consulta médica agendada para as 14h do dia seguinte. A secretária disse: 
- Sr. João Silva, infelizmente para cancelamento com menos de 24 horas, no seu 
plano de saúde há uma taxa de 80% do valor da consulta. Se o Sr. tivesse ligado antes das 
14h não haveria custo para cancelar… Mas o senhor pode optar por reagendá-la. 
- Pois não. Então a senhora, por favor, remarque a consulta para a próxima semana, 
no mesmo horário. 
- Pronto. Consulta reagendada. Deseja mais alguma coisa Sr. João? 
- Sim. Eu quero cancelar a consulta da semana que vem. 
1.2. Arquitetura do computador e o Sistema Operacional 
 
 A arquitetura básica de um computador é apresentada na figura 1.1. A execução das 
instruções ocorre no processador, também chamado de Unidade Central de Processamento 
(CPU - Central Processing Unit). O processador possui registradores internos (não 
detalhados na figura) onde armazena temporariamente os operandos de uma determinada 
instrução. Os operandos geralmente são as variáveis definidas no código do programa de 
alto nível, conforme veremos em breve. Todas as variáveis e demais objetos definidos no 
programa ficam armazenados na Memória (também chamada de memória principal ou 
memória RAM) durante a execução do programa. Pode-se dizer, então, que todo o trabalho 
de execução de um programa simples envolve apenas o processador e a memória principal 
além, é claro, do barramento interno que os conecta e compõem a chamada Arquitetura 
Interna do computador (destacada na parte esquerda da figura 1.1). 
 
 
Figura 1.1 - Arquitetura básica de um computador 
8 
 Introdução à Programação com Python 
 
 Entretanto, para comandar a execução de um programa e visualizar os resultados 
gerados é necessário a utilização de Dispositivos de E/S (Entrada e Saída), mostrados no 
lado direito da figura 1.1. Dentre os dispositivos mais comuns podem ser citados: teclado, 
mouse e microfone como dispositivos de entrada; monitor de vídeo, impressora e caixa de 
som como dispositivos de saída; e disco rígido, pendrive e tela sensível ao toque como 
dispositivos de entrada e saída. 
 
O Disco Rígido é o dispositivo de E/S mais utilizado pois ela armazena de forma 
permanente todos os programas instalados no computador e os arquivos que criamos ao 
editar o código fonte de um programa escrito em uma linguagem de alto-nível. Ao salvar um 
arquivo, o seu conteúdo é gravado no Disco Rígido, sendo possível reutilizá-lo 
posteriormente. Ao criar um novo arquivo usando um editor de textos e após adicionar, por 
exemplo, 200 linhas de código do programa, caso o computador seja desligado todo o 
trabalho será perdido. Isto ocorre porque o arquivo não foi salvo (gravado no disco rígido) 
nem uma vez. A memória principal é volátil, ou seja, seu conteúdo é perdido quando o 
circuito é desenergizado. Por isso, é importante salvar periodicamente seu arquivo de 
trabalho. 
 
 A forma de utilização do disco rígido e dos demais dispositivos de entrada e saída 
passa despercebida porque o Sistema Operacional esconde de propósito detalhes que não 
são importantes para os seres humanos. O Sistema Operacional é um programa que inicia 
seu funcionamento ao ligar o computador e tem como uma de suas principais tarefas a 
identificação da quantidade de memória disponível que ele poderá utilizar e a quantidade 
que ficará disponível para executar os programas dos usuários, além da identificação de 
todos os dispositivos de E/S conectados ao computador. Ou seja, o sistema operacional 
identifica e controla todas as partes físicas (o hardware) do computador. 
 
 A outra tarefa principal dos sistemas operacionais é oferecer uma forma amigável e 
fácil de utilizar o computador para o operador humano, chamada de interface 
homem-máquina ou, simplesmente, interface. Os primeiros sistemas operacionais 
modernos possuíam apenas uma interface de texto, conforme mostrado na figura 1.2. 
 
9 
 Introdução à Programação com Python 
 
Figura 1.2 - Interface de texto do Ubuntu Linux 
 
Neste ambiente, o usuário precisava memorizar* 2 
D = A + B ** 2 
E = D ** 0.5 
F = A / 3 
G = A // 3 
H = A % 3 
I = A + B * C / 2 * D 
J = A + B * C / (2 * D) 
K = I // J 
L = I / J 
M = int(I / J) 
N = float(M) 
 
 
2) Para o código mostrado abaixo, informe o valor que será recebido pela variável em 
cada um dos comandos de atribuição. Qual o tipo da variável em cada comando de 
atribuição ? 
 
A = 2 
B = A + 7 
C = 2 * A + B 
D = C - B > B - C 
E = A + B * C == 120 
F = E and A>B or C > B 
G = A >= 0 and A 100 
I = D and G or E and H 
68 
 Introdução à Programação com Python 
J = D and (G or E) and H 
K = D or G and E or H 
L = (D or G) and (E or H) 
M = (K and L) == (not(not(K) or not(L))) 
N = (K or L) == (not(not(K) and not(L))) 
 
 
3) Para o código mostrado abaixo, informe o valor que será recebido pela variável do 
tipo texto (string) em cada um dos comandos de atribuição. 
 
nome = 'José' 
sexo = 'Masculino' 
sobrenome = 'Leôncio da Silva' 
nomeCompleto = nome + sobrenome 
nomeComplComEspaco = nome + ' ' + sobrenome 
nomeTriplo1 = 3*nomeComplComEspaco 
nomeTriplo2 = 3*(nomeComplComEspaco+' ') 
linha = 'Nome: ' + nomeComplComEspaco + ' Sexo: ' + sexo 
 
 
4) Refaça os exercícios 1, 2 e 3 digitando os comandos na janela do Shell do IDLE e 
mande imprimir os valores para as variáveis e verifique seus acertos e erros. 
 
 
5) Escreva uma expressão que dada uma temperatura em graus Fahrenheit, calcule o 
valor correspondente em graus Celsius, de acordo com a fórmula: 𝐶
5 = 𝐹−32
9
 
 
6) Escreva uma expressão para calcular a área de um círculo, sabendo o valor do raio 
(R). A expressão deve atribuir o valor para a variável de nome Area. 
 
7) Escreva uma expressão para calcular o k-ésimo elemento de uma progressão 
aritmética cujos valores do primeiro elemento e da razão serão armazenados em 
variáveis de nomes a1 e r, respectivamente. O valor da expressão deve ser atribuído 
para uma variável de nome Ak. Dica: faça uma busca na Internet para achar a 
fórmula do k-ésimo elemento de uma progressão aritmética. 
 
 
8) Usando as informações do exercício anterior defina uma expressão para atribuir 
para uma variável de nome Soma, o valor dos 100 primeiros números naturais. Dica: 
faça uma busca na Internet para achar a fórmula do somatório dos elementos de 
uma progressão aritmética. Dica: pesquise na Internet a fórmula da soma dos 
elementos de uma PA. 
 
 
69 
 Introdução à Programação com Python 
9) Generalize a solução do exercício anterior para definir uma expressão para atribuir 
para uma variável de nome SomaN, o valor dos N primeiros números naturais. 
 
 
10) Defina uma expressão para calcular a soma dos N primeiros elementos de uma 
Progressão Aritmética (PA), cujos valores do primeiro elemento e da razão terão 
valores atribuídos para as variáveis a1 e razao, respectivamente. A expressão para 
o cálculo da soma deverá ser atribuído para uma variável de nome SomaNPA. Dica: 
utilize uma outra expressão para atribuir para uma variável An o valor do n-ésimo 
elemento da PA. 
 
 
11) Use a janela do Shell do ambiente de programação IDLE para verificar a solução do 
exercício anterior. Use sequências pequenas para facilitar a verificação do somatório 
dos valores da Progressão Aritmética. Por exemplo para a sequência 2, 5, 8 e 11, na 
qual a1 = 2 e razao = 3, a soma dos valores é 26. 
 
 
12) Defina uma expressão para calcular a soma dos N primeiros elementos de uma 
Progressão Geométrica (PG), cujos valores do primeiro elemento e da razão terão 
valores atribuídos para as variáveis elem1 e razaoPG, respectivamente. A 
expressão para o cálculo da soma deverá ser atribuído para uma variável de nome 
SomaNPG. Dica: utilize uma outra expressão para atribuir para uma variável elemN 
o valor do n-ésimo elemento da PG. 
 
 
13) Use a janela do Shell do ambiente de programação IDLE para verificar a solução do 
exercício anterior. Use sequências pequenas para facilitar a verificação do somatório 
dos valores da Progressão Geométrica. Por exemplo para a sequência 2, 4, 8 e 16, 
na qual elem1 = 2 e razaoPG = 2, a soma dos valores é 30. 
 
 
70 
 Introdução à Programação com Python 
Capítulo 4 - Comandos de Entrada e Saída 
 
A comunicação homem-máquina é importantíssimo para o sucesso de uma solução 
computacional. As informações que são necessárias para a realização das tarefas devem 
estar bem definidas e de fácil entendimento para quem irá fornecê-las. Da mesma forma, a 
saída ou a exibição dos resultados gerados pelo programa devem estar bem organizada de 
forma a facilitar a sua visualização. 
Para atingir estes objetivos serão apresentados neste capítulo os comandos de 
entrada e saída, que servem para fazer a interface homem-máquina. Nos computadores 
convencionais, o dispositivo de entrada padrão é o teclado no qual o usuário digita uma 
sequência de caracteres e depois aperta a tecla “Enter”. Esta tecla indica o final da entrada 
da informação solicitada. Já o dispositivo padrão de saída é o monitor de vídeo. 
Para as seções a seguir está sendo suposto que os comandos de entrada e saída 
estão relacionados, respectivamente com o teclado e o monitor de vídeo. Porém, é bom 
ressaltar que estes dispositivos padrão podem ser alterados como, por exemplo, para 
utilizar arquivos como entrada e/ou saída de dados. 
 
4.1 - Comando de Saída 
 
4.1.1 - Forma básica do comando de saída 
 
Considere o seguinte programa bem pequeno, com apenas um comando, escrito em 
Python: 
print('Olá UFV...') 
 
Esse programa escreverá na tela o seguinte: 
Olá UFV… 
 
 O comando print() escreve na tela (monitor de vídeo) o texto (string) que foi usado 
como parâmetro. Este é o comando utilizado para escrever uma ou mais informações na 
saída padrão do computador. A forma geral do comando print() é mostrada a seguir: 
 print() 
71 
 Introdução à Programação com Python 
 A lista de parâmetros corresponde ao conjunto de informações que se deseja exibir. 
Quando houver mais de um parâmetro (ou valor) a ser exibido, eles devem ser separados 
por vírgulas. A Figura 4.1 apresenta alguns exemplos de comandos print() usando sempre 
mais de um parâmetro. Note que a tela da Figura 4.1 corresponde à janela de edição de 
programas do ambiente de desenvolvimento IDLE (segunda aparição, desde a Figura 1.7) e 
o arquivo de trabalho recebeu o nome de Figura4-1.py. 
 
 
Figura 4.1 - Exemplo de Comandos de Impressão 
 
Os comandos iniciais definem uma variável inteira (idade) e quatro variáveis do tipo 
string (sexo, nome, cabo e espessura). Note que para a variável cabo a delimitação da 
string que contém uma aspas simples (‘) foi feita com aspas duplas (“). Ou seja, quando a 
delimitação de uma string é iniciada com um tipo de aspas, ela deve ter o final de sua 
delimitação com o mesmo tipo de aspas. 
O primeiro comando print possui dois parâmetros: um texto (string) e a variável 
nome. Um texto sempre aparecerá da forma que está escrito entre as aspas. A variável será 
sempre substituída pelo seu valor. O resultado deste primeiro comando será: Nome: Carlos 
Alberto. Note que o espaço em branco (que é um caractere associado à barra de espaço do 
teclado) após Nome: na string (primeiro parâmetro) será exibido. Portanto, adicionar 
caracteres de espaço serve para separar duas informações em uma string. 
O segundo comando print é muito parecido com o primeiro, mas com 4 parâmetros 
ao invés de 2. O primeiro e terceiro parâmetros, que são strings, serão exibidos exatamente 
como foram escritos no comando print. Já o segundo (sexo) e quarto (idade) parâmetros 
são dois nomes de variáveis que serão substituídos pelo valoratual das respectivas 
variáveis presentes na memória (valor da última atribuição feita). 
Finalmente, o terceiro comando print possui apenas duas variáveis como 
parâmetros. Logo, serão exibidos os dois valores das variáveis cabo e espessura. Note que 
o comando print() insere um espaço em branco para separar os parâmetros na exibição. A 
Figura 4.2 apresenta a janela do Shell do ambiente IDLE, com o resultado da execução do 
programa. 
72 
 Introdução à Programação com Python 
 
Figura 4.2 - Resultado da Execução do código da Figura 4.1 
 
Observe que na janela do Shell é exibido apenas o resultado da execução do 
programa, ou seja, só irão aparecer os resultados de cada comando print() do programa. 
Observe também que na mensagem de ‘RESTART’ é indicado o nome do arquivo que foi 
executado (Figura4-1.py). 
 
 
4.1.2. Comando print() com separador e terminador 
 
O comando de impressão print() usa o caractere branco (ou espaço em branco ou 
espaço) como separador padrão, quando existem dois ou mais parâmetros. Observe que no 
último comando print() da Figura 4.1 existem duas variáveis do tipo string como parâmetros. 
A execução do comando resultou na impressão da primeira string, um caractere branco e a 
segunda string: Pirelli’s antichama 20”. O caractere branco está após o último caractere ‘a’ e 
antes do caractere ‘2’. 
É possível alterar o separador padrão utilizando o parâmetro sep= onde 
 corresponde à string de zero ou mais caracteres que se deseja usar para 
separar as informações. A Tabela 4.1 apresenta alguns exemplos de separadores e o 
resultado obtido com a execução do comando, considerando as variáveis definidas na 
Figura 4.1. 
Tabela 4.1 - Exemplos de uso do separador 
Comando Resultado da execução 
print(cabo, espessura, sep=’’) Pirelli's antichama20" 
print(cabo, espessura, sep=’***’) Pirelli's antichama***20" 
print(cabo, espessura, sep=’\t’) Pirelli's antichama 20" 
print(cabo, espessura, sep=’\n’) Pirelli's antichama 
20" 
 
73 
 Introdução à Programação com Python 
No primeiro comando da Tabela 4.1 foi utilizada a string vazia (0 caracteres) como 
separador e, por isso, as duas strings foram impressas como se não houvesse separação. 
No segundo comando o separador foi uma sequência de três asteriscos. Nos dois últimos 
comandos os separadores utilizados fazem parte do grupo de caracteres de controle (ou 
não imprimíveis). O caractere ’\t’ (lê-se contrabarra t) é o espaçamento de tabulação (tecla 
Tab existente nos teclados) que corresponde ao espaço de alguns caracteres (no resultado 
da execução do comando parece ser de 4 espaços). Já o caractere ‘\n’ (contrabarra n) 
corresponde ao “Carriage Return” (tecla Enter dos teclados) e indica que se deve ir para o 
início da próxima linha. Por isso o último comando print() da Tabela 4.1 utilizou duas linhas. 
O caractere ‘\n’ é o terminador padrão do comando de saída print(). Este padrão 
também pode ser alterado utilizando o parâmetro end= onde 
corresponde à string de zero ou mais caracteres que se deseja usar imediatamente após a 
impressão dos parâmetros imprimíveis. A Tabela 4.2 apresenta alguns comandos de 
impressão supondo, novamente, as variáveis criadas na Figura 4.1. 
Tabela 4.2 - Exemplos de utilização do parâmetro de terminação 
Comandos Resultado da Execução 
print(cabo, end=’’) 
print(espessura) 
Pirelli’s antichama20” 
print(cabo, end=’ ’) 
print(espessura) 
Pirelli’s antichama 20” 
print(cabo, end=’***’) 
print(espessura) 
Pirelli’s antichama***20” 
print(cabo, end=’\t’) 
print(espessura) 
Pirelli’s antichama 20” 
print(cabo, end=’\n’) 
print(espessura) 
Pirelli’s antichama 
20” 
 
O uso de separador e/ou terminador diferentes do padrão podem estratégias úteis 
para adequar a formatação da saída gerada pelo comando print(). Da mesma forma, os 
caracteres de controle ‘\n’ e ‘\t’ podem ser utilizados para adequar a formatação da saída, 
inclusive quando utilizados dentro de uma string. Por exemplo, o comando 
print("Pirelli's\tantichama\n20\"") gera a seguinte saída: 
Pirelli's antichama 
20" 
Note que a utilização dos caracteres ‘\t’ e ‘\n’ produziram o espaço de tabulação e a 
quebra de linha, ao serem usados antes e depois da palavra “antichama”, respectivamente. 
O contrabarra permite também que em uma string delimitada por aspas duplas, uma aspas 
dupla seja impressa. Isso ocorrerá se a aspas dupla estiver precedida pelo caractere ‘\’. Ou 
seja, o caractere ‘\’ é usado como um caractere de controle e terá o seu significado definido 
dependendo do caractere que vem na sequência. Por exemplo, o comando 
print("\t\"\\t\"\t\"\\n\"\n\\t\t\\n") irá gerar a seguinte saída: 
74 
 Introdução à Programação com Python 
"\t" "\n" 
\t \n 
O caractere de tabulação é definido somente quando aparece a sequência ‘\t’. Uma 
sequência de caracteres ‘\\t’ vai imprimir ‘\t’ na tela (sem as aspas). A mesma coisa vale 
para o ‘\n’. E, para imprimir as aspas duplas foi utilizada a sequência '\"' (contra barra aspas 
dupla) - usada quatro vezes. Certifique-se de que no comando anterior existem apenas 3 
tabulações ('\t') e um “pula linha” (\n) - estão em negrito no comando para facilitar o 
entendimento. 
 
4.1.3. Comando print() com apenas um parâmetro de texto 
 
 A linguagem Python permite tratar a exibição de várias informações como se 
houvesse apenas um único parâmetro de texto, ou uma única string. Mas, e quando se 
deseja imprimir uma informação que não é texto (um número, por exemplo)? Para fazer 
esta “mágica” o comando de impressão possui uma diretiva de importação de informações 
não textuais para dentro do texto. 
Esta diretiva de importação consiste na inserção do caractere % na string seguido 
do tipo da informação que será inserida no meio do texto: %d para um número inteiro 
(decimal), %f para um número de ponto flutuante e %s para uma variável do tipo string. 
Para informar qual valor de variável que será inserido no texto, deve ser informado o nome 
da variável precedido pelo caractere %, após o fechamento da string e sem o uso de vírgula 
para separar a string do nome da variável. A forma geral para utilizar o comando print desta 
forma seria: 
 print(‘...%... ‘ %) 
onde: especifica o tipo da variável e define o nome da variável a ser 
inserida no texto na posição indicada por %. 
No caso de importação de mais de um valor de variáveis para dentro do texto o 
caractere % seguido do tipo da variável deverá aparecer tantas vezes no corpo da string 
quantas forem as variáveis a serem importadas. Após o fechamento da string, deverá vir o 
caractere % seguido da lista de variáveis entre parênteses, na mesma ordem de aparição 
na string e separadas por vírgulas. A forma geral seria: 
print(‘...%...%... … ‘ %(, , … , para k = 1..N especifica o tipo da variável k e define o nome da 
variável k a ser inserida no texto na posição indicada por %. 
A Figura 4.3 apresenta o código do programa da Figura 4.1 reescrevendo os 
comandos de impressão (print()) usando um parâmetro do tipo string com a importação de 
valores de variáveis. 
75 
 Introdução à Programação com Python 
 
Figura 4.3 - Exemplos de comando print() usando um parâmetro tipo string 
 
Como o ambiente de desenvolvimento IDLE permite trabalhar com dois ou mais 
arquivos simultaneamente, o novo programa foi salvo com o nome Figura4-3.py, conforme 
pode ser observado no cabeçalho da janela. Observe que o primeiro comando print() 
importou apenas uma variável (nome) do tipo string para dentro do texto. O segundo 
comando print()importou duas variáveis (sexo e idade), cujos nomes aparecem entre 
parênteses e separadas por vírgula, após o cacartere %. Já o último comando a string foi 
criada apenas para importar o valor das duas variáveis já que não havia um texto no 
comando correspondente na Figura 4.1. Mas, observe com atenção que um texto foi criado: 
a colocação do caractere de espaço para separar o valor das duas variáveis importadas. 
Caso isto não fosse feito a impressão sairia assim: Pirelli’s antichama20”. 
Para mostrar a equivalência entre os comandos print() das Figuras 4.1 e 4.3, a 
Figura 4.4 apresenta o resultado da execução do código da Figura 4.3. A janela do Shell 
permanece a mesma que foi usada para a execução do programa anterior. A mensagem de 
RESTART que aparece antes da execução de cada programa sempre exibe o nome do 
arquivo fonte. Nesta segunda execução o arquivo fonte utilizado foi o arquivo de nome 
Figura4-3.py. 
 
 
Figura 4.4 - Resultado da Execução dos códigos das Figuras 4.1 e 4.3 
76 
 Introdução à Programação com Python 
As próximas figuras com exibição do resultado de execuções conterão apenas a 
informação referente à última execução feita, iniciando com a mensagem de RESTART. 
 
 
4.1.4. Formatação de dados no comando print() 
 
Considere o trecho de código para imprimir as informações de cadastro de três 
funcionários de uma loja fictícia, mostrado na Figura 4.5. 
 
Figura 4.5 - Exemplo de impressão de informações cadastrais 
O resultado da execução do trecho de código mostrado na Figura 4.5 é apresentado 
na Figura 4.6. Note que o código apresenta 3 comandos print() utilizando apenas os nomes 
das variáveis e 3 comandos print() utilizando a importação dos valores das variáveis para 
dentro de uma string. Existe ainda um print() sem parâmetros, com objetivo de separar os 
dois tipos conjuntos de comandos print() citados anteriormente. 
 
Figura 4.6 - Trecho da janela do Shell com o resultado da execução do código da Figura 4.5 
 
77 
 Introdução à Programação com Python 
Observe que a utilização da diretiva de importação (%) não ajudou muito na 
visualização. Na verdade, parece ter piorado pois os números que representam valores em 
Reais (moeda do Brasil em 2020) que estavam com duas casas decimais, passaram para 
seis casas decimais. Uma precisão desnecessária pois a menor unidade monetária é o 
centavo (exceto para postos de gasolina) e duas casas decimais bastariam. 
O caractere ‘%’ é chamado de operador de formatação de string e permite, dentre 
outras coisas, definir o número de casas decimais, ou a precisão, para exibir os números 
reais ou de ponto flutuante. Na verdade, a formatação permite definir o espaço que o valor 
irá ocupar. Cabe ao programador definir de maneira adequada este espaçamento para que 
o resultado desejado seja obtido. 
A Tabela 4.3 apresenta a forma geral de definição de espaçamento para os 
principais tipos de dados vistos até aqui. 
Tabela 4.3 - Uso do formatador para string, inteiro e ponto flutuante 
Tipo Formatador Observação 
String %Ns N: especifica o espaço total reservado para a exibição do valor 
(opcional). 
P: especifica a precisão (número de casas decimais), apenas no caso 
de números de ponto flutuante. 
As letras s (string), d (inteiro), f (ponto flutuante) e r (booleano) 
usadas no final especificam o tipo da informação a ser importada. 
Inteiro %Nd 
Ponto flutuante %N.Pf 
Booleano %Nr 
 
A definição do espaço para exibição do valor de uma variável usando o valor N (e P 
para número real) é opcional. No caso de número de ponto flutuante é possível especificar 
somente o número de casas decimais, deixando livre o espaço total, ou seja, é possível 
usar, por exemplo, '%.2f' para exibir um valor com duas casas decimais. O espaço total, 
neste caso, será definido pelo número de dígitos da parte inteira do valor. Se o valor na 
variável fosse 102.3516 o valor impresso seria 102.35, ocupando 6 espaços (o ponto 
decimal é contado). 
Caso o espaço total definido pelo parâmetro N seja maior do que o necessário, o 
efeito será a inserção de alguns caracteres em branco antes do início do valor impresso. 
Isto ocorre porque o alinhamento padrão é feito à direita. Quando se deseja inverter o 
alinhamento padrão, para que seja feito à esquerda, basta colocar o sinal negativo ‘-’ antes 
do valor do parâmetro N. 
Suponha que a informação dos três funcionários do código da Figura 4.5 deva ser 
apresentada como se fosse uma tabela, com as informações alinhadas como se estivessem 
em colunas de uma tabela. O comando para a impressão dos dados do primeiro funcionário 
poderia ser reescrito como: 
print('%-24s %-12s %3d %10.2f' %(nome1, cargo1, idade1, salario1)) 
O espaço de 24 caracteres (ou colunas no monitor de vídeo) para escrever o nome 
foi função do maior nome ter 20 caracteres. Da mesma forma, o valor 12 foi escolhido, para 
o espaço onde será escrito o cargo, justamente por ser um pouco maior do que a maior 
string de cargo (vendedora). Ambos terão alinhamento à esquerda por causa da utilização 
78 
 Introdução à Programação com Python 
do caractere ‘-’, antes do valor numérico que definiu o espaço. O espaço de 3 colunas (ou 
caracteres) foi definido para escrever o número inteiro de dois dígitos que representa a 
idade do funcionário. Finalmente, para escrever o valor do salário foi escolhido o 
espaçamento total de 10 colunas, com duas casas decimais. Estes dois últimos valores tem 
alinhamento padrão, à direita. 
Para exibir a informação dos outros dois servidores serão usados comandos de 
impressão com o mesmo espaçamento deste primeiro. Será colocado um comando 
adicional para imprimir um cabeçalho para a tabela, antes dos comandos para imprimir as 
informações dos funcionários. Este comando pode ser definido da seguinte maneira: 
print('Nome%20s Cargo%7s Idade Salário' %(' ', ' ')) 
O comando acima importa dois caracteres branco (ou espaço) para a string. 
‘Nome… ...Salário’. Para o primeiro caractere foram reservados 20 espaços que juntamente 
com os caracteres ‘Nome’ totalizam os mesmos 24 caracteres reservados para imprimir o 
nome do funcionário. Ou seja, os espaços escolhidos para a impressão do cabeçalho e para 
a impressão das informações dos servidores foram de tal forma a dar a ideia de uma tabela. 
A Figura 4.7 mostra o código com os comandos de impressão alterados conforme a 
discussão apresentada. 
 
Figura 4.7 - Código da Figura 4.5 com comandos de impressão reescritos 
 
Um detalhe importante a ser observado é que para este efeito de impressão do tipo 
tabela pressupõe, neste caso, que o tamanho total das strings sejam o mesmo, pois existe o 
alinhamento à esquerda da primeira coluna e o alinhamento à direita da última coluna. Note 
que a string do cabeçalho reserva 27 espaços, tem 4 caracteres branco (entre Idade e 
Salário são 2) e 21 letras (NomeCargoIdadeSalário) totalizando, portanto, um espaço de 52 
caracteres. E cada comando de impressão das informações do funcionário tem três 
caracteres branco (separando os formatadores para facilitar o entendimento) e reserva 
24+12+3+10=49 espaços, totalizando também um espaço de 52 caracteres. O resultado da 
execução do código mostrado na Figura 4.7 é apresentado na Figura 4.8. 
79 
 Introdução à Programação com Python 
 
Figura 4.8 - Resultado da execução do código da Figura 4.7 
 
 Caso os comandos de impressão das informações fossem reescritos sem os 
caracteres em branco, usados para facilitar a visualização, o espaçamento deveria ser 
alterado para manter o alinhamento por coluna com o mesmo número de espaços. Por 
exemplo, se o comando de exibição das informações do segundofuncionário fosse reescrito 
como: 
 print('%-25s%-13s%3d%11.2f' %(nome2, cargo2, idade2, salario2)) 
 O resultado gerado seria exatamente o mesmo da Figura 4.8 Como o parâmetro do 
comando print() é uma string, para cada espaço em branco retirado da string, um aumento 
no espaçamento foi feito. Observe que a string continuou com um tamanho total de 52 
caracteres (25+13+3+11). 
 
 
4.2 - Comando de Entrada 
 
 O comando input() permite ler um valor fornecido utilizando o dispositivo padrão de 
entrada, o teclado. O valor lido deve ser atribuído para uma variável. A forma geral do 
comando input() é a seguinte: 
 = input() 
 
 representa um nome válido de uma variável Python que receberá o valor 
lido. representa uma mensagem que será exibida na tela. Esta mensagem é útil para 
que o usuário seja orientado sobre qual a informação que deverá ser fornecida. 
 
A execução do comando input() causa uma parada na execução do programa que 
espera que uma informação seja enviada, ou uma entrada seja fornecida. No dispositivo 
padrão de entrada que é o teclado, após digitar o valor da entrada o seu envio é feito ao 
pressionar a tecla ‘Enter’. 
 
Um exemplo de um pequeno programa Python utilizando um comando de entrada e 
um comando de saída é mostrado na janela do editor do IDLE na Figura 4.9. A mesma 
figura apresenta também a janela do Shell sobreposta à janela do editor, com o resultado da 
execução do programa Figura4-9.py. 
80 
 Introdução à Programação com Python 
 
Figura 4.9 - Programa simples com comando de entrada e saída. 
 
Na janela do Shell do IDLE, conforme já observado, o texto em azul corresponde às 
informações geradas pelo comando de saída. Porém, a mensagem associada ao comando 
de entrada input() utiliza a mesma cor, pois no fundo trata-se de uma informação de saída, 
ou uma informação que é exibida pelo programa. Assim, o programa da Figura 4.9 exibe a 
mensagem ‘Entre com o seu nome: ’ e para, aguardando a entrada que será fornecida pelo 
usuário. 
 
O texto em preto ‘José da Silva’ foi fornecido pelo usuário do programa, que após a 
digitação deste texto, pressionou a tecla ‘Enter’. Neste momento, o valor da string ‘José da 
Silva’ é atribuído para a variável nome. Na sequência, o comando de impressão escreve na 
tela a string com a importação do valor da variável nome, resultando no texto em azul ‘Bom 
dia, José da Silva!’ 
 
Por padrão, na linguagem Python, o valor recebido via teclado é interpretado como 
string (uma sequência de caracteres). Se o usuário digitar ‘125’ este valor representa um 
texto com os caracteres que representam os algarismos 1, 2 e 5 e não o número 125. Para 
que uma entrada seja interpretada como um valor numérico inteiro ou real (ponto flutuante) 
é necessário explicitar a transformação usando int ou float, respectivamente. A Figura 4.10 
apresenta um pequeno programa exemplificando a transformação para inteiro e ponto 
flutuante. 
 
 Na Figura 4.10, a variável idade será do tipo inteiro (int) e na execução do programa 
lhe foi atribuído o valor 56. Já a variável altura será do tipo ponto flutuante (float) com valor 
definido na execução do programa igual a 1.77. Observando, mais uma vez, que na janela 
do Shell os valores em azul foram escritos pelo programa e os valores em preto foram 
fornecidos pelo usuário. 
81 
 Introdução à Programação com Python 
 
Figura 4.10 - Exemplo de transformação para inteiro e real 
 
 A conversão pode ser aplicada em qualquer comando de atribuição e não apenas 
em comandos de entrada e saída. Alguns exemplos comentados: 
 
 age = int(‘18’) # age recebe o valor inteiro 18 
 x = int(3.14) # x recebe o valor inteiro 3 
 alt = float(‘1.75’) # alt recebe o valor real 1.75 
 y = float(x) # y recebe o valor real 3.0 
 
4.3 - Usando os comandos de entrada e saída em programas 
simples 
 
 A seguir são apresentados dois problemas simples que, em princípio poderiam ser 
resolvidos com as informações vistas até aqui: algoritmos, refinamentos sucessivos, 
variáveis, expressões aritméticas e comandos de entrada e saída. 
 
 Na sequência será mostrado que para os dois casos a solução correta deve 
considerar outra estrutura de programação que será vista no próximo capítulo. Mas que 
com o conhecimento de algoritmos já é possível identificar o problema e resolvê-lo em 
termos de algoritmo. Porém, como as soluções agora são utilizando a linguagem Python, 
elas serão apresentadas no capítulo 5. 
4.3.1. Cálculo da área de um triângulo 
 
Considere que os valores (inteiros e positivos) a, b e c correspondem aos lados de 
um triângulo qualquer. Pelo Teorema de Heron, é possível determinar a área desse triângulo 
como sendo igual a: 
 
, onde 𝐴𝑟𝑒𝑎 = 𝑝(𝑝 − 𝑎)(𝑝 − 𝑏)(𝑝 − 𝑐) 𝑝 = (𝑎 + 𝑏 + 𝑐) ÷ 2
82 
 Introdução à Programação com Python 
 O problema a ser resolvido é muito simples e com as fórmulas necessárias já 
conhecidas. Aliás, conhecidas há muito tempo pois foram formuladas por Heron de 
Alexandria que foi um matemático grego que viveu nos anos 10 a 70 DC. O algoritmo para 
resolver este problema poderia ser apresentado como: 
1. Ler os valores a, b e c 
2. Calcular o valor de p 
3. Calcular a área 
4. Exibir a área calculada 
 
Uma versão refinada do algoritmo poderia ser escrita como: 
1. Leia(a) 
2. Leia(b) 
3. Leia(c) 
4. p = (a+b+c)/2 
5. area = raizquadrada(p.(p-a).(p-b).(p-c)) 
6. imprima(area) 
 
 Esta segunda versão já estaria em um nível de detalhe suficiente para a tradução 
para Python. Entretanto, como calcular a raiz quadrada? Em Python existe uma biblioteca 
matemática com diversas funções, dentre elas a função raiz quadrada. Mas, pode-se utilizar 
a exponenciação, cujo operador já foi apresentado no capítulo 3. Esta operação será 
detalhada na próxima versão do algoritmo. Também será inserida uma mensagem inicial 
para que um usuário que não seja o autor do programa saiba do que se trata. 
 
Feitas estas considerações, a versão final do algoritmo será: 
1. Imprima(‘Cálculo da área de um triângulo de lados a, b e c’) 
2. Leia(a) 
3. Leia(b) 
4. Leia(c) 
5. p = (a+b+c)/2 
6. area = (p.(p-a).(p-b).(p-c)) ** 0.5 
7. imprima(area) 
 
A Figura 4.11 apresenta o código Python correspondente. Note que o operador de 
multiplicação do algoritmo teve de ser convertido para o operador de multiplicação (*) da 
linguagem Python. 
 
 
Figura 4.11 - Programa para cálculo da área de um triângulo 
 
Para testar o funcionamento do programa, ele foi executado três vezes e os 
resultados destas três execuções estão mostrados na Figura 4.12, capturada da janela do 
Shell do IDLE. 
83 
 Introdução à Programação com Python 
 
Figura 4.12 - Três execuções do programa da Figura 4.11 
 
Para a primeira execução foram fornecidos os valores 4, 3 e 5 que representam os 
lados de um triângulo retângulo bastante utilizado nos livros de matemática quando se 
aborda o teorema de Pitágoras ( , o quadrado da hipotenusa (25) é igual a 𝑐² = 𝑎² + 𝑏²
soma do quadrado dos catetos (16+9)). Para este triângulo, a fórmula 
 é válida. Considerando que um dos catetos é a base do triângulo, á𝑟𝑒𝑎 = 𝑏𝑎𝑠𝑒 𝑥 𝑎𝑙𝑡𝑢𝑟𝑎 / 2
o outro cateto será a altura e o cálculo seria , mostrando que o cálculo á𝑟𝑒𝑎 = 4 𝑥 3 / 2 = 6
do programa está correto. 
 
Entretanto, as segunda e terceira execuções apresentaram resultados esquisitos. Na 
segunda o programa informou que a área do triângulo é zero! E na terceira ocorreu um erro 
na execução. O que ocorreu em ambas as situações é que os valores informados para os 
lados do triângulo não formam um triângulo. Para que seja possível formar um triângulo,nenhum dos lados pode ser maior ou igual a soma dos outros dois lados. 
 
Na segunda execução, o lado a é exatamente igual à soma dos lados b e c. 
Portanto, com , a propriedade para formar um triângulo não é satisfeita. Se você 𝑎 = 𝑏 + 𝑐
tentar desenhar um triângulo unindo os três segmentos de reta, perceberá que para fazer a 
união dos vértices, os lados b e c teriam que ficar sobre o lado a, formando uma figura que 
teria área zero. Mas que não é um triângulo, e sim um segmento de reta de tamanho 4. 
 
No terceiro caso, os valores informados para os lados também não permitem a 
formação de um triângulo, pois . Além disso, o cálculo do valor de 𝑎 > 𝑏 + 𝑐
será igual a 3.5. O fator será -0.5, levando o produto 𝑝 = (𝑎 + 𝑏 + 𝑐)/2 (𝑝 − 𝑎)
a um valor negativo (-7). Na linguagem Python o cálculo de 𝑝 * (𝑝 − 𝑎) * (𝑝 − 𝑏) * (𝑝 − 𝑐)
é feito, mas o resultado é um número complexo e no comando de impressão foi − 7
suposto que o tipo da variável area seria um número de ponto flutuante. A mensagem de 
erro do Shell (TypeError: can’t convert complex to float) informa que não foi possível 
converter um número complexo para ponto flutuante. 
 
Mas, este erro só ocorreu porque a condição necessária para determinar se com os 
valores informados para os lados (a, b e c) seria, de fato, possível formar um triângulo. Esta 
84 
 Introdução à Programação com Python 
condição deveria ser verificada antes de se fazer o cálculo da área. E, em caso negativo, 
deveria ser informado ao usuário que não é possível representar um triângulo com os 
valores fornecidos. No próximo capítulo será apresentada a solução para este caso. 
 
 
4.3.2. Cálculo das raízes de uma equação do segundo grau 
 
Um outro problema bastante conhecido é o cálculo das raízes de uma equação do 
segundo grau definida pela expressão ou representada como uma 𝑎𝑥² + 𝑏𝑥 + 𝑐 = 0
função . Os coeficientes a, b e c são valores reais e o coeficiente a 𝑓(𝑥) = 𝑎𝑥² + 𝑏𝑥 + 𝑐
deve ser diferente de zero, pois caso contrário a função não será de segundo grau (x²). 
 
O cálculo das raízes de uma equação de segundo grau pode ser feito utilizando a 
fórmula de Bháskara . 𝑥 = (− 𝑏 ± 𝑏² − 4𝑎𝑐)/2𝑎
 
Conhecendo o problema e sabendo como calcular a resposta, o seguinte algoritmo 
poderia ser proposto: 
1. Imprima(‘Forneça os coeficientes da equação de segundo grau’) 
2. Leia(a) 
3. Leia(b) 
4. Leia(c) 
5. 𝑥1 = (− 𝑏 + 𝑏² − 4𝑎𝑐)/2𝑎
6. 𝑥2 = (− 𝑏 − 𝑏² − 4𝑎𝑐)/2𝑎
7. Imprima(x1, x2) 
 
 A implementação do algoritmo acima está mostrado na Figura 4.13. Note que no 
algoritmo não há uma preocupação formal com a ordem de execução das operações, 
diferentemente do que ocorre nas linguagens de programação. No algoritmo, o numerador 
foi colocado entre parênteses, indicando que todas as suas operações devem ser feitas 
antes da divisão por “2a”. 
 
Porém, se o divisor (2*a) não for colocado entre parênteses no programa Python, 
ocorrerá primeiro uma divisão por 2 e depois uma multiplicação por a. A colocação dos 
parênteses forçará primeiro a ocorrência da multiplicação 2*a e, depois, a divisão por “2a”. 
Observe que a expressão para cálculo da segunda raiz escreve de maneira diferente (e 
correta) o divisor “2a”. O cálculo de b² também foi feito de maneira diferente nas duas 
expressões, mas ambas corretas. 
 
 
Figura 4.13 - Programa para cálculo de raízes de equação do segundo grau 
 
Para testar o programa foram feitas três execuções para diferentes valores de 
coeficientes. Nas duas primeiras execuções o programa respondeu corretamente com as 
85 
 Introdução à Programação com Python 
raízes das duas equações. Porém, na terceira execução o Shell apontou um erro de divisão 
por zero (ZeroDivisionError: float division by zero), conforme mostrado na Figura 4.14. 
 
 
Figura 4.14 - Resultado de execuções do programa da Figura 4.13 
 
A razão do erro está no fato do valor fornecido para o coeficiente a ter sido zero. A 
fórmula de Bháskara pressupõe que o coeficiente a será diferente de zero. De fato, se a for 
zero, a equação não será de segundo grau. Para a terceira execução, com os coeficientes 
informados, a equação seria: uma equação de primeiro grau. 2𝑥 + 1 = 0
 
O programa deveria ter verificado se o valor fornecido para o coeficiente a é 
diferente de zero, para prosseguir com o cálculo. Se o valor for zero do coeficiente a for 
zero, a equação não é de segundo grau e, portanto, o programa deveria informar que com 
este valor não é possível calcular as raízes e terminar a execução do programa. De forma 
similar ao exemplo de cálculo de área de triângulo, cuja solução será vista no próximo 
capítulo. 
 
Alternativamente, o programa poderia informar que o valor zero é inválido e solicitar 
que o usuário forneça uma novo valor. E só prosseguir com a execução do programa após o 
usuário fornecer um valor diferente de zero. Este tipo de solução será visto no capítulo 6 
com a apresentação das estruturas de comando repetitivo da linguagem Python. 
 
4.4. Exercícios 
 
1) Edite o trecho de código do exercício 1 do capítulo 3 usando o editor de programas 
do IDLE e inclua comandos de impressão para informar os nomes e os valores das 
variáveis separadas por tipo (inteiro ou de ponto flutuante). A saída do programa 
deve ser como a mostrada a seguir: 
86 
 Introdução à Programação com Python 
 
 
 
2) Altere os comandos de impressão do exercício anterior para gerar uma saída similar 
à mostrada a seguir. A quebra de linha será determinada pela largura da janela do 
Shell, por isso o resultado deve ser similar e não exatamente igual ao exibido 
abaixo. Na solução deve haver um único comando para imprimir os nomes e valores 
das variáveis inteiras e um outro único comando para imprimir os nomes e valores 
para as variáveis reais (ou de ponto flutuante). As mensagens de texto devem ser 
feitas em comandos de impressão separados, ou seja, deverão existir apenas 4 
comandos de impressão no programa. 
 
 
3) Altere os comandos de impressão do exercício anterior para gerar uma saída igual 
à mostrada a seguir, onde os números de ponto flutuante são apresentados com 
precisão de 3 casas decimais (use %f para formatar os números reais). 
 
 
4) Modifique os comandos de impressão usados no exercício anterior para mostrar a 
saída com os valores exibidos em colunas de largura 6 (use %d para formatar 
também os números inteiros). Observe com atenção que os caracteres de texto (“,” e 
“e”) usados na versão anterior para separar as informações não são mais exibidos. 
87 
 Introdução à Programação com Python 
 
 
5) A solução adotada no exercício anterior não ficou visualmente agradável, 
particularmente para os valores inteiros, que aparecem longe do caractere “=”. Altere 
os comandos de impressão para que a saída seja igual à mostrada a seguir: 
 
 
6) Para melhorar a organização visual da saída, altere os comandos de impressão para 
que os valores sejam impressos com espaço total 10, tendo no máximo 3 valores 
por linha, como mostrado a seguir. Dica: use a quebra de string (\n) e mantenha o 
mesmo número de comandos print da versão anterior. 
 
 
7) Mude o comando de atribuição da variável inteira A para que a atribuição seja feita 
por um valor fornecido pelo usuário. Note na figura mostrada a seguir que o valor 
digitado pelo usuário aparece na cor preta, enquanto que os valores escritos pelo 
programa aparecem em azul. Altere também o comando de impressão das variáveis 
de ponto flutuante, para que o alinhamento seja feito à direita (alinhando o ponto 
decimal dos valores). Na figura é mostrado um exemplo no qual o usuário forneceu o 
valor10. 
 
 
8) Altere o programa para que sejam lidos dois valores: um inteiro que será atribuído 
para a variável A e outro valor real que será atribuído para a variável E. O programa 
deve deixar claro para o usuário que o primeiro valor tem que ser inteiro e o segundo 
88 
 Introdução à Programação com Python 
um valor real. A figura mostrada a seguir apresenta um exemplo de execução no 
qual o usuário informou os valores 12 e 3.5, nesta ordem. 
 
 
9) Edite o trecho de código do exercício 2 do capítulo 3 usando o editor de programas 
do IDLE e inclua comandos de impressão para informar os nomes e os valores das 
variáveis separadas por tipo (inteiro ou booleano). A saída do programa deve ser 
como a mostrada a seguir: 
 
 
10) Altere os comandos de impressão do exercício anterior para gerar a saída similar à 
mostrada na figura a seguir. O programa deve usar um único comando para imprimir 
os nomes e valores de todas as variáveis inteiras e um outro único comando para 
imprimir os nomes e valores de todas as variáveis booleanas. As mensagens de 
texto devem ser feitas em comandos de impressão separados, ou seja, deverão 
existir apenas 4 comandos de impressão no programa. 
 
 
11) Modifique os comandos de impressão do exercício anterior, utilizando um espaço de 
5 posições para imprimir o valor de cada variável (inteira ou booleana). Deverão ser 
89 
 Introdução à Programação com Python 
impressas até 4 variáveis por linha, para gerar uma saída exatamente igual à 
mostrada a seguir. 
 
 
12) Modifique os comandos de impressão da versão anterior para que o programa gere 
a saída igual à mostrada a seguir. 
 
 
13) No programa gerado para resolver o exercício anterior, inclua comandos de leitura 
para que o usuário forneça o valor das 3 variáveis inteiras (A, B e C). Com valores 
diferentes, algumas das expressões podem gerar resultados diferentes, modificando 
os valores das variáveis booleanas. A figura mostrada a seguir apresenta o 
resultado da execução na qual o usuário forneceu os valores -10, 13 e 10, 
respectivamente, para as variáveis A, B e C. 
 
 
14) Escreva um programa para imprimir as variáveis tipo texto do exercício 3 do capítulo 
3, sendo uma variável em cada linha. No final do programa, inclua os comandos 
mostrados a seguir e observe as diferenças entre as saídas. 
 
print('\nNome: %s %s Sexo: %s' %(nome, sobrenome, sexo)) 
print('\nNome:\t%s %s\tSexo:\t%s' %(nome, sobrenome, sexo)) 
print('\nNome:%s %30s Sexo:%10s' %(nome, sobrenome, sexo)) 
print('\nNome:%s %-30s Sexo:%-10s' %(nome, sobrenome, sexo)) 
print('\Nome:\t%s %s\nSexo:\t%s' %(nome, sobrenome, sexo)) 
 
 
90 
 Introdução à Programação com Python 
15) Escreva um programa que solicite ao usuário o valor de temperatura em graus 
Fahrenheit, calcule e informe o valor correspondente em graus Celsius, de acordo 
com a fórmula: . O programa deverá informar o resultado com 1 casa 𝐶
5 = 𝐹−32
9
decimal, conforme o exemplo mostrado a seguir. 
 
 
16) Escreva um programa para calcular a área de um círculo, sabendo o valor do raio 
(R). O programa deverá gerar uma saída como a mostrada a seguir. 
 
 
17) Escreva um programa para calcular o k-ésimo elemento de uma Progressão 
Aritmética cujos valores do primeiro elemento e da razão serão fornecidos pelo 
usuário. O programa deverá calcular também a soma dos k elementos da PA. A 
execução do programa deverá ser como o mostrado na figura a seguir. Dica: 
pesquise na Internet a fórmula da soma dos elementos de uma PA. 
 
 
18) Escreva um programa para calcular a soma dos N primeiros elementos de uma 
Progressão Geométrica (PG), cujos valores do primeiro elemento e da razão serão 
solicitados ao usuário. O programa deverá informar também o valor do N-ésimo 
elemento. A figura a seguir mostra um exemplo de como deve ser a execução do 
programa. Dica: pesquise na Internet a fórmula da soma dos elementos de uma PG. 
 
 
 
 
91 
 Introdução à Programação com Python 
Capítulo 5 - Comandos Condicionais 
 
 
A estrutura de comando condicional permite definir caminhos alternativos para o 
fluxo de execução do programa. Até este ponto os programas apresentados foram todos 
sequenciais, onde a execução era iniciada pelo primeiro comando (primeira linha do código 
fonte) e depois percorria sequencialmente as demais linhas do código, até chegar ao seu 
final. 
 
No final do capítulo passado vimos dois exemplos de programas que podem 
apresentar falhas na execução dependendo dos valores fornecidos pelo usuário (cálculo da 
área de um triângulo e cálculo das raízes de uma equação do segundo grau). Para estes 
dois casos, a solução passa por validar os valores fornecidos pelo usuário, usando um (ou 
mais) comandos condicionais. 
 
5.1. Comando if 
 
Em algumas situações um comando ou um bloco de comandos só deve ser 
executado quando uma determinada condição for verdadeira. Para isto, na linguagem 
Python existe a estrutura de comando condicional mostrada na Figura 5.1. 
 
 if : 
 
 
Figura 5.1 - Estrutura de comando condicional if 
 
Note que, na sintaxe da linguagem Python, o comando é definido pela palavra 
reservada if, uma finalizada pelo caracter ‘:‘ e, na sequência um bloco de um ou 
mais comandos deslocados à direita, representado por na Figura 5.1. Este 
deslocamento à direita ou indentação do código é obrigatório na linguagem Python, sendo 
considerado um erro de sintaxe a sua não utilização. 
 
A execução do comando condicional se dá da seguinte maneira: primeiramente a 
condição é avaliada e caso o resultado da avaliação seja verdadeiro, o bloco de comandos 
vinculados à condição será executado. Se a condição for falsa, o bloco de comandos não 
será executado, passando-se para o próximo comando. Portanto, com este tipo de 
estrutura, um comando (ou um bloco de comandos) poderá ser executado ou não, 
dependendo da condição ser verdadeira ou falsa. 
 
A indentação (deslocamento) auxilia na identificação visual dos comandos que serão 
executados condicionalmente e, além disso, define quais são os comandos que pertencem 
ao bloco de comandos. O próximo comando sequencial deverá ser escrito alinhado com a 
92 
 Introdução à Programação com Python 
palavra reservada if. Considere a Tabela 5.1 com um código genérico de comandos Ci e o 
fluxo de execução para os casos da condição ser verdadeira ou falsa. 
 
Tabela 5.1 - Exemplos dos dois fluxos de execução possíveis de comandos condicionais 
Código Sequência de execução quando 
 == True 
Sequência de execução quando 
 == False 
C1 
C2 
if : 
 C3 
 C4 
C5 
C6 
C1 
C2 
C3 
C4 
C5 
C6 
C1 
C2 
C5 
C6 
C1 
C2 
if : 
 C3 
C4 
C5 
C6 
C1 
C2 
C3 
C4 
C5 
C6 
C1 
C2 
C4 
C5 
C6 
 
 
Para exemplificar, considere o programa para cálculo da área de triângulos da seção 
4.3.1. Para evitar o erro de tentativa de cálculo de área com lados que não formam um 
triângulo é necessário testar se com os valores fornecidos para os lados (a, b e c) é 
possível construir um triângulo. Em caso positivo, o cálculo será feito. O algoritmo poderia 
ser reescrito da seguinte forma: 
 
1. Imprima(‘Cálculo da área de um triângulo de lados a, b e c’) 
2. Leia(a) 
3. Leia(b) 
4. Leia(c) 
5. Se “é triângulo?” : 
5.1. p = (a+b+c)/2 
5.2. area = (p.(p-a).(p-b).(p-c)) ** 0.5 
5.3. imprima(area) 
 
 Note que os comandos 5.1, 5.2 e 5.3 constituem o bloco de comandos 
condicionados ao teste “é triangulo?” e que, portanto, só serão executados quandoo teste 
for verdadeiro. Caso o teste seja falso, o programa vai para o próximo comando, que não 
existe, ou seja, o programa termina sem que o cálculo seja feito. 
 
A condição “é triângulo?” consiste em testar, para cada lado se este lado é menor 
que a soma dos outros dois lados. A condição tem que ser verdadeira para cada um dos 
lados, logo a junção deve ser feita pela função lógica E (and), como a seguir: 
 
 𝑎 : 
 
 else: 
 
Figura 5.4 - Estrutura de comando condicional if/else 
 
A sintaxe do comando é a mesma do comando if simples, com a inclusão da 
cláusula else identificada pela palavra reservada else e o caractere ’:’. A palavra reservada 
else deve estar alinhada com a palavra reservada if. Os blocos de comandos da cláusula if 
e da cláusula else devem estar alinhados e deslocados para a direita. Esta é a indentação 
definida para o comando if-else. 
 
No comando condicional, o teste da condição sempre é executado primeiro. Caso o 
teste seja verdadeiro será executado. Caso contrário (else), será 
executado. Ou seja, o fluxo de execução do programa neste tipo de estrutura tem dois 
caminhos alternativos. Em uma execução, um dos dois blocos sempre será executado, mas 
apenas ele. Os blocos e nunca serão executados em sequência. 
A execução de um bloco, exclui necessariamente a execução do outro. O resultado da 
avaliação da expressão irá determinar qual dos dois será executado. 
 
 
Tabela 5.2 - Exemplos dos dois fluxos de execução possíveis de comandos condicionais 
Código = True = False 
C1 
if : 
 C2 
 C3 
else: 
 C4 
 C5 
C6 
C1 
C2 
C3 
C6 
 
 
C1 
C4 
C5 
C6 
 
 
C1 
if : 
 C2 
 C3 
else: 
 C4 
C5 
C6 
C1 
C2 
C3 
C5 
C6 
C1 
C4 
C5 
 C6 
 
95 
 Introdução à Programação com Python 
Para exemplificar, o algoritmo para cálculo da área de triângulos pode ser 
ligeiramente modificado para informar ao usuário que os valores informados para os lados 
do triângulo não permitem formar um triângulo: 
 
Imprima(‘Cálculo da área de um triângulo de lados a, b e c’) 
Leia(a) 
Leia(b) 
Leia(c) 
Se a= b+c : 
 imprima(‘a deve ser menor que (b+c)’) 
 senão: 
 se b>=a+c : 
 imprima(‘b deve ser menor que (a+c)’) 
 senão: 
 imprima(‘c deve ser menor que (a+b)’) 
96 
 Introdução à Programação com Python 
 
 
Figura 5.6 - Programa Python com uso de comandos if aninhados 
 
O código correspondente a este algoritmo é apresentado na Figura 5.6. Este tipo de 
solução utiliza comandos condicionais aninhados. Na execução deste código sempre que a 
condição do primeiro comando condicional for verdadeira (linha 5), o bloco de comandos 
para calcular e informar a área (linhas 6-8) será executado e o programa termina. 
 
Quando o resultado da condição do primeiro comando condicional for falsa, o fluxo 
de execução vai para o bloco de comandos da cláusula else e os dois comandos de 
impressão (linhas 10 e 11) são executados. Na sequência é testada a condição (linha 12) do 
comando if que verifica se foi o lado a que violou a condição de formação do triângulo. Se 
esta condição for verdadeira será informado para o usuário que ‘a deve ser menor que 
(b+c)’ e o programa termina. 
 
Se a condição da linha 12 for falsa, o fluxo de execução será desviado para a 
cláusula else correspondente (linha 14) e um novo teste do comando condicional da linha 
15 será realizado. Este teste verifica se foi o lado b que violou a condição de formação de 
triângulo. Sendo verdadeira esta condição (linha 15) a mensagem ‘b deve ser menor que 
(a+c)’ será impressa e o programa termina. E, finalmente, se a condição da linha 15 for 
falsa, o comando de impressão da última linha escreverá ‘c deve ser menor que (a+b)’ 
informando que o problema é com o lado c. Repare não foi necessário colocar um terceiro 
teste para saber se o problema foi devido ao lado c, pois para chegar nesta última linha, 
ambos os testes que verificaram, respectivamente, se o problemaera com o lado a e b 
foram falsos. 
 
5.3 Comando if-elif-else 
 
O uso dos comandos condicionais aninhados possui uma desvantagem em relação 
à organização do código. Quando o nível de aninhamento começa a aumentar, a indentação 
obrigatória dos blocos, vai fazendo um deslocamento do código para a direita. Isso, muitas 
vezes, prejudica uma visualização de trechos do código na janela do editor de programas. 
 
A linguagem Python possui uma outra forma de comando condicional que permite 
resolver este problema. A estrutura if-elif-else é mostrada na Figura 5.7. 
97 
 Introdução à Programação com Python 
 if : 
 
 elif : 
 
 … 
 elif : 
 
 ... 
 else: 
 
Figura 5.7 - Estrutura de comando condicional if/elif/else 
 
 
A sintaxe do comando é a mesma do comando if-else com a inclusão da cláusula elif 
entre elas. Podem existir uma ou mais cláusulas elif sendo que cada uma deve especificar 
uma sucedida pelo caractere ‘:’. A palavra reservada elif deve estar alinhada 
com as palavras reservadas if e else. Os blocos de comandos das cláusulas if, elif e else 
devem estar alinhados e deslocados para a direita. Esta é a indentação definida para o 
comando if-elif-else. 
 
O funcionamento desta estrutura é equivalente à utilização de comandos 
condicionais (if) aninhados. A é testada e se for verdadeira, será 
executado e o comando condicional termina. Se for falsa, o fluxo de execução 
vai testar a . Se esta segunda condição for verdadeira, será 
executado e o comando condicional termina. Podem existir várias cláusulas elif, cada uma 
com uma condição a ser testada. Se todas as N condições forem testadas e todos os 
resultados forem falsos, o bloco associado à cláusula else será executado. 
As condições são testadas na ordem em que aparecem no comando. Se houver duas ou 
mais condições verdadeiras, a condição que aparece primeiro, ao ser testada, fará com que 
o bloco de comandos associado a ela seja executado e o comando condicional termina. 
 
Note que, com esta estrutura, todos os blocos do comando condicional estarão com 
o mesmo alinhamento ou com a mesma indentação. A Tabela 5.3 exemplifica os possíveis 
fluxos de instrução para um comando if-elif-else com duas condições. 
 
Tabela 5.3 - Exemplos dos possíveis fluxos de execução de um comando if-elif-else. 
Código = True 
 não 
importa 
 = False 
 = True 
 = False 
 = False 
C1 
if : 
 C2 
 C3 
elif : 
 C4 
 C5 
else: 
 C6 
 C7 
C8 
C1 
C2 
C3 
C8 
 
 
C1 
C4 
C5 
C8 
 
 
C1 
C6 
C7 
C8 
 
 
98 
 Introdução à Programação com Python 
 
No algoritmo a cláusula elif pode ser escrita como “Senãose”. Usando esta notação, 
o final do algoritmo que identifica e informa qual o lado do triângulo que está violando a 
condição pode ser reescrito como: 
 
imprima(‘Os lados informados não formam um triângulo’) 
 imprima(‘Nenhum dos lados pode ser maior ou igual à soma dos outros lados’) 
 Se a >= b+c : 
 imprima(‘a deve ser menor que (b+c)’) 
 Senãose b>=a+c : 
 imprima(‘b deve ser menor que (a+c)’) 
 Senão: 
 imprima(‘c deve ser menor que (a+b)’) 
 
Ao analisar o algoritmo, foi percebido que a mensagem do tipo ‘a deve ser menor 
que (b+c)’ não representa bem a informação, por exemplo, quando o lado a está violando a 
condição de formação do triângulo. Talvez fosse melhor usar algo do tipo ‘a >= (b+c)’. Ou de 
forma mais detalhada, usando o potencial da estrutura condicional que permite vários 
“senãose” e informar mais precisamente que ‘a > (b+c)’ ou ‘a = (b+c)’. Dessa forma, o final 
do algoritmo pode ser reescrito como: 
 
imprima(‘Os lados informados não formam um triângulo’) 
 imprima(‘Nenhum dos lados pode ser maior ou igual à soma dos outros lados’) 
 Se a > b+c : 
 imprima(‘a > (b+c)’) 
 Senãose a==b+c : 
 imprima(‘a = (b+c)’) 
Senãose b>a+c : 
 imprima(‘b > (a+c)’) 
 Senãose b==a+c : 
 imprima(‘b = (a+c)’) 
 Senãose c>a+b : 
 imprima(‘c > (a+b)’) 
 Senão: 
 imprima(‘c = (a+b)’) 
 
A Figura 5.8 apresenta a versão final do programa completo para cálculo da área de 
um triângulo utilizando a estrutura if-elif-else. 
 
99 
 Introdução à Programação com Python 
 
 
Figura 5.8 - Versão final do programa para cálculo da área de um triângulo 
 
A Figura 5.9 mostra a captura de janelas do comando if-elif-else do programa da 
Figura 5.8, ao lado de outro código utilizando comandos condicionais aninhados. Note como 
a versão if-elif-else fica mais compacta. Ambos possuem as mesmas comparações, na 
mesma ordem, e os mesmos comandos de impressão. Nos dois casos, o resultado será o 
mesmo: a impressão de apenas uma das seis mensagens, sempre que os lados não 
formarem um triângulo. 
 
 
Figura 5.9 - Comparação entre o uso de ifs aninhados e if-elif-else 
 
A Figura 5.10 mostra o resultado da execução do programa da Figura 5.8 para as 
mesmas três situações da Figura 5.3. Na primeira execução é possível calcular a área e nas 
duas seguintes não. 
 
100 
 Introdução à Programação com Python 
 
Figura 5.10 - Exemplos de execução da versão final do programa Figura 5.8 
 
 
5.4 Cálculo de raízes de uma equação do 2⁰ grau 
 
O problema introduzido na seção 4.3.2 trata do cálculo das raízes de uma equação 
do segundo grau, na forma , tendo sido implementado um programa 𝑎𝑥² + 𝑏𝑥 + 𝑐 = 0
mostrado na Figura 4.13. Conforme discutido naquela seção, o programa proposto como 
solução possui um problema por não testar se o valor fornecido pelo usuário para o 
coeficiente a era diferente de zero. A solução para este problema seria trivial com o uso de 
comando condicional, para calcular as raízes apenas quando o coeficiente fosse diferente 
de zero. 
 
Um outro caso que precisa ser testado é referente ao discriminante da equação, 
definido como . O discriminante define o número de raízes reais que a Δ = 𝑏² − 4𝑎𝑐
equação de segundo grau terá: 
● , duas raízes diferentes Δ > 0
● , uma raiz (ou duas raízes iguais) Δ = 0
● , não possui raízes reais. Δ 0
pontos distintos, com o ponto de máximo (ou mínimo) da curva fica sobre o eixo x Δ = 0 
(abcissas) e no caso de a curva não corta o eixo x. As equações , ΔObserve que o cálculo do valor do discriminante (delta), para ser testado e 
definir o tipo equação, também auxilia a escrever expressões mais simples, substituindo a 
expressão pelo nome da variável (delta) que recebeu o valor da 𝑏 ** 2 − 4 * 𝑎 * 𝑐
expressão (linha 8 do código). 
 
 
Figura 5.11 - Programa para cálculo de raízes de equação do 2⁰ grau 
 
 
Alguns resultados de execução do programa da Figura 5.11 são apresentados na 
Figura 5.1. As três primeiras execuções correspondem às equações , 𝑥² − 2𝑥 + 1 = 0
 e que foram utilizadas para exemplificar os 3 casos: , uma 𝑥² − 4 = 0 𝑥² + 1 = 0 Δ = 0
raiz; , duas raízes reais, e; , nenhuma raiz real. E na quarta execução foi Δ > 0 Δ■ Calcula-se P'' = (P' – 7) e a Páscoa será a P'' de Abril, já que 
não pode ser celebrada em data posterior a 25 de Abril. 
 
 
Faça um programa que leia um ano e diga o dia e mês que ocorreu (ou ocorrerá) a 
Páscoa naquele ano. Lembre-se de verificar se o ano digitado é válido e se está 
presente na tabela acima. Veja os exemplos: 
 
Digite um ano: 2011 
Em 2011 a Páscoa foi ou será em 24 de Abril. 
 
Digite um ano: 2002 
Em 2002 a Páscoa foi ou será em 31 de Março. 
 
18) Reescreva o código da Figura 5.11 usando apenas 1 comando condicional 
(if-elif-else). Dica: faça o cálculo do determinante ( ) logo após a leitura dos valores Δ
dos coeficientes e antes do comando condicional. 
 
 
 
 
107 
 Introdução à Programação com Python 
Capítulo 6 - Comandos Repetitivos 
 
A estrutura de comando repetitivo permite executar uma mesma tarefa tantas vezes 
quantas sejam necessárias. Em computação este é um fato muito comum: executar tarefas 
repetitivamente. Aliás, essa é uma das grandes vantagens dos computadores: a rapidez e 
eficiência para executar tarefas repetitivamente. Tarefas que se tivessem que ser 
executadas por um ser humano, o deixariam extremamente chateado, cansado e, talvez, 
louco, iriam demorar muito mais e, muito provavelmente, estaria com erros. Imagine, por 
exemplo, conferir todas as apostas de uma loteria de final de ano (algo em torno de 50 
milhões). 
 
Neste capítulo serão apresentadas duas estruturas de comando repetitivo Python: 
while e for. Estas estruturas permitem resolver alguns dos problemas já mencionados no 
capítulo 4. E, em conjunto com as estruturas condicional e sequencial permitem escrever 
qualquer programa. 
 
 
6.1. Comando while 
 
Considere o exemplo do programa visto no final do Capítulo 5 no qual um valor igual 
a zero não permite o cálculo pois ele representa o coeficiente a do termo da equação de 𝑎𝑥²
segundo grau que, com este termo igual a zero deixa de ser de segundo grau. Em termos 
de algoritmo, a estrutura repetitiva já foi vista na seção 2.6. Para esta caso, o trecho de 
algoritmo poderia ser escrito como: 
 
Leia(a) 
enquanto a == 0: 
 imprima(‘Valor tem que ser diferente de 0 (zero)’) 
 Leia(a) 
 
A linguagem Python possui o comando while que permite mapear trechos de 
algoritmo, como o mostrado acima. A forma geral do comando while é mostrada na Figura 
6.1. 
 
while : 
 
 
Figura 6.1 - Forma geral do comando while 
 
A sintaxe do comando é definida com a palavra reservada while, seguida de uma 
 finalizada pelo caracter ‘:‘ e, na sequência um bloco de um ou mais comandos 
deslocados à direita, representado por na Figura 6.1. Como nos comandos 
anteriores, a indentação do código é obrigatória na linguagem Python, sendo considerado 
um erro de sintaxe a sua não utilização. 
108 
 Introdução à Programação com Python 
A execução do comando while tem início com a avaliação da . Quando a 
condição for verdadeira, será executado e a condição será novamente 
avaliada, ao final de cada execução do bloco de comandos. Quando a condição avaliada 
tiver resultado falso, o comando while termina. Observe que, funcionando desta forma, o 
 poderá ser executado zero ou mais vezes. O nome while (enquanto) escolhido 
para o comando indica de maneira clara que: enquanto a condição for verdadeira a 
execução do comando vai ser repetida. 
 
A Figura 6.2 mostra uma parte da janela do editor de programas e da janela do Shell 
com o resultado da execução na qual o usuário fornece o valor zero duas vezes. Na terceira 
vez é fornecido o valor 1 e o programa solicita o valor do coeficiente b. 
 
 
Figura 6.2 - Uso do while para validar uma entrada diferente de zero 
 
Observe que a estrutura é exatamente a mesma usada no algoritmo do início desta 
seção: um comando de leitura (input()) para atribuir um valor para a variável a; o comando 
repetitivo while com um bloco de dois comandos (uma mensagem de erro e o mesmo 
comando de leitura usado antes do comando repetitivo). 
 
O comando de leitura antes do comando repetitivo é necessário para definir o valor 
da variável a que será usada no teste do comando repetitivo que vem na sequência. Caso 
este comando de leitura seja omitido, haverá um erro de sintaxe no teste da condição do 
comando repetitivo, pois a variável a ainda não estaria definida. Ou seja, é importante 
garantir que todos os valores de variáveis que compõem a expressão da condição já 
estejam definidas antes do início do while. 
 
E o comando de leitura dentro do bloco de comandos do comando repetitivo é 
fundamental, pois ele é que irá causar a atribuição de um novo valor para a variável a. 
Quando o valor atribuído para a variável a for diferente de zero, o próximo teste da condição 
do comando repetitivo resultará no valor Falso e o comando repetitivo terminará. 
 
109 
 Introdução à Programação com Python 
 
6.1.1. Cuidado com o loop infinito 
 
O que aconteceria se o comando de leitura não fosse repetido dentro do bloco de 
comandos repetitivos? A resposta pode ser visualizada na Figura 6.3. Note que a 
“eliminação” do comando de leitura interno ao comando repetitivo foi feita com a colocação 
de um caractere ‘#’, transformando o comando em um comentário. Os comentários são 
ignorados pelo interpretador e aparecem na cor vermelha no editor de programas do IDLE. 
A Figura 6.3, mostra o trecho de código com a alteração e a janela do Shell com o resultado 
de duas execuções, a primeira com a = 1, b = 3, c = -4 e a segunda com a = 0. 
 
 
Figura 6.3 - Código com possibilidade de loop infinito 
 
110 
 Introdução à Programação com Python 
Observe que na primeira execução, o comando repetitivo foi executado zero vezes, 
pois para o primeiro valor fornecido para o coeficiente a, igual a 1, a condição do comando 
repetitivo, a == 0, resultou no valor False e o comando repetitivo termina, sem entrar 
nenhuma vez no bloco de comandos a serem executados repetitivamente. Na sequência, a 
partir do comando de leitura para a variável b, o código é idêntico ao mostrado na Figura 
5.11 e, então, os valores 3 e -4 são lidos e atribuídos para as variáveis que representam os 
coeficientes b e c. O valor 25, resultante da expressão , é atribuído para 𝑏 ** 2 − 4 * 𝑎 * 𝑐
a variável delta. O que fará com que os comandos na cláusula else do comando if-elif-else 
seja executado para calcular o valor de duas raízes e imprimir a mensagem vista na Figura 
6.3. 
 
Já na segunda execução do programa ocorreu o chamado loop infinito. O termo loop 
(laço em inglês) em computação significa repetição. Como explicado na seção 6.1 um 
comando repetitivo pode ser executado zero ou mais vezes. Mas, associado com o conceito 
de algoritmo (“um conjunto de regras e procedimentos lógicos perfeitamente definidos que 
levam à solução de um problema em um número finito de etapas”) o comando repetitivo tem 
que terminar, ou tem que executar um número máximo de vezes. 
 
O que gerou o laço infinito foi exatamente a supressão do comando de leitura dentro 
do bloco de comandos repetitivos. O comando de leitura, antes do comando repetitivo, 
atribuiu o valor 0 (zero) para a variável a. Ao testar a condição do comando repetitivo, a==0, 
o resultado foi verdadeiro e, por causa disso, será executado o comando repetitivo que 
agora tem apenas o comando print(). Ora, se o comando print() não altera o valor da 
variável a (quem alterava o valor de a era o comando input(), que virou comentário), então a 
condição do comando repetitivo será verdadeira para sempre e o comando repetitivo não 
terminará… 
 
Por isso,os comandos e digitá-los sem erro 
para que fossem executados. Na figura aparecem dois comandos: o primeiro foi digitado 
corretamente (ls) e lista os diretórios (ou pastas) e arquivos existentes para o usuário 
goulart na máquina de nome lubuntu-goulart; o segundo com um erro de digitação (lx) para 
o qual o sistema operacional responde com uma mensagem de erro (lx: comando não 
encontrado). Essa simples necessidade de memorizar e digitar comandos tornava o uso de 
computadores pouco atraente. Além disso, não havia, na época, programas aplicativos de 
uso geral voltados para o cidadão comum e, por isso, o uso de computador ficava restrito às 
grandes empresas de tecnologia, a algumas universidades e aos grandes centros de 
pesquisa. Este tipo de interface foi utilizado nos computadores de grande porte 
(mainframes) e nos primeiros computadores pessoais, até o início da década de 1990. Os 
principais sistemas operacionais utilizados eram o UNIX e o DOS. 
 
A partir do início da década de 1990 começaram a surgir as interfaces gráficas 
baseadas em janelas, menus e ícones. A Figura 1.3 mostra a interface gráfica de um 
sistema operacional Ubuntu Linux, utilizado no Laboratório de Informática onde acontecem 
as aulas práticas da disciplina de Introdução à Programação I. 
 
 
 
 
10 
 Introdução à Programação com Python 
 
Figura 1.3 - Interface Gráfica do Ubuntu Linux 
 
A figura 1.3 mostra alguns ícones que foram colocados na área de trabalho: 
Gerenciador de Arquivos (Pasta pessoal), Navegador Web Firefox, IDLE, Code Blocks IDE 
e Google Chrome. O usuário pode personalizar a sua área de trabalho, incluindo ou 
excluindo ícones de programas. A partir desta interface gráfica é possível procurar todos os 
programas aplicativos instalados no sistema, clicando no ícone com 9 quadradinhos, no 
canto inferior esquerdo da tela. Um desses aplicativos é o Terminal, que é um programa que 
executa a interface de texto sobre a interface gráfica. Isso é útil para usuários mais 
experientes que conseguem realizar tarefas de forma mais rápida usando os comandos 
desta interface de texto. 
 
 As interfaces gráficas de diferentes sistemas operacionais possuem bastante 
similaridade conceitual pois são baseadas nos mesmos elementos: ícones, janelas e 
menus. Em princípio, o usuário precisa saber qual ícone está associado ao programa que 
ele deseja utilizar. Desta forma, espera-se que os usuários do sistema operacional Windows 
não encontrem maiores dificuldades de utilizar o sistema operacional Ubuntu que é uma das 
versões do sistema operacional Linux. 
 
 
Figura 1.4 - Interfaces Gráficas: Windows, Ubuntu e Mac OS X 
 
 A escolha do Ubuntu Linux para uso no Laboratório de Informática (LBI) se deve ao 
fato dele ser um software livre. Isso significa que é possível obter o sistema operacional e 
11 
 Introdução à Programação com Python 
um grande número de programas aplicativos sem pedir permissão ou autorização de 
nenhuma empresa. Também é possível modificar, atualizar e/ou instalar qualquer programa 
que esteja na base de dados do Ubuntu Linux, em algum repositório da internet. Além disso, 
os problemas com vírus e outras pragas virtuais são muito menores do que os do sistema 
Windows. Tudo isso facilita a manutenção dos sistemas do LBI. 
 
 Outra vantagem dos sistemas baseados no Linux é que eles são gratuitos. Para uma 
instituição pública como a UFV que é mantida com recursos públicos, impostos oriundos de 
todos os contribuintes, esta única razão já seria suficiente para usar o Ubuntu no LBI. 
 
É provável que muitos estudantes matriculados na disciplina INF 100 - Introdução à 
Programação I tenham smartphone com o sistema operacional Android, que é o sistema 
mais usado no mundo neste mercado. O Android e o Ubuntu são exemplos de sistemas 
operacionais construídos sobre o núcleo (kernel) do sistema operacional Linux. 
 
 
1.3. Algoritmos e linguagens de programação 
 
 O uso de computador para resolver problemas reais tem sido cada vez mais 
frequentes. Se no início da utilização de computadores os problemas estavam relacionados 
apenas à área científica, hoje existem aplicativos das mais variadas áreas desenvolvidas 
para o cidadão comum. Aplicativos de redes sociais como Facebook e Instagram são 
bastante conhecidos, totalizando mais de 6 bilhões de downloads (Fonte: Play Store, 
27/03/2020). Dentre outros aplicativos menos conhecidos do público geral, mas que podem 
ser úteis para estudantes da UFV, podem ser citados o UFV Eventos e o Cardápio UFV com 
mais de 11 mil downloads (Fonte: Play Store, 27/03/2020). Ambos foram desenvolvidos com 
participação de estudantes da UFV. 
 
Como desenvolver um aplicativo? A Figura 1.5 mostra de maneira esquemática as 
fases de desenvolvimento de uma solução computacional para um problema do mundo real. 
 
12 
 Introdução à Programação com Python 
 
Figura 1.5 - Fases de desenvolvimento de um programa 
 
 Primeiramente é necessário conhecer qual é o problema que se deseja resolver. 
Definido o problema, a fase de análise visa obter um conhecimento completo do problema, 
de forma a permitir a definição das tarefas que devem ser realizadas para resolvê-lo. O 
passo seguinte é fazer uma descrição sistematizada das tarefas (solução descritiva) que 
devem ser executadas, atentando para a correta ordem de execução. 
 
A solução descritiva geralmente é feita usando a linguagem natural (ex: Português) 
que pode conter ambiguidade, ou seja, duas pessoas podem interpretar de forma diferente 
o que uma tarefa faz. Apenas para exemplificar a ambiguidade do Português pode-se 
utilizar um exemplo não computacional. Na frase “Vejo um homem no alto da montanha 
usando binóculos”, quem está usando binóculos? A pessoa que disse a frase pode ter 
usado binóculos para ver o homem na montanha ou ela pode ter visto que o homem na 
montanha estava portanto binóculos. 
Qualquer potencial ambiguidade deve ser eliminada ao transformar a solução 
descritiva para a forma de algoritmo. Um algoritmo pode ser definido como uma sequência 
finita de instruções bem definidas e não ambíguas. Este conceito será explorado com mais 
profundidade no Capítulo 2. No contexto computacional, cada instrução do algoritmo deve 
estar tão simples e detalhada de forma que poderá ser traduzida para um comando da 
linguagem de programação. 
 
O passo seguinte consiste na tradução de cada instrução do algoritmo para uma 
instrução da linguagem de alto nível escolhida para a implementação do programa. O 
13 
 Introdução à Programação com Python 
resultado desta fase será o chamado código fonte que deve seguir rigorosamente a forma 
permitida de escrita da linguagem de alto nível, a chamada sintaxe. O código ou programa 
fonte vai ficar gravado em um arquivo para ser executado quando demandado pelo 
programador. 
 
Com o programa fonte armazenado em um arquivo, o passo seguinte é fazer a 
tradução para a linguagem que o computador entende que é a linguagem de máquina, onde 
tudo é codificado como uma sequência de bits 0’s e 1’s. A esta forma dá-se o nome de 
código executável. Esta tradução pode ser feita diretamente, sem gerar um outro arquivo ou 
indiretamente, quando é gerado um arquivo executável. No primeiro caso temos as 
linguagens interpretadas, como é o caso da linguagem Python, na qual o programa é 
executado diretamente a partir do programa fonte. No caso de outras linguagens, como por 
exemplo C, é utilizado um compilador que transforma o código fonte em código executável 
que poderá, então, ser executado. 
 
Independente da forma de transformação do código fonte em código executável 
(interpretada ou compilada), ela sempre é feitaé importante observar que no bloco de comandos repetitivos deve sempre 
haver (pelo menos) um comando que torne, em algum momento, a condição de teste falsa, 
para que o comando repetitivo termine e o programa continue a sua execução, terminando 
em um tempo finito. Se todos os comandos repetitivos atenderem a este requisito (terminar 
em algum tempo), o programa estará mapeando de maneira adequada um algoritmo. 
 
 O tempo que um comando repetitivo levará para terminar pode ser indeterminado. É 
o caso do exemplo da Figura 6.2. Primeiramente, porque a avaliação da condição no 
comando repetitivo depende de um comando de entrada (input()), que só termina a sua 
execução após o usuário digitar a informação e apertar a tecla ‘Enter’. Se o usuário iniciar o 
programa e, antes de digitar o primeiro valor, parar durante uma hora para fazer qualquer 
outra atividade, e depois voltar a usar o programa, uma única iteração do comando 
repetitivo vai demorar uma hora. 
 
Em segundo lugar, o número de repetições vai depender dos valores fornecidos para 
o coeficiente a da equação do segundo grau. Se o primeiro valor for diferente de zero, 
conforme já explicado, o valor é válido e o comando repetitivo será executado zero vezes. 
Se o usuário fornecer, no início, uma sequência de N valores zeros antes de fornecer antes 
de fornecer um primeiro valor diferente de zero, o comando repetitivo será executado N 
vezes. Este evento já foi visto na Figura 6.2, em uma execução onde os valores 0, 0 e 1 
foram informados para o coeficiente a, fazendo com que o comando repetitivo fosse 
executado 2 vezes (observe na Figura 6.2 que a mensagem de erro seguida de um novo 
pedido do coeficiente a foram exibidos 2 vezes). 
 
111 
 Introdução à Programação com Python 
 
6.1.2. Número determinado de repetições com o while 
 
 Em algumas situações o número de repetições do comando repetitivo é 
pré-determinado. Por exemplo, suponha que um programa seja feito para ler as notas de 
uma turma com N alunos. A solução geral para este tipo de situação consiste em utilizar 
uma variável auxiliar para contar o número de execuções. A Figura 6.4 mostra um trecho de 
código utilizando o comando while e uma variável i como contador. 
 
i = 
while i : 
 
 i = i + 1 
Figura 6.4 - Forma geral do comando while com contador 
 
O contador será incrementado de uma unidade (i = i + 1) a cada iteração da 
execução do comando repetitivo. O e o juntamente com a 
expressão lógica, determinarão o número de repetições. Por exemplo, um possível código 
para ser executado 10 vezes, poderia ser escrito como: 
 
 i = 0 
 while i = 10 ao invés de iPor exemplo, sendo o valor fixo e igual a verdadeiro (True). 
Mas, como não se pode ter um loop infinito deve ser criada uma forma de se quebrar o loop 
se uma determinada condição for alcançada. Em termos de algoritmo, o trecho anterior, 
poderia ser reescrito como: 
 
enquanto Verdadeiro: 
 Leia(a) 
 se a != 0 : 
 quebra_loop 
 imprima(‘Valor tem que ser diferente de 0 (zero)’) 
 
Note que, semanticamente, os dois trechos de algoritmo são idênticos. Vai ter que 
ser lido um valor inicial (agora dentro do comando repetitivo). Enquanto o valor lido for igual 
a zero, a impressão da mensagem de erro será feita e uma nova iteração do comando 
repetitivo irá realizar nova leitura de valor. Quando o valor lido for diferente de zero, o loop 
será quebrado, com o valor atribuído para a variável a. Inclusive, se o primeiro valor 
fornecido for diferente de zero, a mensagem de erro não será impressa. 
 
Usando a linguagem Python, o trecho de algoritmo mostrado anteriormente pode ser 
escrito, usando a estrutura while-true, como mostrado na Figura 6.5. Nesta mesma figura é 
exibida a janela do Shell, sobreposta à janela do editor de programas, com o resultado da 
execução do programa, para os mesmos valores utilizados na execução mostrada na Figura 
6.2. 
 
114 
 Introdução à Programação com Python 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
Figura 6.5 - Exemplo de utilização da estrutura while-true 
 
O comando no estilo while-true sem o break em seu interior se transformaria em um 
loop infinito. Por isso, é importantíssimo não esquecer da inserção da comando break que, 
geralmente, é vinculada a um comando condicional, como no exemplo. Alguns programas 
têm esta particularidade de se comportarem como um grande laço infinito e, eventualmente 
e muito raramente, executam o break vinculado a uma condição qualquer. 
 
É o caso da maioria dos programas que implementam serviços de internet. Um 
servidor de páginas web, por exemplo, que executa algum código de inicialização e depois 
entra em um loop infinito e espera, sem fazer nada, pela chegada de uma requisição por 
uma página. Ao receber uma requisição, o servidor web procura pela página em seu banco 
de dados e a envia para o requisitante. Caso a página não seja encontrada, o servidor web 
envia uma mensagem de erro (página não encontrada). 
 
Posteriormente a uma destas duas ações, o servidor volta para o comando onde ele 
fica esperando a chegada de uma nova requisição. Um bom servidor de páginas deve ficar 
nesta execução 24 horas por dia, sete dias por semana. Eventualmente ele será parado por 
algum comando do administrador (um break será executado) para alguma manutenção 
rápida ou problema de segurança ou talvez para dar lugar a uma nova versão. 
 
6.2. Comando for 
 
Um comando repetitivo pode ser utilizado um número pré-determinado de vezes, 
conforme discutido na seção 6.1.2, utilizando o comando while e uma variável auxiliar 
115 
 Introdução à Programação com Python 
fazendo o papel de um contador do número de execuções do comando repetitivo. Usando a 
estrutura do comando while é necessário inicializar um contador antes do comando while e 
fazer o incremento deste contador dentro do bloco de comandos repetitivos. Um erro muito 
comum é o esquecimento de incrementar o contador no bloco de comandos repetitivos. 
 
 
6.2.1. Comando for 
 
Para resolver este problema, uma outra estrutura de comando repetitivo com 
incremento automático do contador está presente na linguagem Python. Nesta estrutura, o 
contador é inicializado no próprio comando repetitivo. A Figura 6.6 apresenta uma forma 
geral do comando repetitivo for: 
 
for in range (, ) : 
 
Figura 6.6 - Forma geral do comando for 
 
 
A sintaxe do comando é definida com o uso da palavra reservada for seguida do 
nome da variável a ser utilizada como contador do número de execuções. O cabeçalho do 
comando continua com as palavras reservadas in range (na faixa), seguidas pelos valores 
inicial e final para definição da faixa de valores que o contador irá assumir. O cabeçalho é 
finalizado com o caractere ‘:’. Após o cabeçalho vem o bloco de um ou mais comandos a 
serem executados repetitivamente, com a indentação (deslocamento à direita). 
 
A variável a ser usada como contador é definida no próprio comando, não havendo a 
necessidade de definição anterior ao comando for. Mas, também é possível utilizar alguma 
variável que já tenha sido criada. O será o primeiro valor da variável contador 
e será o último valor. O comando for não executa para = . O incremento padrão do contador é de uma unidade a cada execução ou à cada 
iteração. 
 
O trecho de código usado como exemplo na seção 6.1.2, pode ser reescrito com a 
substituição do while pelo comando for. Para facilitar a comparação, os dois códigos são 
apresentados lado a lado na Tabela 6.2. 
 
Tabela 6.2 - Comparação dos comandos for e while 
Uso do comando for Uso do comando while 
for i in range (0, 10): 
 print(‘%4d’ %i, end) 
i = 0 
while i50 milhões de vezes, o 
que representou 23s de tempo de execução em um computador com processador de 1.86 
117 
 Introdução à Programação com Python 
GHz de clock. O número exato de repetições é calculado como o - 
ou 100000001 - 50000000 = 50000001. 
 
Uma solução usando o comando repetitivo while seria muito mais eficiente se 
utilizasse o valor inicial igual a k e um incremento também igual a k, ao invés de um 
incremento unitário. Este incremento eliminaria ainda a necessidade de comparação, pois a 
regra de geração definiria a seguinte sequência: k, 2k, 3k…, etc. enquanto o número da 
sequência fosse menor do que N. Para o exemplo, a sequência teria apenas dois números 
50000000 e 100000000. Aliás, para este caso nem seria necessário escrever um programa. 
 
Na linguagem Python, o comando for permite especificar o valor do incremento, 
utilizando um terceiro parâmetro, nos parênteses, após as palavras reservadas in range, ou 
mais especificamente, após a definição da faixa, como mostrado na Figura 6.7. 
 
for in range (, , ) : 
 
Figura 6.7 - Forma geral do comando for 
 
O parâmetro de define o valor do incremento que a variável 
 irá receber após cada iteração do bloco de comandos repetitivos. O comando 
repetitivo, para gerar a sequência de números múltiplos de k pode ser escrito da seguinte 
forma: 
 
for i in range(k, N+1, k): 
 print(i, end=’ ‘). 
 
Desta forma, para os valores de N=100000000 e k=50000000 o comando repetitivo 
que imprime o valor de i seria executado apenas duas vezes para os valores de 
i={50000000, 100000000} e o programa é executado em alguns milisegundos. Imagine se o 
bloco repetitivo estivesse relacionado com o processamento de uma transação cujos testes 
fossem mais complexos e demorassem exatamente 1s cada. A solução com o incremento 
não unitário demoraria 2s aproximadamente e a de incremento unitário demoraria cerca de 
3,17 anos, ou seja, aproximadamente 3 anos, 2 meses e 12 dias. 
 
Esta comparação é para que você se convença de que nem sempre é suficiente ter 
uma solução correta. Às vezes, é necessário ter uma solução correta e eficiente. Embora 
este aspecto não seja cobrado nas soluções desta disciplina de Introdução à Programação, 
é fundamental conhecer este aspecto e tratá-lo de maneira adequada (com uma solução 
eficiente) quando ele aparecer. 
 
Note que quando se deseja um incremento diferente do unitário, o valor do 
incremento deve ser definido no cabeçalho do comando for, usando o terceiro parâmetro, 
após a definição da faixa, como mostrado na Figura 6.7. O número de repetições do 
comando for é definido pelos parâmetros que são definidos no cabeçalho do comando for. 
Incrementar a variável no bloco de comandos repetitivos não produz nenhum 
efeito no número de repetições. 
 
Como exemplo, suponha a alteração mostrada a seguir no código utilizando o 
comando for com incremento unitário e no final do bloco de comandos repetitivos, o 
contador está sendo incrementado de k unidades. 
118 
 Introdução à Programação com Python 
 
for i in range(k, N+1): 
 print('antes i=%d' %i, end=' ') 
 if i%k == 0: 
 print('**%d**' %i, end=' ') 
 i = i + k 
 print('depois i=%d' %i) 
 
Para facilitar a compreensão, o valor da variável de controle do comando for é 
impresso no início e no final do bloco de comandos repetitivos. A impressão será feita em 
uma mesma linha e quando o valor de i for múltiplo de k, ele aparecerá impresso no meio 
da linha precedido e sucedido por dois asteriscos (*). Com os valores de k=5 e N=10, a 
saída gerada por este trecho de código será a seguinte: 
 
antes i=5 **5** depois i=10 
antes i=6 depois i=11 
antes i=7 depois i=12 
antes i=8 depois i=13 
antes i=9 depois i=14 
antes i=10 **10** depois i=15 
 
Veja que o número de repetições do comando for foi igual a 6, por causa da faixa 
definida: N+1-k = 10+1-5 = 6. O valor inicial de i = 5 (), com incremento 
unitário a cada nova iteração, eliminando o efeito do comando de incremento, i = i + k. Por 
isso, uma boa prática de programação é não usar comando de atribuição para alterar a 
variável de controle do for. 
 
O comando for também permite especificar execuções em uma faixa com 
incremento negativo (ou decremento) e, desta forma, iniciando a faixa com um número 
maior do que o valor final da faixa. Suponha, por exemplo, que se desejasse imprimir os 
valores múltiplos de k de 1 a N em ordem decrescente. Para resolver este problema, o 
código a seguir poderia ser utilizado: 
 
for i in range(N, k-1, -1): 
 if i%k == 0: 
 print(i, end=’ ‘) 
 
Lembre-se que, com o decremento unitário, o comando for caminha do maior valor 
para o menor valor da faixa especificada e não executa para o valor final da faixa, que deve 
ser igual a k-1 e não igual a k, quando se deseja executar para o valor de i = k. 
 
Como o decremento é unitário, se a faixa de valores for muito grande o número de 
repetições poderá gastar muito tempo, conforme já discutido. Uma solução mais eficiente, 
com o incremento igual a -k, pode ser implementada com o código a seguir: 
 
for i in range(N//k*k, k-1, -k): 
 print(i, end=’ ‘) 
 
A determinação do maior múltiplo foi feita com a divisão inteira de N por k, 
multiplicado por k. Por exemplo, se N=50 e k=8, teremos 50//8*8 = 6*8 = 48. Como as 
operações têm mesma ordem de prioridade, não há necessidade de uso de parênteses. 
119 
 Introdução à Programação com Python 
 
 
 
6.2.3. Comando for-break 
 
Suponha que para resolver o problema anterior, o programador não soubesse 
determinar o valor do maior múltiplo de k no intervalo 1..N. Então, ele decide escrever um 
código para determinar o valor do maior múltiplo, percorrendo a sequência na ordem 
inversa, começando por N. Para cada número na sequência, será feita a operação de resto 
da divisão inteira por k. A primeira vez em que for encontrado o resto igual a zero, a divisão 
foi feita usando o maior múltiplo de k e o comando repetitivo pode parar. 
 
Lembrando que a suposição inicial é de que N>k e, portanto, sempre haverá pelo 
menos um múltiplo na sequência de 1..N (na verdade a verificação pode se feita apenas na 
sub-sequência de k..N). Assim, o maior múltiplo de k encontrado poderá ser utilizado como 
o valor inicial da faixa do comando for. O seguinte código poderia ser usado para encontrar 
o maior múltiplo de k: 
 
mm = N 
while mm % k != 0: # testa se mm não é múltiplo de k 
 mm = mm - 1 # passa para o “próximo” número da sequência 
 
Na linguagem Python o comando break pode ser utilizado para parar o comando 
repetitivo while, como mostrado na seção 6.1.3. Da mesma forma, a comando break pode 
ser utilizada no comando for, geralmente associado a uma condição. Por exemplo, 
encontrar um número que seja múltiplo de k. Desta forma, um código equivalente ao 
mostrado anteriormente pode ser escrito utilizando o comando for: 
 
for i in range (N, k-1, -1): 
if i % k == 0: 
 mm = i # maior múltiplo (mm) 
 break 
 
Observe que as duas estruturas repetitivas executam as mesmas ações: percorrer 
uma lista de números, do maior para o menor, verificando se o número é múltiplo de k; e 
parar quando o número for múltiplo de k. Independente de qual estrutura seja usada, o 
código que virá na sequência para imprimir os múltiplos de k, em ordem decrescente 
poderia ser: 
 
for i in range(mm, k-1, -k): 
 print(i, end=’ ‘) 
 
 
6.3. Alguns exemplos de uso de comandos repetitivos 
 
 Nesta seção serão apresentados alguns problemas cujas soluçõesdemandam a 
utilização de comando repetitivo. A maioria das soluções serão apresentadas utilizando o 
120 
 Introdução à Programação com Python 
comando repetitivo while. No próximo capítulo serão vistos exemplos onde o uso do 
comando for é mais adequado. 
 
 Para cada problema será apresentado o enunciado no estilo de listas de exercícios e 
avaliações. 
 
6.3.1. Cálculo de média 
 
Faça um programa que peça para o usuário digitar as notas de uma turma e, então, 
calcula a média das notas. O número de alunos da turma deve ser requisitado ao usuário, 
antes do programa iniciar a leitura das notas. As notas devem estar no intervalo [0..100] e 
valores fora desta faixa não deverão ser aceitos. 
 
A solução para este problema poderia ser descrita nos seguintes passos: 1. obter o 
número de alunos da turma; 2. ler uma nota; 3. se a nota for válida, totalizar o valor e 
incrementar o número de notas lidas; 4. Voltar ao passo 2 enquanto o número de notas for 
menor que o número de alunos da turma; 5. Calcular e informar a média das notas. 
 
Uma primeira versão para este algoritmo, baseada na descrição feita, pode ser 
escrita como: 3.2.2.5 
 
Leia “número de alunos na turma” 
enquanto “número de notas =0 E nota = 0 E nota = 0 E nota = 0 and notai é divisor de num. Caso contrário, i não é divisor. 
 
Além disso, o algoritmo não considerou a possibilidade de testar vários números. A 
ideia é que após responder se um número é primo ou não, o programa deverá solicitar ao 
usuário um novo número para ser testado. Quando o usuário informar um valor menor ou 
igual a zero. Refinando o algoritmo, com as observações feitas, a segunda versão pode ser 
escrita como: 
 
Escreva(“Este programa verifica se um número é primo”) 
enquanto Verdadeiro: 
 Leia(num) 
 se num ε
4. Escreva r. 
Obs.: o valor de ε corresponde à precisão desejada para o valor da raiz, por 
exemplo, 10⁻⁵. 
 
Em programação muitas vezes o cálculo de um valor utiliza um método numérico. 
Neste caso, o método de Heron, criado na Grécia antiga, muito antes de se imaginar 
construir o primeiro computador, pode ser classificado como um método de aproximações 
sucessivas. 
 
Estima-se um valor inicial, a partir de um valor qualquer. No passo 1, sugere-se um 
chute inicial igual à metade do valor. Os valores estimados vão usar o valor da estimativa 
atual, usando sempre a mesma fórmula: . Para cada valor estimado será 𝑟 = (𝑟 + 𝑥/𝑟)/2
feita uma comparação de quão próximo do valor exato, a estimativa feita está. A estimativa 
do erro é feita pegando o módulo da diferença entre x e r². Quando o módulo da diferença é 
menor do que o valor de o cálculo do valor da raiz é considerado satisfatório. ε
 
A Tabela 6.3 mostra os valores estimados pelo algoritmo e o valor do erro, para cada 
iteração do comando repetitivo, para cálculos da raiz quadrada de 4, 3, 2 e 1. Todos os 
valores estão mostrados com 6 casas decimais, já que a precisão utilizada foi de 10⁻⁵. Em 
negrito, foi feito o destaque para o valor considerado como a resposta correta, dentro da 
margem de erro para cada cálculo. 
 
Observe que para calcular a primeira estimativa (2) coincide exatamente com o 4
valor da raiz e o erro é zero. Para os cálculos de e foram necessárias 3 iterações do 3 2
algoritmo. Observe que o erro para aparece como se fosse zero, mas isso é devido ao 3
uso de 6 casas decimais. Caso a impressão tivesse sido feita com 10 casas decimais, os 
valores de estimativa para e o erro, na terceira iteração seriam, respectivamente 3
1.7320508100 e 0.0000000085. 
 
 
Tabela 6.3 - Estimativas e erro para cálculo de raiz quadrada com precisão 10⁻⁵. 
Iteração 4 3 2 1
 Estim. Erro Estim. Erro Estim. Erro Estim. Erro 
1 2.000000 0.000000 1.750000 0.062500 1.500000 0.250000 1.250000 0.562500 
2 1.732143 0.000319 1.416667 0.006944 1.025000 0.050625 
3 1.732051 0.000000 1.414216 0.000006 1.000305 0.000610 
4 1.000000 0.000000 
 
Este algoritmo converge muito rapidamente para o valor considerado satisfatório, 
dentro da margem de erro especificada. Por isso ele é implementado para cálculo de raiz 
127 
 Introdução à Programação com Python 
quadrada em bibliotecas matemáticas. No código foi utilizada a função abs(x) que, dado um 
número x, informa o seu módulo. Implementar um código para realizar tal tarefa é trivial, 
pois bastaria testar se o valor de x é negativo e, se for, multiplicar por -1. O código que 
implementa o algoritmo discutido anteriormente é apresentado na Figura 6.11, juntamente 
com a exibição do resultado da execução, na janela do Shell, para os valores de raiz 
quadrada de 4, 3, 2 e 1. 
 
Note que os resultados são os mesmos da Tabela 6.3. Obviamente, os valores da 
tabela 6.3 não foram obtidos utilizando uma calculadora, pois poderiam ocorrer erros de 
digitação e levaria muito mais tempo. Ao invés disso, foi utilizado o comando de impressão, 
após cada nova estimativa feita pelo programa com a expressão , para 𝑟 = (𝑟 + 𝑥/𝑟)/2
exibir a nova estimativa (r) e o módulo do erro: print('Estim.: %.6f Erro: %.6f' %(r, (r**2 - x))). 
Os valores gerados pelo programa foram, então, copiados para a tabela 6.3. Na versão final 
do programa, estes comandos de impressão foram retirados e uma nova execução foi feita 
para gerar os resultados apresentados na Figura 6.11. 
 
 
Figura 6.11 - Programa para cálculo de raiz quadrada 
 
128 
 Introdução à Programação com Python 
Observe que no programa o caractere ‘\n’ foi utilizado em alguns comandos de 
impressão paraforçar a criação de uma nova linha para melhorar a visualização dos 
resultados gerados pelo programa. 
 
Note, também, que a variável epson foi criada fora do comando repetitivo enquanto 
que a variável r foi criada dentro da cláusula else, que está dentro de um comando 
repetitivo. Como a precisão (epson) é fixa, ela pode (e deve) ser inicializada uma única vez. 
Em outras linguagens de programação seria chamada de constante e não de variável. Já o 
valor da variável r deve ser inicializada para cada novo cálculo de raiz a ser feito, com um 
valor (x/2) que depende do valor informado pelo usuário. 
 
Eventualmente, em uma outra versão do programa onde o usuário possa definir a 
precisão que ele queira, a variável epson poderia ser inicializada com diferentes valores 
para cada execução do programa ou para cada cálculo novo. 
 
 
6.4. Exercícios 
 
1) Faça um programa que imprima a soma dos 100 primeiros números naturais. 
 
2) Escreva um programa que imprimir os múltiplos de 7 menores que 100. 
 
 
3) Escreva um programa que exiba os números divisíveis por 4 e por 5 menores que 
200. 
 
 
4) Faça um programa que receba um inteiro N e calcule os seus divisores. 
 
 
5) Escreva um programa para ler o número de alunos existentes em uma turma, ler a 
nota de cada aluno e calcular a média aritmética da turma. 
 
 
6) Escreva um programa para escrever a soma dos números pares e a soma dos 
números ímpares de 1 a 200, inclusive. 
 
 
7) Escreva um programa que verifique a validade de uma senha fornecida pelo usuário. 
A senha válida é 1234. Caso a senha informada pelo usuário seja inválida, a 
mensagem "ACESSO NEGADO" deve ser impressa e repetida a solicitação de uma 
nova senha até que ela seja válida. Caso contrário deve ser impressa a mensagem 
"ACESSO PERMITIDO" junto com um número que representa quantas vezes a 
senha foi informada. 
 
 
8) Faça um programa para ler um número entre 1 e 9 e mostrar a tabuada da 
multiplicação do número lido. 
 
129 
 Introdução à Programação com Python 
 
9) Escreva um programa que calcule o fatorial de N (N!), informado pelo usuário. 
Sendo que: N! = 1 * 2 * 3 * ... * (N - 1) * N. Por definição o fatorial de 0 é 1 (0! = 1). 
Caso o usuário digite um valor negativo, o programa deve informar que a função 
fatorial não está definida para números negativos e solicitar um novo número. 
 
 
10) Faça um programa que receba dois números, inteiros e positivos a e b, e calcule , 𝑎𝑏
sem usar a função ou o operador **. 
 
 
11) Escreva um programa para ler 2 notas de um aluno, calcular e imprimir a média final. 
Logo após escrever a mensagem "Calcular a média de outro aluno [S]im [N]ao?" e 
solicitar uma resposta. Se a resposta for “S” ou “s”, o programa deve ser executado 
novamente, caso contrário deve ser encerrado imprimindo a quantidade de alunos 
aprovados, reprovados e que ficaram em exame final, considerando o mesmo 
critério adotado pela UFV, conforme tabela mostrada a seguir. 
 
Nota Situação 
0-39 Reprovado 
40-59 Exame Final 
60-100 Aprovado 
 
OBS: as notas finais na UFV são sempre valores inteiros, com arredondamento para 
cima se o valor decimal for maior ou igual a 0,5 e arredondamento para baixo, caso 
contrário. Ex: 59.4 vira 59 e 59.5 vira 60. 
 
 
12) A CBF contratou você para escrever um programa que faça uma estatística do 
resultado de vários Fla-Flu. Você deve escrever um programa para ler o número de 
gols marcados pelo Flamengo e o número de gols marcados pelo Fluminense em 
um Fla-Flu. Logo após escrever a mensagem "Novo Fla-Flu 1.Sim 2.Nao?" e solicitar 
uma resposta. Se a resposta for 1, o algoritmo deve ser executado novamente 
solicitando o número de gols marcados pelos times em uma nova partida, caso 
contrário deve ser encerrado imprimindo: 
Quantos Fla-Flu fizeram parte da estatística. 
O número de vitórias do Flamengo. 
O número de vitórias do Fluminense. 
O número de Empates 
Uma mensagem indicando qual o time que venceu o maior número de Fla-Flu (ou 
NÃO HOUVE VENCEDOR). 
 
Veja os exemplos: 
Numero de gols do Flamengo: 2 
Numero de gols do Fluminense: 1 
Novo Fla-Flu 1.Sim 2.Nao? 2 
 
--Resultado Final-- 
130 
 Introdução à Programação com Python 
Numero de partidas do Fla-Flu: 1 
Numero de vitorias do Flamengo: 1 
Numero de vitorias do Fluminense: 0 
Numero de empates: 0 
Time com maior numero de vitorias: Flamengo 
 
 
Numero de gols do Flamengo: 0 
Numero de gols do Fluminense: 2 
Novo Fla-Flu 1.Sim 2.Nao? 1 
Numero de gols do Flamengo: 2 
Numero de gols do Fluminense: 0 
Novo Fla-Flu 1.Sim 2.Nao? 1 
Numero de gols do Flamengo: 0 
Numero de gols do Fluminense: 0 
Novo Fla-Flu 1.Sim 2.Nao? 2 
 
--Resultado Final-- 
Numero de partidas do Fla-Flu: 3 
Numero de vitorias do Flamengo: 1 
Numero de vitorias do Fluminense: 1 
Numero de empates: 1 
Nao houve vencedor 
 
 
13) Altere o programa da solução do exercício 12 para incluir como critério de 
desempate o maior número de gols marcados, no caso de não haver time com maior 
número de vitórias. 
 
 
14) Considere somatório de uma série infinita como a mostrada a seguir: 
 
𝑖=2
∞
∑ −1 𝑖( )
𝑖 = 1
2 − 1
3 + 1
4 − 1
5 + 1
6 +...
 
Faça um programa para calcular o somatório dos N primeiros elementos da 
sequência. O valor de N deve ser informado pelo usuário do Programa. Execute seu 
programa para diferentes valores de N e certifique-se de que o somatório é 
convergente. 
 
Altere o programa para que ele execute diversas vezes, parando quando o usuário 
informar um valor menor ou igual a zero para N. 
 
15) Faça um programa para calcular o produto dos N primeiros elementos de uma série, 
conforme mostrado a seguir: 
 
𝑖=1
𝑁
∏ 𝑖
𝑖+1 = 1
2 × 2
3 × 3
4 × 4
5 × 5
6 ×... × 𝑁
𝑁+1
O número de elementos do produtório deverá ser informado pelo usuário do 
programa. Execute seu programa para diferentes valores de N e certifique-se de 
que o produtório é convergente. 
 
131 
 Introdução à Programação com Python 
Altere o programa para que ele execute diversas vezes, parando quando o usuário 
informar um valor menor ou igual a zero para N. 
 
16) Uma série conhecida para o cálculo de foi desenvolvida por Leibniz em 1682, π 
utilizando-se da série de Taylor para a função arctan(x), tomando-se x=1, e, por 
conseguinte, arctan(1) = /4 (Fonte: https://pt.wikipedia.org/wiki/Pi). Assim, pode-se π
escrever que: 
 π =
𝑖=0
𝑁
∑ 4× −1( )𝑖
2×𝑖+1 = 4 − 4
3 + 4
5 − 4
7 + 4
9 − 4
11 +...
 
Faça um programa para calcular o valor de usando o somatório dos N primeiros π
elementos da sequência acima. Execute seu programa para diferentes valores de N 
e verifique como a precisão do resultado evolui com o aumento de N. Imprima o 
resultado com 8 casas decimais. 
 
Altere o programa para que ele execute diversas vezes, parando quando o usuário 
informar um valor menor ou igual a zero para N. 
 
17) Uma outra série conhecida para o cálculo de foi desenvolvida por Nilakantha e tal π
proposição é mostrada a seguir: 
 
 
 π = 3 +
𝑖=1
∞
∑ −1( )𝑖+1×4
2𝑖( ) 2𝑖+1( ) 2𝑖+2( ) = 3 + 4
2×3×4 − 4
4×5×6 + 4
6×7×8 − 4
8×9×10
 
 
Faça um programa para calcular o valor de usando o somatório dos N primeiros π
elementos da sequência acima. Note que o primeiro elemento não segue a regra de 
geração dos demais elementos. Execute seu programa para diferentes valores de N 
e verifique como a precisão do resultado evolui com o aumento de N. Imprima o 
resultado com 8 casas decimais. 
 
Altere o programa para que ele execute diversas vezes, parando quando o usuário 
informar um valor menor ou igual a zero para N. 
 
18) O valor de também pode ser obtido como produtório. Uma destas soluções foi π
proposta pelo matemático francês François Viète, que estudando o método de 
Arquimedes, desenvolveu a seguinte série para o cálculo de em 1593 (Fonte: 
https://pt.wikipedia.org/wiki/Pi): 
 2
π = 2
2 × 2+ 2
2 × 2+ 2+ 2
2 × 2+ 2+ 2+ 2
2 ×...
 
Escreva um programa para calcular o valor de usando o produtório acima, π
considerando os N primeiros elementos da sequência acima. Note que o primeiro 
elemento não segue a regra de geração dos demais elementos. Execute seu 
programa para diferentes valores de N e verifique como a precisão do resultado 
evolui com o aumento de N. Imprima o resultado com 8 casas decimais. 
 
132 
https://pt.wikipedia.org/wiki/Pi
https://pt.wikipedia.org/wiki/Pi
 Introdução à Programação com Python 
Altere o programa para que ele execute diversas vezes, parando quando o usuário 
informar um valor menor ou igual a zero para N. 
 
19) Junte as soluções feitas para os exercícios 16 a 19 para implementar um programa 
que apresente o valor de com precisão de 8 casas decimais, para diferentes π
valores de N, comparando a eficiência de cada um dos algoritmos em convergir mais 
rapidamente para o valor exato. O valor de com 8 casas decimais é 3,14159265. π
O programa deve perguntar ao usuário o número máximo de elementos da série (N) 
e mostrar o valor calculado de para a série com 1 até N elementos, em forma de π
tabela, como mostrado na figura a seguir. 
 
20) Modifique o programa da questão anterior para permitir que o usuário especifique a 
precisão (limitada a 15 casas decimais) e a execução do programa seja feita de 
maneira repetitiva, até que o usuário informe que o número de elementos é zero. O 
programa deverá, ainda, verificar a diferença entre o valor calculado e o valor exato, 
de cada método e informar qual deles teve a menor diferença, ou o melhor, em cada 
passo. O valor de com 15 casas decimais é 3,141592653589793. O programa π
deverá gerar uma saída como a mostrada a seguir: 
133 
 Introdução à Programação com Python 
 
 
 
21) Modifique a implementação do programa mostrado na seção 6.3.2 para determinar 
se um número é primo usando as ideias discutidas no último parágrafo da referida 
seção. Teste seu programa para um número primo grande (ex: 2147483647) e 
verifique que o tempo cairá de alguns minutos para alguns milisegundos. 
 
 
134 
 Introdução à Programação com Python 
Capítulo 7 - Arranjos 
 
 
Até este ponto foram utilizadas apenas variáveis simples ou escalares. Elas são 
muito úteis, mas não permitem realizar alguns tipos de cálculos. Suponha um programa 
para ler uma sequência de notas de uma turma de N alunos e informar: a média das notas, 
a maior nota, a menor nota, o desvio padrão das notas e o número de notas abaixo da 
média. Suponha uma turma com apenas N=4 alunos com a seguinte lista de notas: 65, 92, 
87 e 54. 
 
O cálculo da média é um problema já resolvido na seção 6.3.1, bastando calcular o 
somatório de todas as notas e dividir o valor pelo número de notas lidas (N). O valor do 
somatório deve ser inicializado com o valor zero e, para cada nota lida, incrementar no valor 
do somatório o valor lido. Em Python, para as 4 notas, poderia ser escrito o seguinte código: 
 
soma = 0 
for i in range (0, N): 
 nota = float(input(‘Nota: ‘)) 
 soma = soma + nota 
media = soma/N 
print(‘A média das notas é: %.2f’ %media) 
 
A identificação da maior (ou menor) nota poderia ser feita com a informação da faixa 
de valores das notas, por exemplo, de [0, 100], utilizando a mesma estrutura do código 
acima. A variável maior seria criada antes do comando repetitivo com um valor -1. Com este 
valor inicial, qualquer nota lida na faixa [0, 100] será maior do que o valor inicial. Portanto, 
dentro do comando repetitivo, basta comparar se a nota lida é maior do que a variável 
maior. Se for, a variável maior seria atualizada para receber o valor da nota que acabou de 
ser lida. O código poderia ser incrementado para determinar a maior nota, como mostrado a 
seguir. Em negrito, os comandos para computar e informar a maior nota: 
 
soma = 0 
maior = -1 
for i in range (0, N): 
 nota = float(input(‘Nota: ‘)) 
 soma = soma + nota 
 if nota > maior: 
 maior = nota 
media = soma/N 
print(‘A média das notas é: %.2f’ %media) 
print(‘A maior nota é: %.2f’ %maior) 
 
Analogamente, para identificar a menor nota bastaria criar outra variável (por 
exemplo menor) com valor inicial acima da faixa. E no comando repetitivo, para cada nota 
lida que for menor do que o valor atual da variável menor, o valor da variável menor deverá 
receber o valor da nota que acabou de ser lida. Com esta inclusão, o código ficaria como a 
seguir. Em negrito, agora, os comandos para calcular e exibir a menor nota: 
 
135 
 Introdução à Programação com Python 
soma = 0 
maior = -1 
menor = 101 
for i in range (0, N): 
 nota = float(input(‘Nota: ‘)) 
 soma = soma + nota 
 if nota > maior: 
 maior = nota 
 if notaobjetivos da disciplina 
INF 100 - Introdução à Programação I é apresentar os conceitos fundamentais de 
programação, habilitando o estudante a usar outras linguagens de programação, neste texto 
os arranjos serão apresentados como definido em outras linguagens de programação como 
C, C++, Java, etc. 
 
Um arranjo é um agregado de elementos (conjunto de variáveis) do mesmo tipo, 
todos relacionados a um mesmo nome dentro do programa. Um arranjo pode ser uni, bi, tri 
ou n-dimensional. Nesta seção, será tratado apenas dos arranjos unidimensionais. Cada 
elemento do agregado, ou cada valor individual, será indexado por um número número 
inteiro, indicando a sua posição relativa no arranjo. Os índices dos elementos de um arranjo 
começam sempre de 0. 
 
O esquema de representação de um arranjo unidimensional em memória pode ser 
visto como o diagrama da Figura 7.1, onde cada posição é identificada por um índice e pode 
armazenar um valor de um determinado tipo. 
 
 
 
Figura 7.1 - Esquema de representação de um arranjo 
 
 
No exemplo, a estrutura (arranjo) de nome v contém 5 números inteiros em 
memória. Da mesma forma que acontece com uma variável escalar, um arranjo deve ser 
referenciado pelo seu nome. Porém, quando se deseja acessar um elemento do arranjo, ele 
deve ser referenciado pelo nome do arranjo e o seu índice. 
 
O elemento da posição 4 do arranjo v deve ser referenciado no programa como v[4]. 
O valor de v[4] é igual a -3. Os valores dos índices possui valor -3. Atente para o fato de que 
a posição 4 de um arranjo corresponde à quinta posição, pois a primeira posição é sempre 
a posição 0. 
 
 
Figura 7.2 - Esquema alternativo de representação de um arranjo 
 
No exemplo da Figura 7.1, em que o arranjo possui tamanho igual a 5 (número de 
elementos do arranjo) o interpretador da linguagem Python irá alocar 5 posições na 
memória e associar a primeira posição (0) ao nome do arranjo (v). Por isso, é necessário 
137 
 Introdução à Programação com Python 
usar o nome do arranjo (v) junto com o índice, de modo a definir o deslocamento (em 
posições de memória) a partir da posição inicial, chegando ao elemento desejado. Uma 
outra forma de visualizar uma arranjo é mostrado na Figura 7.2. 
 
Note que não há problema algum em armazenar um mesmo valor em posições 
diferentes de um arranjo, mas os índices do arranjo são sempre distintos, iniciando em 0 e 
incrementado unitariamente até N-1, para um arranjo de tamanho N. No exemplo ilustrado 
nas Figuras 7.1 e 7.2, N=5 e os índices são 0, 1, 2, 3 e 4. Os valores armazenados nas 
posições de índice 1 e 3, ou na segunda e quarta posições são iguais, ou ainda, v[1] = v[3] 
= 3. 
7.1.1 Arranjos em Python 
 
Para criar e manipular arranjos numéricos (vetores e matrizes) em Python, pode ser 
usada a biblioteca numpy, pois ela proporciona uma maior facilidade para criar e inicializar 
os arranjos, além de possuir características similares a outras linguagens de programação, 
permitindo criar arranjos de tipos específicos. Para isso, é preciso importar a biblioteca 
usando a diretiva de importação como mostrado a seguir: 
 
import numpy 
 
Após a importação, as funções definidas na biblioteca numpy podem ser 
referenciadas (usadas) no programa. A função empty permite criar um arranjo de tamanho 
N números reais, não inicializado: 
 
identificador = numpy.empty(N) 
 
O identificador determina o nome da variável do tipo arranjo que identifica o conjunto 
de dados. Exemplo: 
 
notas = numpy.empty(5) # cria o arranjo notas com 5 posições 
alturas = numpy.empty(10) # cria o arranjo alturas com 10 posições 
 
O não inicializado significa que as posições de memória alocadas para o arranjo 
possuem um valor qualquer. Um comando de impressão para mostrar o valor de uma 
posição de um arranjo que acabou de ser criado com a função empty poderia exibir algo 
como 6.9481849316902e-310 (este foi um resultado exibido pelo Shell do IDLE). 
 
Em alguns casos pode ser necessário preencher todas as posições de um arranjo 
com o valor zero. A função zeros realiza esta tarefa. Também é possível dar um 'apelido' 
para uma biblioteca, só para podermos usar um nome menor, chamando numpy de np, por 
exemplo. A seguir, um exemplo de criação de arranjos com todos os valores iguais a zero e 
o uso do apelido para a biblioteca numpy: 
 
import numpy as np 
notas = np.zeros(5) # cria o arranjo notas com 5 posições iguais a 0 
alturas = np.zeros(10) # cria o arranjo alturas com 10 posições iguais a 0 
 
Por padrão, na biblioteca numpy a criação de um arranjo considera que o tipo de 
cada elemento será número real (ou de ponto flutuante). Para criar um arranjo com 
138 
 Introdução à Programação com Python 
elementos de outro tipo deve ser usado o parâmetro dtype=, onde especifica o 
tipo dos elementos do arranjo que será criado. Por exemplo, a criação de um arranjo de 
números inteiros, já inicializado com zeros poderia ser feita assim: 
 
import numpy as np 
idades = np.zeros( 10, dtype=int ) 
 
Quando um arranjo é pequeno, o programador pode definir os valores inciais 
manualmente, como nos comandos a seguir: 
 
A = np.array([4, 3, 2, 1]) # arranjo de números inteiros 
notas = np.array([70.5, 80, 54.3, 77.8]) # arranjo de números reais 
 
Alguns exemplos simples de operações e acesso sobre elementos de um arranjo 
são apresentadas a seguir no trechos de código com comentários (ressaltando um erro 
existente): 
 
v = np.empty(5) # Cria um vetor v de 5 elementos 
 
v[0] = -9 # Atribui valor na primeira posição 
v[1] = 3 # idem, na segunda posição 
v[2] = 4 # idem, na terceira posição 
v[3] = 3 # idem, na quarta posição 
v[4] = -3 # idem, na quinta posição, compare com Figura 7.1 
 
print( v[4] + v[0] ) # exibe -12.0 (-3 + -9) 
v[0] = v[2] = -10 # armazena -10 nas 3a e 1a posições 
v[3] = float(input()) # lê, do usuário, novo valor para v[3] 
 
v[4] = v[3] + v[2]*v[2] # v[4] = valor informado pelo usuário + 100 
print(v[-1]) # Imprime o valor da última posição v[4] 
print(v[5], v[1.5] ) # Erro de acesso (índices inválidos) 
 
O trecho de código executaria até parar no comando input(), à espera de um valor 
digitado pelo usuário. Supondo que o usuário digite o valor 0 (zero) e a tecla Enter. O 
programa, então, imprimiria o valor 100 e terminaria com a exibição de uma mensagem de 
erro : ‘IndexError: index 5 is out of bounds for axis 0 with size 5’. Esta mensagem indica que 
foi feita uma tentativa de acesso a uma posição (5) que não existe no arranjo. Um arranjo 
de tamanho 5, possui índices de 0 a 4. Note, que o índice 1.5 também é inválido, mas não 
chegou a ser analisado pelo interpretador Python, que para a execução no primeiro erro 
encontrado. 
 
Mas porque o comando print() anterior que referenciou a posição -1 não deu erro de 
acesso ou índice fora da faixa? A linguagem Python possui algumas características bem 
peculiares. Uma delas é permitir o uso de índices negativos, dentro de uma faixa bem 
específica, como no penúltimo comando do trecho de código acima. O comando print(v[-1]) 
imprime o valor contido na última posição ou a posição N-1 do arranjo. É como se o arranjo 
também fosse indexado de trás para frente, com o valor -1 referenciando a posição N-1, o 
valor -2 referenciando a posição N-2 e assim por diante, até chegar ao índice -N que 
corresponde à posição N-N, ou posição 0. Ou seja, para um arranjo de 5 elementos, como o 
do exemplo, são permitidos os índices 0 ou -5, 1 ou -4, 2 ou -3, 3 ou -2 e 4 ou -1, para 
139 
 Introdução à Programaçãocom Python 
referenciar da primeira para a última posições do arranjo. Nos exemplos, serão utilizados 
sempre os índices positivos. 
7.1.2 Percorrendo Arranjos 
 
Ao usar arranjos, uma necessidade frequente é percorrer todos os elementos do 
arranjo, fazendo alguma tarefa com cada elemento ou com os elementos que atendam a 
uma determinada condição. Alguns exemplos possíveis: 
 
para cada elemento i do arranjo A: 
 Escreva A[i] na tela 
 
para cada elemento i do arranjo A: 
 Multiplique A[i] por 2 
 
É possível fazer isso facilmente usando o comando repetitivo while. No caso do 
comando while é fundamental fazer a inicialização correta da variável de controle (i) e o seu 
incremento dentro do comando repetitivo: 
 
i = 0 
while i maior: # compara se a nota lida é a maior 
 maior = nota[i] 
 se nota[i]abaixo da media 
# comando repetitivo: computa somatório (nota[i] - media)² e total de notas , v[i-1]): 
 print(' ', mesmalinha) 
 senão: 
 print(' = ', mesmalinha) 
 imprima(v[i]) 
 
A implementação do algoritmo para gerar exatamente a saída vista na Figura 7.4 
pode ser vista na Figura 7.5. 
145 
 Introdução à Programação com Python 
 
Figura 7.5 - Implementação do programa para determinar a relação entre vizinhos 
 
Nesta implementação a informação solicitada ao usuário do programa usa o índice 
i+1 para que não apareça uma mensagem como: ‘0⁰ elemento’ na primeira execução do 
primeiro comando repetitivo for. 
 
Todos os comandos para imprimir o valor de um elemento do arranjo usam a diretiva 
para manter o cursor na mesma linha (end=' '), para que a saída fique exatamente como a 
proposta no exemplo do enunciado. 
 
 
7.2. Arranjos multidimensionais 
 
Os arranjos podem ser multidimensionais para representar estruturas mais 
complexas do que as vistas até aqui. Um exemplo são os arranjos bidimensionais que 
podem ser utilizados para a representação de matrizes. Diversos problemas na computação 
e em outras tantas áreas do conhecimento podem ser mapeados em soluções matriciais. 
 
Um arranjo bidimensional (ou matriz) M pode ser representado por um conjunto de 
células (ou posições) de memória organizadas em linhas e colunas, como representado na 
Figura 7.6, para um arranjo de 3 linhas e 4 colunas. 
 
 M 
Índices 0 1 2 3 
0 1 2.5 0 -4 
1 0 1 -2 0.5 
2 0 4 1 0.7 
 
Figura 7.6 - Representação de um arranjo 3x4 
 
146 
 Introdução à Programação com Python 
Cada elemento é identificado pelo nome do arranjo e por dois índices para 
referenciar a linha e a coluna do elemento. Por exemplo, o elemento M[i][j] corresponde à 
célula posicionada na linha i e na coluna j. Na Figura 7.6, o índice de linha i varia de 0..2 e o 
índice de coluna varia de 0..4. Da mesma forma que a primeira posição de um arranjo 
unidimensional é referenciada pelo índice 0, em um arranjo bidimensional a primeira linha e 
a primeira coluna também são referenciadas pelo índice 0. 
 
Na Figura 7.6, o elemento M[2][1] possui valor 4. Cada posição do arranjo 
bidimensional armazena um único valor. Um arranjo com m linhas e n colunas possui m x n 
posições. O primeiro índice corresponde ao número da linha, enquanto que o segundo 
índice indica o número da coluna. 
 
Uma tarefa comum utilizando arranjos bidimensionais é percorrer todas as suas 
posições para executar alguma tarefa. Um comando repetitivo aninhado dentro de outro 
comando repetitivo pode ser usado para tal tarefa: 
 
para cada linha i do arranjo: 
 para cada coluna j do arranjo: 
 executar tarefa com o elemento M[i][j] 
 
Neste tipo de estrutura, o comando repetitivo interno é executado completamente 
para cada iteração do comando repetitivo externo. Suponha o caso de um arranjo com m 
linhas e n colunas.por um programa (interpretador ou 
compilador). De posse do código executável será possível utilizá-lo para verificar se a 
solução computacional atende aos requisitos especificados na fase de análise do problema. 
Raramente se conseguirá seguir o diagrama da Figura 1.5 passando uma única vez por 
cada uma de suas fases. 
 
Muitas vezes é no momento da execução do programa que se torna possível 
verificar os erros da implementação da solução. A correção de um erro vai demandar, 
necessariamente, a volta a uma das fases anteriores à verificação da solução (execução do 
programa). Na disciplina INF 100, a grande maioria dos problemas é bem simples e a 
correção dos problemas, geralmente, não demandará uma volta à especificação do 
problema. 
 
O tipo mais comum de erro são erros de sintaxe, que ocorrem quando um ou mais 
comandos são escritos de forma incorreta. Este tipo de erro também é o mais fácil de 
verificar, pois é apontado pelo interpretador ou compilador. No caso da linguagem Python o 
interpretador para a execução do programa ao encontrar um erro de sintaxe e uma 
mensagem de erro é exibida com informações para a correção. A correção demanda a volta 
ao passo de edição do código fonte. 
 
Outro tipo de erro é o de semântica que muitas vezes não é identificado pelo 
interpretador Python. Semântica está relacionada com o sentido ou significado de um 
comando. Um caso muito comum, em Python, é a troca do operador de comparação “==” 
com o operador de atribuição “=”. Ou seja, o usuário pretendia atribuir para a variável a, o 
valor da variável b, cujo comando correto seria o comando de atribuição “a = b“, mas acaba 
escrevendo “a == b”, usando o comparador de igualdade (==) invés do comando de 
atribuição (=). O programa executa normalmente, o comando resultará em um valor True ou 
False, que não será armazenado pelo programa, mas a variável a continuará com o mesmo 
valor. Para este tipo de erro também é necessário voltar à fase de edição do programa 
fonte. Mas pode haver erros de semântica associados à solução descritiva (que geralmente 
14 
 Introdução à Programação com Python 
será feita em Português), o que poderia demandar uma volta à fase de análise do problema 
e, consequentemente, correção de todas as fases posteriores. 
 
Da mesma forma, os erros de lógica também podem aparecer em diferentes fases 
do desenvolvimento do programa. Um erro de lógica em uma condição de parada de um 
comando repetitivo poderia colocar o programa em uma execução sem fim (loop infinito) e 
este erro, eventualmente, pode se dever apenas a um erro na digitação. Neste caso a 
correção costuma ser simples com a correção na edição do código fonte. Ou o erro de 
lógica pode ocorrer na fase de análise com a inversão de duas tarefas que tem que ser 
feitas em uma ordem pré-determinada. Neste outro caso, a volta seria para a fase de 
análise do problema. 
 
Neste ponto, é importante ressaltar que quando um programa mais complexo vai ser 
resolvido, cada tarefa identificada na fase de análise pode dar origem a um módulo de 
programa. No final desta disciplina será apresentado o conceito de função que é uma forma 
de estruturar o programa e promover a reutilização de código. O desenvolvimento de um 
módulo ou uma parte ou uma função de um programa complexo vai seguir os mesmos 
passos do diagrama da Figura 1.5. 
 
Para finalizar esta seção, é importante apresentar uma diferença fundamental entre 
as linguagens interpretadas e compiladas. No caso da linguagem interpretada, o código 
fonte pode ser levado para outro computador que tenha um interpretador da mesma 
linguagem que ele será executado. Já o código executável gerado em um computador só 
poderá ser executado em um outro computador que tenha um processador com o mesmo 
conjunto de instruções do primeiro. 
 
Por isso, costuma-se dizer que uma linguagem interpretada é mais portátil do que 
uma linguagem compilada. Isso ocorre porque, na linguagem interpretada, a tradução da 
linguagem de alto nível para a linguagem de máquina é feita em tempo de execução. Todo 
interpretador Python conhece a linguagem Python, obviamente. Um interpretador Python 
feito para um processador precisa conhecer apenas a linguagem de máquina deste 
processador. E as linguagens de máquina são diferentes para processadores diferentes. Até 
mesmo a linguagem de montagem (Assembly) que é um nível intermediário entre a 
linguagem de alto nível e a linguagem de máquina, é diferente para processadores 
diferentes. 
 
Considere uma operação de adição que na linguagem Python utiliza o operador “+” 
para realizar a soma de duas variáveis (“a” e “b”). A expressão em Python seria algo como 
“a + b”. Esta expressão deveria ser completada de alguma forma para formar um comando 
válido da linguagem Python, mas para o momento este fato não é importante. Conforme foi 
dito, em relação à figura 1.1, o processador executa todas as suas operações usando seus 
registradores internos. Assim, para que a operação de soma da linguagem de alto nĩvel 
aconteça são necessárias 3 operações: 1) transferir o conteúdo da variável “a” para um 
registrador R1; 2) transferir o conteúdo da variável “b” para um outro registrador R2; 3) 
executar a operação de soma usando os registradores R1 e R2 como operandos. 
 
15 
 Introdução à Programação com Python 
Embora as operações a serem executadas sejam as mesmas, independente do 
processador, o código Assembly será muito diferente. Para exemplificar serão considerados 
os processadores x86 (Intel/AMD) e RISC, com os respectivos códigos Assembly mostrados 
na tabela 1.1. Note que as instruções podem ter nomes diferentes como no caso da 
movimentação de dados da memória para registrador (mov/lw) e, eventualmente, quando 
tem mesmo nome como no caso da soma (add) a forma de especificar os operandos são 
diferentes: uma linguagem permite especificar apenas 2 registradores enquanto que a outra 
permite definir 3 registradores. Mas em ambas, o primeiro registrador armazenará o 
resultado da operação de soma. 
 
Tabela 1.1 - Códigos Assembly de uma soma de duas variáveis. 
Assembly do 
Processador x86 
Assembly do 
Processador RISC 
Significado para x86 (RISC) 
mov ax, a 
mov bx, b 
add ax, bx 
lw $t0, a 
lw $t1, b 
add $t3, $t0, $t1 
carrega variável a no registrador ax (t0) 
carrega variável b no registrador bx (t1) 
soma registradores ax e bx (t0 e t1), com 
resultado no registrador ax (t3) 
 
Felizmente, para todos nós, esta deve ser a última vez que será falado sobre 
linguagem de Assembly e linguagem de máquina. De agora em diante, será utilizada 
apenas a linguagem de alto nível Python. E, o mais importante, é que usando a linguagem 
Python o seu programa vai executar em uma máquina com processador x86 ou RISC sem 
nenhum problema, assumindo que exista um interpretador Python instalado nesta máquina. 
 
 
1.4. O ambiente de programação no LBI 
 
Como suporte para as aulas práticas da disciplina INF 100 - Introdução à 
Programação I, o Departamento de Informática da UFV possui o Laboratório de Informática 
(LBI) localizado no segundo pavimento do prédio da Caixa Econômica Federal. O LBI 
funciona durante o semestre letivo de segunda a sexta-feira, de 7h às 18h30, 
excetuando-se os feriados e recessos previstos no calendário escolar da UFV. A sala 4 
(sala de Monitoria) pode ser acessada para praticar a programação Python. 
 
Mas é fortemente recomendado que o estudante matriculado em INF 100 instale o 
ambiente com o editor de programas e interpretador Python (IDLE) em seu computador, 
seguindo as instruções da seção 1.4.1 - Home Python. 
 
O LBI possui quatro salas para as aulas práticas sendo duas salas com 24 
computadores e 2 salas com 20 computadores. O acesso a uma das quatro salas só é 
permitido no horário da aula prática. Há ainda uma salaA execução do comando repetitivo externo começa com o índice i igual a 
zero (primeira linha) e, dentro dele, se inicia a execução do comando repetitivo interno com j 
também igual a zero (primeira coluna). Neste momento, o elemento M[0][0] está sendo 
apontado pelos índices i e j. 
 
O comando repetitivo interno continua a sua execução fazendo j igual a 1 (segunda 
coluna), depois 2 (terceira coluna) e assim por diante. Ou seja, a variação do segundo 
índice (j), mantendo o primeiro índice (i) fixo, faz com que a primeira linha seja percorrida, 
coluna por coluna. Quando terminar a primeira iteração do comando repetitivo externo, o 
índice i será incrementado e passará a valer 1 (segunda linha). E o comando repetitivo 
interno será executado novamente, fazendo o índice j variar de 0 a N-1, percorrendo a 
segunda linha, coluna por coluna. E assim, sucessivamente. 
 
Desta forma a matriz vai sendo percorrida por linha. Em algumas situações pode 
ser necessário percorrer a matriz por coluna. Para realizar a tarefa desta maneira, bastaria 
inverter a ordem dos comando repetitivos, fixando no comando repetitivo externo o índice 
da coluna e variando o índice de linha no comando repetitivo interno. 
 
para cada coluna j do arranjo: 
 para cada linha i do arranjo: 
 executar tarefa com o elemento M[i][j] 
 
Uma outra forma de visualizar um arranjo bidimensional é como uma estrutura de 
dados de arranjo de arranjos unidimensionais, conforme mostrado na Figura 7.7, para 
representar o mesmo arranjo exibido na Figura 7.6. 
 
 
147 
 Introdução à Programação com Python 
 
 
Figura 7.7 - Representação de arranjo bidimensional 
 
O primeiro arranjo seria apenas um arranjo de índices (0..m-1), com cada índice 
apontando para um arranjo unidimensional, com os elementos de uma linha da matriz. De 
fato, esta estrutura é utilizada na implementação de algumas linguagens de programação, 
como Python, por exemplo. Ela é bastante flexível, permitindo a sua recorrência para definir 
um arranjo n-dimensional ou para ter estruturas com arranjos de tamanho diferente (mas 
isso é assunto para quem for cursar a disciplina INF 101 - Introdução à Programação II). 
 
 Note que os algoritmos para percorrer o arranjo bidimensional independem da forma 
de representação. Dessa forma, pode-se adotar a representação que se considere mais 
conveniente ou a mais fácil de entender. 
 
7.2.1. Definição de arranjos bidimensionais em Python 
 
A definição de arranjos na linguagem Python pode ser feita diretamente no código 
informando os valores de cada posição. Em geral, esta forma é adotada quando o número 
de elementos é pequeno. A definição do arranjo 3x4 da Figura 7.6 na linguagem Python 
pode ser feita da seguinte forma: 
 
M = [ [1, 2.5, 0, -4], [0, 1, -2, 0.5], [0, 4, 1, 0.7] ] 
 
Uma forma comumente adotada na definição de um arranjo bidimensional é 
escrever os valores de maneira similar à representação em linhas e colunas, como 
mostrado a seguir: 
 
M = [ [1, 2.5, 0, -4] , 
 [0, 1, -2, 0.5] , 
 [0, 4, 1, 0.7] 
 ] 
 
Para o interpretador da linguagem Python não faz diferença a forma de escrita, se 
em uma única linha ou imitando a representação matricial. O importante é que as regras de 
sintaxe sejam respeitadas, ou seja, o identificador deve ser um nome válido, seguido do 
operador de atribuição e dos elementos do arranjo entre colchetes e separados por vírgula. 
Como cada linha possui um conjunto de valores, estes também devem vir entre colchetes e 
separados por vírgulas. 
 
Para a definição de arranjos com um número maior de elementos ou cujos 
elementos serão definidos durante a execução do programa, ou ainda, quando não se sabe 
inicialmente quais serão as dimensões do arranjo. Nestes casos, pode ser utilizada a 
148 
 Introdução à Programação com Python 
biblioteca numpy, como feito para arranjos unidimensionais, obviamente definindo as duas 
dimensões (número de linhas e de colunas), como a seguir: 
 
import numpy as np 
A = np.empty( (3, 4) ) # cria o arranjo A com 3 linhas e 4 colunas 
 
O arranjo criado acima, usando a função empty() da biblioteca numpy, não define 
valores para os elementos de A. Caso tivesse sido utilizada a função zeros(), todos os 
elementos teriam valor 0. Mas a biblioteca numpy também pode ser utilizada quando se 
pretende definir valores iniciais para os elementos da matriz, como em: 
 
import numpy as np 
mi = np.array( [ [1, 2, 3], 
 [4, 5, 6], 
 [7, 8, 9], 
 [10, 11, 12] ] ) 
 # imprime os elementos da matriz mi 
for i in range(0, 4): 
 for j in range(0, 3): 
print('%3d' % (mi[i][j]), end='') 
 print() 
 
O trecho de código acima, além de definir os valores da matriz mi, faz também a 
impressão dos elementos da matriz, usando a implementação do algoritmo de percorrer a 
matriz por linha. Os elementos de cada linha são impressos pelo comando print() dentro do 
comando for interno. Após a impressão de cada elemento, a diretiva ‘end=’ mantém o cursor 
na mesma linha, de forma que todos os elementos da linha da matriz sejam impressos na 
mesma linha na tela do computador. Na primeira iteração do comando for externo, com i=0, 
a primeira linha da matriz foi impressa. 
 
O comando print() dentro do comando for externo (última linha do código), faz pular 
para a próxima linha. Após este print() o comando for externo termina uma iteração e 
incrementará a variável de controle i. Para i = 1, 2 e 3 o comando for será executado 
novamente, imprimindo os elementos das linhas 1, 2 e 3 ou segunda, terceira e quarta linha, 
respectivamente. O resultado da impressão será: 
 
 1 2 3 
 4 5 6 
 7 8 9 
 10 11 12 
 
Note que o parâmetro de formatação com 3 espaços foi suficiente para separar os 
valores inteiros e dar a visão espacial de matriz, como nos livros de matemática, pois os 
maiores valores numéricos ocupam 2 posições. Se o programador tivesse esquecido de 
colocar o espaçamento, usando apenas '%d' invés de '%3d', a impressão sairia como 
mostrada abaixo: 
 
 123 
 456 
 789 
 101112 
149 
 Introdução à Programação com Python 
7.2.2. Exemplos usando matrizes 
 
A tarefa de percorrer um arranjo unidimensional ou bidimensional é, talvez, a tarefa 
mais comum quando este tipo de estrutura de dados é utilizada. Nesta seção serão 
apresentados alguns exemplos básicos de problemas utilizando arranjos. 
7.2.2.1. Pesquisa em matriz 
 
Faça um programa que leia os dados de uma matriz A de números reais, de 
dimensões m x n. Em seguida, o programa deve ler um valor x que deverá ser pesquisado 
na matriz. O programa deverá indicar em que posições da matriz o valor x aparece. 
 
Repare que o enunciado não especificou as dimensões da matriz. Logo, estas 
informações também deverão ser solicitadas ao usuário. Isso é bom, pois o programa ficará 
parametrizado com o número de linhas (m) e o número de colunas (n). O algoritmo para 
resolver este problema pode ser descrito assim: 
 
m = Leia(‘Número de linhas da matriz: ‘) 
n = Leia(‘Número de colunas da matriz: ‘) 
A = arranjo(m, n) 
“Leia os elementos da matriz” 
x = Leia(‘Entre com o valor a ser pesquisado”) 
“Pesquise x na matriz e informe a posição quando encontrar” 
Se “não achou” 
 Escreva(‘x não está presente na matriz’) 
 
O algoritmo acima ainda não está em uma forma que possa ser traduzido para a 
linguagem Python. É necessário refinar as ações “Leia os elementos da matriz” e “Pesquise 
x na matriz e informe a posição quando encontrar”. A primeira é mais simples e corresponde 
à ação de solicitar ao usuário o valor de cada elemento da matriz. Isso pode ser 
implementado com o algoritmo de percorrer a matriz por linha:para i na faixa (0, m): 
 para j na faixa de (0, n): 
 A[i][j] = Leia(‘Elemento i, j) 
 
Já a tarefa “Pesquise x na matriz e informe a posição quando encontrar” deve ser 
feita com um pouco mais de atenção para tratar o caso de não ser encontrado o valor x na 
matriz. O algoritmo básico também será o de percorrer toda a matriz e, para cada elemento, 
fazer a comparação com o valor de x. Se for igual deverá ser impressa a sua posição. Além 
disso deverá ser registrado que o valor foi encontrado. O registro de que o valor foi 
encontrado pode ser feito atribuindo o valor verdadeiro para uma variável booleana. O nome 
dessa variável será achou e seu valor será inicializado com Falso (antes de iniciar a 
pesquisa, não achou é verdade, ou achou é falso). A seguir, o detalhamento desta ação: 
 
achou = False 
para i na faixa (0, m): 
 para j na faixa de (0, n): 
 se A[i][j] == x 
150 
 Introdução à Programação com Python 
 Imprima(i, j) 
 achou = True 
 
A Figura 7.8 apresenta a implementação Python do algoritmo discutido até este 
ponto. Observe que, novamente, alguns elementos fundamentais para um programa como a 
importação da biblioteca numpy e comandos adicionais para melhorar sua usabilidade e 
visualização não estão presentes no algoritmo. 
 
 
Figura 7.8 - Programa para encontrar um valor e informar sua posição em uma matriz 
 
A impressão da matriz não foi solicitada no enunciado, mas fica melhor para o 
usuário verificar se o programa gerou o resultado correto. A Figura 7.9 apresenta o 
resultado de uma execução do programa da Figura 7.8, onde o valor procurado aparece 1 
vez. 
 
151 
 Introdução à Programação com Python 
 
Figura 7.9 - Resultado de uma execução do programa da Figura 7.8 
 
 
7.2.2.2. Verificação de propriedades de uma matriz 
 
Faça um programa que leia os dados de uma matriz A de números reais, de 
dimensões m x n. O programa deverá indicar se a matriz é uma matriz diagonal (elementos 
fora da diagonal principal são todos iguais a zero) e, além disso, se é também uma matriz 
identidade (matriz diagonal com todos os elementos da diagonal principal iguais a 1). 
 
O algoritmo para atender ao que se pede no enunciado pode ser descrito da 
seguinte forma: 
 
m = Leia(‘Número de linhas da matriz: ‘) 
n = Leia(‘Número de colunas da matriz: ‘) 
A = arranjo(m, n) 
“Leia os elementos da matriz” 
“Verifique se a matriz é uma matriz diagonal” 
Se “diagonal”: 
 “Verifique se a matriz é uma matriz identidade” 
 Se “identidade”: 
 Escreva(‘matriz é identidade’) 
 Senão: 
 Escreva(‘matriz é diagonal’) 
Senão: 
 Escreva(‘matriz não é diagonal’) 
 
 Os quatro primeiros comandos do algoritmo são exatamente os mesmos do 
algoritmo da subseção 7.2.2.1 e não serão rediscutidos aqui. Em caso de dúvidas, releia a 
subseção anterior. O foco será no refinamento das ações “Verifique se a matriz é uma 
matriz diagonal” e “Verifique se a matriz é uma matriz identidade”. 
 
 A primeira observação a ser feita é que para uma matriz ser diagonal (e identidade) 
a primeira condição necessária é que ela seja uma matriz quadrada, ou seja, o número de 
linhas deve ser igual ao número de colunas. Somente as matrizes quadradas possuem uma 
152 
 Introdução à Programação com Python 
diagonal principal. E matriz identidade é um caso particular da matriz diagonal. Então, o 
algoritmo informará uma (e apenas uma) das quatro opções: 1) matriz não é quadrada; 2) 
matriz não é diagonal; 3) matriz é diagonal; ou 4) matriz é identidade. Um primeiro 
refinamento das ações para verificar se a matriz é uma matriz diagonal e matriz identidade 
poderia ser escrito como: 
 
se m != n: 
 Escreva(‘A matriz não é quadrada’’) 
senão: 
 “Verifique se a matriz é uma matriz diagonal” 
 Se “diagonal” 
 “Verifique se a matriz é uma matriz identidade” 
 Se “identidade” 
 Escreva(‘matriz é identidade’) 
 Senão 
 Escreva(‘matriz é diagonal’) 
 Senão: 
 Escreva(‘matriz não é diagonal’) 
 
Note que a ação “Verifique se a matriz é uma matriz diagonal” foi deslocada e 
associada ao teste de uma condição, pois a verificação só precisa ser processada quando 
m (número de linhas) for igual a n (número de colunas) - resultado falso do teste m != n. Se 
o teste for verdadeiro, o algoritmo termina escrevendo que a matriz não é diagonal. 
 
A verificação da propriedade de ser diagonal consiste em testar todos os elementos 
fora da diagonal principal são iguais a zero. Para auxiliar na visualização da tarefa a ser 
feita, a Figura 7.9 apresenta três matrizes quadradas de ordem 4: uma não diagonal, uma 
diagonal e a outra identidade. A diagonal principal está destacada em cada uma delas. 
 
 
 
Figura 7.9 - Exemplos de matrizes 
 
A característica dos elementos da diagonal principal é que o número da linha é igual 
ao número da coluna, ou seja, o índice de linha i é igual ao índice de coluna j. 
Consequentemente, os elementos fora da diagonal principal tem o índice de linha i diferente 
do índice de coluna j. 
 
O algoritmo para percorrer toda a matriz pode ser usado e aplicando o teste apenas 
para os elementos que estão fora da diagonal principal. Antes de iniciar o percorrimento da 
matriz, pode-se supor que ela é diagonal. Se algum elemento fora da diagonal principal for 
diferente de zero, ela não será diagonal. Em termos de algoritmo, isto pode ser escrito 
como: 
 
diagonal = True 
153 
 Introdução à Programação com Python 
para i de (0, m): 
 para j de (0, n): 
 se i != j E A[i][j] != 0 
 diagonal = False 
 
Ao terminar este trecho, o algoritmo já terá armazenado na variável diagonal o valor 
verdadeiro ou falso. Se o valor for falso, o algoritmo termina, escrevendo que a matriz não é 
diagonal. Caso contrário, ele processará a verificação dos valores dos elementos da 
diagonal principal, para informar se é uma matriz diagonal qualquer ou se é o caso especial 
da matriz identidade. Para verificar se a matriz é uma matriz identidade, uma lógica similar a 
usada anteriormente pode ser aplicada, porém, o teste agora será para os elementos com 
valor do índice de linha i igual ao índice de coluna j: 
 
identidade = True 
para i de (0, m): 
 para j de (0, n): 
 se i == j E A[i][j] != 1 
 identidade = False 
A versão completa do algoritmo refinado, juntando os refinamentos discutidos, é 
mostrada a seguir: 
 
# lendo dimensões da matriz 
m = Leia(‘Número de linhas da matriz: ‘) 
n = Leia(‘Número de colunas da matriz: ‘) 
A = arranjo(m, n) 
# leitura dos elementos da matriz A 
para i na faixa (0, m): 
 para j na faixa de (0, n): 
 A[i][j] = Leia(‘Elemento i, j) 
#verifica se matriz é quadrada (só pode ser diagonal ou identidade se for quadrada) 
se m != n: 
 Escreva(‘A matriz não é quadrada’’) 
senão: 
 # verifica se é diagonal. Elementos fora da diagonal devem ser iguais a zero 
 diagonal = True 
 # percorre a matriz toda e testa elementos com i != j (fora da diagonal principal) 
 para i de (0, m): 
 para j de (0, n): 
 se i != j E A[i][j] != 0 
 diagonal = False 
 Se “diagonal” 
 # verifica se é identidade. Todos elementos da diagonal devem ser iguais a 1 
 identidade = True 
 # percorre a matriz toda e testa elementos com i = j (da diagonal principal) 
 para i de (0, m): 
 para j de (0, n): 
 se i == j E A[i][j] != 1: 
 identidade = False 
 Se “identidade”:Escreva(‘matriz é identidade’) 
 Senão: 
154 
 Introdução à Programação com Python 
 Escreva(‘matriz é diagonal’) 
 Senão: 
 Escreva(‘matriz não é diagonal’) 
 
 
A implementação deste algoritmo é mostrada na Figura 7.10. O resultado da 
execução do algoritmo para 2 matrizes diferentes é mostrado na Figura 7.11. Foram usadas 
matrizes 3x3 para que a figura não ocupasse mais de uma página. 
 
Novamente o programa faz mais tarefas além daquelas expressas no enunciado, 
como a impressão da matriz. Isso foi feito para o usuário visualizar não só o resultado da 
classificação, mas também os elementos da matriz dispostos em linhas e colunas, de modo 
a facilitar a inspeção visual para observar a correção do resultado. 
 
Outras abordagens diferentes poderiam ser adotadas no algoritmo/programa. Uma 
delas seria obrigar que toda matriz seja quadrada, ou seja, ao invés de aceitar valores 
quaisquer para m e n, o programa poderia forçar que os dois valores fossem sempre iguais. 
 
 
 
Figura 7.10 - Programa para classificação de uma matriz quadrada 
 
155 
 Introdução à Programação com Python 
 
 
 
 
Figura 7.11 - Resultados de duas execuções do programa da Figura 7.10 
 
 
 Outra modificação possível (e desejável) seria no sentido de melhorar a eficiência da 
execução do código. O comando para percorrer todos os elementos de uma matriz executa 
vezes ou vezes, quando a matriz é quadrada (m = n). Uma matriz com 1000 linhas 𝑚 𝑥 𝑛 𝑚²
e 1000 colunas executaria 1000000 a comparação do comando if que está dentro de dois 
comandos for aninhados, tanto para identificar o caso de matriz diagonal quanto para 
identificar depois se a matriz diagonal é um caso particular de matriz identidade. 
 
 No caso da identificação da matriz diagonal, quando o primeiro elemento fora da 
diagonal principal for diferente de zero, o comando repetitivo poderia parar, depois de 
atribuir o valor falso para a variável diagonal. Este é um dos casos onde vale a pena 
156 
 Introdução à Programação com Python 
trabalhar com o comando repetitivo while. Veja como ficaria o código para a identificação da 
propriedade da matriz ser diagonal: 
 
# verifica se é diagonal. Elementos fora da diagonal devem ser iguais a zero 
diagonal = True 
# percorre a matriz até encontrar o primeiro elemento diferente de zero, 
# com i != j (fora da diagonal principal) 
i = 0 # índice da primeira linha 
while diagonal E iYellow (amarelo) e blacK (preto)). Porém, este padrão não será tratado aqui. É 
importante lembrar que no caso de usar os códigos feitos para o padrão RGB, com uma 
figura codificada como CYMK a execução irá gerar um erro na abertura do arquivo.. 
 
A codificação RGB usa os 24 bits do pixel, armazenando o componente R 
(vermelho) no primeiro byte, o componente G (verde) no segundo byte e o componente B 
(azul) no terceiro byte. Em Python é possível ler ou escrever um pixel da imagem e fazendo 
a separação dos componentes RGB na operação de escrita e leitura. 
 
Suponha uma imagem armazenada em uma matriz de nome imagem. O comando 
abaixo lê o valor de um pixel (um elemento da matriz imagem) da linha i, coluna j e atribui 
para cada variável um componente da cor: 
 
 r, g, b = imagem[i][j] 
 
O resultado será a variável r recebendo o valor do componente vermelho, a variável 
g recebendo o valor do componente verde e a variável b recebendo o valor do componente 
azul. 
 
Para atribuir um valor de cor para um pixel na imagem (ou um elemento da matriz 
imagem), o comando de atribuição deve ser feito no sentido inverso, atribuindo uma tripla 
de valores inteiros para um pixel de uma das posições da matriz. No exemplo abaixo, um 
ponto azul está sendo atribuído para um pixel. 
159 
 Introdução à Programação com Python 
 
 imagem[0][0] = (0, 0, 255) 
 
 Os valores precisam estar entre parênteses e separados por vírgula e o efeito deste 
comando será atribuir zero para os componentes vermelho e verde e o valor máximo (255) 
para o componente azul. Desta forma, o comando atribui uma cor azul para o ponto no 
canto superior esquerdo de uma imagem (primeira linha, primeira coluna). Mas, a alteração 
de apenas um ponto na imagem não causa um efeito perceptível para o usuário. 
 
Em geral, manipulação de imagens irá percorrer toda a matriz e aplicar alguma 
transformação em todos os pixels, como por exemplo para realçar o tom de verde em 
relação aos tons de azul e vermelho. Ou aplicar a transformação em apenas alguns pontos, 
como por exemplo, em uma foto da torcida Botafogo transformar apenas os pixels brancos 
em pixels vermelhos e dizer que a foto é da torcida do Flamengo. Ou ainda, poderá 
percorrer apenas parte a matriz, e aplicar as alterações em apenas alguns pontos, como por 
exemplo, na implementação da função de “redução de olhos vermelhos”, onde o usuário 
marca a região dos olhos, mas a transformação será apenas nos pixels onde o componente 
vermelho seja predominante em relação aos outros dois. 
 
Para o processamento de imagens, usando o processamento matricial é necessário 
ter instalado, além da biblioteca numérica numpy (que tem sido usada desde que os 
arranjos unidimensionais foram apresentados), a biblioteca gráfica Pillow. Esta biblioteca é 
importada com o nome de PIL (import PIL). 
 
Um algoritmo genérico para processamento de imagem pode ser descrito como a 
seguir: 
 
largura = obter a largura da imagem 
altura = obter a altura da imagem 
 
para i = 0 até altura-1: 
 para j = 0 até largura-1: 
 pixel = imagem[i][j] 
 Alterar valor do pixel 
 imagem[i][j] = pixel 
 
 Observe que o algoritmo está parametrizado em função da altura e da largura da 
imagem. Para a implementação em Python, estes valores serão obtidos através de uma 
biblioteca de manipulação de imagens, que deverá ser importada no início do código da 
mesma forma que tem sido feito com a biblioteca numpy. 
 
Como exemplo de processamento de imagem, suponha um programa que deve 
implementar as seguintes tarefas: ler uma imagem digital, exibindo-a na tela; alterar o valor 
dos pixels, aumentando o componente verde em 50% e o azul em 30%, e reduzindo o 
vermelho em 10%; exibir a imagem resultante. 
 
O programa para implementar a solução do problema dado é mostrado na Figura 
7.13. Importante observar que o arquivo que contém as funções descritas na Tabela 7.1, 
bem como o arquivo com a imagem a ser processada devem estar no mesmo diretório do 
programa fonte (Figura7-13.py). 
 
160 
 Introdução à Programação com Python 
 
 
Figura 7.13 - Implementação de um programa para alterar as cores de uma imagem 
 
 
O arquivo imagens.py importado no início do código mostrado na Figura 7.13 
(disponibilizado junto com o roteiro de aulas práticas no servidor do LBI) possui uma 
pequena biblioteca com algumas funções de manipulação arquivos de imagens padrão jpg 
e png, dentre outros. As funções estão detalhadas na Tabela 7.1. 
 
Tabela 7.1 - Funções do arquivo imagens.py 
Nome da função Parâmetro de 
entrada 
Tarefa realizada Valor retornado 
Imagem() nome do arquivo 
com a imagem 
lê o arquivo de imagem e 
gera matriz de pixels 
RGB 
matriz de pixels 
altura nenhum informa o número de 
linhas da matriz 
número de linhas da 
matriz 
largura nenhum informa o número de 
colunas da matriz 
número de colunas da 
matriz 
mostrar() nenhum exibe a imagem na tela 
do computador 
nenhum 
 
O resultado da execução do programa é mostrado na Figura 7.14. Note que a janela 
do Shell aparece na parte mais baixa da Figura 7.14, mas nenhum resultado foi impresso 
pelo programa. O único resultado visível do programa é a execução da função mostrar(), 
aplicada duas vezes na matriz im. Na primeira vez foi gerada a imagem mostrada à 
esquerda, que é a imagem original. Na segunda execução foi mostrada a imagem da direita, 
que foi modificada pelo programa. 
 
Como pode ser observado na cor da pele, a imagem original possui um tom mais 
avermelhado, enquanto que a imagem após o processamento ficou mais amarelada. A cor 
de fundo também teve uma alteração substancial pelo processamento feito. 
 
161 
 Introdução à Programação com Python 
 
 
Figura 7.14 - Resultado da Execução do programa da Figura 7.13 (Fonte: foto do acervo 
pessoal de Paula Cerqueira Goulart) 
 
 Uma observação final, apenas para ilustrar, mais uma vez, a importância da 
indentação do código Python. Suponha que o programador tivesse alinhado o último 
comando com o penúltimo - aliás, este é um erro que acontece muito frequentemente nas 
aulas práticas. O efeito desse erro seria exibir a imagem a cada pixel alterado. Isso 
provocaria uma demora muito grande para o programa terminar, além de poder utilizar toda 
a memória do computador, causando uma pane geral. 
 
7.3. Exercícios 
 
1) Faça um programa que leia um arranjo (ou vetor) de 10 elementos e troque todos os 
números negativos por 0, em seguida imprima o vetor modificado. 
 
 
2) Escreva um programa que leia um vetor X de 10 elementos. Crie um vetor Y, com 
todos os elementos de X na ordem inversa, ou seja, o último elemento passará a ser 
o primeiro, o penúltimo será o segundo e assim por diante. Escrever todo o vetor X e 
todo o vetor Y. 
 
162 
 Introdução à Programação com Python 
 
3) Escreva um programa que leia um vetor X de 10 elementos. Em seguida, crie um 
vetor Y da seguinte forma: os elementos de Y com índice par receberão os 
respectivos elementos de X divididos por 2; os elementos com índice ímpar 
receberão os respectivos elementos de X multiplicados por 3. Escrever o vetor X e o 
vetor Y. 
 
 
4) Faça um programa que leia um vetor W de 10 elementos, depois receba um valor V. 
Em seguida, seu programa deve contar e escrever quantas vezes o valor V ocorre 
no vetor W e escrever também em que posições (índices) do vetor W o valor V 
aparece. 
 
 
5) Faça um programa que leia um arranjo de tamanho 10 e escreva o valor do maior 
elemento desse arranjo e a respectiva posição que ele ocupa no vetor. 
 
 
6) Refaça o exercício 2 sem usar umvetor auxiliar (vetor Y). A inversão dos elementos 
do vetor X deverá ser feita utilizando uma variável escalar. 
 
 
7) Escreva um programa para ler um vetor SORTEADOS de 6 elementos contendo os 
números sorteados da Mega-Sena. A seguir, ler um vetor ESCOLHIDOS de até 15 
elementos contendo uma aposta. Uma aposta pode conter de 6 a 15 dezenas. Todos 
os valores devem estar entre 1 e 60. O programa deve garantir que as dezenas 
sorteadas sejam distintas, pois no mundo real se uma dezena sorteada for repetida, 
ela é descartada. O mesmo vale para as dezenas da aposta do usuário. O 
programa deve exibir as dezenas “sorteadas”, as dezenas da aposta e escrever 
quais números da aposta correspondem a números sorteados e quantos pontos ele 
fez. 
 
 
8) Refaça o programa anterior usando a função random.randint para sortear as 6 
dezenas, que deverão ser exibidas somente depois do usuário fazer a sua aposta. 
Nesta versão, o programa deverá informar o valor da aposta feita pelo usuário 
considerando que a aposta simples (6 dezenas) é de R$ 4,50 (valor em agosto de 
2020) e que os valores de outras apostas é dada pelo número de combinações 
possíveis, dada pela expressão: 
 NúmeroDeCombinações = , onde n = número de dezenas do palpite. 
𝑛!
6!(𝑛−6)!
 
 
9) Escreva um programa para ler um vetor A de 10 elementos e um valor X. Copie para 
um vetor S os elementos de A que são maiores que X. Logo após imprima o vetor S. 
 
 
10) Faça um programa que leia um vetor e ordene, de modo crescente, o vetor. 
 
 
163 
 Introdução à Programação com Python 
11) Faça um programa gerar um vetor X de 10 elementos com valores aleatórios entre 
10 e 90. Na sequência, o programa deverá exibir os valores do vetor, em uma 
mesma linha e solicitar que o usuário forneça um valor P (aceitando apenas valores 
entre 0 e 9) que representa a posição de um elemento dentro do vetor X. Imprimir o 
valor do elemento que ocupa a posição informada. Logo após excluir esse elemento 
do vetor, fazendo com que os elementos subsequentes (se houver) sejam 
deslocados uma posição para o início e o valor 0 (zero) seja inserido na última 
posição do arranjo contendo elemento válido. O programa deverá exibir o arranjo, 
após cada eliminação e ser executado até que todos os elementos sejam 
eliminados, imprimindo ao final o arranjo contendo apenas valores 0 (zero). A cada 
eliminação, a faixa permitida para o valor P deverá ser compatível com as posições 
ocupadas por elementos válidos (diferentes de 0). 
 
 
12) Criptografia (Do Grego kryptós, "escondido", e gráphein, "escrita") é o estudo dos 
princípios e técnicas pelas quais a informação pode ser transformada da sua forma 
original para outra ilegível, de forma que possa ser conhecida apenas por seu 
destinatário, o que a torna difícil de ser lida por alguém não autorizado 
(http://pt.wikipedia.org/wiki/Criptografia). 
Uma das mais simples e conhecidas técnicas de criptografia é a Cifra de 
César. É um tipo de cifra de substituição na qual cada letra do texto é substituída por 
outra. Por exemplo, com uma troca de três posições, A seria substituído por D, B se 
tornaria E, e assim por diante. O mesmo se pode aplicar a números, por exemplo, 
com uma troca de cinco posições, 0 seria 5, 1 seria 6 e assim por diante. A 
criptografia também pode ser representada usando aritmética modular. A criptografia 
de um número por uma troca posições pode ser descrita matematicamente como: 
En(x) = (x + n)%Y 
 
A decriptografia é feita de modo similar: 
D(En(x)) = (En(x) - n)%Y = x 
 
onde, Y é o maior valor dos números que se deseja aplicar a Cifra de César e n é o 
valor da distância. O resultado deve estar entre 0 e Y, ou seja, se x+n ou x–n não 
estiverem no intervalo 0...Y, deve-se subtrair ou adicionar Y. Obviamente, após a 
decriptografia, a informação deve ser igual à original. 
 
Faça um programa que leia o valor de n, o valor de Y, o tamanho e o vetor a ser 
criptografado e os elementos deste vetor (a). Em seguida, o programa deverá criar 
um arranjo b para receber os elementos criptografados e imprimir o vetor 
criptografado. Finalmente, o programa deverá criar um vetor c, para receber os 
elementos resultantes da decriptografia dos elementos do vetor b. Veja um exemplo 
da execução do programa: 
 
 
 
164 
 Introdução à Programação com Python 
 
13) O algoritmo de criptografia do exercício anterior é muito simples e dá para observar 
que um número criptografado é sempre igual. Por exemplo, o 2 que aparece 4 vezes 
na sequência original é sempre codificado como 6. Uma forma de tornar o algoritmo 
um pouquinho mais robusto é usar a distância (n) diferente a cada cifragem e 
decifragem dos valores. Uma possibilidade é fazer um incremento modular do valor 
n. Implemente esta alteração no programa do exercício anterior. A Figura abaixo 
apresenta uma saída onde o valor inicial de n foi 4 (primeiro valor fornecido pelo 
usuário) e a cada novo elemento a ser cifrado o valor de n foi incrementado 
(modularmente) de 3 unidades. Observe, que nesta implementação, o valor 2 foi 
criptografado como 2 (duas vezes), 9 e 5. 
 
 
 
 
14) Implemente um algoritmo de criptografia para uma string (lembre-se que uma string 
é um arranjo de caracteres) fornecida pelo usuário, usando o algoritmo do exercício 
12 com as devidas adaptações. Para obter o valor decimal correspondente a um 
caracter deve ser usada a função ord() e para transformar um valor decimal para 
caractere deve ser usada a função chr(). Ambas são funções primitivas da 
linguagem Python e não é necessário importar nenhuma biblioteca para usá-las. 
Considere o maior valor (Y definido no enunciado do exercício 12) igual a 256, 
considerando que os caracteres ASCII variam de 0 a 255. A figura a seguir mostra 
um exemplo execução do programa para a distância (número de troca) igual a 3. 
 
 
 
OBS: Teste o programa para as entradas da figura acima, pois dependendo do texto 
digitado ou da distância (número de troca) coisas estranhas podem acontecer por 
causa dos caracteres de controle do ASCII, tais como os já conhecidos “\n” e “\t” ou 
como o “/0” que indica fim de uma string. 
 
15) O algoritmo de criptografia do exercício anterior também tem o ponto fraco de gerar 
o mesmo caractere cifrado para um dado caractere original. Verifique que a letra “e” 
foi sempre cifrada como “h”. Use a mesma ideia do exercício 13 para fazer um 
incremento modular do valor n. Implemente esta alteração no programa do exercício 
anterior. A Figura abaixo apresenta uma saída onde o valor inicial de n foi 4 (primeiro 
valor fornecido pelo usuário) e a cada novo elemento a ser cifrado o valor de n foi 
incrementado (modularmente) de 3 unidades. Observe, que nesta implementação, o 
valor “e” foi criptografado como “k”, “t”, “}” e “¹”. 
165 
 Introdução à Programação com Python 
 
 
 
OBS: idem à do exercício anterior. 
 
 
16) Faça um programa que leia o número de alunos de uma turma, em seguida leia a 
matrícula e a nota de cada aluno. Após, calcule a média aritmética da turma e 
imprima matrícula e a nota dos alunos reprovados, de exame final e aprovados. 
 
 
17) Implemente o programa discutido na seção 7.1.2 permitindo que o usuário defina o 
valor de N. O programa deverá executar e, ao final, solicitar novamente um valor de 
N para nova execução. Se o usuário fornecer um valor 0 ou negativo, o programa 
deve terminar. Observe que dependendo da quantidade de números gerados na 
sequência, a forma de exibição da saída na tela pode ajudar (ou atrapalhar) a sua 
visualização por parte do usuário do programa. Tente encontrar uma solução 
genérica para se ter sempre uma boa visualização da saída. 
 
 
18) Escreva um programa para criar uma matriz A de dimensõesm x n, definidas pelo 
usuário, que também deverá informar os valores dos elementos da matriz. Em 
seguida, o programa deverá: 
- Calcular a média dos valores da matriz; 
- Calcular o desvio padrão dos valores da matriz; 
- Gerar um arranjo B de dimensão m, contendo na posição i o produto dos 
elementos da linha i da matriz A; 
- Gerar um arranjo C de dimensão n, contendo na posição j a soma dos 
elementos da coluna j da matriz A. 
O programa deverá imprimir a matriz no formato de linhas e colunas, ou seja, em 
uma mesma linha na tela deverão estar todos e somente os elementos daquela linha 
da matriz. Vide exemplo a seguir. 
 
 
19) Refaça o exercício anterior com a geração dos elementos da matriz A usando 
números inteiros e aleatórios na faixa de -10 a + 10. 
 
 
20) Implemente o programa da seção 7.2.2.2 de forma eficiente, ou seja, o programa 
deverá terminar sempre que um primeiro caso quebre a propriedade que está sendo 
investigada (diagonal ou identidade). 
 
 
21) Escreva um programa para somar duas matrizes A e B, armazenando o resultado 
em uma terceira matriz C. O usuário deverá informar o número de linhas e de 
colunas, além de todos os elementos das duas matrizes. O programa deve verificar 
166 
 Introdução à Programação com Python 
se a soma é possível antes de pedir o valor dos elementos ao usuário. Caso a soma 
não seja possível, o programa deverá solicitar novamente ao usuário as informações 
das dimensões das 2 matrizes. Ao final, o programa deverá imprimir as matrizes A, 
B e C. 
 
 
22) Altere a solução do exercício anterior com a geração dos elementos das matrizes A 
e B usando números reais e aleatórios, na faixa entre 0 e 100. 
 
 
23) Escreva um programa para multiplicar duas matrizes A e B, armazenando o 
resultado em uma terceira matriz C. O usuário deverá informar o número de linhas e 
de colunas, além de todos os elementos das duas matrizes. O programa deve 
verificar se a multiplicação é possível antes de pedir o valor dos elementos ao 
usuário. Caso a multiplicação não seja possível, o programa deverá solicitar 
novamente ao usuário as informações das dimensões das 2 matrizes. Ao final, o 
programa deverá imprimir as matrizes A, B e C. 
 
 
24) Refaça o exercício anterior com a geração dos elementos das matrizes A e B 
usando números reais e aleatórios, na faixa entre 0 e 100. 
 
 
25) Modifique o exercício anterior com a geração dos elementos das matrizes A e B 
usando números inteiros e aleatórios, na faixa entre 0 e 1. 
 
 
26) Faça um programa para gerar uma matriz de dimensões n x m, com valores 
aleatórios na faixa entre 0 e 255. Os valores m e n deverão ser informados pelo 
usuário. Após a geração dos elementos da matriz, o usuário deverá selecionar uma 
região indicando um número de linha e um número de coluna válidos. O programa 
deverá, então, calcular o valor médio dos elementos pertencentes à região 
selecionada pelo usuário e atribuir este valor médio para todos os elementos da 
região. Os demais elementos devem permanecer inalterados. O programa deve 
mostrar a matriz original e a matriz após a alteração dos valores da região. 
 
 
27) Jogo da Velha - Use uma matriz 3x3 para para implementar um tabuleiro de jogo da 
velha. Inicialmente, todas as posições devem ser preenchidas com o valor 0 (zero), 
indicando que a posição está vazia. O jogo será jogado por dois jogadores. A 
marcação de uma jogada do jogador 1 será feita atribuindo o valor 1 para a posição 
definida. Para o jogador 2, uma jogada será feita atribuindo o valor 2. O programa 
deverá exibir inicialmente o tabuleiro vazio na tela e implementar a solução para este 
problema considerando: 
- o jogador 1 será o primeiro a preencher uma posição; 
- os jogadores 1 e 2 vão alternar o preenchimento das posições; 
- os números de linha e coluna válidos são de 1 a 3, portanto o programa não 
deve aceitar valores fora desta faixa; 
- uma posição já preenchida não pode ser usada novamente, por nenhum dos 
dois jogadores. Caso um jogador cometa este erro, o programa deverá 
solicitar uma nova posição (ou jogada) para o mesmo jogador; 
167 
 Introdução à Programação com Python 
- a cada jogada válida, o tabuleiro deverá ser exibido na tela; 
- a partir da quinta rodada (ou jogada) o programa deverá verificar se aquela 
marcação determinou um vencedor. Em caso afirmativo, o programa deverá 
terminar informando o número do jogador vencedor; 
- se após a nona jogada não houver vencedor, o programa deverá terminar 
informando que “Deu velha”, ou seja, houve empate. 
 
 
28) Modifique o programa implementado do Jogo da Velha para que o jogador 2 seja o 
seu programa. A jogada do programa deverá ser feita escolhendo aleatoriamente 
uma posição. Caso a posição esteja ocupada, o programa deverá escolher outra e 
repetir o teste de posição ocupada (ou não). A marcação só será efetivada quando a 
escolha aleatória for de uma posição válida. 
 
 
29) Altere a implementação do exercício anterior para que a marcação feita pelo 
programa não seja mais aleatória. Ela deverá seguir a seguinte estratégia: 
- a primeira marcação do programa deverá ser a posição central (2, 2) ou, se 
isso não for possível, a posição deverá ser a do canto superior esquerdo (1, 
1); 
- a segunda marcação deverá ser feita considerando o sucesso do programa 
em ocupar a posição central, na primeira marcação. Em caso positivo, o 
programa deverá verificar se o jogador 1 tem duas marcações em uma 
mesma linha ou em uma mesma coluna, com a terceira posição vazia e, em 
caso afirmativo, o programa deverá marcar esta posição vazia. Caso a 
primeira marcação do programa não tenha sido a posição central, a diagonal 
secundária também deverá ser verificada e a posição vazia deverá ser 
marcada, se as outras duas posições já foram preenchidas pelo jogador 1. 
Caso não exista possibilidade do jogador 1 ganhar com o terceiro 
movimento, o programa deverá marcar uma posição em uma das 
extremidades livres; 
- da terceira marcação em diante, o programa deverá verificar se existe 
alguma marcação que o faça vencedor e, neste caso, escolher esta 
marcação. Caso contrário, deverá verificar se existe alguma opção de 
marcação para (tentar) impedir a vitória do jogador 1 e fazer esta marcação. 
 
 
30) Altere a implementação do programa solução do exercício anterior para que o 
computador jogue sozinho. O jogador 1 deverá usar a marcação aleatória e o 
jogador 2 deverá utilizar a estratégia definida no exercício anterior. Faça a 
implementação para que sejam jogadas N partidas e, ao final o programa informe o 
número de vitórias de cada jogador e o número de empates. 
 
31) Campo Minado é um popular jogo de computador para um jogador. Foi inventado 
por Phil Spencer em 1989 e tem como objectivo revelar um campo de minas sem 
que alguma seja detonada (Fonte: https://pt.wikipedia.org/wiki/Campo_minado). 
Implemente um programa do jogo Campo Minado considerando um tabuleiro 10x10 
e 10 bombas espalhadas aleatoriamente no tabuleiro, pelo programa. Na exibição do 
tabuleiro para o usuário do programa devem ser usados os caracteres “X” para 
posição ainda não revelada, “-” para posição revelada e não vizinha a nenhuma 
bomba, “B” para posição revelada e com bomba (situação em que o jogador perde) 
168 
https://pt.wikipedia.org/wiki/Campo_minado
 Introdução à Programação com Python 
e de “1” a “8” para uma posição revelada e que seja vizinha de pelo menos uma 
bomba (o caracter deve representar o número de bombas vizinhas àquela posição). 
Portanto, o tabuleiro deve ser exibido inicialmente com todas as posições contendo 
“X”. Quando o jogador selecionar uma posição, o caractere verdadeiro (“-”, “B” ou o 
caractere representando o número de bombas vizinhas) deveráser exibido. O 
programa deverá controlar o número de posiçẽs reveladas. Quando uma posição 
selecionada não for vizinha de bombas, o programa deverá exibi-la e todas as 
posições adjacentes a ela que também não forem vizinhas de bombas. 
 
 
 
Para os exercícios a seguir será necessário usar a diretiva de importação (import 
imagens) para incluir as funcionalidades mostradas na tabela 7.1 de abrir um arquivo 
de imagem para posterior manipulação como uma matriz de pixels, pelo seu 
programa. O arquivo imagens.py pode ser obtido neste endereço: imagens.py. 
 
 
32) Implemente um programa para transformar uma foto colorida em uma foto em tons 
de cinza. Um algoritmo para fazer tal conversão pode ser a de pegar a intensidade 
média de cada pixel RGB e atribuir este valor médio para cada componente RGB. A 
figura mostrada a seguir apresenta a foto original à esquerda e a imagem 
manipulada, à direita. A foto utilizada neste e em outros exercícios a seguir é do 
fotógrafo Christian R. Linder, licenciada pela CC BY-SA 3.0, disponível em 
https://pt.wikipedia.org/wiki/Agalychnis_callidryas#/media/Ficheiro:Agalychnis_callidr
yas.jpg. Todos os exercícios seguintes utilizam a mesma foto. Mas, você pode 
utilizar qualquer outro arquivo de imagem nos formatos jpg ou png. 
 
 
 
33) Usando a imagem original e a imagem gerada pelo processamento do programa do 
exercício anterior, faça um programa para combinar as duas imagens, gerando uma 
terceira imagem. O programa deve perguntar ao usuário, qual o percentual da foto 
ele deseja que seja colorida e o sentido da junção: horizontal ou vertical. A parte 
colorida ficará sempre na parte superior ou do lado esquerdo. A figura abaixo mostra 
o resultado de duas execuções do programa: na primeira o usuário escolheu 35% e 
sentido vertical; na segunda execução ele escolheu 60% e horizont. A foto original é 
a mesma do exercício anterior. 
 
169 
https://drive.google.com/file/d/1pfe1v8fuAF9YiZFhOCVyMUZKcUmOQdzN/view?usp=sharing
https://pt.wikipedia.org/wiki/Agalychnis_callidryas#/media/Ficheiro:Agalychnis_callidryas.jpg
https://pt.wikipedia.org/wiki/Agalychnis_callidryas#/media/Ficheiro:Agalychnis_callidryas.jpg
 Introdução à Programação com Python 
 
 
 
34) Uma matriz transposta de uma matriz A, é aquela em que as linhas de A viram 
colunas na matriz transposta. Se a matriz A tiver dimensões m x n, a matriz 
transposta de A terá dimensões n x m. Implemente um programa para pegar um 
arquivo de imagem (matriz de pixels) e gerar a matriz transposta (ou imagem 
transposta). O resultado, se aplicado na foto da nossa foto de perereca, será como o 
mostrado a seguir, com a transposta mostrada no lado direio da figura. OBS: a foto 
utilizada é quase quadrada. Possui 480x482 pixels. 
 
 
 
 
35) Faça um programa para inverter horizontalmente uma foto, ou seja, o programa 
deve trocar os elementos de primeira coluna com os elementos da última coluna, 
trocar os elementos da segunda coluna com os da penúltima e, assim, 
sucessivamente, até chegar no meio da foto, quando a inversão estará finalizada. O 
resultado da execução deverá ser como o mostrado na figura a seguir. 
 
170 
 Introdução à Programação com Python 
 
 
 
36) Faça um programa para inverter verticalmente uma foto, ou seja, o programa deve 
trocar os elementos de primeira linha com os elementos da última linha, trocar os 
elementos da segunda linha com os da penúltima e, assim, sucessivamente, até 
chegar no meio da foto, quando a inversão estará finalizada. O resultado da 
execução deverá ser como o mostrado na figura a seguir. 
 
 
 
 
37) Para proteger a privacidade da nossa perereca, que testemunhou um assassinato 
na lagoa, você deve fazer um programa para borrar a região do rosto dela. Para 
conseguir este efeito, um algoritmo simples é pegar um ponto da imagem e calcular 
a média dos componentes RGB de seus vizinhos (direita, esquerda, acima e abaixo) 
e usar este valor médio para alterar o valor do próprio pixel e dos próximos 9 pixels 
na mesma linha. Este processo deve ser repetido até chegar no “final” da linha. 
Lembre-se que este processo deverá ser feito apenas no entorno do rosto da 
perereca. 
 
171 
 Introdução à Programação com Python 
 
 
 
38) Para aumentar a segurança da perereca a sua imagem será toda criptografada para 
ser transmitida pela Internet, sendo descriptografada na máquina de destino. O 
método de criptografia será o de substituição de César. Cada linha da imagem 
original será copiada para uma nova imagem usando um valor de chave definida 
pelo usuário, com valor entre 0 e 100. Porém, se a mesma chave for utilizada em 
todas as linhas não haverá segurança, pois o resultado seria como o mostrado a 
seguir: 
 
 
 
Para conseguir uma criptografia mais forte uma pequena alteração pode ser feita, 
incrementando modularmente o valor da chave de criptografia a cada linha nova a 
ser criptografada. O módulo deve ser o número de colunas da matriz ou o número 
de pixels em uma linha. O programa deverá gerar uma terceira imagem, a partir da 
imagem criptografada que seja igual à imagem original (lembre-se que no destino só 
existirá a imagem criptografada. A chave usada na criptografia será informada por 
telefone). As imagens a seguir mostram a imagem criptografada (à esquerda) para 
uma chave informada pelo usuário igual a 100 e valor do incremento igual à metade 
do valor da chave. 
172 
 Introdução à Programação com Python 
 
 
 
39) Redução de Olho vermelho é uma técnica comum desde o surgimento das primeiras 
máquinas de fotos digitais, que consiste na identificação de pixels na cor vermelha e 
que estejam na área dos olhos e a troca por outra cor, dependendo da cor dos olhos. 
Sabendo disso, a rã de olhos vermelhos (Agalychnis callidryas) solicitou a sua ajuda 
para ter olhos azuis. Faça um programa para implementar uma solução similar à 
mostrada a seguir, onde a foto original está à esquerda e a foto modificada à direita. 
 
 
 
 
40) Altere o programa anterior para que possa ser escolhida uma opção entre olho azul 
ou olho verde, bem como diferentes tons (intensidades) de uma destas duas cores. 
A figura abaixo mostra o resultado da execução para azul com intensidade 150 e 
para verde intensidade 255. Dica: não permita a seleção de intensidades abaixo de 
80, pois tanto o azul como o verde começam a ficar muito escuros. 
 
173 
 Introdução à Programação com Python 
 
 
 
 
174 
 Introdução à Programação com Python 
Capítulo 8 - Funções 
 
Neste capítulo será mostrada a importância do uso de funções e a possibilidade de 
criação de novas funções por parte do programador. O uso de funções permite uma melhor 
organização do código e reutilização de código, com a criação de bibliotecas próprias. 
 
8.1. Motivação 
 
Na seção 6.3.3 foi discutida a solução para o problema de determinar o valor da raiz 
quadrada de um número, utilizando o algoritmo proposto por Heron de Alexandria. Na 
solução apresentada o trecho de código que executa o cálculo da raiz quadrada era: 
 
epson = 10e-5 
r = x/2 
 r = (r + x/r)/2 
 while abs(r**2 - x) > epson: 
 r = (r + x/r)/2 
 
As cinco linhas de código acima podem ser substituídas por um único comando, se 
for utilizada a função sqrt() da biblioteca matemática (math). Esta função calcula a raiz 
quadrada de um número x passado como parâmetro e retorna o valor calculado. Assim, 
uma maneira correta de usar a função sqrt() é em um comando de atribuição,como 
mostrado a seguir: 
 
 r = math.sqrt( x ) 
 
Obviamente, também deveria ser inserida a linha com a importação da biblioteca 
matemática (import math) antes de se utilizar a função sqrt(). Note que o código fica muito 
mais compacto e o programador precisa apenas de saber a forma correta de utilizar a 
função, sem se importar em como ela foi implementada. Afinal de contas, se ela está na 
biblioteca de funções matemáticas da linguagem Python, ela deve estar bem implementada. 
 
Alguns outros exemplos de funções da biblioteca math são: log(x) - logaritmo; 
log10(x) - logaritmo base 10; exp(x) - exponencial; tan(x) - tangente; sin(x) - seno; cos(x) - 
coseno, etc. A biblioteca math possui uma série de funções hiperbólicas, trigonométricas e 
logarítimicas para números reais. Existe ainda a biblioteca cmath que implementa funções 
para operar com números complexos. 
 
Um dos benefícios do uso de funções é a possibilidade de reuso de código. Quando 
aquele trecho de código precisaria ser repetido várias vezes, em um ou mais programas, ele 
pode ser definido como uma função. Sempre que esse código for necessário, ele pode ser 
substituído pela chamada à função, ou seja, pelo nome da função. 
175 
 Introdução à Programação com Python 
 
 
 
8.2. Funções em Python 
 
A linguagem de programação Python permite a criação de novas funções para 
serem usadas posteriormente. Detalhando a frase anterior, os passos para a criação e uso 
de funções em Python são: declare a função e defina seu código; chame (use) a função em 
outras partes do programa. 
 
Antes de criar uma nova função, é importante que o programador tenha em mente a 
resposta para 3 questões fundamentais. Qual a tarefa que será executada pela função? Se 
forem necessários parâmetros (dados de entrada), quais são esses parâmetros? 
Finalmente, se a função retornar valores, quais são esses valores? 
 
As respostas a essas perguntas irão definir como a função será implementada. A 
tarefa a ser executada pela função deve estar bem definida e, idealmente, ser apenas uma 
única tarefa. A função sqrt() calcula a raiz quadrada de um número. Este número é a 
informação que a função precisa receber (parâmetro de entrada) para executar a sua tarefa. 
E a função sqrt() retorna um valor de ponto flutuante. O fato da função retornar um valor 
obriga que ela seja usada em um comando de atribuição (como no exemplo da seção 8.1) 
ou em uma expressão ou em um comando de impressão, pois o valor retornado precisa ser 
usado. 
 
A forma geral de definição de uma função na linguagem Python é a mostrada a 
seguir: 
 
def nome(): 
 comandos 
 return 
 
 
A definição da função é iniciada com a palavra reservada def seguida do nome da 
função. O nome pode ser qualquer um escolhido pelo programador, mas deve seguir as 
mesmas restrições aplicadas à definição de nomes de variáveis. Mas, é altamente 
recomendado que o nome da função ajude a lembrar a tarefa que a função faz. Por 
exemplo o nome sqrt() é uma abreviatura de square root (raiz quadrada em inglês). 
 
A lista de parâmetros é corresponde aos dados passados para a função executar a 
sua tarefa. Quando existem dois ou mais parâmetros, os nomes devem ser separados por 
vírgulas. Existem funções em que a lista de parâmetros pode ser vazia. E existem, ainda, 
funções nas quais o número de parâmetros pode ser variável. Por exemplo, a função print() 
que está sendo utilizada em quase todos os exemplos de programas. O cabeçalho da 
função é terminado com o caractere ‘:’. 
176 
 Introdução à Programação com Python 
 
O corpo da função, representado por comandos na forma geral, corresponde ao 
conjunto de comandos para implementar a tarefa da função. Observe a indentação dos 
comandos. Eles devem estar deslocados à direita em relação à palavra reservada def. Uma 
linha de código alinhada com a palavra reservada def não faz parte da função. 
 
O comando return é obrigatório para as funções que retornam valores. Quando a 
função retorna dois ou mais valores, estes valores devem ser separados por vírgulas. Um 
return sem lista de valores retornados, indica um ponto de término da execução da função 
ou ponto de retorno. Isso significa que a execução da função terminou e a execução 
continuará na instrução seguinte à instrução que fez a chamada da função. Uma função 
sem o return terá o retorno feito pelo interpretador após executar o último comando da 
função. 
 
A utilização da função, conforme visto na apresentação da função sqrt() na seção 
8.1 consiste em escrever o nome da função em uma linha de código. Para uma função que 
não retorna valores, basta escrever o nome da função como um comando do programa. 
Quando a função retorna valor o seu uso deve ser em um comando de atribuição ou em 
uma expressão ou em um comando de impressão, pois o valor retornado pela função 
substituirá o seu nome na linha de código do programa. 
 
Quando o interpretador Python encontra o nome de uma função, ele procura a 
função (palavra reservada def) em que foi usado aquele nome. É por isso que a definição 
da função tem que ser feita antes de sua utilização. Ao encontrar a função chamada, o 
interpretador passa a executar os comandos daquela função, até que seja encontrado um 
return ou após a execução do último comando (quando ela não tem um return). 
 
8.2.1. Identificando candidato a virar função 
 
Uma tarefa importante a ser feita para implementar funções é justamente a 
identificação de trechos de código candidatos a virarem função. A característica principal é 
que o código implemente uma tarefa que seja comum a vários programas e, eventualmente, 
seja usada mais de uma vez no mesmo programa. 
 
Considere um trecho de código para determinar o dia do mês em que foi ou será o 
domingo de páscoa, para um período, por exemplo de 1980 a 1991. O algoritmo só funciona 
para o intervalo de 1582 a 2499. O trecho de código implementado para obter o perído çe 
mostrado a seguir: 
 
ano1 = int( input('Digite o ano inicial (1582 a 2499): ')) 
while ano1 2499: 
 ano1 = int( input('Digite o ano inicial (1582 a 2499): ')) 
 
print() 
177 
 Introdução à Programação com Python 
 
ano2 = int( input('Digite o ano final (1582 a 2499) : ')) 
while ano2 2499: 
 ano2 = int( input('Digite o ano final (1582 a 2499) : ')) 
... 
 
Observe que os trechos destacados em negrito executam exatamente a mesma 
tarefa: lê um número inteiro e verifica se o valor está entre 1582 e 2499. A única diferença é 
a mensagem exibida que pede “ano inicial” no primeiro trecho e “ano final” no segundo. 
Então, poderia ser implementada uma função para ler um número e fazer este teste, com 
um parâmetro que seria a mensagem de texto a ser impressa. A primeira tentativa de criar a 
função e usá-la no programa é mostrada a seguir: 
 
def leiaInt(msg): 
 v = int( input( msg )) 
 while v 2499: 
 print('Valor deve estar entre 1582 e 2499’) 
 v = int( input( msg )) 
 return v 
 
#programa principal 
ano1 = leiaInt('Digite o ano inicial (1582 a 2499): ') 
 
print() 
 
ano2 = leiaInt( ‘Digite o ano final (1582 a 2499) : ') 
... 
 
Um outro programa feito para ler as notas de uma turma de alunos, também precisa 
de executar a tarefa de ler um valor inteiro e testar se o valor se encontra em uma 
determinada faixa. Inicialmente, o programa lê a quantidade de alunos e só aceita valores 
entre 2 e 50. Depois, o programa lê as notas de cada um do alunos, em um comando 
repetitivo, e estas notas devem estar no intervalo de 0 a 100. Finalmente, a média das notas 
é calculada, após o comando repetitivo. O programa está mostrado aseguir: 
 
while True: 
 n = int( input('Entre com a quantidade de alunos: ')) 
 if n 50: 
 print('Valor deve estar entre 2 e 50') 
 else: 
 break 
 soma = 0 
 for i in range(0, n): 
 while True: 
 x = int( input('Entre com a nota do próximo aluno: ')) 
 if x 100: 
178 
 Introdução à Programação com Python 
 print('Valor deve estar entre 0 e 100') 
 else: 
 break 
soma = soma + x 
media = soma / n 
print('Média das notas:', media ) 
 
Note que não é possível utilizar a função leiaInt() definida anteriormente porque ela é 
específica para testar se o valor está no intervalo 1582 a 2499. Neste último programa é 
necessário testar 2 intervalos diferentes. Mas é possível modificar a função leiaInt() para 
que ela fique mais genérica, definindo novos parâmetros definindo o valor mínimo e o valor 
máximo da faixa de interesse. A segunda versão da função e a sua utilização no segundo 
programa são mostrados a seguir: 
 
def leiaInt(msg, vmin, vmax): 
 v = int( input( msg )) 
 while v vmax: 
 print('Valor deve estar entre %d e %d’ %(vmin, vmax)) 
 v = int( input( msg )) 
 return v 
 
#programa principal 
n = leiaInt('Entre com a quantidade de alunos: ', 2, 50) 
soma = 0 
for i in range(0, n): 
 x = leiaInt('Entre com a nota do próximo aluno: ', 0, 100) 
 soma = soma + x 
media = soma / n 
print('Média das notas:', media ) 
 
A utilização no primeiro exemplo mostrado nesta subseção seria o mostrado a 
seguir: 
 
def leiaInt(msg, vmin, vmax): 
 v = int( input( msg )) 
 while v vmax: 
 print('Valor deve estar entre %d e %d’ %(vmin, vmax)) 
 v = int( input( msg )) 
 return v 
 
ano1 = leiaInt('Digite o ano inicial (1582 a 2499): ', 1582, 2499) 
 
print() 
 
ano2 = leiaInt( ‘Digite o ano final (1582 a 2499) : ', 1582, 2499) 
 
179 
 Introdução à Programação com Python 
O código da definição da função deve aparecer no início de cada programa, ou se 
for implementada como uma função de uma biblioteca, tal biblioteca deverá ser importada 
no início do programa. Depois da função ter sido implementada e testada, com a certeza de 
que está correta o programador poderá usar o seu código sempre. O que é necessário 
saber é: o que a função faz; o que ela precisa receber para executar a sua tarefa; e o que 
ela retorna. Ou seja, as mesmas questões que o programador levou em conta para criar a 
função. 
 
A documentação de uma função costuma ter estas informações escritas logo após o 
cabeçalho e antes do corpo da função. Para esta função, um conjunto de comentários 
possíveis seria como o mostrado a seguir, na próxima versão de implementação da função. 
 
Outra observação importante é que o conjunto de comandos que implementa a 
função pode ser alterado, sem que isso implique em modificação no programa que utiliza a 
função, desde que o cabeçalho da função se mantenha. Ou seja, o nome da função tem 
que ser mantido e a lista de parâmetros também. Na verdade é necessário manter o 
número de parâmetros e a ordem de aparecimento destes parâmetros na lista. Uma 
alteração no nome dos parâmetros também não interfere no uso da função. 
 
Com as alterações no código da função, na versão mostrada a seguir, a utilização 
nos programas seria mantida exatamente do mesmo jeito. E, se a implementação desta 
função estivesse em uma biblioteca, o usuário da função provavelmente nunca saberia que 
ela foi alterada: 
 
 def leiaInt(mensagem, lim_inf, lim_sup): 
 # lê um valor inteiro e testa se está no intervalo [lim_inf, lim_sup] 
 # mensagem: texto a ser exibido para o usuário 
 # lim_inf: limite inferior do intervalo 
 # lim_sup: limite superior do intervalo 
 # retorna o valor lido 
 while True: 
 x = int( input('mensagem: ')) 
 if x lim_sup: 
 print('Valor deve estar entre %d e %d' %(lim_inf, lim_sup)) 
 else: 
 return x 
 
O return funcionará de maneira similar ao break para quebrar o loop infinito. Porém, 
além de forçar o término do comando repetitivo ele também termina a função. Se fosse 
mantido o break na cláusula else, o comando return x deveria ser escrito após o while. 
 
8.2.2. Função que retorna dois (ou mais) parâmetros 
 
180 
 Introdução à Programação com Python 
Às vezes uma função precisa retornar dois ou mais valores. A linguagem Python 
resolve este problema de maneira muito simples, bastando informar a lista de valores, 
separados por vírgula, em um comando return. O comando de atribuição deverá usar um 
número de variáveis à esquerda do operador de atribuição, separadas por vírgula, igual ao 
número de valores retornados pela função. A primeira variável receberá o primeiro valor da 
lista de valores retornados, a segunda variável receberá o segundo valor, e assim por 
diante. 
 
Suponha uma função para ordenar 2 valores. A função precisa receber como 
parâmetros os dois valores a ser ordenados, proceder à ordenação e retornar os valores 
ordenados. A função ordena(x, y) e seu uso são ilustrados a seguir: 
 
def ordena( x, y ): 
 if (xpor valor são 
independentes das variáveis, expressões etc. que geraram os valores passados para a 
função. Considere este segundo exemplo: 
 
 def f( x, y ): 
 z = 2*x + y 
 return z 
 
# programa principal 
z = 2 
w = 1 
print( z ) 
print( f( 2*z, w )) 
print( z ) 
 
Neste segundo exemplo existe uma variável z definida no programa principal e uma 
variável local de mesmo nome z na função f(). A função f() é a mesma do primeiro exemplo 
e, como ela recebeu os mesmos valores, ela retornará novamente o valor 9 (segundo valor 
impresso). Quando isso acontece, toda referência ao nome z dentro do código da função f() 
diz respeito à sua variável local z. Portanto, o comando de atribuição não altera a variável z 
do programa principal. A saída gerada pelo programa será: 
 
2 
9 
2 
 
182 
 Introdução à Programação com Python 
Neste próximo exemplo, uma variável do programa principal (z) é utilizada em uma 
expressão da função f(). O programa imprimirá o valor 11, já que se trata da mesma 
expressão acrescida de “ + z” e o valor de z é igual a 2. 
 
def f( x, y ): 
 k = 2*x + y + z 
 return k 
 
# programa principal 
z = 2 
w = 1 
print( f( 2*z, w )) 
 
Embora este uso seja permitido, ele não é recomendado. A ideia é que as variáveis 
definidas no programa principal sejam utilizadas apenas no programa principal, criando um 
escopo local para o programa principal. 
 
Além disso, pode ocorrer uma ambiguidade se um comando de atribuição for feito 
para uma variável global dentro da função como mostrado a seguir: 
 
def f( x, y ): 
 k = 2*x + y + z 
 z = 1 
 return k 
 
# programa principal 
z = 2 
w = 1 
print( f( 2*z, w )) 
 
Este código ao ser analisado pelo interpretador Python gerará uma mensagem de 
erro, pois será considerado pelo interpretador que a variável z usada na expressão k = 2*x + 
y + z é a variável local definida no comando seguinte (z = 1). O interpretador Python está 
entendendo que os dois comandos citados anteriormente estão em ordem trocada, que a 
variável local z deveria ter sido definida antes de ser usada. 
 
Uma solução para este problema seria dizer explicitamente que a variável z, usada 
na função f() usando o comando global, antes de atribuir valor para z: 
 
 global z # informa para o interpretador que z é global 
 z = 1 
 
Mas, ao usar esta solução uma atribuição feita para a variável global na função será 
refletida na variável global do programa principal. Por exemplo, se houvesse um comando 
para imprimir o valor de z no programa principal, após a chamada da funçao f(), o valor 
exibido seria 1. 
183 
 Introdução à Programação com Python 
 
8.4. Passagem de arranjos como parâmetro 
 
Na linguagem Python ao passar um arranjo como parâmetro, o programa não faz 
uma cópia do arranjo para dentro da variável local no escopo da função, como se faz como 
uma variável escalar. Isso seria muito custoso, pois a quantidade de memória alocada pode 
ser muito grande, em função da dimensão do arranjo. 
 
Em vez disso, ele só passa o endereço da memória onde esse arranjo está 
armazenado. Assim, qualquer alteração feita ao arranjo altera a própria variável passada 
como parâmetro, e não uma cópia dessa variável. Considere o pequeno programa mostrado 
a seguir: 
 
def dobra( vetor ): 
 for i in range( 0, len( vetor )): 
 vetor[i] = vetor[i] * 2 
 
#programa principal 
a = numpy.array([4, 3, 2, 1]) 
print( a ) 
dobra( a ) 
print( a ) 
 
A execução do programa irá gerar a seguinte saída: 
 
[4 3 2 1] 
[8 6 4 2] 
 
Sim. A linguagem Python permite imprimir um arranjo inteiro usando apenas seu 
nome. A primeira linha é o resultado do primeiro comando print() que foi usado antes da 
função dobra() ter sido chamada. E a segunda linha foi gerada pelo segundo print() e, como 
era de se esperar, cada elemento do arranjo teve o seu valor dobrado pela função dobra(). 
 
8.5. De volta aos algoritmos 
 
A utilização de funções permite fazer uma melhor organização do código. Por 
exemplo, o programa principal poderia se resumir à definição das estruturas de dados 
necessárias e chamadas para funções que executarão cada uma das tarefas para resolver 
o problema. 
 
Em projetos de software mais complexos, onde o número de funções tende a ser 
grande, o trabalho em equipe é favorecido com este tipo de organização do código em 
184 
 Introdução à Programação com Python 
funções. O ponto chave é um projeto com a definição precisa dos requisitos de cada função: 
a tarefa que ela deve implementar; os parâmetros que devem ser passados para a função; 
e os valores que a função deve retornar. 
 
Tendo feito esta definição, equipes diferentes podem trabalhar na elaboração do 
código de diferentes subconjuntos do total de funções. Desta forma, o projeto pode ser 
implementado em um tempo mais curto. Bom, mas isso é assunto da área de engenharia de 
software. Nesta disciplina, a ideia é mostrar como os conceitos de algoritmo podem ser 
mapeados na implementação usando funções. 
 
O programa principal pode ser visto como um algoritmo de alto nível, onde cada 
comando seria uma chamada para a função que detalhará a execução daquele passo. Para 
ilustrar, será utilizado um exemplo já apresentado na seção 7.2.2 no programa que verifica 
as propriedades de uma matriz quadrada. 
 
O algoritmo de alto nível que considerava o caso da matriz não ser quadrada era o 
seguinte: 
 
m = Leia(‘Número de linhas da matriz: ‘) 
n = Leia(‘Número de colunas da matriz: ‘) 
A = arranjo(m, n) 
“Leia os elementos da matriz” 
se m != n: 
 Escreva(‘A matriz não é quadrada’’) 
senão: 
 “Verifique se a matriz é uma matriz diagonal” 
 Se “diagonal” 
 “Verifique se a matriz é uma matriz identidade” 
 Se “identidade” 
 Escreva(‘matriz é identidade’) 
 Senão 
 Escreva(‘matriz é diagonal’) 
 Senão: 
 Escreva(‘matriz não é diagonal’) 
 
E esta pode ser a estrutura utilizada no programa principal do programa. Com a 
vantagem de poder economizar algumas variáveis que foram usadas na solução da seção 
7.2.2.2. Na solução que será apresentada em seguida, o número de linhas e colunas da 
matriz deve estar entre 2 e 100, mas considerando que a entrada de dados será manual, na 
execução é recomendável usar um valor pequeno. O programa principal poderia ser escrito 
como mostrado na Figura 8.1. 
 
 
 
185 
 Introdução à Programação com Python 
 
 
Figura 8.1 - Programa principal 
 
Observe que o programa principal utiliza a função leiaInt() que já foi apresentada 
neste capítulo (reuso de código). Além dela, precisam ser definidas as seguintes funções: 
 
Nome: leMatriz. 
Tarefa: ler os elementos da matriz, solicitando valores ao usuário. 
Parâmetros: Matriz (arranjo), número de linhas e número de colunas do arranjo. 
Valor retornado: nenhum. 
 
Nome: ehDiagonal. 
Tarefa: verificar se a matriz é diagonal (todos os elementos fora da diagonal principal 
devem ser iguais a zero). 
Parâmetros: Matriz (arranjo), dimensão da matriz* 
Valor retornado: Booleano (True se a matriz for diagonal). 
(*) só faz sentido testar se a matriz é diagonal quando ela é quadrada (o número de 
linhas é igual ao número de colunas). Dimensão é o número de linhas (ou de colunas) da 
matriz quadrada. 
 
Nome: ehIdentidade. 
Tarefa: verificar se a matriz é identidade (todos os elementos da diagonal principal 
são iguais a 1). 
Parâmetros: Matriz (arranjo), dimensão do arranjo**. 
Valor retornado: Booleano (True se a matriz for identidade). 
(**) também só faz sentido testar se a matriz é identidade quando ela é quadrada. 
Dimensão éde monitoria com 12 computadores 
e uma bancada sem computadores na qual o estudante poderá utilizar seu próprio 
computador portátil, se preferir. O(s) monitor(es) da disciplina INF 100 fazem atendimento 
16 
 Introdução à Programação com Python 
em horários que são divulgados na recepção do LBI, no início de cada semestre letivo. 
Todos os computadores do LBI possuem o Sistema Operacional Linux, distribuição Ubuntu. 
 
Para a execução das atividades nas salas do LBI, o estudante matriculado na 
disciplina INF 100 utilizará o navegador de Internet Firefox (ou Google Chrome), o servidor 
do LBI, um leitor de arquivos PDF (Portable Document Format), o ambiente de 
desenvolvimento IDLE e o gerenciador de arquivos. O estudante utiliza uma conta padrão 
cujo nome de usuário é “Aluno” e a senha é informada na primeira aula prática. 
 
A Figura 1.6 apresenta a tela com a área de trabalho da conta do usuário Alunos, 
com a identificação dos ícones relacionados aos programas citados no parágrafo anterior. 
Esta conta está programada para apagar todos os arquivos ao final da sessão. Assim, todo 
estudante que utilizar esta mesma conta sempre encontrará a sua pasta padrão vazia. 
 
 
Figura 1.6 - Área de trabalho do usuário Alunos no LBI 
 
Toda aula prática possui um roteiro e, eventualmente, um ou mais arquivos 
adicionais que ficam armazenados no servidor do LBI. Um leitor de arquivos PDF é 
necessário, pois todos os roteiros de aulas práticas são disponibilizados em formato PDF. 
Existem diversos leitores de PDF gratuitos disponíveis na Internet. Todos os computadores 
do LBI possuem leitor de PDF. Em geral, a configuração permite abrir o arquivo PDF em 
uma nova aba do navegador de internet. Mas também é possível que seja aberta uma 
janela nova com a imagem do arquivo PDF. 
 
Nas máquinas do LBI, para facilitar a vida do estudante, existe um ícone que está 
associado ao navegador de internet Firefox já configurado com a página inicial sendo o 
servidor do LBI. Desta forma, basta clicar no referido ícone para abrir a tela de acesso ao 
servidor do LBI. Para acessar o servidor do LBI o estudante usa seu número de matrícula 
como nome de usuário e sua senha definida na primeira aula prática. 
17 
 Introdução à Programação com Python 
 
Os dias e horários que um estudante pode acessar o servidor do LBI é programado 
de acordo com o seu horário de aula prática na disciplina INF 100 e com o tipo de atividade: 
presencial ou a distância. Quando o estudante optar por realizar a atividade a distância, ele 
poderá usar o navegador de internet de sua preferência fornecendo o endereço completo do 
servidor do LBI: http://linux-server.lbi.ufv.br. Os procedimentos para obter o material (roteiro 
e arquivos adicionais) para a realização da aula prática e a entrega do trabalho são os 
mesmos para quem está no LBI ou para quem está em casa ou outro lugar qualquer. 
 
 O ambiente de desenvolvimento IDLE possui duas partes principais: uma interface 
para execução de comandos (shell) e um editor de programas Python integrado. Ao clicar 
no ícone do IDLE será aberta uma janela como a mostrada na Figura 1.7(a). Para que seja 
aberta a janela do editor de programas (Figura 1.7(b)) é necessário selecionar, na janela do 
Shell, no menu de arquivo (File) a opção de criar um novo arquivo (File -> New File) ou abrir 
um arquivo já existente (File -> Open). 
 
 
 
(a) Shell (b) Editor de Programas 
 
Figura 1.7 - Ambiente de desenvolvimento IDLE 
 
Embora as janelas sejam parecidas, o propósito delas é bem diferente. Mas tem 
diferenças perceptíveis também. A primeira é que o programa associado ao ícone IDLE na 
área de trabalho é o Shell. 
 
Outra diferença é que no topo janela do Shell aparece a informação de que se trata 
do Shell da linguagem Python versão 3.5.2 (Python 3.5.2 Shell), enquanto que na janela do 
editor de programas aparece Untitled (Sem Título) porque foi usada a opção para criar um 
novo arquivo (File -> New File) que ainda não teve seu nome definido (a definição do nome 
se dá quando o arquivo for salvo pela primeira vez). Uma outra diferença é que a janela do 
editor de programas está vazia (sem texto) à espera de que o usuário comece a escrever o 
18 
http://linux-server.lbi.ufv.br
 Introdução à Programação com Python 
seu programa Python. Já na janela do Shell são exibidas informações sobre o interpretador 
Python e, depois, é exibido o prompt de comandos representados pelos caracteres >>>. 
 
Este prompt de comandos (>>>) indica que o Shell está esperando que algum 
comando seja digitado e que seja dada a ordem para sua execução, através da digitação da 
tecla “Enter”. Considere um exemplo simples onde se deseja atribuir para um objeto de 
nome C, a soma de dois outros objetos A e B. A Figura 1.8 apresenta a utilização do Shell 
para executar tal tarefa. 
 
Após cada comando, no exemplo da Figura 1.8, foi colocado um comentário (#) na 
mesma linha. Tudo o que vem após o caractere “#” é ignorado pelo interpretador Python, ou 
seja, não faz parte do comando. Por isso é chamado de comentário. Como será visto, o 
comentário é muito útil para que outros programadores possam entender com mais 
facilidade o que o código faz e, até mesmo para que o próprio programador se lembre do 
que o código faz, se ele ficar muito tempo sem mexer naquele programa. A seguir será 
detalhado o significado de cada comando e cada resposta gerada pelo interpretador Python. 
 
 
 
Figura 1.8 - Exemplo de comandos no Shell do IDLE 
 
Os dois primeiros comandos são para criar os objetos (ou variáveis) A e B, com 
valores 2 e 5, respectivamente. Para estes comandos o interpretador Python não gera 
nenhuma saída, dando a impressão de que nada ocorreu. O terceiro comando foi o nome 
do primeiro objeto (A) e como resposta o Shell exibiu o seu valor 2. Note que na linha de 
resposta ao comando não aparece o prompt (>>>), além de exibir a resposta em outra cor 
(azul). O quarto comando foi similar ao terceiro, só que para o objeto B. 
 
O comando seguinte gera como resposta uma mensagem de erro, já que o nome do 
objeto C, do qual se pretendia exibir o valor armazenado, ainda não havia aparecido e, 
portanto, era desconhecido do interpretador Python. A resposta a este comando “inválido” é 
19 
 Introdução à Programação com Python 
uma mensagem de erro que informa ter havido um erro de nome, mais explicitamente que o 
nome C não está definido: “NameError: name 'C' is not defined”. O comando seguinte (C = 
A + B) corrige o erro, definindo o objeto C com valor inicial igual a soma dos valores atuais 
de A e B. Agora, na sequência, o comando C exibe o valor 7. 
 
Toda a informação digitada no Shell é perdida quando sua janela é fechada ou se o 
computador for desligado, como no caso de uma queda de energia durante a aula prática. 
Por isso, o Shell deve ser usado somente para efetuar pequenos testes. E, nas aulas 
práticas, o Shell deverá ser usado apenas para abrir (ou criar) o arquivo com o programa 
que será desenvolvido para ser entregue no final do prazo determinado e para visualizar o 
resultado da execução do programa, conforme será mostrado a seguir. 
 
Para que não se perca o trabalho, os comandos do programa Python deverão ser 
digitados na janela do editor de programas e deverão ser gravados em um arquivo. Por 
convenção, todos os arquivos com programa escrito na linguagem Python devem ter 
terminação .py, como por exemplo p01.py, teste.py ou SerieFibonacci.py. Para exemplificar 
será usado um pequeno programa com comandos equivalentes aos comandos do Shell 
usados na Figura 1.8. Uma diferençao número de linhas (ou de colunas) da matriz quadrada. 
 
Nome: imprimeMatriz. 
Tarefa: imprimir os elementos da matriz, organizados por linha e coluna. 
Parâmetros: Matriz (arranjo)***. 
Valor retornado: nenhum. 
186 
 Introdução à Programação com Python 
(***) nesta função foi definido apenas 1 parâmetro, apenas para mostrar a função 
shape da biblioteca numpy, que retorna 2 valores: o número de linhas e o número de 
colunas de um arranjo bidimensional. 
 
A implementação das cinco funções usadas pelo programa principal são mostradas 
na Figura 8.2. 
 
 
Figura 8.2 - Implementação das funções 
 
Os comentários inseridos no código da Figura 8.2 foram bem sucintos porque o 
detalhamento de cada função já havia sido apresentado no texto. Mas para uma boa 
documentação do código isso deveria ser feito. 
 
8.6. Jogo da Velha 
 
O jogo da velha é um jogo de tabuleiro bastante conhecido e na sua versão mais 
simples pode ser implementado com um arranjo 3x3. O objetivo do jogo é fazer uma 
187 
 Introdução à Programação com Python 
marcação vencedora, que consiste de um jogador conseguir escrever a sua marca em 3 
posições consecutivas, em uma mesma linha ou em uma mesma coluna ou em uma mesma 
diagonal. Os jogadores fazem marcações de maneira alternada, podendo usar apenas 
posições ainda não utilizadas. A Figura 8.3 apresenta três configurações possíveis para um 
tabuleiro de Jogo da Velha. 
 
 X O X X X O 
 O X O O X X 
 X X O O 
Figura 8.3 - Representação esquemática de um tabuleiro de Jogo da Velha 
 
 
À esquerda é mostrado um tabuleiro no início de um jogo, ainda sem nenhuma 
marcação. Na parte central da Figura 8.3 tem-se um tabuleiro no qual o jogador com a 
marcação ‘X’ venceu o jogo, por ter colocado 3 marcas consecutivas na diagonal 
secundária. E do lado direito temos um final em que houve empate. É possível afirmar que o 
jogador com a marcação ‘X’ foi o primeiro a jogar, pois ele tem uma marcação feita a mais 
do que o jogador com a marcação ‘O’. 
 
Vamos escrever um algoritmo para controlar o andamento de um jogo da velha no 
qual o primeiro jogador será o de número 1 e usará a marcação ‘X’. Consequentemente o 
jogador da marcação ‘O’ será chamado de jogador 2. 
 
O algoritmo de um jogo poderia ser descrito da seguinte forma: 
 
 1. Criar o tabuleiro Tab com todas as posições vazias 
 2. Imprime o tabuleiro inicial 
 3. Definir Jogador 1 como primeiro a jogar 
 4. Inicializar um contador de jogadas 
5. Criar uma variável para informar se “alguém venceu” 
 6. Loop para controlar as jogadas (máximo de 9 jogadas, no caso de empate) 
6.1. Jogador da vez faz a sua marcação 
 6.2. Incrementa o contador de jogadas 
6.3. Exibe o tabuleiro atualizado 
 6.4. Testa se a jogada foi vencedora e atualiza a variável “alguém venceu” 
 6.5. Se ninguém venceu 
 6.5.1. troca o jogador e a marcação 
 7. se alguem_venceu : 
 Informa o número do jogador vencedor 
 senão : 
Informa que deu Empate 
 
 O mapeamento do algoritmo para um programa Python pode ser feito de forma 
direta, considerando que os comandos em alto nível serão implementados como funções. 
188 
 Introdução à Programação com Python 
Obviamente, que nem sempre se consegue esse mapeamento sai na primeira tentativa, 
principalmente com relação a quantos e quais parâmetros serão necessários em cada uma 
das funções. A Figura 8.4 mostra o código Python do programa principal da implementação 
do Jogo da Velha. 
 
 Todas as funções foram implementadas em um outro arquivo de nome auxiliar.py, 
que está sendo apelidado de aux no comando de importação, na primeira linha do código. 
Assim, todas as funções usadas no arquivo de implementação do Jogo da Velha (programa 
principal) devem usar o prefixo aux. antes do nome da função, como aparece na 3a. linha 
de código (Tab = aux.inicalizaTabuleiro(l, c)). 
 
 
Figura 8.4 - Programa Principal do Jogo da Velha 
 
 
 Resta agora detalhar a implementação de cada uma das funções usadas pelo 
programa principal e codificadas no arquivo auxiliar.py. Pode ser observado que algumas 
funções são bem simples e que, em uma primeira análise, talvez nem demandassem uma 
implementação como função. Porém, será detalhado como é possível modificar a 
implementação de uma função para tornar o programa mais genérico e funcional, sem a 
necessidade de mexer no código do programa principal, desde que o nome da função, o 
número e ordem dos parâmetros não sejam alterados. 
 
A Figura 8.5 apresenta algumas das funções implementadas no arquivo auxiliar.py. 
A função inicializaTabuleiro(l, c) simplesmente usa a função full da biblioteca numérica 
189 
 Introdução à Programação com Python 
numpy. Ao contrário da função empty que não define nenhum valor para um arranjo, a 
função full define todos os valores iguais ao valor passado como parâmetro (caractere ‘-’). 
Ela retorna o arranjo criado. E, por se tratar de um arranjo, o valor retornado é o endereço 
do arranjo criado dentro da função, que continua existindo após a função terminar. 
 
 
 
Figura 8.5 - Primeiras funções do arquivo auxiliar.py 
 
 
A função imprimeTabuleiro(A) nada mais é do que a função que já foi vista aqui para 
imprimir os elementos de um arranjo bidimensional no formato visto nos livros de 
matemática. Note que como o único parâmetro da função é o nome do arranjo, ela usa a 
função shape da biblioteca numpy para descobrir o número de linhas e o número de 
colunas do arranjo. 
 
Em seguida, a função inicializaJogo() não tem nenhum parâmetro de entrada e 
define que a marcação será o caractere ‘X’ e o número do primeiro jogador será 1. Ou seja, 
é uma função que retorna 2 valores. Note que esta função poderia ser modificada para 
sortear o número 1 ou 2, usando a função randint() e, dependendo do número sorteado 
poderia retornar ‘X’ e 1 ou retornar ‘O’ e 2. Dessa forma, o jogador 2 teria chance de ser o 
primeiro a jogar de vez em quando. 
 
A função leiaInt() dispensa apresentações pois já foi vista em mais de uma 
oportunidade ao longo deste texto. Note que a leiaInt() não foi usada no programa principal, 
190 
 Introdução à Programação com Python 
mas apenas dentro do arquivo auxiliar.py. E, não custa ressaltar, mais uma vez a 
importância da reutilização de código (que também ocorreu no caso da imprimeTabuleiro()). 
 
A Figura 8.6 apresenta as outras funções implementadas no arquivo auxiliar.py. 
 
 
Figura 8.6 - Outras funções implementadas no arquivo auxiliar.py 
 
A função fazMarcação(T) recebe como parâmetro o arranjo bidimensional que 
representa o tabuleiro do Jogo da Velha. Ela usa a função leiaInt() para garantir que o valor 
inteiro será validado no intervalo 1 a 3, que são os valores válidos para número de linha e 
coluna. Porém, mesmo com uma posição válida é necessário testar se a posição escolhida 
está vazia. No caso de estar vazia, o loop pseudo infinito é quebrado e os valores de linha e 
de coluna escolhidos pelo jogador são retornados pela função. Caso a posição esteja 
ocupada, a mensagem de erro será impressa e o jogador terá que escolher novamente uma 
nova posição, até que seja escolhida uma posição vazia. 
 
A função vencedor() recebe como parâmetros de entrada o arranjo representando o 
tabuleiro, a posição (número de linha e de coluna) da marcação feita e a marcação usada. 
O teste verifica se há 3 marcações consecutivas na linha da marcação, na coluna da 
marcação e no caso da posição pertencer à uma das diagonais (ou às duas - caso da linha 
2 coluna 2 - para o jogador)é que para exibir o valor de um objeto na linguagem 
Python deve-se usar o comando print() fornecendo como parâmetro o nome do objeto a ter 
seu valor exibido. Ao invés de escrever simplesmente “A” como foi o comando no Shell, no 
programa deve-se escrever o comando “print(A)”. A Figura 1.9 mostra a janela do editor de 
programas. 
 
 
 
Figura 1.9 - Programa com erro 
 
 Antes de executar um programa que foi escrito na janela do editor do programa é 
preciso salvá-lo. Isso pode ser feito utilizando a opção do menu “File -> Save” ou digitando 
as teclas “Ctrl+S” (significa: manter pressionada a tecla Ctrl e pressionar a tecla S). Porém, 
se você tentar executar o programa sem salvá-lo, o IDLE exibirá uma mensagem para que 
você o salve. A ideia é que a versão a ser executada deve ser exatamente a que você está 
vendo na tela. Note que o arquivo da Figura 1.9 já havia sido salvo (gravado no disco rígido) 
quando a tela foi capturada, conforme o nome do arquivo que aparece no topo da janela 
(primeiro.py). 
 
 Para executar o programa deve-se usar a opção do menu “Run -> Run Module” ou a 
tecla de atalho F5 que fica na parte superior do teclado. A saída ou resultado da execução 
20 
 Introdução à Programação com Python 
do programa será exibida na janela do Shell. No código, o comando para exibir o conteúdo 
do objeto (variável) C está antes da sua criação e definição do valor. Por isso, a saída 
exibida conterá uma mensagem de erro, conforme mostrado na Figura 1.10. 
 
 
Figura 1.10 - Janela do Shell com a saída do programa da Figura 1.9 
 
Note que o interpretador Python lê o programa e vai executando os comandos 
sequencialmente. A primeira linha é ignorada pois é apenas um comentário. As duas linhas 
seguintes criam e definem o valor inicial dos objetos A e B, porém não produzem nenhuma 
saída para o Shell. Na sequência, existem dois comandos de impressão (print()) que geram 
saídas para o Shell com a exibição dos valores 2 e 3, dos objetos A e B, respectivamente. 
 
O terceiro comando de impressão contém um erro pois usa o nome de um objeto 
que ainda não foi definido. A definição do objeto C está na linha seguinte (linha 7), mas o 
interpretador não enxerga isso, pois ele tenta executar os comandos na sequência em que 
eles foram escritos pelo programador. Este erro ocasiona a mensagem de erro na janela do 
Shell (vide Figura 1.10). Note que, além de indicar o tipo de erro (NameError: name ‘C’ is 
not defined) o interpretador também informa a localização do erro no dentro do código, 
neste caso na linha 6 (File "/home/goulart/primeiro.py", line 6, in ). Também é 
informado o nome do arquivo porque programas mais complexos podem ser compostos por 
mais de um arquivo. 
 
 A correção, neste caso, consiste em trocar de posição a linha 6 com a linha 7, 
colocando a definição do objeto C (C = A + B) antes de sua impressão (print(C)). Após 
qualquer modificação no texto do programa, a janela do editor exibe o nome do arquivo 
entre ‘*’ para indicar que a versão vista na janela é diferente da gravada no disco rígido, 
como pode ser visto na Figura realizar tal modificação 
 
21 
 Introdução à Programação com Python 
 
Figura 1.11 - Programa sem erros 
 
 Após a correção, usando a tecla de atalho F5, o IDLE pedirá novamente que o 
arquivo do programa (primeiro.py) seja salvo e, após confirmação, executará novamente o 
programa com a correção feita, gerando a saída exibida na Figura 1.12. Nesta figura 
aparecem as saídas da primeira e segunda execuções. Entre cada execução, o 
interpretador informa que houve um reinício (Restart) da execução, informando também o 
nome do arquivo (primeiro.py) que teve a execução iniciada, com sua localização no 
computador (/home/goulart) na mensagem destacada pela sequència de caracteres “=”: 
“=================== RESTART: /home/goulart/primeiro.py ====================”. 
Como o programa foi corrigido e está sem nenhum erro, a segunda saída apresenta apenas 
os três valores impressos pelos três comandos print(), imprimindo na sequência os valores 
de A, B e C, respectivamente 2, 5 e 7. 
 
Figura 1.12 - Janela do Shell com as duas execuções do programa primeiro.py 
 
 Caso alguma informação apresentada aqui sobre o programa não tenha ficado clara 
não se preocupe, pois o conceito de variável e o comando print() serão apresentados de 
maneira detalhada nos próximos capítulos. O mais importante desta seção é a informação 
de que, nas aulas práticas ou quando for usar o ambiente de desenvolvimento IDLE, o Shell 
é usado apenas para abrir ou criar seu(s) arquivo(s) de trabalho e depois disso, verificar as 
saídas geradas pelo programa. Os arquivos de trabalho devem ser editados na janela do 
editor de programas. 
 
22 
 Introdução à Programação com Python 
 Outro programa que pode ser útil é o gerenciador de arquivos que serve para que o 
usuário organize seus arquivos e diretórios (ou pastas). Esta organização é muito 
importante para permitir a localização rápida de um arquivo no computador. No caso do 
sistema instalado no LBI, que é uma versão do Linux, o diretório ou pasta do usuário fica no 
diretório de nome “home”. E cada pasta de usuário possui algumas pastas (diretórios) 
previamente definidas. A figura 1.13 mostra o gerenciador de arquivos aberto pelo usuário 
“goulart” na máquina onde este documento estava sendo editado. Note que na barra de 
navegação é mostrada a informação completa do caminho da localização atual 
“/home/goulart” que é o diretório padrão do usuário. No caso da conta usada no LBI o 
caminho será “/home/alunos”. Na área de visualização são exibidas os ícones associados 
às pastas criadas pelo sistema para o usuário (“Área de Trabalho”, “Documentos”, 
“Downloads”, “Imagens”, “Modelos”, “Música”, “Público” e “Vídeos”) além do ícone vinculado 
ao arquivo Python “primeiro.py”. 
 
 
Figura 1.13 - Gerenciador de Arquivos mostrando a pasta do usuário “goulart”. 
 
Usando o gerenciador de arquivos, o usuário pode criar novas pastas para organizar 
seus arquivos da maneira que ele considerar a mais adequada. Entretanto, nas máquinas 
do LBI, o usuário não poderá criar suas pastas e deixar seus arquivos guardados lá, pois ao 
final de cada sessão todos os arquivos do usuário Alunos são apagados, restaurando as 
pastas e arquivos padrão. Assim, no LBI o gerenciador será usado mais frequentemente 
para localizar os arquivos baixados do servidor, em geral, o roteiro da aula prática e, 
eventualmente, um ou mais arquivos python. Suponha, por exemplo, que após baixar 
(realizar o download) o arquivo “p01.pdf” com o roteiro da aula prática 1, ele não tenha 
aparecido ao lado do arquivo “primeiro.py” na área da pasta padrão do usuário. O que 
fazer? 
23 
 Introdução à Programação com Python 
 
Figura 1.14 - Gerenciador de Arquivos mostrando o conteúdo da pasta “Downloads” 
 
Neste caso o gerenciador de arquivos deve ser usado como um navegador para 
percorrer as pastas em busca do arquivo desejado. O mais comum é o arquivo ser baixado 
para a pasta “Downloads” que é uma das pastas existentes na área do usuário. Para 
acessá-la, basta clicar no ícone da pasta “Downloads” que o gerenciador passará a exibir, 
então, o conteúdo da pasta “Downloads”, como mostrado na Figura 1.14. Dentre os 
diversos arquivos que o usuário “goulart” já havia baixado se encontra o arquivo “p01.pdf”. 
Agora, bastaria clicar sobre o ícone do arquivo “p01.pdf” para abri-lo com o leitor de PDF 
padrão do sistema operacional e verificar o seu conteúdo. 
 
Caso o arquivo não estivesse na pasta “Downloads” o processo poderia ser repetido 
com qualquer outra pasta, usando os ícones de navegação () na partesuperior 
esquerda da janela ou clicando diretamente no nome da pasta desejada que aparece na 
lista na área esquerda da janela (“Pasta Pessoal”, “Área de Trabalho”, “Documentos”, 
“Música”, “Imagens”, “Vídeos” e “Downloads”). Note que na lista, a pasta que está em uso 
aparece com o fundo cinza: “Downloads” na Figura 1.14 e “Pasta Pessoal” na Figura 1.13. 
“Pasta Pessoal” corresponde à pasta principal de cada usuário: “/home/goulart” no exemplo 
usado neste material e “/home/alunos” no caso da conta usada pelos alunos no LBI. 
 
1.4.1 - Home Python 
 
Para realizar as atividades práticas de programação será necessário a instalação do 
ambiente de desenvolvimento IDLE-Python e bibliotecas numérica e gráfica em um 
computador pessoal. Existem versões do IDLE-Python para diversos sistemas operacionais. 
A seguir são apresentadas as instruções para instalação nos sistemas operacionais Linux e 
Windows. 
 
 Para instalação no sistema operacional Linux é necessário estar conectado à 
Internet, pois os arquivos são buscados em repositórios da versão do sistema operacional 
24 
 Introdução à Programação com Python 
instalado no computador. Após certificar-se que a conexão está operacional, basta seguir a 
seguinte sequência de passos: 
 
1) Acesse a página da disciplina INF 100 no PVANet e pegue o arquivo instalaIDLE. 
2) Abrir um terminal e entrar no diretório onde o arquivo instalaIDLE foi salvo. 
3) Executar no terminal o comando “sudo su” (sem as aspas) e fornecer a senha de 
administrador. Os comandos a seguir devem ser executados pelo usuário 
administrador do sistema, ou seja, após a execução do comando deste passo 2. 
4) Executar o comando “chmod +x instalaIDLE” (sem as aspas) para incluir a 
permissão de execução para o arquivo instalaIDLE, que é um arquivo executável 
(script). 
5) Executar o comando “./instalaIDLE” para executar o script que fará o resto do 
trabalho. 
 
 O processo de instalação costuma demorar alguns minutos, em função da 
velocidade de acesso à Internet e carga do servidor onde está localizado o repositório dos 
arquivos que serão baixados para seu computador. Fique atento para eventuais mensagens 
de erro, que indicam eventual falha no processo de instalação. Mensagens de advertência 
(warning) indicam que um problema foi detectado, mas contornado e a instalação terá sido 
bem sucedida se houver apenas mensagens de advertência. 
 
 Para quem não está matriculado na disciplina INF 100 e, portanto, não tem acesso 
ao PVANet, a instalação pode ser feita com a seguinte sequência de 7 comandos, como 
superusuário: 
> apt-get update 
> apt-get install --upgrade python3-pip -y 
> pip3 install --upgrade pip -y 
> apt-get install --upgrade libfreetype6-dev build-essential g++ libjpeg8-dev pkg-config 
python3-cairocffi libjpeg-dev zlib1g-dev liblcms2-dev libwebp-dev tcl8.6-dev tk8.6-dev 
python-tk -y 
> pip3 install --upgrade matplotlib Pillow 
> apt-get install --upgrade python3-scipy python3-tk -y 
> apt-get install --upgrade idle3 
 
Há ainda um vídeo com tutorial mostrando a instalação no Linux, que pode ser visualizado 
neste endereço: https://youtu.be/YmI3vQIRMHQ. 
 
 Para instalação no sistema operacional Windows, é recomendado tentar primeiro a 
instalação pela loja da Microsoft, que funciona muito bem para as versões 10 e 11 do 
Windows. Lembre-se que para fazer a instalação é necessário que o seu computador esteja 
conectado à Internet. Abra o terminal de comandos do Windows, digitando CMD na busca 
(ícone da lupa) da interface gráfica. Após abrir o terminal de textos digite o comando 
“python” seguido da tecla Enter. Caso o Python não esteja instalado, o contato com a loja da 
Microsoft será feito e os programas necessários serão baixados e instalados de forma 
automática. O Python é gratuito, não sendo cobrada nenhuma taxa para a sua instalação. 
 
25 
https://youtu.be/YmI3vQIRMHQ
 Introdução à Programação com Python 
Caso este primeiro método não funciona, a instalação pde ser feita manualmente do pacote 
disponível no endereço https://www.python.org/downloads/windows/. Você deve baixar a 
release mais recente do Python 3, para a versão do seu Windows. Após fazer o download 
do instalador e iniciar a instalação do Python é IMPORTANTE selecionar a opção para 
incluir o Python na lista de caminhos (PATH) do Windows. Esta opção é apresentada em 
uma das janelas exibidas no processo de instalação e deve ser marcada. 
 
 Se isso for feito não haverá problemas na execução dos seus códigos. Porém, se 
esta opção não for marcada, é possível que o IDLE não seja executado, ou ainda, que ele 
não encontre as bibliotecas gráfica, numérica, etc., e como consequência, alguns 
programas podem não funcionar porque não conseguiram encontrar as bibliotecas nos 
comandos de importação (import). 
 
 Este instalador não instala as bibliotecas numpy e PIL (bibliotecas de manipulação 
de arranjos e de processamento de imagens, respectivamente), que serão necessárias para 
algumas implementações. Assim, os passos seguintes deverão ser feitos mesmo para 
quem já tem o Python-IDLE instalado. A instalação das bibliotecas citadas pode ser feitas 
usando o Shell do Windows (Command ou cmd) com comandos específicos. Para instalar a 
biblioteca gráfica PIL um dos 3 comandos a seguir resolverá o problema: 
 python -m pip install Pillow 
Dependendo de como o Python foi nomeado no seu sistema (python, python3 ou py) um 
dos dois comandos alternativos a seguir podem funcionar: python3 -m pip install Pillow ou 
py -m pip install Pillow. 
 
Analogamente, para a instalação da biblioteca numérica numpy existem os 
comandos possíveis poderiam se um dos 3 a seguir: 
python -m pip install numpy : 
python3 -m pip install numpy 
py - m pip install numpy 
 
 A instalação é feita buscando arquivos na Internet. Logo, o computador deverá estar 
conectado à rede para a instalação do Anaconda e/ou das bibliotecas. Na página da 
disciplina INF 100 – Introdução à Programação I no PVANet, há um vídeo que mostra de 
forma detalhada a instalação do Anaconda. Para quem não está matriculado na disciplina 
INF 100 e, portanto, sem acesso ao PVANet, o vídeo com tutorial mostrando a instalação no 
Windows, pode ser visualizado neste endereço: https://youtu.be/MFWTQxUauTw 
(atualizado em janeiro de 2021). 
 
1.5. Exercícios 
 
1) O vídeo https://www.youtube.com/watch?v=nKIu9yen5nc apresenta depoimentos de 
figuras como Mark Zuckerberg (Facebbok), Jack Dorsey (Twitter), Bill Gates 
(Microsoft), Chris Bosh (Jogador de Basquete da NBA), dentre outros, sobre suas 
26 
https://www.python.org/downloads/windows/
https://youtu.be/MFWTQxUauTw
https://www.youtube.com/watch?v=nKIu9yen5nc
 Introdução à Programação com Python 
primeiras experiências com programação. Após assistir ao vídeo responda as 
perguntas a seguir. Quem disse as seguintes frases (tradução livre): 
 
a. “you don’t have to be a genious to know how to code. You have to be determined.” 
(você não precisa ser um gênio para saber como programar. Você deve ser 
determinado.) 
b. “the programmers of tomorrow are the wizards of the future.” (programadores de 
amanhã são os magos do futuro). 
c. “Coding is something that can be learned and… I know it can be intimidating… a 
lot of things can be intimidating, but, you know, what isn’t.” (Programar é algo que 
pode ser aprendido e… eu sei que pode ser intimidador… muitas coisas podem ser 
intimidadoras, mas, você sabe, o que não é?. 
d. “I think the first program I wrote asked things like, what’s your favourite colour? Or, 
how old are you?”. (Eu acho que o primeiro programa que escrevi perguntava coisas 
como, qual sua cor favorita? Ou, quantos anos você tem?). 
e. “(programming) it’s the closest thing we have to a super power.” ((Programação) éa coisa mais próxima que temos de super poder). 
 
2) No vídeo https://www.youtube.com/watch?v=6XvmhE1J9PY, o então presidente dos 
EUA, Barack Obama, fala sobre a importância estratégica do ensino de 
programação nas escolas. Você concorda com a visão dele. Escreva um parágrafo 
com sua opinião sobre a importância estratégica da programação na sua área de 
atuação como futuro profissional. 
 
3) O vídeo https://www.youtube.com/watch?v=Fkd9TWUtFm0 apresenta um 
“experiente” desenvolvedor de aplicativos falando de como iniciou sua precoce 
carreira. Quais foram as linguagens de programação que ele citou já ter utilizado? 
 
4) Identifique no seu computador a quantidade de memória RAM, a velocidade do 
processador e o tamanho do disco rígido. 
 
5) Suponha que um computador gaste, em média, 8 ciclos de processador para 
executar cada instrução aritmética de ponto flutuante. Um programa de simulação 
executa 10 bilhões de instruções de ponto flutuante. Quanto tempo um computador 
do início da década de 1980 com processador de ciclo de 1 MHz demoraria para 
executar este programa? 
 
6) Quanto tempo o seu computador demoraria para executar o mesmo programa do 
exercício 5? 
 
7) Instale o interpretador IDLE-Python em seu computador. Certifique-se de que as 
bibliotecas numérica (numpy) e gráfica (PIL) estejam instaladas (Execute o 
programa abaixo, para testar a importação das referidas bibliotecas). Ao final da 
execução a mensagem “Olá mundo…” (sem as aspas) deverá ser exibida na janela 
do Shell. 
 
27 
https://www.youtube.com/watch?v=6XvmhE1J9PY
https://www.youtube.com/watch?v=Fkd9TWUtFm0
 Introdução à Programação com Python 
 import numpy 
 import PIL 
 print(‘Olá mundo...’) 
 
 
 
28 
 Introdução à Programação com Python 
Capítulo 2 - Algoritmos 
 
No capítulo 1 foi apresentada a figura 1.5 com as fases de desenvolvimento de um 
programa, que se inicia com a análise do problema para se obter uma solução descritiva e, 
a seguir, descrever a solução em forma de um algoritmo. Mas o que vem a ser um 
algoritmo? É o que será descrito neste capítulo. 
 
2.1 Definição de Algoritmo 
 
Alguns dicionários informam que um algoritmo pode ser definido de forma simples 
como uma sequência de ações executáveis. Esta definição genérica abarca a maioria das 
situações do cotidiano como será visto nos exemplos a seguir. No contexto computacional 
um algoritmo pode ser definido como “um conjunto de regras e procedimentos lógicos 
perfeitamente definidos que levam à solução de um problema em um número finito de 
etapas” (Fonte: https://www.google.com/search?q=algoritmo). 
 
No nosso dia a dia temos como exemplos de algoritmos uma receita culinária de pão 
de queijo, um manual de montagem de um brinquedo ou de equipamento, uma rota definida 
por um aplicativo de mapas para se chegar a um destino, etc. Em cada um dos três casos 
citados, se as ações definidas forem seguidas à risca, ao final o resultado deveria ser 
algumas unidades de pão de queijo para serem degustadas, um brinquedo ou equipamento 
montado e a chegada ao destino, respectivamente. 
 
2.2 Algoritmo computacional e não computacional 
 
Daqui para frente será utilizado o exemplo da receita, ou do algoritmo, para produzir 
pão de queijo mostrando as similaridades e diferenças para um algoritmo computacional. A 
tabela 2.1 apresenta uma receita de pão de queijo detalhando em uma coluna a lista de 
ingredientes e na outra coluna as instruções para fazer os pães de queijo. 
 
Uma receita, em geral, como mostrado na tabela 2.1, possui duas partes: o conjunto 
de ingredientes e o modo de preparo. O conjunto de ingredientes corresponderia ao 
conjunto de dados do algoritmo computacional, que compreende as informações que 
precisam ser processadas para se chegar ao resultado desejado. Exatamente como se faz 
com os ingredientes da receita. No caso computacional, como será visto a partir do Capítulo 
3, o programador pode construir novos dados mais complexos (estruturas de dados) usando 
os tipos de dados primitivos da linguagem de programação. 
 
 
29 
 Introdução à Programação com Python 
Tabela 2.1 - Receita de Pão de Queijo 
Ingredientes Modo de preparo 
- 4 copos (americano) de polvilho 
doce (500 g); 
- 1 colher (sopa) tempero ou sal a 
gosto 
- 2 copos (americano) de leite (300 ml) 
- 1 copo (americano) de óleo (150 ml) 
- 2 ovos grandes ou 3 pequenos 
- 4 copos (americano) de queijo minas 
meia cura ralado 
- óleo para untar 
 
1. Coloque o polvilho em uma tigela grande. 
2. À parte, aqueça o sal, o leite e o óleo. 
3. Quando ferver, escalde o polvilho com essa 
mistura, mexa muito bem para desfazer 
pelotinhas. 
4. Deixe esfriar. 
5. Acrescente os ovos, um a um, alternando com 
o queijo e sovando bem, até a massa ficar 
homogênea, após cada adição. 
6. Unte as mãos com óleo, se necessário. 
7. Enrole bolinhos de 2 cm de diâmetro e 
coloque-os em uma assadeira untada. 
8. Leve ao forno médio (180º C), preaquecido. 
9. Asse até ficarem douradinhos. 
 
 
O modo de preparo da receita culinária corresponde ao algoritmo propriamente dito, 
pois ele descreve as ações que devem ser executadas para, usando os ingredientes, se 
produzir o resultado desejado. Entretanto, as ações que o computador consegue executar 
são ações muito simples e devem ser definidas de forma que não haja nenhuma dúvida 
sobre o que se está querendo executar. Da mesma forma, os dados a serem processados 
pelo computador tem que ser exatos, não podendo ter nenhum tipo de ambiguidade. 
 
2.3. Propriedades de um algoritmo 
 
Voltando à definição de algoritmo apresentada é possível destacar algumas das 
propriedades que todo algoritmo deve ter. Algoritmo é “um conjunto de regras e 
procedimentos lógicos perfeitamente definidos que levam à solução de um problema em um 
número finito de etapas”. As propriedades dos algoritmos foram definidas por Donald Knuth 
(https://pt.wikipedia.org/wiki/Donald_Knuth): 
• Finitude: um algoritmo deve sempre terminar após um número finito de ações; 
• Definição: cada passo de um algoritmo deve ser definido com precisão; as ações a 
serem executadas deverão ser especificadas rigorosamente e sem ambiguidades; 
• Entrada: são os valores que são fornecidos ao algoritmo. Essas entradas são 
tomadas a partir de conjuntos de objetos especificados; 
• Saída: são os valores resultantes das ações do algoritmo relacionadas com as 
entradas especificadas; 
• Eficácia: são todas as operações a serem realizadas no algoritmo devem ser 
suficientemente básicas e podem, em princípio, ser feitas com precisão e em um 
período de tempo finito por um homem usando papel e lápis. 
30 
 Introdução à Programação com Python 
 
A primeira propriedade (finitude) está relacionada com o tempo esperado para se 
obter o resultado. Em um tempo finito os pães de queijo tem que sair do forno e ninguém 
pode morrer de fome enquanto espera. Para alguns problemas computacionais mais 
complexos é necessário verificar se o problema pode ser resolvido, usando o computador 
que se tem disponível. Por exemplo, uma previsão de tempo baseada em imagens de 
satélite para o dia seguinte não pode levar mais do que poucas horas. Se demorar, por 
exemplo, dois dias o resultado seria a previsão do tempo de ontem… No caso da disciplina 
INF 100 todos os problemas apresentados são relativamente simples e não será feita este 
tipo de análise. 
 
A propriedade de definição está relacionada com a parte do conceito de algoritmo 
que diz “... e procedimentos lógicos perfeitamente definidos que levam à solução…”. Isto 
significa que não pode haver ambiguidade(dúvida) sobre o que está escrito no algoritmo, 
tanto na definição dos ingredientes (conjunto de dados) quanto nas ações ou comandos do 
modo de preparo ou do algoritmo. 
 
A propriedade de entrada está associada com o conjunto de informações 
necessárias (os ingredientes) para serem processadas e/ou transformadas para se chegar 
ao resultado esperado. E a propriedade de saída corresponde exatamente ao resultado 
esperado, quando se pode comprovar a correção do algoritmo. Estão saindo pães de queijo 
do forno? Ou está saindo um bolo? 
 
Finalmente, a propriedade de eficácia está relacionada com o grau de simplicidade 
de cada ação definida no algoritmo tem. A ação está suficientemente detalhada e simples? 
É realmente uma única ação? Caso estes requisitos não sejam atendidos é necessário 
refinar a ação, ainda complexa, quebrando-a em duas ou mais ações. Esta tarefa que pode 
ser executada repetidas vezes é chamada de refinamentos sucessivos. É importante 
lembrar que a versão final de um algoritmo computacional deve ser tal que, cada ação 
represente um único comando da linguagem de programação que será usada. Na próxima 
seção, cada ação do algoritmo para fazer pães de queijo deverá ser especificada de forma 
a representar uma única ação simples. 
 
2.4. Refinamento sucessivo e estruturas de programação 
 
Nesta seção serão apresentadas versões sucessivas e refinadas do algoritmo para 
fazer pães de queijo para exemplificar a eliminação de ambiguidades e a apresentação das 
três estruturas básicas de programação: sequencial, condicional e repetitiva. Estas três 
estruturas são suficientes para escrever qualquer programa computacional. Por isso, é 
importante, desde já, entender tais estruturas mesmo quando aplicadas a um exemplo não 
computacional. 
 
A primeira estrutura é a sequencial. Todo algoritmo (e programa) é composto por 
uma sequência de ações relacionadas com o que é necessário para poder. Observe que na 
31 
 Introdução à Programação com Python 
Tabela 2.1, as ações do modo de preparo estão numeradas, indicando a ordem (sequência) 
em que as ações devem ser executadas. Esta ordem é importante para a correção da 
solução. As estruturas condicional e repetitiva serão apresentadas durante o processo de 
refinamento do algoritmo. 
 
Será suposto que existe um conjunto de equipamentos para permitir a execução das 
ações que aparecerão nas próximas versões do algoritmo em seus refinamentos sucessivos 
tais como: panela e tabuleiro (colocar), mixer (misturar), batedeira (bater), fogão (aquecer, 
ferver), forno (ligar, regular temperatura, assar), lixeira (descartar), balança (pesar), jarra de 
1 litro com gradação de 10 em 10 ml (medir), ralador de queijo (ralar), tigela grande e tigela 
pequena (colocar). 
 
2.4.1 Eliminando ambiguidades 
 
Imagine que a receita será feita por um computador ou um robô ou mesmo por um 
ser humano que nunca fez nenhuma receita em toda sua vida e muito menos pão de queijo. 
O primeiro tipo de ambiguidade aparece na lista de ingredientes. Uma informação que pode 
ser muito clara para um cozinheiro experiente pode ser de difícil entendimento para alguém 
sem experiência na cozinha. 
 
Ao ler na lista de ingredientes “1 colher (sopa) tempero ou sal a gosto” poderão 
surgir diversas algumas dúvidas: usar tempero ou sal? Qual tempero, pimenta? Qual é a 
colher de sopa? Qual quantidade corresponde ao “a gosto”? Uma colher de sopa rasa, 
cheia? Para não haver estas ambiguidades o ingrediente deveria ser algo como “10g de 
sal”. O que significa um ovo grande? Pode ser ovo de pata? O que significa “meia cura”? 
 
Os ingredientes serão redefinidos pensando que a receita será feita por um ser 
humano sem nenhuma experiência culinária. A ideia é que não haja nenhuma dúvida 
sobre o que deverá ser utilizado em cada ação do algoritmo. Para tornar mais claro, foi 
inserido um comentário (texto que aparece após o caractere #) para cada ingrediente, 
indicando se precisaria ser pesado ou medido, considerando a forma de comercialização. 
Por exemplo, será considerado que o queijo meia cura foi comprado já ralado e que o 
pacote de polvilho doce é de 500g. Mas o sal teria de ser pesado e o leite e óleo teriam de 
ser medidos para . 
 
Tabela 2.2 - Ingredientes não ambíguos da Receita de Pão de Queijo 
 Ingredientes Comentário 
- 500g de polvilho doce; # pacote de 500g 
- 10g sal; # Quantidade extraída de pacote de 1 kg 
- 300 ml de leite # Quantidade extraída de saco de 1l. 
- 200 ml de óleo # Quantidade extraída de garrafa de 1l. 
- 2 ovos de galinha # Quantidade extraída de caixa com 12 
- 400g de queijo ralado # Quantidade comprada a granel (minas meia cura) 
32 
 Introdução à Programação com Python 
 
 Observe que não está sendo dada mais a opção de usar sal ou tempero. A receita 
usa apenas sal e em quantidade específica (10g). Se esta quantidade de sal deixará os 
pães de queijo sem sal ou muito salgados, o autor não faz ideia. Mas, não tem mais a 
ambiguidade de botar sal a gosto. Ou usar outro tempero no lugar do sal. Sempre que 
forem usados estes ingredientes não ambíguos, a sensação de salgado do resultado será a 
mesma, para uma mesma pessoa. 
 
 Outro detalhe é que em um algoritmo, assim como nas linguagens de programação, 
é possível adicionar comentários, que não fazem parte do algoritmo em si, mas ajudam a 
documentá-lo. Na tabela 2.2, o caractere # foi usado para identificar o início de um 
comentário: tudo o que vem após o #, na mesma linha, não faz parte da lista de 
ingredientes, mas auxilia um cozinheiro inexperiente a saber como adquirir ou como usar 
aquele ingrediente. Os comentários são muito úteis como parte da documentação dos 
algoritmos (e programas), facilitando o entendimento por outras pessoas que tiverem 
acesso ao algoritmo (código) e ajudando ao próprio autor do algoritmo (código) a lembrar 
detalhes de sua criação. 
 
2.4.2. Refinamento do Algoritmo 
 
Algumas ações também possuem ambiguidades ou não estão definidas com o grau 
de detalhamento para permitir que a receita seja feita sem nenhum problema. Considere, 
por exemplo, a ação número 5 “Acrescente os ovos, um a um, alternando com o queijo e 
sovando bem, até a massa ficar homogênea, após cada adição”. Claramente existem mais 
de uma ação neste passo 5, a saber: acrescentar ovo, acrescentar queijo, sovar e verificar 
se a massa está homogênea. 
 
Uma possível ambiguidade estaria no verbo “sovar” que, eventualmente, não seria 
entendida por algumas pessoas sem a consulta a um dicionário. No algoritmo será feita a 
substituição do verbo “sovar” pelo verbo “bater” explicitando que esta ação deve ser 
realizada na batedeira. Esta explicitação poderá ser feita com a colocação de comentários 
no algoritmo. Um comentário será sempre precedido do caractere “#”, para indicar que não 
se trata de um comando. 
 
O detalhamento de uma operação para eliminação de ambiguidade ou para 
quebrá-la em duas ou mais ações é chamado de refinamento. A técnica de refinamento 
deve ser aplicada tantas vezes quantas forem necessárias, para que, ao final, o algoritmo 
contenha apenas operações triviais. Esta técnica é conhecida como refinamento sucessivo 
do algoritmo. 
 
 A Figura 2.1 apresenta uma segunda versão, primeiro refinamento do algoritmo 
(modo de preparo) considerando os ingredientes já definidos na Tabela 2.2, com o 
detalhamento das operações ou ações, em particular, da ação 5 da versão 1, que descreve 
33 
 Introdução à Programação com Python 
que deve os ovos devem ser acrescentados um

Mais conteúdos dessa disciplina