Função e parâmetro: quebrar o problema em partes
Decompor um algoritmo grande em funções com nome honesto: parâmetro, argumento, retorno e o teste de cada parte isolada, executado no Node.
Função encapsula uma tarefa com entradas e saída; decomposição transforma um problema grande em tarefas menores que podem ser nomeadas, testadas e combinadas. O ganho principal não é reduzir linhas, mas reduzir quantas regras você precisa manter na cabeça ao mesmo tempo.
O domínio é um boletim que valida notas, descarta a menor, calcula média e classifica a situação. Sem decomposição, cada mudança atravessa um bloco corrido. Com funções, a regra nova encontra um endereço.
Um problema grande é uma pilha de perguntas menores
Antes de código, escreva as perguntas em ordem:
1. As notas são válidas?
2. Qual nota deve ser descartada?
3. Qual é a média das restantes?
4. Qual situação corresponde à média?
5. Como apresentar o resultado?Esse pseudocódigo revela cinco responsabilidades. Uma função pode responder cada pergunta. A lista não executa no Node; ela evita misturar raciocínio e sintaxe cedo demais.
Pense numa cozinha com estações: uma pessoa confere ingredientes, outra prepara, outra monta. A analogia ajuda a enxergar contratos. O limite é que funções não são pessoas e chamar muitas camadas também tem custo de leitura; separar sem motivo cria peregrinação pelo arquivo.
O nome é um teste de responsabilidade
Uma função chamada validarNotasCalcularMediaEClassificar admite três verbos. Separe os resultados:
function calcularMedia(notas) {
return notas.reduce((soma, nota) => soma + nota, 0) / notas.length;
}
function classificar(media) {
return media >= 7 ? 'aprovado' : 'recuperação';
}
const media = calcularMedia([8, 7, 9]);
console.log(media, classificar(media));O nome não precisa narrar a implementação. Ele declara o resultado. Se você troca laço por reduce, calcularMedia continua honesto porque o contrato não mudou.
Parâmetro, argumento e retorno
Na definição, notas é parâmetro. Na chamada, [8, 7, 9] é argumento. 8 é o retorno:
function calcularMedia(notas) {
const soma = notas.reduce((total, nota) => total + nota, 0);
return soma / notas.length;
}
const resultado = calcularMedia([8, 7, 9]);
console.log(resultado);Parâmetro nomeia o papel, não um caso concreto. notas funciona melhor que notasDaAna, porque a função deve servir a qualquer aluno que cumpra o contrato.
Retorno encerra a chamada e entrega um valor. Uma função pode ter vários return, desde que todos representem caminhos compreensíveis. O fluxograma ajuda a enxergar caminhos sem resposta.
Imprimir não é devolver
Uma função que apenas mostra parece correta no terminal, mas não alimenta a classificação:
function calcularMedia(notas) {
const media = notas.reduce((soma, nota) => soma + nota, 0) / notas.length;
console.log(media);
}
const media = calcularMedia([8, 7, 9]);
console.log(`retorno: ${media}`);console.log é saída para observação; return é saída da função para o programa. Corrija trocando o efeito por retorno e deixe a apresentação numa camada externa.
Quatro funções compõem o boletim
Cada parte recebe o mínimo necessário:
function validar(notas) {
return notas.length >= 2 && notas.every((nota) => Number.isFinite(nota) && nota >= 0 && nota <= 10);
}
function descartarMenor(notas) {
const copia = [...notas];
copia.splice(copia.indexOf(Math.min(...copia)), 1);
return copia;
}
function calcularMedia(notas) {
return notas.reduce((soma, nota) => soma + nota, 0) / notas.length;
}
function classificar(media) {
return media >= 7 ? 'aprovado' : 'recuperação';
}
const notas = [6, 8, 7.5, 8];
if (!validar(notas)) throw new RangeError('Notas inválidas');
const consideradas = descartarMenor(notas);
const media = calcularMedia(consideradas);
console.log(consideradas, media.toFixed(2), classificar(media));O resultado 7.83 foi executado no Node. Mais importante, a regra “descartar a menor” mora numa função isolada. Validar não conhece média; classificar não conhece a lista.
Teste cada parte sem executar o programa inteiro
Entradas pequenas dão diagnósticos específicos:
function classificar(media) {
return media >= 7 ? 'aprovado' : 'recuperação';
}
for (const [entrada, esperado] of [[6.9, 'recuperação'], [7, 'aprovado'], [10, 'aprovado']]) {
const obtido = classificar(entrada);
console.log(entrada, obtido, obtido === esperado);
}Se esse teste falha, você não precisa investigar descarte nem soma. Decomposição reduz a área de busca do erro. Depois transforme verificações em testes automatizados no framework do projeto.
Medindo o impacto da regra nova
No bloco corrido, descartar a menor exige encontrar o trecho de soma, copiar a lista e substituir a entrada do laço. Na versão decomposta, o fluxo recebe uma chamada nova e a função concentra a regra. Para não inventar medição, contamos um conjunto explícito de linhas marcadas como alteradas:
const alteracoesVersaoCorrida = [12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22];
const alteracoesVersaoDecomposta = [8, 9, 10];
console.log('corrida', alteracoesVersaoCorrida.length);
console.log('decomposta', alteracoesVersaoDecomposta.length);A contagem pertence a este exemplo controlado, não é lei universal. Uma arquitetura ruim pode ter muitas funções e ainda espalhar a mudança. A evidência útil é a localização: três linhas dentro de uma responsabilidade com nome.
Lista longa de parâmetros é sintoma
Parâmetros demais tornam a ordem frágil:
function resumo({ aluno, media, faltas, turma }) {
return `${aluno} | ${turma} | média ${media} | faltas ${faltas}`;
}
console.log(resumo({ aluno: 'Lia', media: 8, faltas: 2, turma: 'A' }));Um objeto nomeia argumentos e permite mudar a ordem da escrita. Não use objeto para esconder que a função depende de quinze dados desconexos; nesse caso, reveja a responsabilidade e o modelo.
Missão: três funções para a nota final
Crie calcularMediaPonderada, atingiuFrequencia e definirSituacao. Antes de JavaScript, escreva entrada e retorno de cada uma. Teste a borda de média sete e frequência 75%.
const calcularMediaPonderada = (notas, pesos) => notas.reduce((soma, nota, i) => soma + nota * pesos[i], 0) / pesos.reduce((a, b) => a + b, 0);
const atingiuFrequencia = (presencas, aulas) => presencas / aulas >= 0.75;
const definirSituacao = (media, frequenciaOk) => media >= 7 && frequenciaOk ? 'aprovado' : 'recuperação';
const media = calcularMediaPonderada([6, 8], [1, 1]);
console.log(media, atingirFrequenciaSemErro(0));
function atingirFrequenciaSemErro() {
const ok = atingiuFrequencia(75, 100);
return definirSituacao(media, ok);
}Revise dependências depois de decompor. Uma função de cálculo não deve ler variável global de turma nem escrever no terminal. Receba tudo que precisa e devolva resultado. Essa pureza não é obrigação universal, mas facilita teste de lógica porque a mesma entrada produz a mesma saída.
Evite também funções que apenas repassam chamada sem acrescentar nome útil, validação ou composição. Cada camada aumenta distância entre problema e regra. Extraia quando reduz carga mental, concentra mudança ou permite testar uma decisão isolada.
No fluxo principal, leia as chamadas como pseudocódigo: validar, descartar menor, calcular média, classificar, apresentar. Se a sequência não conta a história do requisito, melhore nomes ou fronteiras antes de adicionar comentários extensos.
Contratos de erro fazem parte da decomposição. Decida se uma função lança exceção, devolve resultado discriminado ou retorna ausência. Não misture formas sem motivo; quem chama precisa saber como continuar em cada caso.
Teste a composição além das partes. Funções isoladas podem cumprir contratos incompatíveis: uma devolve reais, outra espera centavos; uma aceita lista vazia, outra divide pela quantidade. Um caso de ponta a ponta pequeno prova que as fronteiras se encaixam.
Quando a regra mudar, anote quais funções precisaram de edição. Se a mudança atravessa todas, talvez a divisão siga etapas técnicas em vez de responsabilidades de negócio. Use essa evidência para refatorar depois que os testes preservarem o comportamento.
O critério é testar cada função isolada e a composição. Depois compare decomposição com recursividade, pratique nos exercícios resolvidos, consulte o guia de lógica e siga a trilha.
Perguntas frequentes
Quantas linhas uma função deve ter?
Parâmetro e argumento são sinônimos?
Dúvidas e comentários
Travou em algum passo? Pergunte aqui — a equipe e outros alunos respondem.
Entrar para perguntarÉ o mesmo login gratuito dos cursos.
Nenhuma dúvida por aqui ainda — a primeira pode ser a sua.
Todo o código deste artigo foi executado em Node v26.3.0, e as saídas exibidas são as reais — como produzimos este conteúdo.
Fontes consultadas
- ECMAScript — Function Definitions — tc39.es
- ECMAScript — Return Statement — tc39.es


