Lógica Booleana

Na Lição 03, aprendemos sobre operadores, incluindo os operadores lógicos and, or, not. Nesta lição, vamos nos concentrar nos julgamentos de verdadeiro/falso — o conceito mais fundamental em ciência da computação. A lógica booleana é a base de todas as declarações condicionais, controles de laço e verificações de permissão.


1. Valores Booleanos: True e False

Existem apenas dois valores booleanos: True e False. Eles são nomeados em homenagem ao matemático britânico George Boole, que fundou a álgebra booleana — a base teórica do "0 e 1" da computação moderna.

PYTHON
print(True)    # Saída: True
print(False)   # Saída: False
print(type(True))   # <class 'bool'>

Operadores de comparação produzem resultados booleanos:

PYTHON
print(5 > 3)      # True
print(10 == 5)    # False
print(7 <= 7)     # True
print(3 != 3)     # False

Booleanos também são Números

Em Python, True e False são na verdade subclasses de intTrue equivale a 1, False a 0:

PYTHON
print(True + True)      # 2 (True=1, dois Trues = 2)
print(True * 10)        # 10
print(False * 100)      # 0
⚠️ Atenção: Embora True == 1 e False == 0 sejam verdadeiros em Python (então True + True é igual a 2), nunca os use dessa forma. Valores booleanos são para julgamento lógico, não para aritmética. Escrever código como score + True deixará os leitores confusos.

Exemplo: Resultados de Exame de Saúde (Dificuldade ⭐)

PYTHON
# Gera valores booleanos com operadores de comparação
age = 25
height = 175
weight = 70

is_adult = age >= 18          # True
is_tall = height > 170        # True
is_heavy = weight > 80        # False

print(f"Adulto: {is_adult}")
print(f"Alto: {is_tall}")
print(f"Acima do peso: {is_heavy}")

# Exibe diretamente valores booleanos — eles são valores, não texto
print(f"Adulto E Alto: {is_adult and is_tall}")
▶ Experimente

Saída:

TEXT
Adulto: True
Alto: True
Acima do peso: False
Adulto E Alto: True

2. not: Negação

not significa "inverter" — branco vira preto, preto vira branco.

PYTHON
print(not True)      # False
print(not False)     # True
print(not (5 > 3))   # False (5>3 é True, negado é False)

not é comumente usado em dois cenários:

Cenário 1: Verificando "não atendimento a uma condição"

PYTHON
# Não é admin — não pode entrar no backend
is_admin = False
if not is_admin:
    print("Você não tem acesso de administrador.")
# Saída: Você não tem acesso de administrador.

Cenário 2: Verificando se uma variável está vazia

PYTHON
# Verifica se o usuário não forneceu um nome
username = ""
if not username:
    print("Nome de usuário não pode estar vazio!")
# Saída: Nome de usuário não pode estar vazio!

Há um truque de "conversão booleana implícita" do Python aqui — a string vazia "" equivale a False em verificações de condição. Então not username é True quando username é uma string vazia. Abordaremos quais valores são "falsy" mais adiante.

💡 Dica: not significa "negação." No código, if not is_admin: é lido como "se não for admin."


3. and: Ambos Devem Ser Verdadeiros

and significa "ambos" — ambas as condições devem ser verdadeiras para o resultado ser True. Se qualquer uma for falsa, o resultado é False.

Esquerda Direita Resultado
True True True
True False False
False True False
False False False
PYTHON
age = 22
has_id = True

# Ambas as condições devem ser atendidas
can_buy_alcohol = age >= 18 and has_id
print(can_buy_alcohol)   # True (maior de idade e tem documento)

# Outro cenário: solicitar cartão de crédito requer renda >= 50k E pontuação de crédito >= 600
income = 80  # milhares
credit_score = 650
qualified = income >= 50 and credit_score >= 600
print(f"Solicitação de cartão de crédito: {qualified}")   # True

Exemplo: Verificação de Login (Dificuldade ⭐)

PYTHON
# Simula login — nome de usuário correto E senha correta
username_correct = True
password_correct = False

can_login = username_correct and password_correct
print(f"Resultado do login: {can_login}")   # False — senha errada

# Adiciona outra camada: conta não deve estar bloqueada
account_locked = True
can_login = username_correct and password_correct and not account_locked
print(f"Resultado final: {can_login}")   # False — conta está bloqueada
▶ Experimente

Saída:

TEXT
Resultado do login: False
Resultado final: False

4. or: Pelo Menos Um Verdadeiro

or significa "ou" — se pelo menos uma condição for verdadeira, o resultado é True. Apenas quando ambas são falsas o resultado é False.

