2. • A contest for “esoteric” Ruby programming
– i.e., a Ruby version of IOCCC
– TRICK 2015 is the second contest
Transcendental /ˌtransɛnˈdɛnt(ə)l/
“relating to a spiritual realm” *
「霊的領域に関する」
「世俗を超越した」「超絶技巧」
Imbroglio /ɪmˈbrəʊlɪəʊ/
“an extremely confused, complicated, or
embarrassing situation” *
「極めて混乱した、恥ずかしい事態」
* according to Oxford Dictionaries
4. • Announces the winners of TRICK 2015
– And demonstrates each winning entries
• The winning entries will be published at:
No k!
http://github.com/tric /trick2015/
6. • Write the most Transcendental, Imbroglio Ruby
program
現世利益のない、意味不明な Ruby プログラムを書く
• Illustrate some of the subtleties (and design issues) of
Ruby
Ruby のある種の神秘性 (と仕様バグ) を明らかにする
• Show the robustness and portability of Ruby
interpreters
Ruby 処理系の意外な堅牢性と移植性を示す
• Stabilize the spec of Ruby by the presence of valuable
but unmaintainable code
メンテナンス不能だが価値あるコードを世に放つことで Ruby の仕様を
安定化する
7. • IOCCC: International Obfuscated C Code Contest
• UCC: Underhanded C Contest
• OPC: Obfuscated Perl Contest
• IORCC: International Obfuscated Ruby Code Contest
1990 1995 2000 2005 2010 2015
C
Perl
Ruby
1985
IOCCC 1984-present
UCC 2005-present
OPC 1996-2000
IORCC 2005
TRICK
2013, 2015
8. 1. Your entry must be a complete Ruby program.
2. The size of your program must be <= 4096 bytes in
length. The number of non-space characters must be
<= 2048. The total size of your compressed
submission must be less than ten megabyte in size.
3. You can submit multiple entries, and your team may
consist of any number of members.
4. The entirety of your entry must be submitted under
MIT License.
5. Your entry must bring the judges a surprise,
excitement, and/or laughter.
9. • MRI 2.2 is recommended.
– Other implementations like JRuby are also allowed.
• You can use a gem library.
– We expect such entries to be much more interesting.
– Abusing gem to get around the size limit is discouraged.
• The judges would prefer more stoic, more portable,
and/or more funny entries.
• You are encouraged to examine the previous
winners of TRICK and IOCCC.
• Do not include your identity in your program.
– The judges will keep all entries anonymous during
judgment.
10. Yusuke Endoh (@mametter)
Koichiro Eto (@eto)
Shinichiro Hamaji (@shinh)
Yutaka Hara (@yhara)
Yukihiro Matsumoto (@yukihiro_matz)
Sun Park (@sunleonid)
Hirofumi Watanabe (@eban)
11. eto
– Media Artist.
– Chairman at NicoNicoGakkai Beta.
shinh
– The admin of anarchy golf.
– IOCCC winner.
yhara – The author of Japanese esolang book.
matz – The creator of Ruby.
leonid – The 1st super Ruby golfer.
eban – The 2nd super Ruby golfer.
– The world’s No.1 IOCCC player.
– Advocate for Transcendental programming.mame
12. • A textbook of
Transcendental
Programming
– 超絶技巧プログラミングの
入門書
– ¥2,680 + tax
– Buy it in the branch shop!
19. • TRICK 2015 became an international contest?
– Thank you for all the submitters!
JP
US
BE
PL TW
JP
cf. TRICK 2013
(I’m using 3D pie charts here to obfuscate the precise number of submissions.)
20. • Evaluated each entry with score 1..10.
• Selected 12 entries.
– Top 5 awards:
best entries by average score.
– 7 Judges’ awards:
entries of each judge’s best score
• The judges are allowed to submit their works.
– Of course, the author does not evaluate his own entry.
– In TRICK 2013, the judges won 5 awards out of 10.
– Good News: The judges could win just one award in
this conest.
5th
4th
21. • From here, this talk has a lot of spoilers!
– Exit now if you want to enjoy analyzing the winners.
• The winning entries will be published at:
No k!
http://github.com/tric /trick2015/
25. • A main program is zlib-compressed and
Base64-encoded.
eto award
eval(%w{
require'zlib';
eval(
Zlib::Inflate.inflate(
'<main code in zlib in base64>'.
unpack('m')[0]
)
)
}*"")
27. leonid award
p (?¥A-p +
?¥B-p +
?¥C-p +
?¥D-p +
?¥E-p +
…snip…
?¥X-p +
?¥Y-p +
?¥Z-p).b
.tr 'A-Z', ('_')/~0
BEGIN{class Object ; def
-(o)self end;alias/ -end}
28. • is a one-character string literal
• Do you know escape sequences and ?
• @leonid’s comment
– “Not sure how I would comment on it, since the code by itself
is pretty straightforward on what it's supposed to do.”
leonid award
p "¥C-a" #=> "¥x01”
p "¥C-b" #=> "¥x02”
p "¥C-c" #=> "¥x03”
p "¥M-a" #=> "¥xE1”
p "¥M-b" #=> "¥xE2”
p "¥M-c" #=> "¥xE3”
¥M-X¥C-X
?X
p ?A #=> "A"
p ?¥n #=> "¥n"
30. eban award
Description from Ky.
----------
What if $1 and under junk games take over the world. It would makes you crazy.
We must fight against the future and will soon launch a new fantastic action game named TRICK!!!
Demo
----------
2020-03-25
Criminal 1 :: There he is! Kill the traitor.
Agent 1 :: Cover the man until 006 and 007 rescue us.
Agent 2 :: Okay. Come here!
Criminal 2 :: You must die if you bother us.
How to Get Demo Started if not for path in ENV
-
The command shows ruby version like this:
1.1
next __LINE__
ruby -v
'ruby 2.2.3p173 (2015-08-18 revision 51636) [x86_64-darwin14]'
1.2
next __LINE__
ruby entry.rb
end
31. • A polyglot of Ruby and Markdown!
– Invalid code is skipped in various ways.
– Similar to the Silver award of the previous contest,
but this is more clever.
eban award
Description from Ky.
----------
What if $1 and under junk games take over the world. …
Criminal 1 :: There he is! Kill the traitor.
Agent 1 :: Cover the man until 006 and 007 rescue us.
1.1
next __LINE__
ruby -v
34. • A message is encoded as a time sequence
1. Sorts the time sequence
2. Converts each time to an integer as UNIX time
3. Prints the integers as ASCII characters
• This program is a nice demonstration that
Ruby doesn’t suffer from “the Year 2038 problem.”
mame award
39. shinh award
lines = Array.new
open(__FILE__) do |fl|
fl.each_line{|line|
lines.push(line)
}
m=15+15
n=62
$e = lines.
map do|ln|
sz = ln.size
;
(sz<5?sz+m:sz+n).
chr().swapcase
end.join
$e
eval "#$e"
end
40. • Another Ruby program is hidden in “line lengths”
– Even changing the indent breaks this program!
– BTW: We kind of knew the author was a committer
since it works only on ruby trunk.
shinh award
lines = Array.new
open(__FILE__) do |fl|
fl.each_line{|line|
lines.push(line)
18
23
22
21
puts"……"
p+62
u+62
t+62
s+62
43. • Problem: no room to write “eval”!
• Key idea to solve
– Abuse of symbol array literal
• Detailed solution
– This margin is too narrow to explain.
– Read Chapter 6 of mame’s book!
• shinh discovered the same technique
independently
yhara award
p %I{ foo bar } #=> [:foo, :bar]
47. • SAT solver in 194 bytes!
Finds an assignment to satisfy a given Boolean formula*
• Implementation trick
– Converts a given formula to Regexp matching problem
s.t. the matching is possible iff the formula is satisfiable.
x and !y x=true, y=false
x and !x UNSATISFIABLE
input output
* must be in conjunctive normal form
50. • All-solution Sudoku solver
• A magic for mixing data and code
• Nicely demonstrates a use case of Fiber
– Elegant and hard to understand, at the same time!
class String;def[]*a;$*<<a;b;end
code="pri"[1, 2, 3]+"nt 1"
code="print 1"
$*=[[1, 2, 3]]
String#b ≒ self
52. ;; ;; ;; ;;
;; ;; ;; ;;
;;eval$s =%q[i=1#
eval(%q[ xxxxxxxx
xx xxxx xx xx xxxx xx
xx xxxx xx xx xxxx xx
xxxxxxxx xxxxxxxx
xxxxxxxx xxxxxxxx
xx xx xxxxxxxxxx xx xxxxxxxx
j, t, p=0,[?;]," ev al$s=%qx
[#$s]".split*"";i,j,t=i-j,i+j,(x
[b=?¥s]*j.abs+t).map{|s|r=t.shix
ft ||b;r.gsub!(?;){p.slice!0}if $x
f| |=p>p=p.center(i*i+j*j,?;);r ,x
s=[s,r]if(i*j<0);(b*i.abs+s).ljx
ust(r.size).gsub(b){r[$`.size]|x
|b}}unti l$ f;puts(t)# xx xx
xxxxxxxx xx xxxxxxxxxx xx xx
xxxxxxxx xxxxxxxx
xxxxxxxx xxxxxxxx
xx xxxx xx xx xxxx xx
xx xxxx xx xx xxxx xx
xxxxxxxx x].gsub¥
/x.*|¥s/ ,"")#];;
;; ;; ;; ;;
;; ;; ;; ;;
53. • The author’s remarks:
• Amphisbaena(アンフィスバエナ)
– “A mythical serpent
with a head at each end” *
> geminum caput amphisbaenae, hoc est et a cauda,
> tamquam parum esset uno ore fundi venenum.
> aliis squamas esse, aliis picturas, omnibus exitiale virus.
>
> — GAIUS PLINIUS SECUNDUS, Naturalis Historia 8.85.1
* according to Oxford Dictionaries
56. • One liner with a lot of percents
%%%while eval '_=%%r%%(.)..
.¥1=%%=~[%%%%,,,,,%%%s ?=]
*%%%%%%#"]*%%%%3x+1?%%'.% %
%",%*p(_||=eval($**%%%))
57. • Collatz sequence calculator
– if n is even, n = n / 2
– if n is odd, n = 3n+1
• Example: starting with n = 3
Collatz conjecture: Any n will eventually boil down to 1.
• How is the program great?
– It uses no integer arithmetic, no branch.
ALU:
Arithmetic Logic Unit
算術論理演算装置
103 5 16 8 4 2 1
58. • Example: How to branch if N is even or not
– Note: This is more simplified than the original code.
– Integer arithmetic is even more complicated.
[ ", ", ", ", ]; …even… #"]; …odd…
", ×N
[ ", ", ", ]; …even… #"]; …odd…
String Comment
String
60. big, temp = Array 100000000**0x04e2
srand big
alias $curTerm $initTerm
Numeric
Interrupt
big += big
printout _pi_ finish if $never
init ||= big
$counter ||= 02
…snip…
61. • Piphilology(円周率覚え歌)
– A sentence to memorize the first digits of π
– A famous example
• The program does the same by using Ruby tokens
– Note: lexical tokens ≠ space-separated units
Yes I have a number
3 1 4 1 6. ≈ π
big , temp = Array 100000000 ** 0x04e2
3 1 4 1 5. 9 2 6
62. • Abuse “alias” of global variables
– to access the same value from token of different length
• “ ” is a storage!
– It returns the previous seed.
– It can be used as a latch.
– An assignment always requires
one-length token “=”.
alias $curTerm $initTerm
srand 1
p srand 2 #=> 1
p srand 3 #=> 2
p srand 4 #=> 3
srand
63. • 77 tokens are essential.
• 165 tokens are just no-op fillers.
• The blowup ratio:
Enumerable
Fixnum
Bignum
Math
Complex
Comparable
TrueClass
Dir
Encoding
Data
An example of fillers
165+77
77
≈ 3.14
64. • The winners who are here, come to the stage.
– You have a right to earn applause
• 受賞者でご臨席の方は、前に集まってください
– 拍手喝采をどうぞ
67. • Dishonor: the title of “insane”
• Top five entries will be checked into the Ruby
official repository in “sample” directory
– Ruby 2.3.0 will have them (perhaps)
68. • The winning entries will be published soon at:
• Thank you for all participants!
• See you in the next TRICK 201X!
No k!
http://github.com/tric /trick2015/