it-swarm-pt.tech

"Não há nova linha no final do arquivo" aviso de compilador

Qual é o motivo do seguinte aviso em alguns compiladores C++?

Não há nova linha no final do arquivo

Por que eu deveria ter uma linha vazia no final de um arquivo de origem/cabeçalho?

178
LeChuck2k

Pense em alguns dos problemas que podem ocorrer se não houver uma nova linha. De acordo com o padrão ANSI, o #include de um arquivo no início insere o arquivo exatamente como está na frente do arquivo e não insere a nova linha após o #include <foo.h> após o conteúdo do arquivo. Portanto, se você incluir um arquivo sem nova linha no final do analisador, ele será exibido como se a última linha de foo.h estivesse na mesma linha da primeira linha de foo.cpp. E se a última linha de foo.h fosse um comentário sem uma nova linha? Agora a primeira linha de foo.cpp é comentada. Estes são apenas alguns exemplos dos tipos de problemas que podem surgir.


Só queria apontar as partes interessadas para a resposta de James abaixo. Enquanto a resposta acima ainda está correta para C, o novo padrão C++ (C++ 11) foi alterado para que este aviso não seja mais emitido se estiver usando C++ e um compilador em conformidade com C++ 11.

Do padrão C++ 11 pela postagem de James:

Um arquivo de origem que não esteja vazio e que não termine em um caractere de nova linha, ou que termine em um caractere de nova linha imediatamente precedido por um caractere de barra invertida antes que qualquer emenda ocorra, deve ser processado como se um novo caractere adicional caracteres de linha foram anexados ao arquivo (C++ 11 §2.2/1).

207
TJ Seabrooks

A exigência de que todos os arquivos de origem terminem com uma nova linha não escapada foi removida no C++ 11. A especificação agora lê:

Um arquivo de origem que não esteja vazio e que não termine em um caractere de nova linha, ou que termine em um caractere de nova linha imediatamente precedido por um caractere de barra invertida antes que qualquer emenda ocorra, deve ser processado como se um novo caractere adicional caracteres de linha foram anexados ao arquivo (C++ 11 §2.2/1).

Um compilador em conformidade não deve mais emitir este aviso (pelo menos não ao compilar no modo C++ 11, se o compilador tiver modos para diferentes revisões da especificação da linguagem).

42
James McNellis

C++ 03 Standard [2.1.1.2] declara:

... Se um arquivo de origem que não estiver vazio não terminar em um caractere de nova linha ou terminar em um caractere de nova linha imediatamente precedido por um caractere de barra invertida antes que qualquer emenda ocorra, o comportamento será indefinido.

24
Igor Semenov

A resposta para o "obediente" é "porque o C++ 03 Standard diz que o comportamento de um programa que não termina em nova linha é indefinido" (parafraseado).

A resposta para os curiosos é aqui: http://gcc.gnu.org/ml/gcc/2001-07/msg01120.html .

15
Vytautas Shaltenis

Não está se referindo a uma linha em branco, é se a última linha (que pode ter conteúdo) é terminada com uma nova linha.

A maioria dos editores de texto colocará uma nova linha no final da última linha de um arquivo, portanto, se a última linha não tiver uma, haverá o risco de o arquivo ter sido truncado. No entanto, existem razões válidas para você não querer a nova linha, portanto, é apenas um aviso, não um erro.

6
Leigh Caldwell

#include irá substituir sua linha pelo conteúdo literal do arquivo. Se o arquivo não terminar com uma nova linha, a linha que contém o #include que o inseriu será mesclada com a próxima linha.

5
moonshadow

Claro que na prática todo compilador adiciona uma nova linha após o #include. Agradecidamente. - @mxcl

não específico C/C++, mas um dialeto C: ao usar a extensão GL_ARB_shading_language_include o compilador glsl no OS X avisa NÃO sobre uma nova linha ausente. Então você pode escrever um arquivo MyHeader.h com um protetor de cabeçalho que termina com #endif // __MY_HEADER_H__ e você irá perder a linha após o #include "MyHeader.h" com certeza.

2
Jan-Philip Loos

Porque o comportamento difere entre versões C/C++ se o arquivo não terminar com nova linha. Especialmente desagradável é mais antigo C++ - versões, fx em C + + 03, o padrão diz (fases de tradução):

Se um arquivo de origem que não está vazio não termina em um caractere de nova linha ou termina em um caractere de nova linha imediatamente precedido por um caractere de barra invertida, o comportamento é indefinido.

O comportamento indefinido é ruim: um compilador em conformidade com o padrão pode fazer mais ou menos o que deseja aqui (inserir código malicioso ou qualquer outro) - claramente uma razão para o aviso.

Embora a situação seja melhor em C++ 11, é uma boa ideia evitar situações em que o comportamento é indefinido em versões anteriores. A especificação C++ 03 é pior que a C99, que proíbe tais arquivos (o comportamento é então definido).

2
skyking

Eu estou usando c-livre IDE versão 5.0, no meu progrm de 'c + +' ou 'c' eu estava recebendo o mesmo problema.apenas no final do programa ou seja última linha do programa (depois de chaves de função pode ser principal ou qualquer função), pressione enter - linha não. será aumentado em 1. depois de executar o mesmo programa, ele será executado sem erro.

2
divesh

Esse aviso também pode ajudar a indicar que um arquivo poderia ter sido truncado de alguma forma. É verdade que o compilador provavelmente lançará um erro do compilador de qualquer maneira - especialmente se estiver no meio de uma função - ou talvez um erro de vinculador, mas estes podem ser mais enigmáticos e não têm garantia de ocorrer.

É claro que esse aviso também não é garantido se o arquivo for truncado imediatamente após uma nova linha, mas ainda pode detectar alguns casos que outros erros podem perder e fornecer uma dica mais forte para o problema.

0
mwfearnley