Esquerda Direita Resultado
True True True
True False True
False True True
False False False
PYTHON
# Pode descansar em fins de semana ou feriados
is_weekend = True
is_holiday = False
can_rest = is_weekend or is_holiday
print(can_rest)   # True (é fim de semana)

# Segurança do metrô: se você tem água OU bebida, precisa de verificação
has_water = True
has_drink = False
need_check = has_water or has_drink
print(f"Verificação necessária: {need_check}")   # True

Exercício: Verificação Completa da Tabela Verdade

PYTHON
# Verifica a tabela verdade com código — todas as combinações de and e or
a = True
b = True
print(f"{a} and {b} = {a and b}")
print(f"{a} or  {b} = {a or b}")

a = True
b = False
print(f"{a} and {b} = {a and b}")
print(f"{a} or  {b} = {a or b}")

a = False
b = True
print(f"{a} and {b} = {a and b}")
print(f"{a} or  {b} = {a or b}")

a = False
b = False
print(f"{a} and {b} = {a and b}")
print(f"{a} or  {b} = {a or b}")

Saída:

TEXT
True and True = True
True or  True = True
True and False = False
True or  False = True
False and True = False
False or  True = True
False and False = False
False or  False = False

5. Avaliação de Curto-Circuito

Mencionamos isso na Lição 03, mas é tão importante que vamos nos aprofundar. Os operadores lógicos do Python param de avaliar imediatamente quando o resultado é determinado, sem executar a expressão restante.

Curto-circuito and: Esquerda é False → Direita Não Executada

PYTHON
def check_right():
    print("-> check_right foi chamada!")
    return True

print("False and check_right():")
result = False and check_right()   # check_right NÃO será executada
print(f"Resultado: {result}\n")

print("True and check_right():")
result = True and check_right()    # check_right será executada
print(f"Resultado: {result}")

Saída:

TEXT
False and check_right():
Resultado: False

True and check_right():
-> check_right foi chamada!
Resultado: True

Curto-circuito or: Esquerda é True → Direita Não Executada

PYTHON
print("True or check_right():")
result = True or check_right()    # check_right NÃO será executada
print(f"Resultado: {result}")

Usos Clássicos da Avaliação de Curto-Circuito

1. Acesso Seguro: Prevenindo Erros com None

PYTHON
# Suponha que user pode ser None (usuário não existe)
user = None
# user.get("name") daria erro — None não tem método get

# Use curto-circuito para proteger:
name = user and user.get("name")
print(name)   # None — user é falsy, curto-circuitou, user.get() não foi chamado

# Se user existir:
user = {"name": "João Silva"}
name = user and user.get("name")
print(name)   # João Silva

2. Definindo Valores Padrão

PYTHON
# Se o usuário não digitou um nome, use um padrão
user_input = ""           # String vazia (falsy)
name = user_input or "convidado"
print(f"Bem-vindo, {name}")   # Bem-vindo, convidado

user_input = "João Silva"
name = user_input or "convidado"
print(f"Bem-vindo, {name}")   # Bem-vindo, João Silva
💡 Dica: O padrão user_input or "default" é muito pytônico — se o lado esquerdo é falsy (string vazia), use o direito; se truthy (tem conteúdo), use o esquerdo. Ele aproveita o comportamento de curto-circuito do or.


6. Valores Truthy e Falsy

Em Python, qualquer valor pode ser usado como booleano em uma condição. Alguns valores são considerados "falsy," e todo o resto é "truthy."

Valores Falsy Comuns

PYTHON
# Estes valores equivalem a False em condições
print(bool(False))      # False — booleano falso
print(bool(0))          # False — zero
print(bool(0.0))        # False — float zero
print(bool(""))         # False — string vazia
print(bool([]))         # False — lista vazia (abordado mais adiante)
print(bool(None))       # False — valor nulo

Todo o resto é truthy:

PYTHON
print(bool(1))          # True — número diferente de zero
print(bool(-5))         # True — números negativos também são truthy!
print(bool("Python"))   # True — string não vazia
print(bool(" "))        # True — um espaço é um caractere, não vazio é truthy
print(bool([1, 2]))     # True — lista não vazia
⚠️ Atenção: -5 e " " (espaço) são ambos truthy, o que pode surpreender você. -5 é um inteiro diferente de zero, então é truthy. Um espaço é um caractere, tornando a string não vazia, então é truthy. Apenas uma string vazia "" é falsy.

Usando Truthiness para Simplificar Código

PYTHON
# Não recomendado (verboso)
name = "João Silva"
if name != "":
    print(f"Olá, {name}")

# Recomendado (conciso)
name = "João Silva"
if name:
    print(f"Olá, {name}")

