Fundamentos
A estrutura if e else em Python: decisões, recuo e erros de indentação
Aprenda a usar if e else em Python para o programa escolher entre dois caminhos, entender o recuo como parte da sintaxe e corrigir os erros de indentação.
Por Prof. Rodrigo Faustino · Atualizado em · 14 min de leitura
O if faz o programa executar um bloco de código só quando uma condição é verdadeira, e o else define o que fazer quando ela é falsa. O bloco é o conjunto de linhas recuadas logo depois da linha que termina em dois-pontos. Em Python, esse recuo não é enfeite de formatação: ele faz parte da sintaxe, e é ele que diz quais linhas pertencem ao if, quais pertencem ao else e quais já estão fora dos dois.
Até aqui, os programas desta série rodaram de cima para baixo, uma linha depois da outra, sem escolher nada. Com if e else o programa passa a decidir, e todo o trabalho de condições dos dois artigos anteriores ganha um lugar para entrar. Este texto mostra a estrutura, o que pode ir no lugar da condição, as formas curtas, o que muda na ESP32 e os erros de indentação que aparecem em qualquer turma, inclusive com a briga mais antiga da programação: tabs ou espaços.
O problema: o programa que sempre faz a mesma coisa
Imagine um termostato que lê a temperatura de uma sala. Se um programa só soubesse seguir em linha reta, ele ligaria o ventilador sempre ou nunca ligaria, e a leitura do sensor não serviria para nada. O que se quer é o contrário: com 31 graus, ligar o ventilador, e com 22, deixar desligado. Isso é uma decisão, e uma decisão precisa de três coisas: uma pergunta de sim ou não, o que fazer se a resposta for sim e o que fazer se for não.
A pergunta é a condição, a expressão que vira True ou False, como as dos artigos sobre operadores relacionais e lógicos e sobre tabelas-verdade. As duas respostas são os blocos. A estrutura que junta tudo se escreve assim:
temperatura = 31
if temperatura > 30:
print("ligar ventilador")
else:
print("ventilador desligado")
print("fim da checagem")
temperatura = 22
if temperatura > 30:
print("ligar ventilador")
else:
print("ventilador desligado")
print("fim da checagem")A saída é ligar ventilador, fim da checagem, ventilador desligado e fim da checagem. O mesmo código, com valores diferentes, tomou caminhos diferentes. E a linha print("fim da checagem") rodou nos dois casos, porque ela está na margem, fora dos dois blocos.
A IA que lembra da sua vida e mora no seu computador
- Memória de longo prazo com a fonte de cada resposta
- Funciona offline: seus dados ficam no seu PC
- Lê PDFs, slides, fotos e gravações de reunião
Plano Essencial grátis para sempre
A anatomia do if
Uma estrutura if tem quatro partes. A palavra if, que abre a decisão. A condição, que pode ser qualquer expressão que dê verdadeiro ou falso. O dois-pontos no fim da linha, que avisa "o bloco começa aqui". E o bloco, as linhas recuadas com a mesma quantidade de espaços. O else é opcional e tem só duas partes: a palavra, com os dois-pontos, e o seu bloco. Ele não leva condição, porque significa "em todos os outros casos". Se o if e o else aparecem juntos, um e só um dos dois blocos roda.
Depois do último bloco, o programa volta para a margem e segue. É a regra que a figura mostra: os dois caminhos se juntam na primeira linha que não está recuada.
O que pode ir no lugar da condição
Qualquer expressão serve, e o Python decide pelo valor de verdade dela. Pode ser uma comparação (nota >= 6), uma combinação com and, or e not (x > 5 and x < 20), uma variável que já guarda um booleano (via_interditada) ou até um valor que não é booleano. Nesse último caso, a regra é a mesma do artigo anterior: o zero, o texto vazio, a lista vazia e o None contam como falsos, e todo o resto conta como verdadeiro.
for v in (0, 1, "", "texto", [], [0], None, "False", " "):
if v:
print(repr(v), "verdadeiro")
else:
print(repr(v), "falso")A saída tem nove linhas: 0 falso, 1 verdadeiro, '' falso, 'texto' verdadeiro, [] falso, [0] verdadeiro, None falso, 'False' verdadeiro e ' ' verdadeiro. Repare nas duas últimas. O texto "False" é verdadeiro, porque não está vazio, e um único espaço também. É um jeito prático de testar "o usuário digitou alguma coisa?": if nome: é verdadeiro se houver texto. Mas é também a origem de um erro conhecido, em que alguém lê "False" do teclado e acha que o programa vai entender como falso.
O for que aparece aqui repete o bloco para cada valor da lista, e o módulo de repetição vai explicá-lo com calma. O que importa neste exemplo é o if e o else dentro dele.
As formas curtas
O Python tem três atalhos que aparecem em código real, e vale reconhecê-los.
nota = 7
situacao = "aprovado" if nota >= 6 else "reprovado"
print(situacao)
if nota >= 6: print("passou")
if nota < 6: print("nao passou")
else: print("ok")
if nota > 5:
pass
else:
print("nunca")
print(5 == True, 1 == True, bool("False"))A saída é aprovado, passou, ok e False True True. O primeiro atalho é a expressão condicional, valor1 if condição else valor2, que escolhe um valor em vez de um bloco: é útil para atribuições curtas, mas quanto mais longa a condição, pior fica a leitura. O segundo é o if de uma linha só, com o comando logo depois dos dois-pontos, que só serve quando o corpo é uma instrução simples. O terceiro é o pass, um comando que não faz nada e existe para ocupar um bloco que a sintaxe exige. Na última linha, uma armadilha: 5 == True é False, embora o 5 seja verdadeiro numa decisão. Por isso if x == True: quase sempre está errado, e o certo é escrever apenas if x:.
Ifs dentro de ifs
Um bloco pode conter outro if. O recuo cresce um nível e o Python entende que o if interno só é avaliado se o externo for verdadeiro.
x = 10
if x > 5:
print("a")
if x > 8:
print("b")
print("c")
print("d")
nome = ""
if not nome:
print("sem nome")
if x > 5 and x < 20:
print("faixa")
if 5 < x < 20:
print("faixa 2")
if x == 10:
print("dez")
if x != 10:
print("nao dez")
else:
print("e dez")A saída começa com a, b, c e d: o b fica no segundo nível, o c volta ao primeiro nível de recuo e o d sai de tudo. Depois vêm sem nome, faixa, faixa 2, dez e e dez. Os ifs encadeados e a escolha entre mais de duas opções são o assunto do próximo artigo, com o elif. Por enquanto, a regra de ouro é simples: cada nível de recuo abre um bloco novo, e voltar para a margem esquerda fecha tudo.
O recuo decide a quem a linha pertence
O recuo é o que torna o Python tão legível, e também o que faz um erro de uma linha virar um comportamento diferente sem nenhum aviso. A figura mostra duas versões do mesmo texto.
nota = 4
if nota >= 6:
print("aprovado")
print("parabens!")
else:
print("reprovado")
print("---")
if nota >= 6:
print("aprovado")
else:
print("reprovado")
print("parabens!")A saída é reprovado, uma linha de separação, reprovado e parabens!. Na primeira versão, o print("parabens!") está dentro do if, e só quem foi aprovado recebe os parabéns. Na segunda, a linha está na margem, depois do else, e todo mundo recebe, inclusive quem repetiu de ano. Nenhuma das duas versões dá erro, e o programa roda normalmente. Quem escreve a segunda versão sem querer só descobre quando alguém reclama da mensagem.
A convenção do Python, definida no guia de estilo PEP 8, é usar quatro espaços por nível. Não é obrigatório que sejam quatro, mas é obrigatório que sejam sempre os mesmos dentro do mesmo bloco. No editor do PyPlaca, a tecla Tab insere quatro espaços, então dá para apertar Tab sem pensar no assunto.
Em sala de aula: erros de indentação
Os erros abaixo se repetem em toda turma que começa a escrever if, e cada um tem uma mensagem própria. Conhecer a mensagem é metade da correção.
Faltou o dois-pontos
O erro mais frequente de quem está começando e um dos mais frequentes de quem vem de outra linguagem, onde o bloco abre com chaves ou com a palavra then:
x = 5
if x > 3
print("maior")Traceback (most recent call last):
File "main.py", line 2
SyntaxError: invalid syntaxA mensagem do MicroPython é genérica e aponta a linha do if. O Python do computador é mais gentil e diz SyntaxError: expected ':'. Quando aparecer um invalid syntax numa linha que começa com if, else, for ou while, olhe o fim dela antes de qualquer outra coisa.
O corpo sem recuo
x = 5
if x > 3:
print("maior")Traceback (most recent call last):
File "main.py", line 3
SyntaxError: invalid syntaxO dois-pontos está certo, mas a linha seguinte ficou na margem, então o if ficou sem corpo. No Python do computador o erro é mais específico: IndentationError: expected an indented block after 'if' statement on line 2. O erro aponta para a linha 3, a que deveria estar recuada.
O recuo a mais
x = 5
if x > 3:
print("maior")
print("de novo")Traceback (most recent call last):
File "main.py", line 4
IndentationError: unexpected indentUma linha que ficou mais para dentro do que a anterior, sem que a anterior terminasse em dois-pontos, é um recuo que o Python não sabe de onde veio. É comum depois de colar um trecho de código no meio de outro, ou de apertar a barra de espaço sem perceber.
O recuo que não bate
x = 5
if x > 3:
print("a")
print("b")Traceback (most recent call last):
File "main.py", line 4
IndentationError: unindent doesn't match any outer indent levelA primeira linha do bloco tem oito espaços, e a segunda voltou para quatro, um nível que nunca foi aberto. O Python não sabe se a segunda linha está dentro ou fora. O mesmo erro aparece quando o else fica com um recuo diferente do if a que ele pertence. Já um else sem nenhum if antes dele dá só SyntaxError: invalid syntax.
O espaço que ninguém vê
Quem copia código de um PDF, de um slide ou de uma conversa às vezes leva junto um espaço especial, o "espaço que não quebra" (NBSP). Ele parece igual a um espaço comum e não é. O resultado é um SyntaxError: invalid syntax numa linha que parece perfeita aos olhos. No Python do computador, a mensagem é mais clara: SyntaxError: invalid non-printable character U+00A0. Se uma linha está visivelmente certa e o Python insiste que não, apague os espaços do começo dela e digite de novo.
O erro que não dá erro
O caso mais traiçoeiro é o da seção anterior, quando o recuo errado ainda é um programa válido. Não há mensagem para consultar, só o comportamento estranho. A defesa é ler o código olhando a coluna da margem, e não só o texto, e conferir para cada linha de um bloco a pergunta "a quem esta linha pertence?". Um truque de quem ensina: pedir ao aluno que passe o dedo na linha vertical do recuo e diga em voz alta onde o bloco acaba.
Tabs ou espaços: a briga que não acaba
Existe uma discussão que já azedou equipes, revisões de código e até jantares: o recuo se faz com a tecla Tab ou com a barra de espaço? Na série Silicon Valley, da HBO, o tema virou piada com direito a crise de nervos. Na terceira temporada, o protagonista, Richard Hendricks, é do time dos tabs, e ao programar ao lado de uma antiga paixão que usa espaços, ele não aguenta ouvir o barulho da barra de espaço e acaba cancelando o convite que tinha feito. Na cabeça de Richard, o assunto está encerrado: programador usa tabs, e a discussão não tem segundo turno.
O Python, que leva o recuo mais a sério que qualquer outra linguagem, resolveu o impasse do jeito dele: nas duas escolhas o programa funciona, mas misturar as duas num mesmo bloco, de um jeito que deixe o recuo ambíguo, é proibido. No Python 3, o resultado é um TabError, e é o único caso em que a briga acaba em mensagem de erro. A paz, na prática, é simples. Aperte a tecla Tab se quiser, mas peça ao editor que escreva quatro espaços no lugar, como o do PyPlaca já faz. Richard continua feliz com a tecla dele, a colega continua feliz com a barra de espaço, e o Python só exige que ninguém misture.
Da ementa ao semestre planejado
- Plano de ensino e calendário montados sozinhos
- Diário de aulas pronto para colar no SIGA
- Slides e listas de exercícios com gabarito
Versão Community grátis · Windows
O que muda na ESP32
A estrutura e as regras são as mesmas no MicroPython e no Python do computador. Mudam as mensagens de erro, e uma delas muda o comportamento. A tabela resume o que o simulador mostra e o que o Python do computador (3.13) mostra para os mesmos erros:
| Erro | Simulador (MicroPython) | Python no computador |
|---|---|---|
falta o : no if | SyntaxError: invalid syntax | SyntaxError: expected ':' |
| corpo sem recuo | SyntaxError: invalid syntax | IndentationError: expected an indented block after 'if' statement on line 2 |
| recuo a mais | IndentationError: unexpected indent | IndentationError: unexpected indent |
| recuo que não bate | IndentationError: unindent doesn't match any outer indent level | IndentationError: unindent does not match any outer indentation level |
else sem if | SyntaxError: invalid syntax | SyntaxError: invalid syntax |
| espaço NBSP | SyntaxError: invalid syntax | SyntaxError: invalid non-printable character U+00A0 |
| Tab numa linha e oito espaços na seguinte | roda sem reclamar | TabError: inconsistent use of tabs and spaces in indentation |
A última linha é a que importa. No simulador, o recuo é medido em colunas, e um Tab vale oito. Por isso uma linha com um Tab e outra com oito espaços parecem iguais para ele e o programa roda. No Python do computador, a mistura é recusada com TabError. O mesmo arquivo pode funcionar na placa e falhar no computador, ou o contrário, e a saída segura é a de sempre: quatro espaços em tudo, sem tabs no arquivo.
O if na ESP32 costuma decidir a partir de um pino. Num botão com resistor de pull-up, o pino vale 0 quando o botão está apertado, e o programa liga ou apaga um LED:
from machine import Pin
import time
botao = Pin(4, Pin.IN, Pin.PULL_UP)
led = Pin(2, Pin.OUT)
while True:
if botao.value() == 0:
led.value(1)
else:
led.value(0)
time.sleep_ms(50)O while True: repete o bloco para sempre, e dentro dele o if escolhe o que fazer a cada 50 milissegundos. Repare nos níveis de recuo: o while abre o primeiro, o if e o else ficam nele, e os led.value() ficam um nível mais para dentro. O time.sleep_ms(50) está alinhado com o if, então roda a cada volta, qualquer que seja o resultado. O artigo sobre pull-up e pino flutuante explica por que o botão lê zero quando apertado.
Exercício: ano bissexto
Escreva um programa que diga se um ano é bissexto. A regra: é bissexto quem é divisível por 4, exceto os divisíveis por 100, a menos que também sejam divisíveis por 400. Pense primeiro na condição, com and e or, e use o % para testar a divisibilidade. Confira com 2024, 1900, 2000 e 2023.
for ano in (2024, 1900, 2000, 2023, 2100, 1996):
if ano % 4 == 0 and (ano % 100 != 0 or ano % 400 == 0):
print(ano, "bissexto")
else:
print(ano, "nao bissexto")A saída é 2024 bissexto, 1900 nao bissexto, 2000 bissexto, 2023 nao bissexto, 2100 nao bissexto e 1996 bissexto. O 1900 é divisível por 4 e por 100, mas não por 400, então fica de fora, e o 2000 passa pela exceção da exceção. Repare nos parênteses: sem eles, o and seria resolvido antes do or e a condição mudaria de significado, como no artigo sobre os operadores lógicos. Para ler o ano do teclado, troque o for por ano = int(input("Ano: ")), como no artigo sobre conversão de tipos. Um bom teste é montar a tabela-verdade da condição e conferir que o programa a segue.
Perguntas frequentes
Preciso sempre do else?
Não. O if sozinho é a forma mais comum: se a condição for verdadeira, o bloco roda, e se não for, o programa simplesmente segue adiante. O else só entra quando existe uma ação para o caso contrário.
Posso usar parênteses na condição?
Pode, e if (x > 3): funciona. Mas eles não são necessários, e a convenção do Python é omiti-los. Os parênteses servem para agrupar partes da condição, como no exemplo do ano bissexto.
Quantos espaços devo usar no recuo?
Quatro, que é a convenção da comunidade. O que o Python exige é que sejam sempre os mesmos no mesmo bloco. Configure o editor para inserir quatro espaços quando você aperta Tab e evite misturar tabs e espaços no mesmo arquivo.
Qual a diferença entre if x: e if x == True:?
O if x: pergunta se o valor de x é verdadeiro no sentido do Python, o que vale para qualquer número diferente de zero e qualquer texto não vazio. O if x == True: pergunta se x é igual ao True, o que é falso para o número 5. Use a primeira forma.
Por que meu if não faz nada, mas também não dá erro?
Costuma ser a condição que nunca é verdadeira, ou uma linha com recuo errado que saiu do bloco. Imprima a condição antes do if para ver o valor e confira, linha a linha, a coluna em que cada comando começa.
Para continuar
A trilha Lógica com Python tem desafios que usam a estrutura. O Maior de idade e o Par ou ímpar são o aquecimento com um if e um else, o Aprovação na escola cobra uma condição composta, e o Positivo ou negativo pede mais de duas respostas, o que prepara o terreno para o próximo artigo.
O próximo assunto é o if, elif e else em Python: como escolher entre três ou mais caminhos sem empilhar ifs, e como as condições aninhadas se comportam quando o recuo cresce.