17
\$\begingroup\$

Now is the time to show off your abilities to write bad code. I am trying out a new sort of programming puzzle, most similar, I think, to the underhanded C contest. The main difference is that this is not nearly as nefarious: it's just some good clean fun. The goal of the puzzle is to pack as many bugs as you can into a program. The winner of this contest is the one who writes the program with the most bugs per character.

To avoid a huge thread of comments asking for clarification, I should define right now what I consider to be qualifying bugs.

First, a bug is not an error. If it is a problem that can be detected by the interpreter as an error (e.g. mismatched delimeters, badly-formed syntax, acessing a property of a null object, etc.) or if it prevents the program from executing or continuing, it is not a bug. Otherwise, you could type in four characters and the interpreter could list eight syntax errors and you could claim a bug-character ratio of 2.

Second, the bug must not be obviously wrong and a bug is not an easter egg. This is certainly a subjective criterion, but I think essential to this sort of contest. This means that you cannot have conditional code that specifically mangles the code in obvious ways. (Read: use a turing pit language, because nobody will know the difference).

Third, the bug must be plausible. This is subjective, like the one above, but the bug must look like it could have been written by a less-than-meticulous or perhaps ignorant person, or someone who just made a mistake. This includes, for example, off-by-one errors or syntax that is valid and looks correct but causes undesired behavior (say, using square brackets instead of parentheses).

The bug can cause any sort of undesired behavior to the program, including, but certainly not limited to, undesired output for some exceptional cases, have different behavior based on something that is seemingly unrelated (e.g. output displays differently depending on whether the current time ends with an odd or even number of seconds), memory leaks, loss of data, and so on.

Example Problem:

Make a program that displays all of the ASCII characters in ascending order of their numerical value.

Example answer:

Brainf***, 5 chars, 1 bug, 0.2 bug-char ratio

+[+.]

Bug: does not display the ASCII character for 1. Could be fixed by changing to .+[.+].

Ok, I think you should mostly have gotten it by now, here is your puzzle:

Decode a Caesar Cipher and Sort the Words Alphabetically

A caesar cipher is created by taking a series of letters and shifting them n letters over in the alphabet. If it goes all the way to the beginning or end of the alphabet, A comes after Z, and Z comes before A. For example:

Mannequin
Nboofrvjo //Shifted over 1 or -25
Wkxxoaesx //Shifted over 10 -16
Ftggxjnbg //Shifted over -7 or 19

You will be given two inputs (you can get input however is most convenient for you, within reason). The first input is the words, and the second input is the value it is shifted over. Your task is to output the decoded words, and then output the decoded words after they have been sorted alphabetically.

Example (no offense to bad boys, it's just an example):

First input: gtdx wjbfwiji. ljy Gfi hfssty

Second input: 5

First output: boys rewarded. get Bad cannot

Second output: Bad boys cannot get rewarded.

Good luck!

\$\endgroup\$

closed as off-topic by Wheat Wizard, Blue, Kritixi Lithos, Laikoni, user62131 Feb 18 '17 at 19:12

This question appears to be off-topic. The users who voted to close gave this specific reason:

  • "Questions without an objective primary winning criterion are off-topic, as they make it impossible to indisputably decide which entry should win." – Wheat Wizard, Blue, Kritixi Lithos, Laikoni, Community
If this question can be reworded to fit the rules in the help center, please edit the question.

  • \$\begingroup\$ Your example's second input is not -5 ? \$\endgroup\$ – YOU Apr 26 '11 at 6:55
  • \$\begingroup\$ @S.Mark: The input is 5 because the task is to decode the cipher. \$\endgroup\$ – Nabb Apr 26 '11 at 7:26
  • \$\begingroup\$ Ah, I see. @Nabb, Thanks! \$\endgroup\$ – YOU Apr 26 '11 at 7:30
  • \$\begingroup\$ Do we have to support both capital and lowercase letters? \$\endgroup\$ – Joey Adams Apr 26 '11 at 16:21
  • 1
    \$\begingroup\$ @Peter: I've opened a new discussion on meta that concerns this question (among others). Perhaps you would like to comment. \$\endgroup\$ – dmckee Apr 27 '11 at 2:26
14
+50
\$\begingroup\$

Ruby, 136 characters, 7 bugs, ratio = 0.051

o=gets[/\d+/].to_i
$,='\s'
a=gets.split(/ /).map{|w|w.gsub(/[^.,:;?!]/){(97+($&.ord-97-o)%26).chr}}
print a.join,a.sort_by{|a|a[0]}.join
  1. [/\d+/]: negative numbers have their sign removed (a seeming attempt at input validation)

  2. '\s': backlash escapes are only interpreted within double-quoted strings, so this won't generate a space but rather a literal \s

  3. split(/ /): unlike a plain split, this won't split on newlines (so the last word will keep the newline)

  4. /[^.,:;?!]/: this regex excludes punctation, but not uppercase characters, digits or underscores, and, most critically, newlines

  5. 97: anything other than punctation or lowercase letters will get garbled

  6. sort_by{|a|a[0]}: apparently the programmer didn't know about sort, and instead used this ridiculous method, which doesn't sort words starting with the same letter

  7. print: unlike puts, doesn't print a newline between each argument (so the strings come out glued together)

\$\endgroup\$
9
\$\begingroup\$

I'm not going to accept my own answer, but I thought I would show you the ultimate buggy sorting decipherer. The great thing about it is I didn't even plan most of the bugs.

Brainf***: 483 chars, 11 bugs

,------------------------------------------------[>,---------]<[<]>[>[
->]<[<]>-]>[+++++++++.>]<[---------------------------<]>>[[>>>>>>>>>>>
>>>>>>>>>>>>>>>>>>>>>>>+<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<-]>]>[[>>>>>
>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>+<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
<<<<<<<<<<<<<<<<-]>]>[[>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>+<<<<<<<<<<<<<<<
<<<<<<<<<<<<<<<<-]>]>[[>>>>>>>>>>>+<<<<<<<<<<<-]>]++++++++++.>[[>>>>>>
>>>>>>>>>>+<<<<<<<<<<<<<<<<-]>]>[>+++++++++++++++++++++++++++.]

Input:

5 gtdx wjbfwiji. ljy Gfi hfssty 

Output:

bo_sre]arded)getBadcannot
adbo_scannotgetre]arded)

