Napisz najkrótszy program, który generuje najwięcej ostrzeżeń i błędów kompilatora

42

Wyzwanie:

Napisz bardzo krótki program, który po skompilowaniu tworzy najwięcej ostrzeżeń i błędów kompilatora. Można go napisać w dowolnym języku programowania.

Punktacja:

Wynik określa się równaniem: errors_and_warnings_length/code_length. Najwyższy wynik wygrywa.

Przykład:

Program C # classma 5 znaków i generuje 3 ostrzeżenia, co stanowi wynik (1/5) * 3 = 0,6.

EDYTOWAĆ:

Z powodu pewnych nieporozumień programy muszą mieć co najmniej 1 znak długości. W przeciwnym razie uzyskałoby wynik nieskończoności.

MD XF
źródło
17
Chociaż podoba mi się koncepcja, uważam tę metrykę za nieco niepokojącą. Jaki kompilator? Jakie ustawienia (szczególnie w odniesieniu do ostrzeżeń)? Mam na myśli, że gcc -Wall -pedanticbardzo różni się od zwykłego ol` gccróżni się od tccjest prawdopodobnie różni się od jakiegoś innego kompilatora c.
dmckee
2
Po prostu pobierz kompilator w języku rosyjskim lub niemieckim, otrzymujesz DŁUGIE błędy (nie ma
sensu
2
Chciałbym zobaczyć odpowiedzi w językach innych niż C / C ++.
Ken Bloom
4
Spodobałoby mi się, gdyby wyzwaniem było wygenerowanie jak największej liczby różnych błędów
Hannesh
3
Ahem. W przeciwnym razie jego wynik byłby nieokreślony .
wizzwizz4

Odpowiedzi:

94

GCC wynik 2 200 /36 ≈ 4,5 x 10 58

#include __FILE__
#include __FILE__

Właściwie nie skończyłem kompilować tego kodu, ale w oparciu o testy i prostą matematykę powinien on wygenerować łącznie 2 200 #include nested too deeply błędów.

Oczywiście program jest trywialnie rozszerzalny. Dodanie trzeciego wiersza doprowadza wynik do 3 200 /54 ≈ 4,9 x 10 93 . Cztery linie nadają 4 200 /72 ≈ 3,6 x 10 118 , i tak dalej.

Ilmari Karonen
źródło
6
Bardzo sprytna odpowiedź. +1
Książę John Wesley
5
Zgadzam się, że jestem bardzo sprytny, ale liczę to jako 1 błąd („zagnieżdżony zbyt głęboko”), a nie osobny błąd dla każdej linii śledzenia wstecznego.
Kevin
1
@Kevin: Żeby było jasne, powinien generować ten błąd 2 ⁰⁰ razy, raz dla każdej możliwej ścieżki, którą można osiągnąć limit zagnieżdżania. Fakt, że każdy błąd zawiera również 200 wierszy śledzenia wstecznego, sprawia, że ​​dane wyjściowe są jeszcze bardziej szczegółowe.
Ilmari Karonen
1
Hmm Mógłbym przysięgać, gdy wypróbowałem go wczoraj wieczorem gcc za kaucją po 1 błędzie, ale wydaje się, że teraz drukuje więcej. Sprzeciw wycofany. Nawiasem mówiąc, czy 200 ze standardu c?
Kevin
1
@Kevin Per gcc.gnu.org/onlinedocs/gcc-4.8.2/cpp/Implementation-limits.html : „ Nakładamy arbitralny limit 200 poziomów [zagnieżdżonych #include], aby uniknąć niekontrolowanej rekurencji. Standard wymaga co najmniej 15 poziomy ”.
zwolnij
48

C, 0 znaków - Wynik = (1/0) * 1 = Nieskończoność



generuje 1 błąd:

/usr/lib/gcc/i686-pc-linux-gnu/4.7.0/../../../crt1.o: In function `_start':
(.text+0x18): undefined reference to `main'
collect2: error: ld returned 1 exit status

Uwaga: http://ideone.com/xdoJyA

l0n3sh4rk
źródło
49
1/0 jest niezdefiniowana, a nie „nieskończoność”.
Frank
3
+1 Nawet jeśli 1/0 jest niezdefiniowany, jest wyraźnie większy niż jeden podzielony przez dowolną większą liczbę. 0 bierze ciasto.
jnm2
6
@ jnm2 nie jestem tego pewien. 1/0 jest niezdefiniowane i chociaż prawy bok zbliża się + nieskończoność, to wcale nie czyni 1/0 zdefiniowanym.
kaoD
5
Ponieważ domena jest pozytywna, myślę, że to, co powiedziałem, ma sens. Teoria jest fajna, ale myślę, że potrzebujemy tutaj zdrowego rozsądku. Pamiętaj, że najwięcej błędów kompilatora przy najmniejszej ilości kodu. Limit jest oczywisty.
jnm2
15
1,0 / 0,0 = + INF, przynajmniej zgodnie z IEEE 754 :) Musisz po prostu wykonać obliczenia w zmiennoprzecinkowym.
Keith Randall
19

GCC, wynik 5586.6 (i więcej w razie potrzeby)

179 znaków, 1000003 ostrzeżeń / błędów (za pomocą -Wall)

#define E a,a,a,a,a,a,a,a,a,a
#define D E,E,E,E,E,E,E,E,E,E
#define C D,D,D,D,D,D,D,D,D,D
#define B C,C,C,C,C,C,C,C,C,C
#define A B,B,B,B,B,B,B,B,B,B
_(){A,A,A,A,A,A,A,A,A,A}

Oczywiście można to dowolnie rozszerzyć. Na przykład użycie 10 #defines zamiast 5 i długości 20 „wywołań” zamiast 10 doprowadziłoby do wyniku około (20 ** 10) / (179 * 4) = 14301675977.65 (i zajęłoby sporo czasu, aby uruchomić ;)

schnaader
źródło
7
Używając #define X(A) A,A,A,A,A,A,Ai X(X(X(X(X(X(A))))))możesz powielać kod znacznie szybciej.
ugoren
12

GCC dwa razy, 86

22 znaki, 1898 błędów + ostrzeżenia w moim systemie.
Jestem pewien, że to podejście można znacznie ulepszyć, wybierając dłuższe pliki o krótszych nazwach.

#include</usr/bin/gcc>
ugoren
źródło
3
/usr/bin/gdbjest znacznie większy (5,5 mln vs 760 tys.), ale /vmlinuzprzy 5,6 mln może być najlepszym wyborem.
wchargin
12

HQ9 ++, 1 (limit (n + 29) / n)

Poniższe emituje ostrzeżenie Warning: this is not a quinedla każdego Q w kodzie.

QQQQQ...Q
Warning: this is not a quine

Małe jest dobre, prawda? Hmm ...

boothby
źródło
FWIW, to żart. Jeśli to nie było oczywiste.
stoisko do
10

C, .727

11 znaków, 5 błędów, 3 ostrzeżenia, (1/11) * 8 = .727273

m(;){@,x}2

cc -g -Wall    er.c   -o er
er.c:1: error: expected declaration specifiers or '...' before ';' token
er.c:1: warning: return type defaults to 'int'
er.c: In function 'm':
er.c:1: error: stray '@' in program
er.c:1: error: expected expression before ',' token
er.c:1: error: 'x' undeclared (first use in this function)
er.c:1: error: (Each undeclared identifier is reported only once
er.c:1: error: for each function it appears in.)
er.c:1: warning: left-hand operand of comma expression has no effect
er.c:1: warning: control reaches end of non-void function
er.c: At top level:
er.c:1: error: expected identifier or '(' before numeric constant

luser droog
źródło
Zliczam 5 błędów plus 3 ostrzeżenia
Kevin
Przypuszczam, że masz rację. Liczyłem ciągi „error:” i „warning:”.
luser droog
5
Myślę, że wygrasz, jeśli policzymy tylko różne błędy / ostrzeżenia.
ugoren
Jeśli w wierszu polecenia użyto opcji -Werror, ostrzeżenia są przenoszone na błędy. A także, który zastosowany kompilator C wpłynie na liczbę zgłaszanych błędów (lub jeśli -Werror jest dostępny itp.) Można argumentować, że długość wiersza poleceń do wywołania może być liczona jako część długości „programu” ... i każdy wersja kompilatora na każdej platformie jest osobną kategorią. :-)
Dr. Rebmu
8

NASM, wynik 63/40 * 2 ^ 32 ≈ 2,905 * 10 ^ 19

%rep 1<<32
%rep 1<<32
!
%endrep
%endrep

Wyjdzie c.asm:3: error: label or instruction expected at start of line2 ^ 64 razy. Ponownie można to łatwo rozszerzyć na znacznie większe wyniki.

Kopiuj
źródło
2

C ++ 98 (211 bajtów) g ++ - 5 (Ubuntu 5.2.1-23ubuntu1 ~ 12.04) 5.2.1 0151031

Chciałem zobaczyć, jak dobrze sobie radzę w C ++ bez korzystania z preprocesora. Ten program generuje 2139 390 572 bajtów danych wyjściowych, z których większość jest pojedynczym komunikatem o błędzie.

template<int i,class S,class T>struct R{typedef R<i,typename R<i-1,S,S>::D,typename R<i-1,S,S>::D>D;};template<class S,class T>struct R<0,S,T>{typedef S D;};void f(){R<27,float,R<24,int*const*,int>::D>::D&E=4;}

me@Basement:~/src/junk$ ls -l a.C
-rw-rw-r-- 1 me me 211 Apr 27 21:44 a.C
me@Basement:~/src/junk$ g++-5 a.C -fmax-errors=1 2>a.C.errors.txt
me@Basement:~/src/junk$ ls -l a.C.errors.txt 
-rw-rw-r-- 1 me me 2139390572 Apr 27 22:01 a.C.errors.txt

Nie golfowany:

template <int i, class S, class T>
struct R {
    typedef R<i, typename R<i-1,S,S>::D, typename R<i-1,S,S>::D> D;
};
template <class S, class T>
struct R<0, S, T> {
    typedef S D;
};
void f() {
    R<27, float, R<24, int*const*, int>::D>::D &E = 4;
}

Ten program działa poprzez zdefiniowanie rekurencyjnego szablonu struktury R, ​​który zawiera typedef D zawierający dwie kopie R. Daje to nazwę typu, która rośnie wykładniczo, która jest drukowana w całości w komunikacie o błędzie. Niestety, g ++ wydaje się dusić podczas próby wydrukowania komunikatu o błędzie dłuższego niż (1 << 31) bajtów. 2 139 3990 572 bajtów było najbliżej limitu bez przekroczenia limitu. Jestem ciekawy, czy ktoś może dostosować limity rekurencji i typy parametrów, 27, float, 24, int*const*aby zbliżyć się do limitu (lub znaleźć kompilator, który może wydrukować jeszcze dłuższy komunikat o błędzie).

Fragmenty komunikatu o błędzie:

a.C: In function ‘void f()’:
a.C:1:208:  error:  invalid  initialization  of non-const reference of type
‘R<27, float, R<24, R<23, R<22, R<21, R<20, R<19, R<18, R<17, R<16, R<15,
R<14,  R<13, R<12, R<11, R<10, R<9, R<8, R<7, R<6, R<5, R<4, R<3, R<2, R<1,
int* const*, int* const*>, R<1, int* const*, int* const*> >, R<2, R<1, int*
const*,  int*  const*>,  R<1, int* const*, int* const*> > >, R<3, R<2, R<1,
int* const*, int* const*>, R<1, int* const*, int* const*> >, R<2, R<1, int*
const*,  int* const*>, R<1, int* const*, int* const*> > > >, R<4, R<3, R<2,
R<1, int* const*, int* const*>, R<1,
...
int*  const*,  int*  const*>  > > > > > > > > > > > > > > > > > > > > > > >
>::D& {aka R<27, R<26, R<25, R<24, R<23,  R<22,  R<21,  R<20,  R<19,  R<18,
R<17,  R<16,  R<15,  R<14, R<13, R<12, R<11, R<10, R<9, R<8, R<7, R<6, R<5,
R<4, R<3, R<2, R<1, float, float>, R<1, float, float> >, R<2,  R<1,  float,
float>,  R<1,  float, float> > >, R<3, R<2, R<1, float, float>, R<1, float,
float> >, R<2, R<1, float, float>, R<1, float, float> > > >, R<4, 
...
, R<1, float, float>, R<1, float, float> > >, R<3, R<2, R<1, float, float>,
R<1, float, float> >, R<2, R<1, float, float>, R<1, float, float> > > > > >
>  >  >  >  >  >  > > > > > > > > > > > > > > >&}’ from an rvalue of type
‘int’
    template<int    i,class   S,class   T>struct   R{typedef   R<i,typename
R<i-1,S,S>::D,typename  R<i-1,S,S>::D>D;};template<class  S,class  T>struct
R<0,S,T>{typedef                         S                         D;};void
f(){R<27,float,R<24,int*const*,int>::D>::D&E=4;}


                                                        ^
compilation terminated due to -fmax-errors=1.

2 139 3990 572 bajtów / 211 bajtów = 10 139 291,8

Obliczanie nakrętki
źródło
Dlatego zawsze używam STLfilt ... Witamy w PPCG! To świetne pierwsze zgłoszenie!
Mego
1
Niestety wydaje się, że źle zrozumiałem wyzwanie; Wygląda na to, że zgłoszenia są oceniane według liczby komunikatów o błędach, a nie liczby bajtów. Oczywiście mój wpis 1 błędu nie jest zbyt konkurencyjny. Być może moja odpowiedź powinna zostać przeniesiona tutaj
Obliczanie nakrętki
-1

SmileBASIC, 1/1 = 1

A

Generuje błąd Syntax Error in 0:1

12Me21
źródło
SB zawsze generuje tylko jeden błąd na raz, więc to naprawdę jedyna odpowiedź, jaką możesz zrobić.
snail_