C Comentários
Um comentário é um texto que você escreve dentro do código e que o compilador ignora por completo. Ele não vira parte do programa, não aparece na tela e não deixa nada mais lento: serve só para as pessoas que vão ler o código, inclusive você daqui a um mês. O C tem dois tipos de comentário, e esta aula mostra os dois, os cuidados com cada um e um uso que você vai fazer o tempo todo: "desligar" uma linha para testar.
- O comentário de linha,
//, e desde quando ele existe no C. - O comentário de bloco,
/* … */, que pode ocupar várias linhas ou ficar no meio de uma. - Comentar código para testar, e o truque do
#if 0. - Por que um
/* */não pode ficar dentro de outro. - O que vale a pena escrever num comentário (e o que não vale).
- Os erros reais que os comentários causam.
Os exemplos foram compilados na máquina fictícia da Ana com o comando padrão do guia, gcc -std=c23 -Wall -Wextra, na pasta ~/c.
A ideia: anotações a lápis na receita
Pense numa receita de família, cheia de anotações a lápis na margem: "a vó usava menos açúcar", "não deixar mais de 40 minutos", "esta parte é opcional". A cozinheira lê as anotações, mas não as "cozinha": elas não vão para dentro do bolo. Às vezes a anotação até risca um passo inteiro: "~~acrescentar nozes~~ (o Pedro é alérgico)".
Os comentários são essas anotações. O compilador pula tudo o que está marcado como comentário, como se não estivesse lá.
1. Comentário de linha: //
Duas barras, //, começam um comentário que vai até o fim da linha. Ele pode ocupar a linha inteira ou ficar depois de uma instrução:
// compras.c: mostra a lista de compras da Ana
#include <stdio.h>
int main(void) {
printf("Lista de compras:\n"); // título
printf("- arroz\n");
printf("- feijão\n");
return 0;
}
$ gcc -std=c23 -Wall -Wextra compras.c -o compras $ ./compras Lista de compras: - arroz - feijão
- // compras.c: …
- Linha 1: um comentário que ocupa a linha toda. É comum começar o arquivo dizendo o que ele faz.
- // título
- Linha 5: um comentário no fim de uma linha de código. O
printfantes dele roda normalmente; só o que vem depois das//é ignorado.
Nada dos comentários apareceu na saída, e o programa é exatamente o mesmo que seria sem eles.
// chegou no C99 C99
O // veio do C++ e só entrou no C oficial em 1999. Antes disso, só existia o /* */. Se você compilar como C89/C90 (o C de 1989), o gcc recusa:
$ gcc -std=c89 antigo.c -o antigo
antigo.c: In function ‘main’:
antigo.c:4:5: error: C++ style comments are not allowed in ISO C90
4 | // comentário de linha
| ^
antigo.c:4:5: note: (this will be reported only once per input file)
"Comentários no estilo C++ não são permitidos no ISO C90". Hoje em dia isso quase não acontece: só em projetos muito antigos ou que exigem o C89 de propósito. Com -std=c99 ou mais novo, o // funciona.
2. Comentário de bloco: /* … */
O outro tipo começa com /* e termina com */. Tudo o que fica entre os dois é ignorado, mesmo que ocupe várias linhas:
#include <stdio.h>
/*
* Programa da lista de compras.
* Autora: Ana
*/
int main(void) {
printf("Lista de compras:\n");
printf("- arroz\n");
printf("- feijão\n");
return 0; /* tudo certo */
}
- /*
- Linha 3: abre o comentário.
- * Programa da… / * Autora: Ana
- Linhas 4 e 5: o texto. Os
*no começo de cada linha não são obrigatórios: são só um costume, para deixar claro que aquilo ainda é comentário. - */
- Linha 6: fecha o comentário. A partir daqui, é código de novo.
- /* tudo certo */
- Linha 11: um comentário de bloco curto, no fim de uma linha.
Diferente do //, o /* */ termina onde você mandar, e por isso pode ficar até no meio de uma linha, com código antes e depois:
#include <stdio.h>
int main(void) {
printf("Total: " /* sem centavos */ "R$ 30\n");
return 0;
}
$ gcc -std=c23 -Wall -Wextra meio.c -o meio $ ./meio Total: R$ 30
O comentário sumiu, e os dois textos entre aspas, agora vizinhos, foram juntados (você viu isso em Sintaxe). Funciona, mas comentário no meio da linha atrapalha a leitura; use com moderação.
3. Comentar código para testar
Este é o uso mais prático dos comentários no dia a dia. Quer ver como o programa se comporta sem uma linha, mas não quer apagá-la? Transforme a linha em comentário. Os programadores chamam isso de comentar a linha (e, para voltar, descomentar):
#include <stdio.h>
int main(void) {
printf("Lista de compras:\n");
printf("- arroz\n");
printf("- feijão\n");
/* printf("- chocolate\n"); */
// printf("- sorvete\n");
return 0;
}
$ gcc -std=c23 -Wall -Wextra compras3.c -o compras3 $ ./compras3 Lista de compras: - arroz - feijão « nada de chocolate nem de sorvete
As duas linhas continuam no arquivo, prontas para voltar: basta apagar o // (ou o /* e o */) e compilar de novo. Quase todo editor de código tem um atalho para isso; no VS Code e em muitos outros, é Ctrl + /, que coloca ou tira // nas linhas selecionadas.
Missão: a Ana está de dieta. Comente (não apague!) a linha do chocolate, para ela não aparecer na lista. Use // ou /* */, como preferir.
#include <stdio.h>
int main(void) {
printf("Lista de compras:\n");
printf("- arroz\n");
printf("- chocolate\n");
printf("- feijão\n");
return 0;
}
#include <stdio.h>
int main(void) {
printf("Lista de compras:\n");
printf("- arroz\n");
// printf("- chocolate\n");
printf("- feijão\n");
return 0;
}
4. Um /* */ não pode ficar dentro de outro
Esta é a pegadinha dos comentários de bloco. O */ fecha o comentário na primeira vez que aparece, não importa quantos /* vieram antes. Veja o que acontece quando a Ana tenta comentar duas linhas, e uma delas já tinha um comentário:
#include <stdio.h>
int main(void) {
printf("Lista de compras:\n");
/*
printf("- arroz\n"); /* o arroz acabou? */
printf("- feijão\n");
*/
return 0;
}
$ gcc -std=c23 -Wall -Wextra aninhado.c -o aninhado
aninhado.c: In function ‘main’:
aninhado.c:6:28: warning: ‘/*’ within comment [-Wcomment]
6 | printf("- arroz\n"); /* o arroz acabou? */
aninhado.c:8:6: error: expected expression before ‘/’ token
8 | */
| ^
Siga o compilador, da esquerda para a direita:
- Linha 5:
/*abre o comentário. - Linha 6: o segundo
/*é só texto dentro do comentário (o-Wallavisa: ‘/*’ within comment, "/*dentro de comentário"). Logo depois, o primeiro*/fecha o comentário. - Linha 7: o
printf("- feijão\n");voltou a ser código. - Linha 8: sobrou um
*/solto, que não significa nada para o compilador: erro.
Dizemos que os comentários de bloco não se aninham (não ficam um dentro do outro). O // não tem esse problema: um /* ou um */ dentro de um comentário // é só texto, e um // dentro de /* */ também.
O truque do #if 0
Para desligar um trecho grande que já tem comentários de bloco dentro, há um truque do pré-processador: #if 0 ("se falso") no começo e #endif no fim. Tudo entre os dois some antes da compilação, com comentários e tudo:
#include <stdio.h>
int main(void) {
printf("Lista de compras:\n");
#if 0
printf("- arroz\n"); /* o arroz acabou? */
printf("- feijão\n");
#endif
printf("- café\n");
return 0;
}
$ gcc -std=c23 -Wall -Wextra ifzero.c -o ifzero $ ./ifzero Lista de compras: - café
O #if é explicado na aula Compilação Condicional. Por enquanto, basta saber que #if 0 … #endif funciona como um "comentário que aninha".
5. Dentro das aspas não é comentário
Um // ou um /* dentro de um texto entre aspas é só texto, e aparece na tela normalmente:
#include <stdio.h>
int main(void) {
printf("Site: http://exemplo.com\n");
printf("Isto /* não é */ comentário\n");
return 0;
}
$ gcc -std=c23 -Wall -Wextra string.c -o string $ ./string Site: http://exemplo.com Isto /* não é */ comentário
Ainda bem: senão, nenhum programa conseguiria mostrar um endereço da internet.
6. O que escrever num comentário
Comentar bem é uma arte. A regra principal: o código diz o que está sendo feito; o comentário diz por quê.
| Comentário que não ajuda | Comentário que ajuda |
|---|---|
printf("- arroz\n"); // mostra arroz(repete o que o código já diz) | printf("- arroz\n"); // o integral, não o branco(diz algo que o código não diz) |
return 0; // retorna 0 | return 0; // 0 = deu tudo certo (útil enquanto você aprende) |
| Um comentário antigo que não confere mais com o código (pior do que nenhum) | Ao mudar o código, mude o comentário junto |
Bons lugares para um comentário:
- No topo do arquivo: o que o programa faz, quem escreveu, como compilar.
- Antes de um trecho complicado: a ideia geral, em uma ou duas frases.
- Avisos para o futuro: "cuidado: esta conta não funciona com números negativos". Muita gente marca tarefas pendentes com
// TODO:("a fazer"), e os editores costumam destacar essa palavra.
Nas primeiras aulas, vale comentar mais do que o normal: escrever "o que esta linha faz" com as suas palavras ajuda a fixar. Com o tempo, os comentários ficam mais raros e mais úteis. E pode escrever em português, com acento: o compilador ignora tudo mesmo.
/** … */: comentários de documentação
Em projetos maiores, você vai ver comentários que começam com /** (duas estrelas), com marcações como @param e @return. Para o compilador, são comentários de bloco comuns. Mas ferramentas como o Doxygen leem esses comentários e geram páginas de documentação automaticamente. Eles aparecem antes de funções, um assunto da aula Funções.
Os dois tipos, e qual usar
| Tipo | Vai até | Bom para |
|---|---|---|
// … C99 | O fim da linha | Notas curtas; comentar uma ou poucas linhas de código |
/* … */ | O */ (pode ser várias linhas depois) | Textos longos, como o cabeçalho do arquivo; código que precisa compilar como C89 |
#if 0 … #endif | O #endif | Desligar um trecho grande que já tem comentários dentro |
Qual usar? No dia a dia, // para quase tudo, e /* */ para textos de várias linhas. Muitos projetos antigos e o código do Linux preferem /* */ em tudo; num projeto que já existe, siga o costume dele.
Quando dá errado
error: unterminated comment
$ cat aberto.c
#include <stdio.h>
int main(void) {
printf("Lista de compras:\n");
/* comentário que nunca fecha
return 0;
}
$ gcc -std=c23 -Wall -Wextra aberto.c -o aberto
aberto.c: In function ‘main’:
aberto.c:5:5: error: unterminated comment
5 | /* comentário que nunca fecha
| ^
aberto.c:4:5: error: expected declaration or statement at end of input
4 | printf("Lista de compras:\n");
| ^~~~~~
O que significa: "comentário não terminado". Um /* foi aberto e nunca fechado, então o resto do arquivo inteiro virou comentário, inclusive o return 0; e a } (por isso o segundo erro: o arquivo "acabou" com a main aberta). No editor do guia, o Clang diz unterminated /* comment.
Como consertar: feche o comentário com */ no lugar certo. Editores com cores ajudam muito: tudo o que virou comentário fica da mesma cor.
warning: ‘/*’ within comment e um erro logo depois
O que significa: há um /* */ dentro de outro (seção 4). O primeiro */ fechou o comentário antes da hora.
Como consertar: use // nas linhas que você quer desligar, ou tire o comentário de dentro, ou use #if 0 … #endif.
warning: multi-line comment: uma linha sumiu
$ cat barra.c
#include <stdio.h>
int main(void) {
// pasta: C:\Users\ana\
printf("Esta linha some!\n");
printf("Esta aparece.\n");
return 0;
}
$ gcc -std=c23 -Wall -Wextra barra.c -o barra
barra.c: In function ‘main’:
barra.c:4:5: warning: multi-line comment [-Wcomment]
4 | // pasta: C:\Users\ana\
| ^
$ ./barra
Esta aparece. « cadê a outra linha?
O que significa: em C, uma barra invertida \ no último caractere da linha emenda a linha de baixo nela. O comentário //, que deveria acabar na linha 4, "engoliu" a linha 5. O aviso diz "comentário de várias linhas", e só aparece com -Wall.
Como consertar: não termine um comentário // com \. Acrescente qualquer coisa depois (um ponto, por exemplo) ou use /* */.
C++ style comments are not allowed in ISO C90
O que significa: o programa está sendo compilado como C89/C90 (-std=c89 ou -std=c90), que não tem o //.
Como consertar: compile com uma versão mais nova (-std=c23) ou, se o projeto exige o C89, troque os // por /* */.
Referência rápida
| Escrita | O que faz |
|---|---|
// texto | Comentário até o fim da linha (desde o C99) |
/* texto */ | Comentário até o */; pode ter várias linhas ou ficar no meio de uma |
/** texto */ | Comentário de documentação (lido pelo Doxygen); para o compilador, é um /* */ |
// printf(…); | "Comentar" uma linha: ela fica no arquivo, mas não roda |
#if 0 … #endif | Desliga um trecho inteiro, mesmo com comentários dentro |
/* … /* … */ … */ | Errado: comentários de bloco não se aninham |
\ no fim de um // | Cuidado: emenda a linha de baixo no comentário |
"http://…" | Dentro das aspas, // e /* são texto comum |
Exercícios
1. Comentário de linha
Complete com os símbolos que transformam o resto da linha em comentário:
2. Fechar o bloco
Complete o comentário de bloco:
3. Desligar um trecho
Que linha vem antes do trecho para desligá-lo com o pré-processador (e termina com #endif)?
4. O que aparece na tela com printf("Oi\n"); // printf("Tchau\n");?
5. Por que /* a /* b */ c */ dá erro?
6. Qual comentário é mais útil?
Missão final: o comentário que engoliu o código
Missão: a Ana tentou desligar a linha da sobremesa e criou um problema: há um comentário de bloco dentro de outro. Rode e leia as mensagens. Depois conserte, de modo que o cardápio mostre só arroz, feijão e salada, sem nenhum aviso. (Dica: troque o comentário de fora por //.)
Cardápio do dia: - arroz - feijão - salada
#include <stdio.h>
int main(void) {
printf("Cardápio do dia:\n");
printf("- arroz\n");
printf("- feijão\n");
printf("- salada\n");
/*
printf("- pudim\n"); /* sobremesa de domingo */
*/
return 0;
}
#include <stdio.h>
int main(void) {
printf("Cardápio do dia:\n");
printf("- arroz\n");
printf("- feijão\n");
printf("- salada\n");
// printf("- pudim\n"); /* sobremesa de domingo */
return 0;
}
Resumo
- Comentários são anotações para pessoas: o compilador ignora tudo o que está neles.
//vai até o fim da linha (desde o C99)./* */vai até o*/e pode ter várias linhas.- "Comentar" uma linha desliga o código sem apagá-lo: ótimo para testar.
- Comentários de bloco não se aninham: o primeiro
*/fecha tudo. Para desligar um trecho que já tem/* */, use//ou#if 0…#endif. - Dentro das aspas,
//e/*são texto comum. - Um bom comentário diz por quê, não o que. Ao mudar o código, atualize o comentário.
- Próximo passo: Saída com printf.