# Não recomendado
score = 85
if score != 0:
    print(f"Pontuação: {score}")

# Recomendado
score = 85
if score:
    print(f"Pontuação: {score}")
💡 Dica: Aproveitar a truthiness torna o código mais limpo. if name: é mais "pytônico" que if name != "":. Mas cuidado para não abusar — if score: não será executado quando score=0. Se você precisar distinguir entre "pontuação é 0" e "sem pontuação," use is not None.


7. is e is not: Comparação de Identidade

is compara se duas variáveis apontam para o mesmo objeto (o mesmo espaço na memória), não se seus valores são iguais. Mencionamos isso na Lição 03; aqui estão mais exemplos para reforçar.

PYTHON
# == compara valores, is compara identidade
a = [1, 2, 3]
b = [1, 2, 3]
c = a

print(a == b)     # True — mesmos valores
print(a is b)     # False — mas não é o mesmo objeto lista
print(a is c)     # True — c é a, aponta para a mesma lista

# Cache de inteiros pequenos (otimização interna do Python)
x = 256
y = 256
print(x is y)     # Pode ser True — inteiros pequenos são armazenados em cache

x = 1000
y = 1000
print(x is y)     # Pode ser False — inteiros grandes não são armazenados em cache
⚠️ Atenção: Nunca use is para comparar inteiros ou strings por valor. Embora inteiros pequenos possam às vezes retornar True com is devido à otimização interna do Python, isso é um detalhe de implementação e não é confiável. Sempre use == para comparação de valor.

O Uso Correto: Verificando None

A comunidade Python tem uma convenção — ao verificar se um valor é None, sempre use is, nunca ==:

PYTHON
# Abordagem correta
result = None
if result is None:
    print("Sem resultado")

# Não recomendado
if result == None:
    print("Sem resultado")

Casos de Uso Comuns


❓ Perguntas Frequentes

P: Qual a diferença entre True e "True"? R: True (sem aspas) é um valor booleano; "True" (com aspas) é uma string. Eles são diferentes: type(True) é <class 'bool'>, type("True") é <class 'str'>. Em uma condição, if "True": é sempre True (string não vazia é truthy), e if "False": também é sempre True (também não vazia). Então nunca coloque aspas em valores booleanos em condições. P: Quando devo usar is vs ==? R: Use == em 99% dos casos. is é convencional apenas em um cenário — verificar None: if result is None:. Use == para todas as outras comparações de valor. Lembre-se: == compara "valor," is compara "identidade." P: Quais armadilhas a avaliação de curto-circuito de and/or tem? R: A armadilha mais comum envolve chamadas de função. Se você colocar uma chamada de função no lado direito de and ou or, ela pode não executar devido ao curto-circuito, e você não saberá que foi pulada. Se essa função tem efeitos colaterais (logging, envio de emails, atualização de contadores), o curto-circuito pode causar comportamento inconsistente. Boa prática: se a expressão do lado direito tem efeitos colaterais, não dependa do curto-circuito — escreva-as separadamente. P: Por que not not "hello" retorna True? R: not "hello" primeiro avalia "hello" como booleano (string não vazia é truthy), nega para obter False. Então not not "hello" nega False novamente, obtendo True. Portanto, not not x equivale a bool(x) — convertendo x para booleano. Mas este padrão é incomum; use bool(x) diretamente para clareza.


📖 Resumo


📝 Atividades

  1. Iniciante (Dificuldade ⭐): Prediga os valores destas expressões, depois verifique:

    • not (10 > 5)
    • True and False or True
    • not False and True
    • (5 > 3) or (2 > 10) and (8 == 8)Dica: Observe a precedência — and tem precedência maior que or
  2. Intermediário (Dificuldade ⭐⭐): Escreva código para validar a string de entrada de um usuário:

    • Se a entrada estiver vazia, exiba "A entrada não pode estar vazia"
    • Se a entrada for totalmente espaços, trate também como "A entrada não pode estar vazia" (Dica: use strip())
    • Se o comprimento da entrada for menor que 6, exiba "A entrada deve ter pelo menos 6 caracteres"
    • Caso contrário, exiba "A entrada é válida"
  3. Avançado (Dificuldade ⭐⭐⭐): Escreva um "verificador de números de três dígitos." Dado um número de 3 dígitos num (ex.: 153), determine:

    • É par? (use %)
    • É divisível por 3 e 5?
    • É palíndromo? (dígito das centenas igual ao dígito das unidades, ex.: 121, 353)
    • Quantas das condições acima são atendidas? Exiba a contagem.

    Use apenas expressões booleanas para todas as verificações — sem declarações if (reserve para a próxima lição).

100%