diff --git a/1994/README.md b/1994/README.md index a09e18efc..9275d00c1 100644 --- a/1994/README.md +++ b/1994/README.md @@ -40,7 +40,7 @@ The ideal 3rd judge would have all of the following: * thorough knowledge of the C language (ANSI and K&R) * thorough knowledge of common C libs (libc, libm, libcurses, ...) - * reasonable written communication skills (able to write *.hint files) + * reasonable written communication skills (able to write README.md files) * appreciation for well-written non-obfuscated code * willing to devote ~4 weekend days in January (starting Jan 96) for judging * located in the San Francisco (California, USA) Bay Area, or diff --git a/1998/dorssel/Makefile b/1998/dorssel/Makefile index 56588a7cb..d9a73cab9 100644 --- a/1998/dorssel/Makefile +++ b/1998/dorssel/Makefile @@ -166,7 +166,7 @@ ENTRY= dorssel PROG= ${ENTRY} # OBJ= ${PROG}.o -DATA= dorssel.hint2 +DATA= dorssel.hint TARGET= ${PROG} # ALT_OBJ= diff --git a/1998/dorssel/README.md b/1998/dorssel/README.md index 8f32efa66..0e37fb2aa 100644 --- a/1998/dorssel/README.md +++ b/1998/dorssel/README.md @@ -10,84 +10,86 @@ make all -### To run +### To run: echo Simple as 123 | ./dorssel echo '.... --- .-- -.. --- . ... .. - -.. --- - .... .- -' | ./dorssel -## Judges' comments +## Judges' comments: - How does the program decide which way to convert? +How does the program decide which way to convert? - What obsolescent feature are we talking about? (No, it's not a - C language feature.) +What obsolescent feature are we talking about? (No, it's not a +C language feature.) - The author suggests that you try to answer the following questions: +The author suggests that you try to answer the following questions: - - Which character in the initializing string is totally irrelevant? - - Which two relevant characters in the initializing string may be - exchanged without altering the behavior? - - Which characters in the initializing string are somewhat irrelevant, - and to what values may they be changed without altering the behavior? - - Which characters may be used to enlarge the initializing string by - one without altering the behavior ? +- Which character in the initializing string is totally irrelevant? - Extra credit: Change the program so that it does not SHOUT IN ALL CAPS. +- Which two relevant characters in the initializing string may be exchanged +without altering the behavior? - You might also want to read the dorssel.hint2 file. +- Which characters in the initializing string are somewhat irrelevant, and to +what values may they be changed without altering the behavior? -## Author's comments +- Which characters may be used to enlarge the initializing string by one without +altering the behavior ? - Usage - ===== - This program converts ASCII to Morse code, and vice versa. +Extra credit: Change the program so that it does not SHOUT IN ALL CAPS. - The program reads in lines from standard input and writes its result to - standard output. The direction of conversion is determined on a per - line basis. Each line must consist of a maximum of 952 characters - followed by a new line character, they must not contain any NUL - characters. Otherwise, some characters may be lost in the conversion. +You might also want to read the [dorssel.hint](dorssel.hint) file. - - Encoding to Morse code: - The program knows the Morse codes for all Latin letters (a-z, case - insensitive) and decimal digits (0-9). Any other characters are - replaced by an ASCII space ' '. Morse code per converted character is - written as a sequence of '.' and '-' characters, each sequence - followed by a space. +## Author's comments: - - Decoding from Morse code: - Morse code should be typed as sequences of '.' and '-' characters, - separated by a space. Extra spaces will be echoed back (to separate - words). Unknown sequences will be converted to a '?' character. +Usage +===== - Notes - ===== +This program converts ASCII to Morse code, and vice versa. - The program assumes both source and execution character sets to be - ASCII. As far as I can tell, the program is conforming and does not - invoke undefined behavior. +The program reads in lines from standard input and writes its result to +standard output. The direction of conversion is determined on a per +line basis. Each line must consist of a maximum of 952 characters +followed by a new line character, they must not contain any NUL +characters. Otherwise, some characters may be lost in the conversion. - Hints - ===== +- Encoding to Morse code: The program knows the Morse codes for all Latin +letters (a-z, case insensitive) and decimal digits (0-9). Any other characters +are replaced by an ASCII space ' '. Morse code per converted character is +written as a sequence of '.' and '-' characters, each sequence followed by a +space. - - Try +- Decoding from Morse code: Morse code should be typed as sequences of '.' and +'-' characters, separated by a space. Extra spaces will be echoed back (to +separate words). Unknown sequences will be converted to a '?' character. + +Notes +===== + +The program assumes both source and execution character sets to be +ASCII. As far as I can tell, the program is conforming and does not +invoke undefined behavior. + +Hints +===== + +Try ./dorssel < dorssel.c | ./dorssel - to see what variables, numbers, and functions are used. (Does a - better job than most C beautifiers). +to see what variables, numbers, and functions are used. (Does a +better job than most C beautifiers). - - Filter your text twice (as in the previous sample) to obtain a version - of your text that can be reversibly morsified, i.e. +- Filter your text twice (as in the previous sample) to obtain a version of your +text that can be reversibly morsified, i.e. ./dorssel | ./dorssel | ./dorssel | ./dorssel - is the same as +is the same as ./dorssel | ./dorssel - - The file "dorssel.hint2" contains all the information needed to - understand this program. For an obfuscated spoiler, try +- The file "dorssel.hint" contains all the information needed to understand this +program. For an obfuscated spoiler, try - ./dorssel < dorssel.hint2 + ./dorssel < dorssel.hint diff --git a/1998/dorssel/dorssel.hint2 b/1998/dorssel/dorssel.hint similarity index 100% rename from 1998/dorssel/dorssel.hint2 rename to 1998/dorssel/dorssel.hint diff --git a/1998/fanf/README.md b/1998/fanf/README.md index 46ec496c0..d86cf524f 100644 --- a/1998/fanf/README.md +++ b/1998/fanf/README.md @@ -13,18 +13,18 @@ make all - NOTE: This may take a while. Some systems may have problems building - this entry because of the system resources it requires. +NOTE: This may take a while. Some systems may have problems building +this entry because of the system resources it requires. -### To run +## To run ./fanf -## Judges' comments - To use: - Enter an expression on standard input. Here are some - sample expressions that you can use: +### To use: + +Enter an expression on standard input. Here are some +sample expressions that you can use: ((\a(\b(\c(d)))) e) @@ -46,74 +46,73 @@ ) ) - This program translares lambda expressions into combinator - expressions. But you do not need to know Lambda Calculus to be - impressed by this program! +## Judges' comments: - See the file: +This program translates lambda expressions into combinator +expressions. But you do not need to know Lambda Calculus to be +impressed by this program! - fanf.lambda +See the file [fanf.lambda](fanf.lambda) for more examples of lambda calculus +source. - for more examples of lambda calculus source. +Notice how large the code grows from the fanf.c into the final +fanftmp2.c C program. Take a look at that final C program again, +can you begin to understand what it is doing? - Notice how large the code grows from the fanf.c into the final - fanftmp2.c C program. Take a look at that final C program again, - can you begin to understand what it is doing? - - Look at the first stage of the C pre-processing: +Look at the first stage of the C pre-processing: cc fanf.c -E > fanftmp1.c - Skip to the bottom of fanftmp1.c (after all of the #include header - stuff ... look for a line of the form: # 2 "fanf.c" near the bottom) - and look at the resulting code. This code, when C pre-processed - will expand into over 342 times the original code (ignoring #include - headers) to produce fanftmp2.c. That program in turn, when compiled - translates a single lambda expression on standard input into - combinator expressions on standard output. +Skip to the bottom of fanftmp1.c (after all of the #include header +stuff ... look for a line of the form: # 2 "fanf.c" near the bottom) +and look at the resulting code. This code, when C pre-processed +will expand into over 342 times the original code (ignoring #include +headers) to produce fanftmp2.c. That program in turn, when compiled +translates a single lambda expression on standard input into +combinator expressions on standard output. - Extra credit question: +### Extra credit question: - What do you have to do to make this program work with an - old non-ANSI C preprocessor? +What do you have to do to make this program work with an old non-ANSI C +preprocessor? -## Author's comments +## Author's comments: - My program is a demonstration of some practical applications of - theoretical computer science. The application it implements is a program - for translating lambda expressions into combinator expressions. +My program is a demonstration of some practical applications of +theoretical computer science. The application it implements is a program +for translating lambda expressions into combinator expressions. - What the program does - ===================== +What the program does +===================== - The syntax of lambda expressions recognised by the program is as - follows: The basic atoms are variables which are single characters other - than backslash or parentheses, e.g. `a' or `b' or `@'. Variables are - combined by function application which is written e.g. `(f a)' which is - the function `f' applied to the argument `a'. Application groups to the - left, so `(f a b c)' is equivalent to `(((f a) b) c)'. Functions are - created from lambda terms which are written in the form `\a(expr)' which - is the function taking argument `a' and having value `expr'. Lambda is - spelt `\' because ASCII isn't good enough. Lambda binds tightly, so - `\a\bcd' is equivalent to `((\a(\b(c))) d)'. Whitespace is ignored. +The syntax of lambda expressions recognised by the program is as +follows: The basic atoms are variables which are single characters other +than backslash or parentheses, e.g. `a` or `b` or `@`. Variables are +combined by function application which is written e.g. `(f a)` which is +the function `f` applied to the argument `a`. Application groups to the +left, so `(f a b c)` is equivalent to `(((f a) b) c)`. Functions are +created from lambda terms which are written in the form `\a(expr)` which +is the function taking argument `a` and having value `expr`. Lambda is +spelt `\` because ASCII isn't good enough. Lambda binds tightly, so +`\a\bcd` is equivalent to `((\a(\b(c))) d)`. Whitespace is ignored. - For example, the identity function, called `I', is written `\x(x)'. A - simple expression is `(I a)' which is equivalent to `(\x(x) a)', which - has the value `a'. Another function called `K' is defined as `\x\y(x)' - and it evaluates as follows: +For example, the identity function, called `I`, is written `\x(x)`. A +simple expression is `(I a)` which is equivalent to `(\x(x) a)`, which +has the value `a`. Another function called `K` is defined as `\x\y(x)` +and it evaluates as follows: K p q -> \x\y(x) p q -> \y(p) q -> p - Another function of interest is `S', defined as `\f\g\x((f x) (g x))'. - My program demonstrates the fact that any lambda expression can be - translated into an equivalent "combinator expression" which involves - only `S', `K', `I' (the combinators), and application, with no - variables or lambda abstractions. In fact, even `I' is unnecessary, - since it is equivalent to `S K K': +Another function of interest is `S`, defined as `\f\g\x((f x) (g x))`. +My program demonstrates the fact that any lambda expression can be +translated into an equivalent "combinator expression" which involves +only `S`, `K`, `I` (the combinators), and application, with no +variables or lambda abstractions. In fact, even `I` is unnecessary, +since it is equivalent to `S K K`: I z -> \a(a) z @@ -125,41 +124,41 @@ -> \x\y(x) z (K z) -> z - The algorithm for translating lambda expressions into combinator - expressions works as follows. There are three forms of lambda expression - to consider: variables, applications, and abstractions. +The algorithm for translating lambda expressions into combinator +expressions works as follows. There are three forms of lambda expression +to consider: variables, applications, and abstractions. - trans `v' -> `v' (variable) - trans `a b' -> (trans `a') (trans `b') (application) - trans `\ab' -> abs a (trans `b') (abstraction) +trans `v` -> `v` (variable) +trans `a b` -> (trans `a`) (trans `b`) (application) +trans `\ab` -> abs a (trans `b`) (abstraction) - There are a further three cases to consider for the body of lambda - expressions, where we need to do the magic that transforms away the - variables. +There are a further three cases to consider for the body of lambda +expressions, where we need to do the magic that transforms away the +variables. - abs a `f x' -> `S' (abs a `f') (abs a `x') - abs a `b' -> `K b' (b != a) - abs a `a' -> `I' +abs a `f x` -> `S` (abs a `f`) (abs a `x`) +abs a `b` -> `K b` (b != a) +abs a `a` -> `I` - E.g. suppose we had combinator expressions for `+' and `3' and we wanted - to see what the combinator expression for doubling 3 looked like: +E.g. suppose we had combinator expressions for `+` and `3` and we wanted +to see what the combinator expression for doubling 3 looked like: - trans `\x(+ x x) 3' - -> (trans `\x(+ x x)') (trans `3') - -> (abs x (trans `+ x x')) `3' - -> (abs x `+ x x') `3' - -> `S' (abs x `+ x') (abs x `x') `3' - -> `S' (`S' (abs x `+') (abs x `x')) `I' `3' - -> `S' (`S' (`K +') `I') `I' `3' - -> `S (S (K +) I) I 3' + trans `\x(+ x x) 3` +-> (trans `\x(+ x x)`) (trans `3`) +-> (abs x (trans `+ x x`)) `3` +-> (abs x `+ x x`) `3` +-> `S` (abs x `+ x`) (abs x `x`) `3` +-> `S` (`S` (abs x `+`) (abs x `x`)) `I` `3` +-> `S` (`S` (`K +`) `I`) `I` `3` +-> `S (S (K +) I) I 3` - We can then check that this evaluates to the expected result: +We can then check that this evaluates to the expected result: - S (S (K +) I) I 3 - -> S (K +) I 3 (I 3) - -> K + 3 (I 3) (I 3) - -> + (I 3) (I 3) - -> + 3 3 + S (S (K +) I) I 3 +-> S (K +) I 3 (I 3) +-> K + 3 (I 3) (I 3) +-> + (I 3) (I 3) +-> + 3 3 It is possible to perform a slightly more compact translation with a couple of simple optimisations. For example, note that `K (a b)' is the diff --git a/1998/fanf/fanf.lambda b/1998/fanf/fanf.lambda index 74ddab607..924d18010 100644 --- a/1998/fanf/fanf.lambda +++ b/1998/fanf/fanf.lambda @@ -6,7 +6,7 @@ -- multi-character identifiers and uses ` instead of \ because that's -- easier to enter inside a Haskell string). It also contains the Haskell -- code I used to translate the lambda calculus into combinators using --- the fully optimising algorithm described in the .hint file. +-- the fully optimising algorithm described in the README.md file. -- -- Tony Finch -- diff --git a/all/README.md b/all/README.md index 04f74ee07..e9e819d9c 100644 --- a/all/README.md +++ b/all/README.md @@ -102,7 +102,7 @@ syntax changing as we did to get old programs to compile on strict ANSI C compilers. Last, read the judges' comments/spoilers on the program. Hints -for `foo.c' are given in `foo.hint'. Often they will contain suggested +for `foo.c` are given in `README.md`. Often they will contain suggested arguments or recommended data to use. If you do gain some understanding of how a program works, go back to @@ -114,12 +114,12 @@ Regarding the source archive: Each sub-directory contains all the entries for a single year. Often the file names match one of the last names of the author. Judges' -hints are given in files of the form ``*.hint''. +hints are given in files of the form `README.md`. You may need to tweak the Makefile to get everything to compile correctly. -Read the hint files for suggestions. +Read the README.md files for suggestions. -The rules for a given year are given in the file named ``rules''. Each +The rules for a given year are given in the file named `rules.txt`. Each archive contains a copy of the rules for the upcoming contest. The following URL is the official archive of the winning entries: diff --git a/faq.html b/faq.html index efcee4c23..15f38e06b 100644 --- a/faq.html +++ b/faq.html @@ -447,9 +447,7 @@ Now, Microsoft makes AT&T look mild and kind in comparison. :-( (IMHO) ). BTW: See the story about the '' -Bill -Gates'' award. :-) +Bill Gates'' award. :-) diff --git a/years.html b/years.html index 438bf9c2a..1d1d6004d 100644 --- a/years.html +++ b/years.html @@ -2261,7 +2261,7 @@ Contest