List of bugs:

Input/Display bugs:

  1. Nonpositive numbers or numbers that are more than one digit break the program.

  2. The decipherer does not make Z come before A. It just subtracts the ASCII character value.

  3. Spaces appear as the ASCII ESC (27) character.

  4. If the input is not terminated by a tab, the program does not continue after the input instructions.

  5. The program has to be manually terminated. It will continually display the ESC character until stopped.

  6. The program will break if the input file is not ASCII encoded.

  7. The program does not display the first character of the sorted output.

Sorting bugs:

I implemented the sorting extremely naively.

  1. The program breaks when the number of words does not equal 5.

  2. The program breaks if the number of bytes of input exceeds 60.

  3. The program can only sort correctly if the alphabetical order is identical to the example input.

  4. The program adds extra spaces if any of the words are smaller than the example input and overwrites characters if any of the words are longer.

I have a bug-char ratio of 0.0228. Admittedly, Joey beat me, but I take pride in the fact I only used 8 different characters in my program, and my bugs are much more critical.

\$\endgroup\$
  • 2
    \$\begingroup\$ re]arded? Sounds serious. \$\endgroup\$ – Joe Z. Mar 14 '13 at 15:34
7
\$\begingroup\$

C - 224 characters, 2 bugs, 7 cases of undefined behavior

Edit: My assessment here is incorrect. Overflowing an unsigned integer is, in fact, well-defined in C. Moreover, comparison between signed and unsigned is well-defined too, but the compiler warns because the way it's defined may not be what you think.

m(char**a,char**b){return strcmp(*a,*b);}main(int c,char*v[]){unsigned i,j
,o;o=atoi(v[1])+19;for(i=2;i<c;i++)for(j=0;j<=strlen(v[i])-1;j++)v[i][j]=(
tolower(v[i][j])-o)%26+97;qsort(v,c,sizeof(v),m);for(i=2;i<c;puts(v[i++]));}

Usage:

$ ./a.out 5 gtdx wjbfwiji ljy Gfi hfssty
bad
boys
cannot
get
rewarded

Breakdown:

m(char**a,char**b){return strcmp(*a,*b);}
main(int c,char*v[])
{
    unsigned i,j,o;

    // Undefined behavior if o is assigned negative value.
    o=atoi(v[1])+19;

    // Comparison between signed and unsigned integer.
    for(i=2;i<c;i++)
        // * Bug: if strlen(v[i]) is zero, subtraction will overflow
        //        unsigned value, and loop will have extra iterations.
        // * strlen is implicitly declared.
        //   Undefined behavior if sizeof(void*) != sizeof(int)
        for(j=0;j<=strlen(v[i])-1;j++)
            // tolower expects either an unsigned char casted to an int, or EOF.
            // Thus, undefined behavior if v[i][j] is non-ASCII.
            v[i][j]=(tolower(v[i][j])-o)%26+97;

    // * Bug: Program name and offset are included in the sort.
    //        "./a.out" and "5" both happen to be less than lowercase strings.
    // * qsort is implicitly declared.
    //   Undefined behavior if sizeof(void*) != sizeof(int)
    qsort(v,c,sizeof(v),m);

    // Comparison between signed and unsigned integer.
    for(i=2;i<c;puts(v[i++]));
}
\$\endgroup\$
  • \$\begingroup\$ Good job for breaking the ice. I'll say you have a 0.0402 bug-char ratio. \$\endgroup\$ – Peter Olson Apr 26 '11 at 19:11
  • \$\begingroup\$ @Peter Does that include comments and whitespace/CRLFs? \$\endgroup\$ – Mateen Ulhaq Apr 26 '11 at 21:33
  • \$\begingroup\$ @muntoo No. It is 9/224. \$\endgroup\$ – Peter Olson Apr 26 '11 at 21:37
  • \$\begingroup\$ But shouldn't it output the unsorted text as well? \$\endgroup\$ – Lowjacker Apr 26 '11 at 23:29
