Isso é limitado a Java e C # pela sintaxe que eu acho.
Neste quebra-cabeça de programação, você deve produzir Exception
s que podem ser capturados, mas lançados novamente no final do bloco catch.
try
{
while(true)
try
{
// you are only allowed to modify code between this try { } brackets
}
catch(Exception ex2) { }
}
catch(Exception ex1)
{
// your goal is to reach this catch block by modifying the code ...
// in the inner try block above
// You win if you reach this part and execute on of the following code lines
Console.WriteLine("You won!"); // for C#
// Or
System.out.println("You won!"); // for Java
}
Você pode inserir código livremente antes e depois desse trecho.
O código mais curto para alcançar o catch
bloco externo vence.
code-golf
c#
java
programming-puzzle
user21634
fonte
fonte
Respostas:
C #, 46 (88 incluindo clichê)
O
Abort()
método gera um ThreadAbortException , que é uma exceção especial que é automaticamente relançada no final de cada bloco de captura (a menos queThread.ResetAbort()
seja chamado).fonte
Personagens C # 24
finaliza o bloco try interno antes do pretendido, permitindo-me causar uma exceção fora do bloco try.
fonte
int a=1/0;
?)int a=
lá? Algumas linguagens permitem que você acabou de escrever a expressão1/0
Java, 76 ou 31
Contando apenas as inserções feitas no código, ignorando novas linhas. 76 se você contar tudo o que adicionei, 31 se você excluir a primeira e a última linha, ou seja, apenas a contagem
int a=1/0;try{}catch(Error e){}
.fonte
catch
bloco após o trecho, ele não.Java (OpenJDK 8) ,
6560 bytes (com uma pequena modificação no wrapper)Experimente online!
Requer que ambas as instâncias de
catch (Exception …)
na pergunta sejam alteradas paracatch (Throwable …)
. Em teoria, isso deveria ser mais seguro, não menos, mas permite que essa solução seja possível.Salvei 5 bytes sobre a primeira versão desta resposta usando uma referência de método em vez de uma lambda.
Java 4, 104 bytes (não testado, deve funcionar com o wrapper original)
Experimente online! (o link vai para uma implementação do Java 8, portanto, não funciona)
Usando recursos que foram removidos das versões modernas do Java, é possível resolver até a versão do quebra-cabeça que requer um
Exception
. Provavelmente, pelo menos. (O Java 4 já é muito antigo e não me lembro quais recursos ele contém ou não. Como pode ser visto, havia muito menos recursos no Java naquela época e, portanto, era mais detalhado; não tínhamos lambdas, então eu tive que criar uma classe interna.)Explicações
A maioria das soluções para esta pergunta está em C # (junto com uma solução Java que engana usando colchetes desbalanceados como uma forma de injeção de código e uma solução Perl que também não está em Java). Então pensei que valeria a pena tentar mostrar como esse quebra-cabeça também pode ser resolvido "adequadamente" em Java.
Ambos os programas são efetivamente idênticos (portanto, o fato de o primeiro programa funcionar me dá grande confiança de que o segundo programa também funcionaria, a menos que eu tenha acidentalmente usado um recurso que não seja Java-4;
Thread#stop
foi preterido no Java 5).O
Thread#stop
método de Java funciona, nos bastidores, fazendo com que um lançamento seja lançado no encadeamento em questão. O lançamento planejado para esse fim éThreadDeath
(Error
especificamente, porque as pessoas geralmente tentam capturar exceções e os designers de Java não queriam que isso acontecesse), embora isso permita que você jogue qualquer coisa (ou acostume-se; em algum momento após o término da API) projetados, os designers de Java perceberam que essa era uma idéia incrivelmente ruim e removeram a versão do método que leva os argumentos diretamente). Obviamente, mesmo a versão lançadaThreadDeath
é uma operação bastante arriscada sobre a qual você pode dar poucas garantias (por exemplo, permite solucionar esse quebra-cabeça, algo que "não deveria" ser possível), então você não deve use-o, mas a partir do Java 8, ele ainda funciona.Esse programa funciona gerando um novo encadeamento e solicitando que ele force uma exceção de volta ao encadeamento principal. Se tivermos sorte, isso será feito em um momento em que estamos fora do
catch
bloco interno (não podemos escapar docatch
bloco externo até que o programa termine, porque há um loop em torno dele). Como já adicionamos o loop de maneira conveniente, é economizador de bytes simplesmente usá-lo para permitir a criação de threads, na esperança de que um deles atinja o tempo correto. Isso normalmente parece acontecer em alguns segundos.(Nota do TIO: a versão atual do TIO está bastante inclinada a interromper esse programa no início de sua execução, provavelmente devido a todos os threads que estão sendo criados. Ele pode funcionar no TIO, mas não funciona de maneira confiável, portanto, muitas vezes são necessárias algumas tentativas para obtenha a saída "Você ganhou!".)
fonte
C #
fonte
Perl 5 , 37 ou 36 bytes
Experimente online!
Acontece que essa pergunta se traduz em Perl bem o suficiente para criar um quebra-cabeça interessante também. O
try
equivalente de Perl é chamado (um pouco confuso)eval
e especifica uma exceção definindo@_
como uma exceção se ela ocorreu e a cadeia nula caso contrário. Como tal, umcatch
bloco é implementado via comparação@_
com a cadeia nula.Essa solução funciona criando um objeto (cuja classe é o programa como um todo; você pode usar arquivos Perl arbitrários como classes, como o inverso do Java (onde você pode usar classes arbitrárias como arquivos)). Essa é a
bless[]
parte (bless
normalmente só aparece no fundo dos construtores, como a primitiva que transforma as coisas em objetos em primeiro lugar, mas você pode usá-la diretamente se realmente quiser;[]
é o alocador de memória para o objeto - um construtor de lista, neste case - e como a classe não é fornecida, é considerada a que está sendo executada atualmente). Enquanto isso, damos à nossa "classe" (ou seja, o arquivo principal) um método personalizado de comparação com stringuse overload
, e fazemos com que esse método crie uma exceção (quebrando assim o ciclo e resolvendo o quebra-cabeça); podemos colocar ouse overload
em qualquer lugar e, embora tradicionalmente se encaixe nas outras definições de método e se aproxime da parte superior do arquivo, podemos colocá-lo na lacuna que recebemos e ainda funciona. (Se colocarmos no final do arquivo, poderíamos omitir o ponto-e-vírgula após ele, levando a uma solução de 36 bytes, mas isso é trapaça, pois é indiscutível uma trapaça, pois depende do programa ter um ponto-e-vírgula à direita em primeiro lugar, o que é não é garantido.) Na verdade, é mais curto sobrecarregar a operação stringify e permitir que o Perl gere automaticamente uma comparação de strings a partir disso, do que sobrecarregar diretamente a comparação de strings (porque sobrecarregar alguns operadores também obriga a sobrecarregar outros operadores).Agora, tudo o que precisamos fazer é jogar nosso objeto usando
die
. Eleeval
termina e, quando tentamos comparar$@
com a cadeia nula (para ver se houve uma exceção), a comparação lança outra exceção e escapamos do exterioreval
.fonte