Estou executando o ActivePerl 5.14.2 de 32 bits do ActiveState no Windows 7. Eu queria mexer com um gancho de pré-confirmação do Git para detectar programas sendo verificados com erros de sintaxe. (De alguma forma, eu apenas consegui fazer um commit tão ruim.) Então, como programa de teste, anotei isso aleatoriamente:
use strict;
use warnings;
Syntax error!
exit 0;
No entanto, ele compila e executa sem avisos e o nível de erro é zero na saída. Como essa sintaxe é válida?
no indirect
parar aqueles aconteçawhatever / 25 ; # / ; die "this dies!";
Respostas:
Perl tem uma sintaxe chamada "notação indireta de método". Permite
para ser escrito como
Então, isso significa
é o mesmo que
ou
Não é apenas uma sintaxe válida, mas não resulta em um erro de tempo de execução, porque a primeira coisa executada é
exit(0)
.fonte
!exit(0)
não pode mais ser um erro de tipo do que!$x
uma vez que nenhum deles é digitado.new Class
eprint $fh ...
nãoClass->new(...)
e$fh->print(...)
. Eu vou garantir que isso causa uma estranha mensagem de erro, #Não sei por que, mas é isso que Perl faz disso:
Parece que o analisador pensa que você está chamando o método
Syntax
noerror
objeto-... Estranho mesmo!fonte
exit(0)
é avaliado primeiro, fazendo com que o programa saia antes de tentar passar o resultado'error'->Syntax()
.new Class
invés deClass->new()
. Para chamar o métodoSyntax
, aexit
função é executada, para que o erro em tempo de execução nunca ocorra.use strict; use warnings; error->Syntax(! print "hi");
Rende: Sintaxe Ok no perl -MO = Deparse também, masuse warnings
provavelmente deve dizer algo, pois pode descobrir que não está sendo carregado. Em vez disso, gera um erro de tempo de execução "Não é possível localizar o método do objeto ..".O motivo de você não receber um erro é que o primeiro código executado é
Porque você não tinha ponto e vírgula na primeira linha:
O compilador adivinhará (incorretamente) que se trata de uma chamada de sub-rotina com um
not
operador!
acionado. Em seguida, ele executará os argumentos dessa sub-rotina, o que aconteceexit(0)
, quando o programa sai e define o nível de erro como 0. Nada mais é executado. , para que não sejam relatados mais erros de tempo de execução.Você notará que se você mudar
exit(0)
para algo como esseprint "Hello world!"
, receberá um erro:e seu nível de erro será definido:
fonte
>The compiler will guess (incorrectly)
O compilador não pode fazer nada incorretamente.Como observado acima, isso é causado pelo método indireto que chama a notação. Você pode alertar sobre isso:
Produz:
Isso requer o módulo CPAN indireto .
Você também pode usar
no indirect "fatal";
para causar a morte do programa (é isso que eu faço)fonte
Tente o Perl 6 , ele parece atender às suas expectativas mais rapidamente:
fonte
TLDR; Dificilmente
fonte