Por que padronizar interrupções, continuação e retorno
Em pseudocódigo, comandos de controle de fluxo como PARE/SAIA, CONTINUE e RETORNE existem para lidar com situações excepcionais ou para simplificar regras locais. O problema aparece quando eles viram “atalhos” frequentes: o fluxo fica difícil de seguir, surgem múltiplos pontos de saída e o leitor precisa simular mentalmente muitos caminhos possíveis.
Este capítulo padroniza o uso desses comandos para manter o fluxo previsível, evitando o efeito “espaguete” (saltos e saídas antecipadas espalhadas).
Vocabulário e intenção de cada comando
PARE/SAIA (interromper laços)
PARE (ou SAIA) encerra imediatamente o laço atual. Use quando uma condição de parada não se encaixa bem na condição do laço ou quando um evento torna inútil continuar iterando (por exemplo, “encontrei o item; não preciso procurar mais”).
- Escopo: afeta apenas o laço mais interno.
- Intenção: “não faz sentido continuar iterando”.
CONTINUE (pular para a próxima iteração)
CONTINUE interrompe a iteração atual e segue para a próxima. Use para descartar casos rapidamente (por exemplo, “se o registro está inválido, ignore e vá para o próximo”).
- Escopo: afeta apenas o laço mais interno.
- Intenção: “este caso não deve executar o restante do corpo do laço”.
RETORNE (sair de função/procedimento)
RETORNE encerra a execução de uma função/procedimento. Em funções, normalmente devolve um valor; em procedimentos, pode apenas encerrar.
- Ouça o áudio com a tela desligada
- Ganhe Certificado após a conclusão
- + de 5000 cursos para você explorar!
Baixar o aplicativo
- Escopo: afeta a função/procedimento atual.
- Intenção: “já tenho o resultado” ou “não posso continuar por pré-condição violada”.
Regras de uso para evitar fluxo “espaguete”
Regra 1: cada interrupção deve ter uma condição explícita e justificável
Antes de usar PARE, CONTINUE ou RETORNE, escreva a condição de forma direta e verificável. Evite condições implícitas (“se der ruim”) e prefira critérios objetivos.
- Bom:
SE idProcurado = idAtual ENTÃO PARE - Ruim:
SE achou ENTÃO PARE(se “achou” não estiver claramente definido no contexto)
Regra 2: limite o número de pontos de saída
Como padrão, busque:
- Laços: no máximo 1
PAREpor laço (0 é melhor quando a condição do laço resolve). - Laços: no máximo 1
CONTINUEpor laço (use para “filtro” no topo). - Funções: preferir 1
RETORNEno final; permitir retornos antecipados apenas para validação de pré-condições (guard clauses) ou casos triviais.
Regra 3: se usar CONTINUE, use como “filtro” no início do laço
Coloque as condições de descarte no começo, para reduzir indentação e manter o “caminho principal” mais visível.
- Padrão recomendado: validar/filtrar → processar.
Regra 4: prefira reescrever o laço para não precisar de PARE
Muitas vezes, PARE pode ser substituído por:
- Uma condição de laço mais precisa (quando possível).
- Uma variável de controle (ex.:
encontrou) que governa a continuidade.
Use PARE quando a alternativa deixar o laço artificialmente complexo.
Regra 5: não use interrupções para “pular” etapas de negócio
Se o algoritmo tem etapas (validar, calcular, persistir, responder), não use RETORNE no meio para escapar de responsabilidades que deveriam ser tratadas de forma estruturada (por exemplo, sempre registrar erro, sempre liberar recurso, sempre atualizar estado). Em pseudocódigo essencial, isso aparece como caminhos que “somem” sem executar ações obrigatórias.
Passo a passo: como decidir entre PARE, CONTINUE e reescrita
Passo 1: identifique o objetivo do laço ou função
Escreva em uma frase: “este laço existe para…” ou “esta função retorna…”. Isso ajuda a justificar interrupções.
Passo 2: classifique o caso que motivou a interrupção
- Filtro local (registro inválido, item irrelevante) → tende a ser
CONTINUE. - Objetivo atingido (encontrou o item, condição final alcançada) → tende a ser
PAREouRETORNE(se estiver em função de busca). - Pré-condição violada (entrada impossível, parâmetro inválido) → tende a ser
RETORNEantecipado.
Passo 3: tente reduzir interrupções com estrutura
Antes de aceitar a interrupção, tente uma reescrita:
- Transformar “vários retornos” em “uma variável resultado + retorno único”.
- Transformar “vários breaks” em “condição do laço + estado”.
- Transformar “vários continues” em “um filtro composto no topo”.
Passo 4: se mantiver a interrupção, torne-a óbvia
- Coloque a condição perto do início do bloco onde faz sentido.
- Evite aninhar
PARE/CONTINUEem múltiplos níveis deSE. - Se necessário, adicione um comentário curto explicando a razão (não o óbvio).
Exemplos comparativos: fluxo confuso vs estruturado
Exemplo 1: busca em lista (PARE) com fluxo confuso
Versão com fluxo confuso (muitos caminhos e estado implícito):
FUNÇÃO EncontrePreco(produtos, idProcurado) RETORNA NUMÉRICO preco <- -1 PARA cada p EM produtos FAÇA SE p.id = idProcurado ENTÃO preco <- p.preco PARE SENÃO SE p.ativo = FALSO ENTÃO CONTINUE SENÃO SE p.preco < 0 ENTÃO preco <- -2 PARE FIM SE FIM SE FIM SE FIM PARA RETORNE precoProblemas típicos:
CONTINUEaparece no meio e compete com outras regras.PAREé usado para “erro” e para “sucesso”, misturando intenções.- O leitor precisa rastrear códigos mágicos (
-1,-2) e por que saem cedo.
Versão estruturada (filtro no topo, intenção separada):
FUNÇÃO EncontrePreco(produtos, idProcurado) RETORNA NUMÉRICO precoEncontrado <- -1 PARA cada p EM produtos FAÇA SE p.ativo = FALSO ENTÃO CONTINUE FIM SE SE p.id = idProcurado ENTÃO SE p.preco < 0 ENTÃO precoEncontrado <- -2 // preço inválido para o item encontrado PARE FIM SE precoEncontrado <- p.preco PARE FIM SE FIM PARA RETORNE precoEncontradoO que melhorou:
CONTINUEvirou um filtro claro e único.PAREocorre apenas quando o objetivo do laço foi mostrar-se inútil continuar: o item foi encontrado (com sucesso ou com erro específico).- O “caminho principal” (verificar id → retornar preço) está mais visível.
Exemplo 2: validação e cálculo (RETORNE) com retornos espalhados
Versão com fluxo confuso (muitos retornos no meio):
FUNÇÃO CalculeDesconto(valor, cupom, cliente) RETORNA NUMÉRICO SE valor <= 0 ENTÃO RETORNE 0 SE cliente.bloqueado ENTÃO RETORNE 0 SE cupom = VAZIO ENTÃO RETORNE 0 SE cupom.expirado ENTÃO RETORNE 0 SE cupom.tipo = "PERCENTUAL" ENTÃO RETORNE valor * cupom.percentual SENÃO SE cupom.tipo = "FIXO" ENTÃO RETORNE cupom.valor SENÃO RETORNE 0 FIM SEQuando isso atrapalha:
- Se futuramente for obrigatório registrar motivo do desconto zero, haverá muitos pontos para alterar.
- O retorno vira “atalho” para tudo, e a função perde um fluxo legível.
Versão estruturada (guard clauses apenas para pré-condições críticas ou retorno único com variável):
FUNÇÃO CalculeDesconto(valor, cupom, cliente) RETORNA NUMÉRICO desconto <- 0 SE valor <= 0 ENTÃO RETORNE 0 FIM SE SE cliente.bloqueado ENTÃO RETORNE 0 FIM SE SE cupom = VAZIO OU cupom.expirado ENTÃO RETORNE 0 FIM SE SE cupom.tipo = "PERCENTUAL" ENTÃO desconto <- valor * cupom.percentual SENÃO SE cupom.tipo = "FIXO" ENTÃO desconto <- cupom.valor SENÃO desconto <- 0 FIM SE RETORNE descontoO que melhorou:
- Retornos antecipados ficaram restritos a pré-condições claras (não faz sentido calcular).
- O cálculo em si tem um único ponto de retorno, facilitando manutenção.
Exemplo 3: abuso de CONTINUE vs reescrita com bloco principal
Versão com fluxo confuso (muitos continues):
PARA cada item EM itens FAÇA SE item = NULO ENTÃO CONTINUE SE item.tipo ≠ "VENDA" ENTÃO CONTINUE SE item.valor <= 0 ENTÃO CONTINUE SE item.cancelado ENTÃO CONTINUE total <- total + item.valorFaturavel(item)FIM PARAVersão estruturada (condição composta e caminho principal):
PARA cada item EM itens FAÇA SE item ≠ NULO E item.tipo = "VENDA" E item.valor > 0 E NÃO item.cancelado ENTÃO total <- total + item.valorFaturavel(item) FIM SEFIM PARACritério prático:
- Se os
CONTINUEsão apenas filtros simples, uma condição composta pode ficar mais legível. - Se a condição composta ficar grande demais, volte ao padrão “filtro no topo” com 1
CONTINUEe agrupe validações em um únicoSE(ou em uma função auxiliar, se existir no seu padrão).
Padrões recomendados (templates) para copiar
Template 1: filtro no topo com CONTINUE
PARA cada x EM colecao FAÇA SE NÃO condicaoParaProcessar(x) ENTÃO CONTINUE FIM SE // caminho principal processe(x)FIM PARATemplate 2: busca com PARE
encontrado <- FALSOresultado <- valorPadraoPARA cada x EM colecao FAÇA SE atende(x) ENTÃO resultado <- extraiaResultado(x) encontrado <- VERDADEIRO PARE FIM SEFIM PARATemplate 3: função com guard clauses + retorno único
FUNÇÃO F(...) RETORNA T SE preCondicaoFalha ENTÃO RETORNE valorPadraoOuErro FIM SE resultado <- ... // processamento principal RETORNE resultadoChecklist de revisão de controle de fluxo
- Há algum
PAREque poderia ser substituído por uma condição de laço mais clara? - Cada
PAREtem uma justificativa objetiva (objetivo atingido ou continuidade inútil)? - Existe mais de um
PAREno mesmo laço? Se sim, eles representam intenções diferentes que deveriam ser separadas? - Existe mais de um
CONTINUEno mesmo laço? Dá para transformar em um único filtro no topo ou em uma condição composta legível? - Algum
CONTINUEestá escondido dentro de vários níveis deSE? Dá para mover a condição para o início do laço? - Uma função tem muitos
RETORNE? Quais são pré-condições (aceitáveis) e quais são atalhos de lógica (suspeitos)? - Há ações obrigatórias que podem deixar de acontecer por causa de
RETORNEantecipado (ex.: registrar motivo, atualizar estado, liberar recurso)? - Os pontos de saída (retornos e quebras) são fáceis de localizar visualmente e entender sem simular muitos caminhos?
- Os nomes das condições deixam claro por que a interrupção ocorre (sem “achou”, “ok”, “valido” genéricos)?