5
\$\begingroup\$

JavaScript: 403 characters, 8 bugs, ratio = 0.0199

Although not as bad as C, JavaScript does have design flaws that can lead to bugs, at least when used by a novice (demo with all bugs unfixed).

function W(v){D.write("<input value="+v+">");return D.body.lastChild}function R(J){I=S.indexOf(C=i.value[J]);H=s.value;if(!I){o.value+=C}if(H>0){o.value+=S[I+H]}if(H<0){o.value+=S[I-26-H]}p.value=o.value.split(" ").sort().join(" ");setTimeout("R("+(J+1)+")",99)}D=document;S="ZYXWVUTSRQPONMLKJIHGFEDCBA";S+=S;S+=S.toLowerCase();i=W("input");s=W("shift");W("run type=button onclick=R(0)");o=W("");p=W("")

function W(v) {
    D.write('<input value=' + v + '>');
    return D.body.lastChild;
}

function R(J) {
    I = S.indexOf(C = i.value[J]);
    H = s.value;
    if(!I) o.value += C;
    if(H > 0) o.value += S[I + H];
    if(H < 0) o.value += S[I - 26 - H];
    p.value = o.value.split(' ').sort().join(' ');
    setTimeout('R(' + (J + 1) + ')', 99);
}

D = document;

S = 'ZYXWVUTSRQPONMLKJIHGFEDCBA';
S += S;
S += S.toLowerCase();

i = W('input');
s = W('shift');
W('run type=button onclick=R(0)');
o = W('');
p = W('');

  1. I + H is string concatenation, not addition: undefinedundefinedundefined...
  2. !I is not the correct way to check the return value of .indexOf(), which returns -1 for a non-match: boysVrewardedVV...
  3. Missing else keywords: boys Vrewarded.V Vget...
  4. Will not stop at end of input: ...cannotundefinedundefined...
  5. Won't correctly handle zero shift (e.g. just trying to use the program to sort words)
  6. Will it handle a negative shift? Not correctly.
  7. Double-clicking the button causes a second timeout to start, leading to incorrect output (demo with most of the previous bugs fixed):
    boys rebwoayrsd erde.w agredte dB.a dg ecta nBnaodt cannot.
  8. Output text boxes must be empty when the button is clicked

Also note that this will not work on older versions of IE because it uses an extension to ECMAScript 3 that was only standardized in ES5.

\$\endgroup\$
  • 2
    \$\begingroup\$ Good call on not including lack of IE support in your list of bugs, I would have been quite tempted to add it, and I almost suggested it because it is a very common "bug" in web development, until I thought about whether or not lack of support for Netscape 4 (or any arbitrary browser) would really be a bug. \$\endgroup\$ – Peter Olson Apr 27 '11 at 5:19
  • \$\begingroup\$ Well, lack of support for an obsolete browser certainly hurts no one, but lack of support for a current one would. Unless you're a hip and totally rad Web 2.0 company creating stuff at the bleeding edge of technology until it bleeds out I'd say it is a bug. (Re-read the answer; lack of support for older versions is likely no bug, then. XP is long out of mainstream support and all supported Windows versions have a decent version of IE to run which even comes through automatic updates). \$\endgroup\$ – Joey Apr 27 '11 at 13:57
1
\$\begingroup\$

Python3 184 characters, 4 bugs. Bug ratio 0,0217

import string
d=input()
y=int(input())
print("".join(sorted(d.translate(str.maketrans("".join([chr(x)for x in range(96,123)]),"".join([chr(96+(x+y)%26)for x in range(26)]))).split())))

degolfed:

data = input() #string to convert
y = int(input()) #value to shift
print("".join(
    sorted(
        data.translate(
            str.maketrans(
                "".join([chr(x) for x in range(96,123)]),
                "".join([chr(96+(x+y)%26) for x in range(26)]))
            ).split()
        )))

Example input: gtdx wjbfwiji. ljy Gfi hfssty
Example input: -5
Example output: Gcanxrbmmnsfdsqdv`qcdc.

Known bugs:

  1. Does not convert upper-case characters
  2. Includes ` and converts to/from it.
  3. Does not convert non-ascii characters (åäö)
  4. Does not print spaces.
  5. Can handle, but ignores, punctuation -- I choose not to count this, but if I do my ratio goes to 0.027)

I'm not very good at coming up with bugs deliberately.

\$\endgroup\$

Not the answer you're looking for? Browse other questions tagged or ask your own question.