SlideShare a Scribd company logo
1 of 47
Download to read offline
Esoteric, Obfuscated, Artistic
Programming in Ruby
Yusuke Endoh (@mametter)
Cookpad Inc.
Bath Ruby Conference 2018
(2018/03/23)
And Now for Something
Completely Different — in Ruby
Yusuke Endoh (@mametter)
Cookpad Inc.
Bath Ruby Conference 2018
(2018/03/23)
Yusuke Endoh (@mametter)
• MRI committer
– Was the release manager for 2.0
– Implemented coverage.so,
keyword arguments, etc.
• Branch coverage (Ruby 2.5)
• Working at Cookpad Inc.
– Cookpad employs
two full-time Ruby committers
(Koichi Sasada and me)
• A recipe sharing platform service
– Monthly Average Users: 90 million
– https://cookpad.com/uk
PR: Cookpad Inc.
• A recipe sharing platform service
– Monthly Average Users: 90 million
– https://cookpad.com/uk
PR: Cookpad Inc.
We're hiring!
HQ is in Bristol
Aim to be No.1 in 100 countries
(Now in 22 Languages and 68 Countries)
Today's Topic
• "Completely different" Ruby programs
– Ruby can do anything!
• Agenda
– 1. Ruby with limited letters
– 2. Funny, self-descriptive Ruby programs
1. RUBY WITH
LIMITED LETTERS
A Ruby program
require "1234567890"
164494982952174876928097944808592
345203368399394864831728762954025
223544083864187912864887414172728
297936126807895282322033562499828
91940559064073941914244494205218
Demo
• "Hello, world!" program by using only
numbers
– You can encode not only Hello world,
but also any Ruby programs
$ ruby H3110.rb
Hello, Bath & Bristol Ruby!
$
Hello world only by numbers
Internal
• Gödel numbering
• Ruby's black magic
Hello world only by numbers
Internal: Gödel numbering
• A technique to encode
any given string to a natural number
– In: a byte array 𝑛1, 𝑛2, 𝑛3, 𝑛4, 𝑛5, …
– Out:2 𝑛1 × 3 𝑛2 × 5 𝑛3 × 7 𝑛4 × 11 𝑛5 × ⋯
– To decode it, use prime factorization
• The gem uses much easier way
– Encoding: str.unpack("H*")[0].hex
– Decoding: [num.to_s(16)].pack("H*")
Hello world only by numbers
Internal: Ruby's black magic
• How to get the number
– It is just placed at the toplevel of code
• My answer:
– ObjectSpace.each_object(Integer)
• Unsure if this is portable, but it works anyway
– Try to decode all enumerated integers,
identify the desired Ruby code, and eval
– See the source code (32 lines) in detail
• https://github.com/mame/1234567890
Hello world only by numbers
How to install
Hello world only by numbers
$ gem install 1234567890_
Don't forget underscore!
(rubygems.org required at least one letter)
Hello world only by "_"
require "_"
____ _ _____ ____ __ ____ ____ __ ___ ____
__ __ _ ______ _____ ___ _ _ ___ _____
______ ____ _ _ ____ _ _ ____ _ ____ __ __
___ _ ______ ___ __ ______ _ ___ _____ __
____ __ ___ ___ ______ ___ _ ______ ___ __
_ ___ _ ______ ___ __ ______ _ ____ __ _
___ ______ ____ ____ __ __ ____ __ ___
____ _ ____ ____ _ _ _ ______ ___ ___ __
_____ ____ __ ____ ___ _____ ___ ____ ___
__ _ ______ ____ _ ______ _____
Demo
• "Hello, world!" program written using
only underscores
$ ruby __hello__.rb
Hello, Bath & Bristol Ruby!
$
Hello world only by "_"
Internal: Base-6
• Encode the Gödel number in Base-6
• Represent each digit with underscores
– Use length (n+1) for digit n
• Why base-6 is chosen?
– To minimize the expected code length:
log 𝑏 126 × ൗ𝑏
2 + 1 + 1
Hello world only by "_"
304313…
____ _ _____ ____ __ ____ …
You can install
$ gem install _
Hello world only by "_"
Summary
• Ruby beats letter limitation
• More?
– See my RubyConf 2017 talk
begin begin begin public begin begin def each
clear rescue begin begin begin end end end
concat begin dup ensure concat begin clear
concat concat concat concat concat concat size
concat begin begin begin size end end end
begin size end ensure begin clear end end end
concat begin dup ensure concat begin clear
begin concat concat size end until hex
concat concat concat concat begin size end
concat concat begin size end rescue upcase
begin concat begin concat size end end
begin size end ensure begin clear end end end
concat begin dup ensure concat begin clear
concat begin concat size end unless begin end
begin concat concat concat begin size end end
@_="_"=~/$/;_=@_+@_;$><<(""<<(_*_*_+@_)*_*_*_<<
((_+@_)*_*_*_+@_)*_*_+@_<<(((_+@_)*_*_+@_)*_+@_
)*_ *_ << ( ( (_+@_ )*_*_+
@_) * _+ + @_) * _*_ <<((((+
_+@_)*_ * _+ + +@_ )*_+@_)*
_++ @_ )* _ ++@_ <<((_*_+@_
)*_ + + + @_)* _*_ <<_*_*_*_*
_<< ( (_ * _ +@_) *_*_*_++@_
)*_<<(((_++@_)*_+@_)*_*_+@_)*_*_+@_<<((_+@_)*_*
_*_*_ +@_)* _<<( ( (_+ +@_
)*_ ++ @_ ) *_+
@_) *_*_*_+ @_<< ( _* _ *_*_*_++
@_) *_+@_<< (((( _ ++ + +@_)*
_*_ ++ @_ )* _ +@_)*_++
@_)*_ +@_<< (((( _+ + @_)*_*_+
@_)*_+@_)*_+@_)*_<<(((_+@_)*_*_*_+@_)*_+@_)*_<<
_*_*_*_*_+@_<<(_*_+@_)*_)#_$`/^|:()[_-|?|_||:`/
Only symbols Only alphabets
2. FUNNY, SELF-DESCRIPTIVE
RUBY PROGRAMS
Self-descriptive ???
eval(s=s=
%w@proc{|
n|z=32.ch
r;k="[#{n
+=1}]";u=
":>==;<==?"[m=n**4
%-15,m+13]||"#{$f=
k}";d="Y.E.#{c=64.
chr}*'')";$f||d<<z
+k;t="eval(s=s=%w#
{c+s=s[0,
334]}#$f#
";25.time
s{|y|m=u.
bytes.map
{|v|t<<s;
(0..[62-v
,2].min).
map{|x|"i
f0zgl11p0
zghuhku744d8hzeg41qtfx7xs7t
wflr".to_i(36)[x+32+v*3-y/5
*44]<1?z*9:t.slice!(0,9)}<<
z}.join.rstrip;y>23&&m[-9,9
]=d;puts(m)}}[1]#pY.E.@*'')
Self-descriptive FizzBuzz
eval(s=s=
%w@proc{|
n|z=32.ch
r;k="[#{n
+=1}]";u=
":>==;<==?"[m=n**4
%-15,m+13]||"#{$f=
k}";d="Y.E.#{c=64.
chr}*'')";$f||d<<z
+k;t="eval(s=s=%w#
{c+s=s[0,
334]}#$f#
";25.time
s{|y|m=u.
bytes.map
{|v|t<<s;
(0..[62-v
,2].min).
map{|x|"i
f0zgl11p0
zghuhku744d8hzeg41qtfx7xs7t
wflr".to_i(36)[x+32+v*3-y/5
*44]<1?z*9:t.slice!(0,9)}<<
z}.join.rstrip;y>23&&m[-9,9
]=d;puts(m)}}[1]#pY.E.@*'')
eval(s=s=%w@proc{|n|z=32.ch
r;k="[#{n+=1}]";u=":>==;<==
?"[m=n**4%-15,m+13]||"#{$f=
k}";d="Y.E.#{c=64.chr}*'')"
;$f||d<<z+k;t="eval(s=s=%w#
{c+s=s[0,
334]}#$f#
";25.time
s{|y|m=u.
bytes.map
{|v|t<<s;(0..[62-v,2].min).
map{|x|"if0zgl11p0zghuhku74
4d8hzeg41qtfx7xs7twflr".to_
i(36)[x+32+v*3-y/5*44]<1?z*
9:t.slice!(0,9)}<<z}.join.r
strip;y>2
3&&m[-9,9
]=d;puts(
m)}}[2]#p
roc{|n|z=
32.chr;k="[#{n+=1}]";u=":>=
=;<==?"[m=n**4%-15,m+13]||"
#{$f=k}";d="Y.E.#{c=64.chr}
*'')";$f||d<<z+k;t="eval(s=
s=%w#{c+s=s[0,334]Y.E.@*'')
eval(s=s=%w@proc{|n|z=32.ch
r;k="[#{n+=1}]";u=":>==;<==
?"[m=n**4%-15,m+13]||"#{$f=
k}";d="Y.E.#{c=64.chr}*'')"
;$f||d<<z+k;t="eval(s=s=%w#
{c+s=s[0, 334]}#$f# ";25.times{|y|m=u. bytes.map{|v|t<<s;
(0..[62-v ,2].min). map{|x|"if0zgl11p0 zghuhku744d8hzeg41
qtfx7xs7t wflr".to_ i(36)[x+32+v*3-y/5 *44]<1?z*9:t.slice
!(0,9)}<< z}.join.r strip;y>23&&m[-9,9 ]=d;puts(m)}}#proc
{|n|z=32. chr;k="[# {n+=1}]";u=":>==;< ==?"[m=n**4%-15,m+
13]||"#{$f=k}";d="Y.E.#{c=6 4.chr}*'' )";$f||d<
<z+k;t="eval(s=s=%w#{c+s=s[ 0,334]}#$ f#";25.ti
mes{|y|m=u.bytes.map{|v|t<< s;(0..[62 -v,2].min
).map{|x|"if0zgl11p0zghuhku 744d8hzeg 41qtfx7xs
7twflr".to_i(36)[x+32+v*3-y /5*44]<1? z*9:t.sli
ce!(0,9)} <<z}.join .rstrip;y >23&&m[-9
,9]=d;put s(m)}}pro c{|n|z=32 .chr;k="[
#{n+=1}]" ;u=":>==; <==?"[m=n **4%-15,m
+13]||"#{ $f=k}";d= "Y.E.#{c= 64.chr}*'
')";$f||d <<z+k;t=" eval(s=s= %w#{c+s=s
[0,334]}# $f#";25.t imes{|y|m=u.bytes. map{|v|t<<s;(0..[6
2-v,2].mi n).map{|x |"if0zgl11p0zghuhk u744d8hzeg41qtfx7x
s7twflr". to_i(36)[ x+32+v*3-y/5*44]<1 ?z*9:t.slice!(0,9)
}<<z}.joi n.rstrip; y>23&&m[-9,9]=d;pu ts(m)}}proc{|n|z=3
2.chr;k=" [#{n+=1}] ";u=":>==;<==?"[m= n**4%-15,Y.E.@*'') [3]
Internal
• Reconstruct self
• Reshape itself
as the next number
– Embedded font data
– Fizzbuzz
– Shaping
• Output the result
• Make it "executable
ASCII-art"
Self-descriptive FizzBuzz
eval(s=s=
%w@proc{|
n|z=32.ch
r;k="[#{n
+=1}]";u=
":>==;<==?"[m=n**4
%-15,m+13]||"#{$f=
k}";d="Y.E.#{c=64.
chr}*'')";$f||d<<z
+k;t="eval(s=s=%w#
{c+s=s[0,
334]}#$f#
";25.time
s{|y|m=u.
bytes.map
{|v|t<<s;
(0..[62-v
,2].min).
map{|x|"i
f0zgl11p0
zghuhku744d8hzeg41qtfx7xs7t
wflr".to_i(36)[x+32+v*3-y/5
*44]<1?z*9:t.slice!(0,9)}<<
z}.join.rstrip;y>23&&m[-9,9
]=d;puts(m)}}[1]#pY.E.@*'')
Quine
• A program that outputs itself
• Trick
– Step 1. Reconstruct self as a string
– Step 2. Print it
• Additional step makes Quine "funny"
eval s="puts('eval s='+s.inspect)"
Self-descriptive FizzBuzz
Embedded font data
Self-descriptive FizzBuzz
• Original data (165 bytes)
• Replace spaces with "0", and "#" with "1"
• Interpret each line as binary number (50 bytes)
• Shorten them by to_s(36) (35 bytes)
### ## ### ### # # ### ### ### ### ### ### ##
# # # # # # # # # # # # # # # # # # ##
# # # ### ### ### ### ### # ### ### ### ## #
# # # # # # # # # # # # # # # # # #
### ### ### ### # ### ### # ### ### # ## # ##
111 110 111 111 101 111 111 111 111 111 111 110 0 00
101 010 001 001 101 100 100 001 101 101 100 101 1 11
101 010 111 111 111 111 111 010 111 111 111 110 0 01
101 010 100 001 001 001 101 010 101 001 100 101 1 10
111 111 111 111 001 111 111 010 111 111 100 110 1 11
1073733623,2905756245,1063256021,2371130133,1063231487
0hr9u5z, 1c20fv9, 0hl19lh, 137pjpx, 0hl0qnz
Executable ASCII-art
• Write a code with no space and backslash
• Wrap it with "eval(%w(" and ").join)"
• You can shape your code as you like
puts"Hello,world!"
eval(%w(puts"Hello,world!").join)
eval(%w(pu
ls "H
el lo
,w or
ld!")*"")#
#=> Hello,world!
Quine-relay
eval$s=%q(eval(%w(B=92.chr;g=32.chr;puts(eval(%q(N=10.chr;n=0;e=->s{Q[Q[s,B],?"].K(N,B+?n)};E=->s{'("'+e[s]+'")'};d=->s,t=?"{s.K(t){t+t}};def~f(s,n)s.K(/.{1,#{n*255}}/m){yield$S=E[$s=$&]}end;Q=->s,t=?${s.K(t){B+$&}};R=";return~0;";V=->
s,a,z{s.K(/(#{B*4})+/){a+"#{$&.size/2}"+z}};C=%w(System.Console~Write);$C=C*?.;$D="program~QR";$G="~contents~of"+$F="~the~mix!g~bowl";$L="public~static";rp=->s,r{v="";[r.!ject(s){|s,j|o={};m=n=0;s.size.times{|i|o[f=s[i,2]]||=0;c=o[f]+=
1;m<c&&(m=c;n=f)};v=n+v;s.K(n,(j%256).chr)},v]};%(fn~mX{Z`x21("{}",#{E["object~QR~extends~App{#{f(%((display~"#{e[%(Zf("1d;s/.//;s/1/~the~sum~of~a~son~and0/g;s/0/~twice/g;s/2/`x59ou~are~as~bad~as/g;s/3/~a~son`x21Speak~your~m!d`x21/g^n#
The~Relay~of~Qu!e.^n#Ajax,~a~man.^n#Ford,~a~man.^n#Act~i:~Qu!e.^n#Scene~i:~Relay.^n#[Enter~Ajax~and~Ford]^n#Ajax:^n#");function[]=f(s);for~i=1:2:length(s),Zf("2%s3",part(dec2b!(hex2dec(part(s,i:i+1))),$:-1:2)),end;endfunction`n#{s,v=rp
["Transcript~show:~'#{d["Z"+E[%(fun~p~n=Z(Int.toSJ~n`x5e"~");p~0;p~0;p~130;List.tabulate(127,p);SJ.map(fn~c=>(p(3+ord~c);Z"-1~0~";c))#{E[%(puts~"#{Q[e[%(echo~'a::=`x7e#{Q[Q["let~s=#{E["!t~mX{Z#{d[E[%(module~QR;!itial~beg!~#{f("let~s=#{
E[%(Module~QR:Sub~MX:Dim~s,n,i,c~As~Object:n=Chr(10):For~Each~c~!"#{d["<?xml#{O="~version='1.0'"}?><?xml-#{I="stylesheet"}~type='text/xsl'href='QR.xslt'?><xsl:#{I+O}~xmlns:xsl='http://www.w3.org/1999/`x58SL/Transform'><xsl:output~metho
d='text'/><#{U="xsl:template"}~match='/'><`x21[CDATA[#{%(sub~f(s$,n)Z(s$);:for~i=1to~n~Z("Y");:next:end~sub:f("#{V[e[%(H,format="#{y="";f("^H{-}{txt}{#{Q["echo~-E~$'#{Q[Q[E[%(with~Ada.Text_Io;procedure~qr~is~beg!~Ada.Text_Io.Put("#{d[%
(!terp:library"afnix-sio"`ntrans~O(n){trans~o(afnix:sio:OutputTerm)`no:H(Byte(+~128~n))}`ntrans~f(v~n){`nO(+(/~n~64)107)`nO(n:mod~64)`nO~v}`ntrans~D(n){if(<~n~4){f(+(*~6~n)9)48}{if(n:odd-p){D(-~n~3)`nf~27~48`nf~36~11}{D(/~n~2)`nf~21~48
`nf~48~20}}}`ntrans~S"#{e[%W[STRINGz:=~226+~153,a:=z+~16 6,b:=a+"2 "+z+~160,c:=b+"8"+z+~165,t:="#!clude<iostream>"+~(10)+"!t"+~(32)+"mX{puts#{d[E[%(class~QR{#$L~void~ma!(SJ[]v){System.out.Z(#{E["H('#{Q[e["implement~ma!0()=Z"+E["BEGIN{
Z#{E[%(echo~'#{%(f(s){System.out.Z(s);}s="389 **6+44 *6+0 0p45*,"; for(c:#{E[(s="#!clude<iostream>`n!t~mX{std::cout<<#{E[%(class~Program{#$L~void~MX{#$C("Qu!e~Relay~Coffee.^n^nIngredients.^n");for(!t~i=9;i++<126;)#$C($"{i}~
g~caffe!e~{i}^n");#$C("^nMethod.^n");foreac h(c h ar~c~!#{E[%((doseq[s(lazy-cat["IDENTIFICATION~DIVISION.""PROGRAM-ID.~QR.""PROCEDURE~ DIVISION."'DISPLA`x59](map~#(str"~~~~^""(.replace~%1"^"""
^"^"")"^"&")(re-seq~#".{1,45}""#{e["(f=(n )- >Array(n+1).jo!~'Y');console.log('%s',#{V[E[%((H-l!e"#{e["impor t~std.stdio;void~mX{H(`x60#{%(method~MX{Z(@"#{d["
[#{%(class~QR:Application{void~f(SJ~con st~s,!t~n){for(Pr!t(s);n;n--)Pr!t("Y");}void~MX{#{f("IO.puts "+E[%((pr!c~"#{e["`nma!(_)->`nio:fH#{d[E['Zf
n("""'+d[?"+"%option~noyywrap`n%%`n%%` n!t~mX{puts#{E["echo~'#{Q[Q[%(~:~A~."#{g*9}"~;~:~ B~A~."~WRITE(*,*)'"~A~;~:~C~B~T`x59PE~."
~'"~CR~;~:~D~S"~#$D"~C~S^"~Z~^"(&"~C~ S^"~#{e[%(Z"#{e["s:=OutputTextUser();Write All(s,#{E[%(Zf"#{e[d[f('set~Z"-";Z'+E
[%(package~ma!;import"fmt";func~mX{ fmt.Pr!t#{E[%(236:j;{119:i;{206i-:i;.48<{ 71+}{[i]^48-*}if}%}:t;"algoritmo~Q
R;!"[195][173]++'cio~imprima("'"0 1314 1"t"/12131"t~6*"/1:1918151:??62714 13/4=3626612/2 /353251215/`x5a0`x5a0R"t"#{e[%(
show~"z=new~java.util.zip.G`x5aI POutp utStream(System.out);z.H('#{ "ma!=putStr"+E["class~QR{#$L ~function~mX{neko.Lib.Z#{E[%(p
rocedure~mX;i:=c:=0;s:=#{E[%(.c lass ~public~QR`n.super~#{$T="ja va/io/Pr!tStream"}`n.method~#$L~ma!([L #{S="java/lang/S"}J;)V~;]`n.
limit~stack~2`ngetstatic~#{S}ys tem/out~L#$T;`nldc~"#{ e[%(class~QR{#$L~void~ ma!(SJ[]v){SJ~c[]=new~SJ[99999],y="",z=y,s=" #{z=t=(0..r=q=126).map{|n|
[n,[]]};a="";b=->n{a<<(n%78+55) %84+ 42};(%(P={0:'[+[]]',m:'((+[])'+(C= "['constructor']" )+"+[])['11']"};for(R~!~B=('`x21[]@`x21`x21[]@[][[ ]]@'+(A="[]['fill']")+"@(
[]+[])['fontcolor']([])@(+('11e20 ')+[])['split']([])@"+A+C+"('return~escape')()("+ A+')').split( '@'))for(E~!~D=eval(G='('+B[R]+'+[])'))P[T=D[E]]=P[T]| |G+"['"+E+"']";for(G='[
',B=0;++B<36;)P[D=B.toSJ(36)]= B<10?(G+='+`x21+[]')+']':P[D]||"(+('"+B+"'))['to'+( []+[])"+C+"[ 'name']]('36')";A+=C+"('console.log(unescape(^"";for(E~!~G =#{E[%(A=Z;A("echo~'k`
x60");[(A("`x60`x60s"`x5e8* "i");for~j=6:-1:0;x=(Int(c)>>j)%2+1;A("`x60"*"kki"[x:x+1 ])end)fo r~c~!~jo!(["Section`x48eader+name:=QR;SectionPublic-ma!<-(";[ "^"$(replace(replace(
s,"Y","YY"),"^"","Y^""))^" .Z;"for~s=matchall(r".{1,99}",#{Q[E["console.log"+Q[E[%(@s=g loba l[#{i=(s=%(`x48AI~1.2`nVISIBLE~"#{"x=sJ.K(#{V[E["changequote(<@,@ >)`ndef!e(p,<@#{"all
:`n`t@echo~'#{d["l!el:99 999;Z#{E["solve~satisfy;output~[#{E[%(.assembly~t{}.method~#$L~ vo id~MX{.entrypo!t~ldstr"#{e["m{{`x21:~x`nqr:~|-`n~:db`x60#{e[s="$Z#{E[%(#!clude< stdio.h>`nmodule~QR{
}implementation{!t~mX_ _attribute__((C,spontaneous)){puts#{E["Zf#{E["echo"+E["#import<stdi o.h>#{ N}!t~mX{puts#{E["Z_sJ"+E["s=toascii#{E["Z#{E["$console:l!e[#{"# $D(output);beg!~H(#
{f((p="eval";%($_="#{ s,v=rp["$_='#{Q[%(<?php~$z=3+$w=strlen($s=#{Q[E["!t~mX{H#{E["(#{?_*11} )dup~=/s(|~~~~~.~~~|)def(#{Q["qr:-H('#{Q[e["!it{#{f (%(Z('cat("')`nfor
~c~!"".jo!(["echo~'s ay~''%s'''^n"%l~for~l~!#{E[d[d["eval$s=%q(#$s)",?'],?']]}.split("^n")]): Z('r=fput(char(%d))'%ord(c))`nZ('end^n")')#),6 ){"Zf#{d[$S,?%]};"
}}}"],?']}').",B]}) {9~7{exch~dup~1~and~79~mul~32~add~exch~2~idiv~3~1~roll~s~exch~2~!dex~exch~p ut~1~sub~dup~6~eq{1~sub}if}repeat~s~=~pop ~pop}forall~=~quit
"]+R}}"]]})*3;echo" ^x89PNG^r^n^x1a^n";$m="";$t="^xc0^0^xff";for($i=-1;++$i<128*$z;$m.=$c--?($w- $c||$i>$z)&&$i/$z<($c<$w?ord($s[(!t)( $c/3)]):$c--%3+2)?
$t[2].$t[$c%3%2].$ t[$c%3]:"^0^0^0":"^0")$c=$i%$z;foreach(array("I`x48DR".pack("NNCV",$w+2,128,8,2 ),"IDAT".gzcompress($m),"IEND")as$ d)echo~pack("NA*N
",strlen($d)-4,$d, crc32($d));).K(B,"`x7f"),?']}';s:g/^x7f/Y/;Z~$_",128..287];s="$_='#{Q[s,c=/['Y]/ ]}';$n=32;$s='#{Q[v,c]}';$s=`x7 es{..}{$a=$&;$b=c
hr(--$n&255);`x7e s/$b/$a/g;}eg;Z";(s+N*(-s.size%6)).unpack("B*")[0].K(/.{6}/){n=$&.to_i~2;((n+14)/2 6*6+n+47).chr}}";s|.|$n=ord $&;substr~unpack(
B8,chr$n-!t($n/32 )*6-41),2|eg;eval~pack'B*',$_).scan(/[~,-:A-z]+|(.)/){p="s++#{$1?"chr~#{$1.ord}+e": $&+?+};"+p};p),1){"'#$s' ,"}}'')end.".K(/[:
;()]/){?`x5e+$&}} ]"]};quit"]};t=num2cell(b=11-ceil(s/13));for~n=1:9m={};for~i=1:141f=@(x,y,n)repmat ( ['Ook'~char(x)~'~Ook' ~char(y)~'~'],[1~a
bs(n)]);m(i)=[f(z =46,63,n)~f(q=z-(i<13)*13,q,i-13)~f(33,z,1)~f(63,z,n)];end;t(x)=m(diff([0~s(x=b= =n )])+13);en d;Zf ('%%s',t{:})"]]+R} }"]]}`n"]};return~
0;}~})]};"]}`x60` n~global~_start`n~_start:mov~edx,#{s.size}`n~mov~ecx,m`n~mov~ebx,1`n~mov~eax,4` n ~!t~128`n~mov ~ebx,0`n~mo v~eax,1`n~!t~12 8`nx:~|`n~}}{{{qr}}
}"]}"call~void~[ms corlib]#{C*"::"}(sJ)ret})]}];"]};quit();",?$].K(?'){"'^''"}}'"}@>)`np"],?&,?& ] },'&(%d+)&',fu nction(s)retur n~sJ. rep('Y',tonu mber(s))end);Z(x)".
K(/[:"]/,":^0")}"` n`x4bT`x48`x58B`x59E~B`x59E)).size+1}x~i8]c"#{s.K(/[^"`n`t]/){"^%02`x58"%$ &. ord}}^00"declare~i32@puts(i8*)d ef!e~i32@mX{ %1=call~i 32@puts(i8*getelemen
tptr([#{i}x~i8],[#{ i}x~i8]*@s,i32~0,i32~0))ret~i32~0})],?#]]]})];");"],"^n")];[for~i=0:2:4; x=(( Int(c)%83-10)>>i)%4+1;A("ski`x60 "[x:x])end~for~c ~!"AG- `x48-`x48Fy.IlD==;=jd
lAy=;=jldltldltl{lAu lAy=jtlldlAyFy=?=jdlAyGFyFyG2AFy>zlAFFBCjldGyGFy>GFy.AGy=G==n`x48==nl ldC=j@=j tlldltldlAut11"];A("'"))]})A+="' +`x21[]+'"+G.charCo deA t(E).toSJ(16);for(A+="
^".replace(/'+`x21[] +'/g,^"%^")))')()",R=0;R<9;R++)A=A.replace(/'.*?'/g,function(B){T= [];for(E=1 ;B[E+1];)T.push(P[B[E++]]);return~T.jo!('+')});conso l e.log('"'+A+'"'))).byte
s{|n|r,z=z[n]||(b[r/7 8];b[r];q<6083&&z[n]=[q+=1,[]];t[n])};b[r/78];b[r]}";!t~i=0,n=0 ,q=0;for(;++n< 126;)c[n]=""+(char)n;for(;i<#{a.size};){q=q*78+(s .charAt(i)-13)%84;if(i++
%2>0){y=q<n?c[q]:y;c[n ++]=z+y.charAt(0);System.out.Z(z=c[q]);q=0;}}}})]}"`n!vokevi rtual~#$T/Zln(L#{S }J;)V`nreturn`n.end~method)+N]};H("DO,1<-#"|| *s);s?while~t:=ord(move(1)
)do{i+:=1;u:=-i;every~0t o~7do{u:=u*2+t%2;t/:=2};H("PLEASE")^(i%4/3);H("DO,1SUB# "||i||"<-#"||((c-u)%2 56));c:=u;};H("PLEASEREADOUT,1^nPLEASEG IVEUP");end)]};}}"].tr(?"+B
,"`x21`x7e")}'.tr('`x7e`x 21','YY^u0022')as~byte[]);z.close()"`n)]}"{"W""w"@j ~1+:j^-~118%1+*}%"/35512 416612G61913@921/17A331513"t'") ;fim')]};})],61){"Zn#$S`n"},?
%]]}"`nquit)]});CloseStream (s);QUIT;"]}")]}"~DUP~A~."~DO~10~I=1,"~.~CR~S "~&A,&"~C~."~10~~~~~~CONTINU E"~CR~S^"~&A)^",&" ~C~0~DO~B~."~&char("~COUNT~.~."
~),&'"~CR~LOOP~S^"~&^"^""~C~S "~end~#$D"~C~A~."~STOP"~CR~A~."~END"~CR ~B`x59E~;~D~),B],?`x21].K(?',%('"' "'))}'"]};}".K(?"){'"34,"'}.K(N){
'"10,"'}+?",?%]+'~""")'],?`x7e] }."]}"))],15){"f(#{V[$S[1..-2] ,'",',');f("']},0);"}}}})}]pq"]}");})} `x60);}"]}"))].K(?`x60,"Yx60"),'#{f
(',')}']})"]}"))["~~~~^"~^".""STO P~RUN."])](Zln( str"message(STATUS~^"~~~~~"(.replace(.replac e(str~s)"Y""YY")"^"""Y^"")"^")")))).re
verse]})#$C($"Put~caffe!e~{(!t)c}~!t o#$F.^n");#$C("Liquify#$G.^nPour#$G~!to~the~bak!g~ dish.^n^nServes~1.^n");}})]};}/****//****
/";t={};b="";L="";n=i=0;D=->n{L<<(n+62) %92+35;D};s.bytes{|c|n>0?n-=1:(t[c]=(t[c]||[]).reject{|j| j<i-3560};x=[];t[c].map{|j|k=(0..90).f!d{|k|n
ot~s[i+1+k]==s[j+k]}||91;k>4&&x<<[k,j]};x=x. max)?(n,j=x;x=b.size;(u=[x,3999].m!;D[u%87][u/87];L<<b[0,u];b[0,u ]="";x-=u)while~x>0;x=4001+i-j;D[x%87][x/87][n-5]
):b<<c;t[c]+=[i+=1]};"#!clude<stdio.h>`nchar*p=#{E [L]},s[999999],*q=s;!t~mX{!t~n,m;for(;*p;){n=(*p-5)%92+(p[1]-5)%92*87;p+=2;if(n >3999)for(m=(*p++-5)%92+6;m--;q++)*q=q[4000-n];else~for(
;n--;)*q++=*p++;}puts(s)#{R}}")]}){s+="00g,";for(m=1;m<256;m*=2)s+="00g,4,:"+(c/m%2>0?"4+":"")+",";f(s);s="4,:,";}f(s+s);for(c:Base64.getDecoder().decode("kaARERE`x58/I0ALn3n5ef6l/Pz8+fnz58/BOf5/7/hE`x58/O`x5azM5mC`x58/Oczm`x5azBPn5+`x
58/OczMznBL/nM5m`x5azBPu++fPPOc5zngnnO`x5azO`x5agnBMGAW7A==")){c=c<0?256+c:c;for(i=0;i++<3;c/=8)f(c%8);f("8*+8*+,");}f("@");).K(?',%('"'"'))}'|sed~-e's/Y/YY/g'~-e's/"/Yq/g'~-e's/.*/Z~"&"^nquit/')]}}"]],?']}');".K(B,?`x5e)]}.replace("`x
5e","Y"));}})]]};}";FORiTO`~UPBtDO`~INTn:=ABSt[i];Z(~(50+n%64)+c+~(50+n%8MOD8)+c+~(50+nMOD8)+b+"`x4a"+a)OD]*"REPR"]}"`ntrans~c~0`ndo{D(Integer(S:get~c))`nf~35~39}(<(c:++)(S:length))`nf~24~149)].K(N,'"&Character'+?'+'Val(10)&"')}");end;
)]+"`nsys.exit~0",B],?']}'",/[^{}]/]}}",35){y<<",`n"+$S;"%s"}}")+y],'",','):f("']}",0))}]]></#{U}></xsl:#{I}>"].K~N,'"&~VbLf~&"'}":s="~~~":For~i=0To~7:s~&=Chr(32-(Asc(c)>>7-i~And~1)*23):Next:#$C(s~&n~&Chr(9)&n~&"~~"):Next:#$C(n~&n~&n):
End~Sub:End~Module)]}`nput=s`nZ`nqa`x21",3){%($H("%s",#$S);)+N}}end~endmodule)],?%]+R}}"]},i=0,t='k';while(s[i])t='^x60.'+s[i++]+t;console.log(t)",B],?`x21].K(?',%('"'"'))}'"^n::=^na")],/[`[`]$]/]}")]};Z"0~0~-1";)],?']}';cr",127..255];
f(%(variable~s=`x60#{s.K(/.{1,234}/){$&.K("`x60",%(`x60+"`x60"+`x60))+"`x60+`n`x60"}}`x60,i;for(i=0;i<129;i++)s=strreplace(s,pack("C",255-i),substrbytes(`x60#{v[0,99]}`x60+`n`x60#{v[99..-1]}`x60,i*2+1,2));Zf("%s",s)),7){"f('%s')`n"%$s.
unpack("`x48*")}}Zf("^n#[Exeunt]");quit)]}")),196){%(Z#$S;)}}}"]});})).gsub(/[!HJKXYZ^`~]/){[B*2,:write,B,:tring,:gsub,"ain()",B*4,:print,g,:in][$&.ord%47%12]})))*"")#_buffer_for_future_bug_fixes_#_buffer_for_future_bug_fixes_#_buffer_
############################################################################## Quine Relay -- Copyright (c) 2013, 2014 Yusuke Endoh (@mametter), @hirekoke #############################################################################)
Quine-relay
• A Ruby code
• that generates Rust code
• that generates Scala code
• …
• that generates REXX code
• that generates the original Ruby code
128 languages
involved
in total
Quine-relay
Quine-relay
• A Ruby code
• that generates Rust code
• that generates Scala code
• …
• that generates REXX code
• that generates the original Ruby code
128 languages
involved
in total
Quine-relay
Demo
https://travis-ci.org/mame/quine-relay
Quine-relay
Internal
– Step 1. Reconstruct self as a string
– Step 2. Wrap Python's Hello world
– Step 3. Print it
Quine-relay
eval s="puts( 'eval s='+s.dump )"
Ruby's Quine
print( "Hello!" )
+Python's Hello world
eval s="puts('print('+('eval s='+s.dump).dump+')')"
↓RubyPython Quine
Internal
• In theory: Repeat this process for 127
languages
• In practical: The naïve approach
explodes the size of intermediate code
– To avoid this problem, it uses many tricks
• compression algorithm
• on-time code generation
• etc.
– See the generator in detail
https://github.com/mame/quine-relay/blob/master/src/code-gen.rb
Quine-relay
Monumental Quine
A column object 3D model data
Ruby code
is inscribed
You can buy it at Shapeways!
https://www.shapeways.com/shops/mametter
Execute
the code
3D
printer
Internal
• The shorter is code, the cheaper ☺
– 3D printing fee: $15 per one line
– The code does not contain complex-glyph letters
("3", "8", "g") to omit them from font data
33
eval(_=%[b='DEILMQTVY';eval((%[a=(-1)EE0.5;f=->EfVf.each_slice(2)Y;c=->wVz=->dVd.mapVd=d.rotate(1)YY
;Q=->k,l,mV((m-k)E(l-k).conT).arQ<0Y;y=[];x=0.99;o,T=w.partitionV|n|d=0;z[n].mapV|k,l|y<<f[k,x,k,1,l
,1,l,x];d+=k.conTElY;d.arQ<0Y;f[o,T,[[0,d=2IEa,d+15,15]],o.map(Dd=:reverse),T.map(Dd),[]].mapV|o,T|T
.mapV|h|z[h].max_byV|u,|u.realY;Y.sort_byV|i,|-i.realY.mapV|h|i,=h;v=0;o.mapV|n|z[n].mapV|x|m,l,E,k=
x;e=(i-m).arQEE2;v<eDD(d=Q[k,m,l])^(Q[k,m,i]^d|(Q[m,l,i]^d))DDo.allMV|n|z[n].allMV|k,l|[i,m,k,l].uni
q.size<4||Q[i,k,l]==Q[m,k,l]||Q[i,m,k]==Q[i,m,l]YYDD(v=e;w=n;T=Ex,m,Eh,i)YY;w[0..-1]=TY;o.mapV|v|t,=
s=z[v];n=->rVk,m,l=r;k=k[2],l,m[2];r[I]=Q[Ek]DDv.allMV|q|z[k].anyMV|k,l|q==k||Q[k,q,l]YYY;z[s].mapV|
k,l,m|l[0,2]=k,m;n[l]Y;(s[I..-1].mapVt=t[1]until(t[I]);k,m=l=t;m[0],k[1]=t;n[m];n[t=k];lY<<t).mapV|k
,m,l|y<<f[k[2],x,l,x,m[2],x]YY;x=1Y;yY;e=0;%[`^Tx52t<^cd,7/w(kabvbEz5arIwIa17.=c'slxr=-'4|e)EwkMI,_^
pvMVhsnME.rLw_k)^tp>+TIEduE45u>mv%^Y=Vny-`zce)k`heIt%`Vzf;c2nk4d|Vp^D_,,|kDDL2r_sDy%%fiMV6cYE)5`,m/k
YQ/;IEezMVv,QchILY|p%%i<vstDt)=M7vLcT>=4Q2(vwael61//<ck>-l67uQ;2Tq,c_'qEIcm1cL;i++2-tYdbenq%pxr;2'Vn
(uDa)n)zf4w)%5vh;ssV5kI;)z;2=+Toe<VL_D0`VLu;ook_y+eT`>IeT9-(i<MiVdd)ib_y+x`s^_u>M1s/mYQvEY`vMxu%Y0u5
7Qaoh2<Mkd'vtkp^zTc`E->Ep+icop_u0%=-zv,omq`Qz/41DV'`f9L5`M'bVxx%/;qLtq12%q:V'9,fD,ovu%qr|+e+rudI`Ir0
5chVd+Q5`II76rY0laT%b(I>Y%EQ1xf^|r,1)%4--zQa'<qxL-7Y0+|'vvbIxso0usv;%.I:pLQbe5a),Vu|91(0EIv^T>c5Dmd:
9-I15%Lp/>>z57^,Th2>%la0;5`dE1<xvrd09^9zz<.t,LpofrTTsQi'u5;Lwp7+zmm`'>qy;f6)||Ikw_0wdMM5<hmn64wbQ_rD
m'>so7b..4qy`nQrz%Vf7Ii^epY(x=|49Lh(=>sI_sbofb7|qM,unaD%^i:|;_tEEnb-DDt`t%I2h;0x5f^yhs,pbLf+m^e>yqzQ
'%::|^=,5-b=^_1x1se`kp,%wq4T%;'E.:Dsp_V-0||,)=;.a|<%0QY:;t:fEmk:4|_%o-.:aooq/6mThdvz4`uQqY1r'em.5'z1
2p7e%%pp6ebMM,m`5QpYx'd`,`6a4T)6Q.k.E.YsdiE^ox9pyrsr%|(kfn=y9q`6;=V<z%9(0cf^yp=:Irw-c/y>%iie%)y-1i(y
'V-n^uTva%l0Q>,yz;E0:LbV'eTb6MIb``Da.__ihbacxY|fc6>pTtl;ivVt,q>/%w,=hnI+i90>10u59te,Ildw4p94x`iwvs`f
+^)w1M>%wf^].bytesV|i|e=eE59+(i-5)%L9Y;Q=->iVk=e%i;e/=i;kY;d=VI2=>c[[]]Y;54.upto(1I0)V|h|d[h%L9+I7]=
c[(0..Q[5]).mapVl=o=T=[];n=0;(-2..Q[17]).mapV[l=Q[2],o=Q[1I]+Q[21]Ea+1+a]Y.flat_mapV|m,n|E,(h,)=[[o,
l],[(o+o=n)/2,0]][0..lDl=m]Y.mapV|o,l|n=l<1M((n==0ML:1).upto(L)V|k|T<<h+kE(n-h)/4+kEkE(o-2En+h)/64Y;
h=o;0):oY;TY]Y;n=[];m=0;v=aEE0.04;z=15/v.arQ;w=-0.2I;h='eval(_=%['+_+'])';h.tr(b,']+b+%[').bytesV|o|
q=-w+s=wEm+=1;r=vEp=vEEmEz;d[o].mapV|v|n<<v.mapV|v,l|T,k=v.rect;[(p+(r-p)ET/=15)El,q+wET-k]YY;m<101D
Dn+=[f[p,q,r,s,E[r,0]E(m/100),r,2,p,2],f[p,2,r,2,k=rET=0.976,2,TE=p,2],f[T,2,k,2,k,x=-715,T,x],f[T,x
,k,x,r,x,p,x],f[p,x,r,x,r,s-l=690,p,q-l,E[p,x+2]E(1/m)]];Y;T=VY;k=VY;l=''<<I2;m=n.mapV|i|(p,q),(r,s)
,(t,u)=Ei;p-=r;r-=t;Mf+l+i.mapV|m|[[T,:v,Em],[k,:vn,(rE(q-s)-pE(s-u))Ea,(p.conTEr).imaQ]].mapV|T,o,p
,w|T[[o,E(p.rect<<w).mapV|p|(pE500).round/z/10Y]El]||=T.size+1YE'//'YElY;o=''<<I5;puts(%(Q%squine')%
l,o+%V'+(eval(%[Y+h+%V]);exit);'Y,T.keys,k.keys,m,o+M');]).tr(b,'%)27>fiz|'.tr('x%-|','%-'<<125)));'
[[[ Monumental Quine (c) 2015 Yusuke Endoh -- tested with ruby 2.2.1 -- built on 2015/04/01 ]]]'])
Embedded TrueType Font Data
+ Renderer
Triangulation Algorithm
for Font Polygons
3D Model Generator
Monumental Quine
15 quzzle
• An interactive Quine
eval$s=%w[b=0 x4160ab7de523 f8c9;i=(m=0.. 15).find{|i|1
>b&m=15<<4*i} ;t=m|n=m<<4*o =("AdABrBlBAu A"=~/(.)#{ARG
V*''}¥1/||04| |0)-4;(n<1||n >1<<64||[255< <12]&[t>>040|
|___________9 |__________12 |___________8 |__________15
|0,t>>16,t]!= [])?t=0:i+=o; ;s="eval$s=%% w[b=0x%016x"%
(b^=t.&b|m&b> >o*4)+$s.gsub (/(¥|_+¥d+)+/ ,'')[/;.*/]+"
]*''||0"<<92| |1;z=s=s.scan (/.{13}/);3.t imes{|j|s[(i|
|___________3 |___________2 |___________5 |__________14
|0)/4*8+i+j*4 ,0]=m=(z=32.c hr)*13};c=b;4 .times{puts((
0..3.times{pu ts((s.slice!( 0,4)*z).rstri p)}).map{j=c%
16;c/=16;;(0| |0)<(j)?"|"+j .to_s.rjust(1 2,"_"):m}*(z|
|__________13 |___________7 |__________11 |__________10
|0),z)};b==0x fedcba9876543 21&&("%b"%"1t
v7c1th0wylel7 3ba35knw3t".t o_i(36)).tr("
01",".#").sca n(/.{25}/){pu ts$&}]*''||0¥
|___________6 |___________1 |___________4
Tiq-taq-toe
• The world's first quine containing AI
s="n=' '[0,2]
d|=1<< $*[0].
to_i-1 ;m,i=[
f=proc {|b|a=
[];[73 ,7,84,
273,56 ,146,"
proc{| t|[t*=
"",s].map{|u|u.gsub!(35.chr,"")};d=0000000;eval(s+t)}[
%w(448,292].find{|m|b&m==m}?1:9.times{|i|b&(513<<i)<1&
&a<<[-f[1<<i|b>>9|b<<9][0],i]}&&a.min||0}][0][d];s='s=
"'+s.s plit*'
'+'"pr oc{|t|
[t*="" ,s].ma
p{|u|u .gsub!
(35.ch r,"")}
;d=0%0 6o;eva
l(s+t) }[%%w(
'%d|=$*[0]?0:512<<i;s<<t+")]";27.times{|y|i=y/10;y%=10
;puts(y>6?s.slice!(0,54):(0..4).map{|x|x&1>0?(i+=3;s.s
lice!(0,6)):62[y]<1?n*7:n+(y*5-5...y*5).map{|j|1105[j-
7]<1&& d[i]|d
[i+9]> 0&&~j&
5981[j /2]^d[
i]>0?3 5.chr*
2:n;}* ""+n}*
"")}|| __(C).
YEndoh 2009)]
qng and qif
 qng
– A png image file
containing
Ruby code that
produces this image
 qif
– A gif version
Lipogram Quine
format= %%->{#({#){#.{#0{#1{#2{#3{#4{#5{#6{#7{#8{#9{#h{#k{#l{#p{#v{#w{#<{#*{#a{#b{#c{#d{#e{#f{;
t=->s,x,y{->&u{u[s,x,y]}[&:tr]};z="!-{";->&u{u[y="().0123456789hklpvw<*abcdef¥¥",t["m~i",",-~",
"$-{"]+t["$",z,"i-{"],t[t["YQUO@g=`@W='@ABCDEFGHIJKLMNOPQRSTUVWXYZ';g=^YQUO@g=`@^+g+^AA^;Y=?=;n
=Y+OoWUO_Q UriUVOYsTY+Y;x=- >s{sBVyt Ys};q,=n[u =^ZormUt^]?@u
=ZormUtA?[ DC,TFEBBDEI]-x[u +?`]:x[W +?`]-x[y]: n=~/=Z?o?r?m?
U?t?=/?x[u ]-x[$&]:Y;z='ZormUt= C``->{H{Dt=- >s,x,y {Js,x, y]}[&: tr]};z=^!-{
^;Jy=^I^,t [^m~iK,-~K$-{^]+t[^$ ^,z,^i-{^],t [t[^EK C^+$/, ^^],^G ^,t[^qntuz|
yKm-|^,z]+ t[^;jmnrxy>,K&-{K$-{ ^]+t[^o;tK/- {^,z]] ]}[&Jt [^xjsi K&-{^,z]]}[
&:to_sym]] }[]`;DYQUO^@YQUO@@`R ``SS`R`F`T`` `ABPUW N@``MT `AAA^' BgsuV@/[C-L
]/A{[FEBWM r,$/,gBtr@'`^'+W,j=L IBWMrSSLGSSI GSSGHSSL CA,TgB unPUWN@^MT^
A,j,?#+WBW MUrsT^{#^,W+LEBWMrTE ,^->&u{u[^,' ^,^'][YQ UO$&]} ;GGBtimYs{|
y|Print@@@ CBBLGABmUP{|x|^qZXzm uDHjtVOCuVnO ooCYHWIJyrnonDmE GtijRU oNFxGWXxuOm
CmIEYRXsgZ EgqOKQMGHJOKQnYuuVYy IrCEmrPqVgno irYDnnxLDjZWCGyN nZmnIy zKXignRYPnz
DuCYgMHyyM JjqWYD ODruUPCm DtqFqFDCrrJVxXJzOg MWQGNnUuio^Bt
o_i@FIA[x/ E-D+@y +DA/ETGI ]>C?@FEBWMrA:@z[C] ==$/||!z[C]??
;:zBsOiWY!@C,DAA}T^^+$/ABtr@@!$T[C]&&q||CABWMr,^^AA;z[C]==$/&&z[C]=^^};Yxit;;;;;;;AA"," "+$/,""
],"`^@-Z",t["qntuz|y","m-|",z]+t[";jmnrxy>,","&-{","$-{"]+t["o;t","/-{",z]]]}[&->&u{u[t["xjsi",
"&-{",z]]}[&:to_sym]]}[]%;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
eval"(eval((%w%%<<%w%566716c68276d3528236d3728292e20313233343536373839386b6c6076777c3a216263646
566672b376d322566716c68276d3528222b276b222929222b356d3f3d3b3e6d356b2c6f63616c6f5671627961626c65
637a256b256b387d3d2e337b737e22697475637d7b317c2d3e6b557d32266f627d6164722d5f38257d366f627d61647
92f3b51303c2a23323e2e2132363d5d287b557b2f352d5a387b536b2f352d5d287b597d5a3e6d3e7f2d366f3f6f327f
3d6f316f347f3d3f2f387b557d5d287b54262d5a356b3a7d37266f627d61647d3035252d2e3b753b71347d3d2e337c2
87c297b77337c287c297d5d7b562a34727d5d7b3a7d32212d2b722b37397d3226322c247b522d6e79683c2d2e78342d
2b722d5b247b5224222c2a7c22296d2b722d5c247b547b52223830322b242f2c22222d5c2224322c247b52217e64757
a7c79783d6d2c7 22c2a7 d5b247b522b3 a6d6e62787 97e3c2 8362d2b7834
2d2b722d5b247b 522f6b 34783f2d2b72 2c2a7d5d5d 5d7b56 27347b52287
a637968362d2 b722c2a7d5d5d7 b562a3 47f6f537 97 d6d5d5d7 b5 d552b313566
716c62282566 716c6828252775 252c3c 35277523 35 2a252525 29 2e2071636b6
82525286a2 529292922272e276 375726 82f2b5 03d293 d5f292 b7b53323e23
68627c242f 2c276e2472782725 22272b 236c2a 6d3936 3e2368 627c3c39343
c3c36343c3 c343 53c3c3 930392 c2a276 e257e6 071636 b6 82 2286a22292c
2a6c2f332b 236e 236861 62737a 222b73 222c23 6b2932 3e 23 68627a223c2
22d2e36257 b757b5 22c272 22c22272d5 b55667 16 c6 4262d5d7b34
343e24796d 65637b 7c797c 7072796e64 782828 20 3e 2e2934392e2
d61607b7c787 c722 176646 a7d6 571353a6 4726c6 035726 e6c6f6 f6035653366
3739727e6f6e 613d 623434 796a 67716f6b 633874 336468 757c6d 603d6632356
77463776662376 17c683 678643 5373c6 8367e6 565757 265697 63270323d62
707172676e6f69 627561 3e6e68 79313a 666360 34397b 6e666d 6e66397a783
469676e6775607e6a71357035676865397978673a617365613c6132757160703d613471733173313032727732687467
3a7c67686366743b6e6165796f622e247f6f59682336392b587f223d213b28297b21392f223a24363d5e303f3823323
e236862792a382a7b503d5d3d342f2c7c712a7b503d5f3f3b3a3a7e237c6963656128203c2139292d7a22222b242f29
2e2472782821242a2b503d5626217c7c70392e2368627c222229292b3a7b503d5d3d342f26262a7b503d5d32222d7b3
56879647b3b3b3b3b3b3b39292%*%%%).pack(%%h*%)))";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
Demo
• Works as an ordinary Quine
$ ruby lquine.rb > lquine2.rb
$ diff –s lquine.rb lquine2.rb
lquine.rb and lquine2.rb are identical
Lipogram Quine
"a" is removed from the world!
format= %%->{#({#){#.{#0{#1{#2{#3{#4{#5{#6{#7{#8{#9{#h{#k{#l{#p{#v{#w{#<{#*{#a{#b{#c{#d{#e{#f{;
t=->s,x,y{->&u{u[s,x,y]}[&:tr]};z="!-{";->&u{u[y="().0123456789hklpvw<*abcdef¥¥",t["m~i",",-~",
"$-{"]+t["$",z,"i-{"],t[t["YQUO@g=`@W='@ABCDEFGHIJKLMNOPQRSTUVWXYZ';g=^YQUO@g=`@^+g+^AA^;Y=?=;n
=Y+OoWUO_Q UriUVOYsTY+Y;x=- >s{sBVyt Ys};q,=n[u =^ZormUt^]?@u
=ZormUtA?[ DC,TFEBBDEI]-x[u +?`]:x[W +?`]-x[y]: n=~/=Z?o?r?m?
U?t?=/?x[u ]-x[$&]:Y;z='ZormUt= C``->{H{Dt=- >s,x,y {Js,x, y]}[&: tr]};z=^!-{
^;Jy=^I^,t [^m~iK,-~K$-{^]+t[^$ ^,z,^i-{^],t [t[^EK C^+$/, ^^],^G ^,t[^qntuz|
yKm-|^,z]+ t[^;jmnrxy>,K&-{K$-{ ^]+t[^o;tK/- {^,z]] ]}[&Jt [^xjsi K&-{^,z]]}[
&:to_sym]] }[]`;DYQUO^@YQUO@@`R ``SS`R`F`T`` `ABPUW N@``MT `AAA^' BgsuV@/[C-L
]/A{[FEBWM r,$/,gBtr@'`^'+W,j=L IBWMrSSLGSSI GSSGHSSL CA,TgB unPUWN@^MT^
A,j,?#+WBW MUrsT^{#^,W+LEBWMrTE ,^->&u{u[^,' ^,^'][YQ UO$&]} ;GGBtimYs{|
y|Print@@@ CBBLGABmUP{|x|^qZXzm uDHjtVOCuVnO ooCYHWIJyrnonDmE GtijRU oNFxGWXxuOm
CmIEYRXsgZ EgqOKQMGHJOKQnYuuVYy IrCEmrPqVgno irYDnnxLDjZWCGyN nZmnIy zKXignRYPnz
DuCYgMHyyM JjqWYD ODruUPCm DtqFqFDCrrJVxXJzOg MWQGNnUuio^Bt
o_i@FIA[x/ E-D+@y +DA/ETGI ]>C?@FEBWMrA:@z[C] ==$/||!z[C]??
;:zBsOiWY!@C,DAA}T^^+$/ABtr@@!$T[C]&&q||CABWMr,^^AA;z[C]==$/&&z[C]=^^};Yxit;;;;;;;AA"," "+$/,""
],"`^@-Z",t["qntuz|y","m-|",z]+t[";jmnrxy>,","&-{","$-{"]+t["o;t","/-{",z]]]}[&->&u{u[t["xjsi",
"&-{",z]]}[&:to_sym]]}[]%;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
eval"(eval((%w%%<<%w%566716c68276d3528236d3728292e20313233343536373839386b6c6076777c3a216263646
566672b376d322566716c68276d3528222b276b222929222b356d3f3d3b3e6d356b2c6f63616c6f5671627961626c65
637a256b256b387d3d2e337b737e22697475637d7b317c2d3e6b557d32266f627d6164722d5f38257d366f627d61647
92f3b51303c2a23323e2e2132363d5d287b557b2f352d5a387b536b2f352d5d287b597d5a3e6d3e7f2d366f3f6f327f
3d6f316f347f3d3f2f387b557d5d287b54262d5a356b3a7d37266f627d61647d3035252d2e3b753b71347d3d2e337c2
87c297b77337c287c297d5d7b562a34727d5d7b3a7d32212d2b722b37397d3226322c247b522d6e79683c2d2e78342d
2b722d5b247b5224222c2a7c22296d2b722d5c247b547b52223830322b242f2c22222d5c2224322c247b52217e64757
a7c79783d6d2c7 22c2a7 d5b247b522b3 a6d6e62787 97e3c2 8362d2b7834
2d2b722d5b247b 522f6b 34783f2d2b72 2c2a7d5d5d 5d7b56 27347b52287
a637968362d2 b722c2a7d5d5d7 b562a3 47f6f537 97 d6d5d5d7 b5 d552b313566
716c62282566 716c6828252775 252c3c 35277523 35 2a252525 29 2e2071636b6
82525286a2 529292922272e276 375726 82f2b5 03d293 d5f292 b7b53323e23
68627c242f 2c276e2472782725 22272b 236c2a 6d3936 3e2368 627c3c39343
c3c36343c3 c343 53c3c3 930392 c2a276 e257e6 071636 b6 82 2286a22292c
2a6c2f332b 236e 236861 62737a 222b73 222c23 6b2932 3e 23 68627a223c2
22d2e36257 b757b5 22c272 22c22272d5 b55667 16 c6 4262d5d7b34
343e24796d 65637b 7c797c 7072796e64 782828 20 3e 2e2934392e2
d61607b7c787 c722 176646 a7d6 571353a6 4726c6 035726 e6c6f6 f6035653366
3739727e6f6e 613d 623434 796a 67716f6b 633874 336468 757c6d 603d6632356
77463776662376 17c683 678643 5373c6 8367e6 565757 265697 63270323d62
707172676e6f69 627561 3e6e68 79313a 666360 34397b 6e666d 6e66397a783
469676e6775607e6a71357035676865397978673a617365613c6132757160703d613471733173313032727732687467
3a7c67686366743b6e6165796f622e247f6f59682336392b587f223d213b28297b21392f223a24363d5e303f3823323
e236862792a382a7b503d5d3d342f2c7c712a7b503d5f3f3b3a3a7e237c6963656128203c2139292d7a22222b242f29
2e2472782821242a2b503d5626217c7c70392e2368627c222229292b3a7b503d5d3d342f26262a7b503d5d32222d7b3
56879647b3b3b3b3b3b3b39292%*%%%).pack(%%h*%)))";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
$ sed s/a//g lquine.rb
Lipogram Quine
"" is removed from the world!
formt= %%->{#({#){#.{#0{#1{#2{#3{#4{#5{#6{#7{#8{#9{#h{#k{#l{#p{#v{#w{#<{#*{#{#b{#c{#d{#e{#f{;
t=->s,x,y{->&u{u[s,x,y]}[&:tr]};z="!-{";->&u{u[y="().0123456789hklpvw<*bcdef¥¥",t["m~i",",-~",
"$-{"]+t["$",z,"i-{"],t[t["YQUO@g=`@W='@ABCDEFGHIJKLMNOPQRSTUVWXYZ';g=^YQUO@g=`@^+g+^AA^;Y=?=;n
=Y+OoWUO_Q UriUVOYsTY+Y;x=- >s{sBVyt Ys};q,=n[u =^ZormUt^]?@u
=ZormUtA?[ DC,TFEBBDEI]-x[u +?`]:x[W +?`]-x[y]: n=~/=Z?o?r?m?
U?t?=/?x[u ]-x[$&]:Y;z='ZormUt= C``->{H{Dt=- >s,x,y {Js,x, y]}[&: tr]};z=^!-{
^;Jy=^I^,t [^m~iK,-~K$-{^]+t[^$ ^,z,^i-{^],t [t[^EK C^+$/, ^^],^G ^,t[^qntuz|
yKm-|^,z]+ t[^;jmnrxy>,K&-{K$-{ ^]+t[^o;tK/- {^,z]] ]}[&Jt [^xjsi K&-{^,z]]}[
&:to_sym]] }[]`;DYQUO^@YQUO@@`R ``SS`R`F`T`` `ABPUW N@``MT `AAA^' BgsuV@/[C-L
]/A{[FEBWM r,$/,gBtr@'`^'+W,j=L IBWMrSSLGSSI GSSGHSSL CA,TgB unPUWN@^MT^
A,j,?#+WBW MUrsT^{#^,W+LEBWMrTE ,^->&u{u[^,' ^,^'][YQ UO$&]} ;GGBtimYs{|
y|Print@@@ CBBLGABmUP{|x|^qZXzm uDHjtVOCuVnO ooCYHWIJyrnonDmE GtijRU oNFxGWXxuOm
CmIEYRXsgZ EgqOKQMGHJOKQnYuuVYy IrCEmrPqVgno irYDnnxLDjZWCGyN nZmnIy zKXignRYPnz
DuCYgMHyyM JjqWYD ODruUPCm DtqFqFDCrrJVxXJzOg MWQGNnUuio^Bt
o_i@FIA[x/ E-D+@y +DA/ETGI ]>C?@FEBWMrA:@z[C] ==$/||!z[C]??
;:zBsOiWY!@C,DAA}T^^+$/ABtr@@!$T[C]&&q||CABWMr,^^AA;z[C]==$/&&z[C]=^^};Yxit;;;;;;;AA"," "+$/,""
],"`^@-Z",t["qntuz|y","m-|",z]+t[";jmnrxy>,","&-{","$-{"]+t["o;t","/-{",z]]]}[&->&u{u[t["xjsi",
"&-{",z]]}[&:to_sym]]}[]%;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
evl"(evl((%w%%<<%w%566716c68276d3528236d3728292e20313233343536373839386b6c6076777c3216263646
566672b376d322566716c68276d3528222b276b222929222b356d3f3d3b3e6d356b2c6f63616c6f5671627961626c65
637256b256b387d3d2e337b737e22697475637d7b317c2d3e6b557d32266f627d6164722d5f38257d366f627d61647
92f3b51303c223323e2e2132363d5d287b557b2f352d5387b536b2f352d5d287b597d53e6d3e7f2d366f3f6f327f
3d6f316f347f3d3f2f387b557d5d287b54262d5356b37d37266f627d61647d3035252d2e3b753b71347d3d2e337c2
87c297b77337c287c297d5d7b56234727d5d7b37d32212d2b722b37397d3226322c247b522d6e79683c2d2e78342d
2b722d5b247b5224222c27c22296d2b722d5c247b547b52223830322b242f2c22222d5c2224322c247b52217e64757
7c79783d6d2c7 22c27 d5b247b522b3 6d6e62787 97e3c2 8362d2b7834
2d2b722d5b247b 522f6b 34783f2d2b72 2c27d5d5d 5d7b56 27347b52287
637968362d2 b722c27d5d5d7 b5623 47f6f537 97 d6d5d5d7 b5 d552b313566
716c62282566 716c6828252775 252c3c 35277523 35 2252525 29 2e2071636b6
825252862 529292922272e276 375726 82f2b5 03d293 d5f292 b7b53323e23
68627c242f 2c276e2472782725 22272b 236c2 6d3936 3e2368 627c3c39343
c3c36343c3 c343 53c3c3 930392 c2276 e257e6 071636 b6 82 228622292c
26c2f332b 236e 236861 62737 222b73 222c23 6b2932 3e 23 68627223c2
22d2e36257 b757b5 22c272 22c22272d5 b55667 16 c6 4262d5d7b34
343e24796d 65637b 7c797c 7072796e64 782828 20 3e 2e2934392e2
d61607b7c787 c722 176646 7d6 5713536 4726c6 035726 e6c6f6 f6035653366
3739727e6f6e 613d 623434 796 67716f6b 633874 336468 757c6d 603d6632356
77463776662376 17c683 678643 5373c6 8367e6 565757 265697 63270323d62
707172676e6f69 627561 3e6e68 79313 666360 34397b 6e666d 6e66397783
469676e6775607e671357035676865397978673617365613c6132757160703d613471733173313032727732687467
37c67686366743b6e6165796f622e247f6f59682336392b587f223d213b28297b21392f22324363d5e303f3823323
e2368627923827b503d5d3d342f2c7c7127b503d5f3f3b337e237c6963656128203c2139292d722222b242f29
2e24727828212422b503d5626217c7c70392e2368627c222229292b37b503d5d3d342f262627b503d5d32222d7b3
56879647b3b3b3b3b3b3b39292%*%%%).pck(%%h*%)))";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
$ sed s/a//g lquine.rb
Lipogram Quine
Demo
• You can delete any one letter
• It automatically restore itself!
$ sed s/a//g lquine.rb > broken.rb
$ ruby broken.rb > broken2.rb
$ diff –s broken.rb broken2.rb
broken.rb and broken2.rb are identical
Lipogram Quine
Internal
• Main trick:
– This code executes code2
• The string literal is just ignored
• If "a" is removed:
– This code executes code1 and terminates
Lipogram Quine
"#a{ code1;exit }"; code2
"#{ code1;exit }"; code2
String interpolation!
Internal
• Basic structure:
Lipogram Quine
"#a{#b{#c{…
A code without "a","b","c",…
exit
}"
A code with only "a","b","c",…
More? Read my book!
• "The World of
Obfuscated,
Esoteric, Artistic
Programming"
– Contains about 40
codes like this talk
– Written in Japanese
Related contests
• International Obfuscated C Code Contest
(IOCCC)
– A programming contest for hard-to-read
programs written in C language
• Transcendental Ruby Imbroglio Contest
for rubyKaigi (TRICK)
– The judges (including I) held TRICK twice
– TRICK FINAL is now open (~ 2018/03/31)
• https://github.com/tric/trick2018
• Winners will be awarded at RubyKaigi 2018
Conclusion
• Ruby is incredibly flexible
– You can use Ruby with broken keyboards
(only numbers, or only underscores)
– You can write artistic and super-robust
Quine in Ruby
• Ruby Programming is fun
– Even without practicality
– If you like practicality, join 
• One more thing…
A Quine for Bath Ruby Conference
"#a{#b{#c{…

More Related Content

What's hot

Automatically Spotting Cross-language Relations
Automatically Spotting Cross-language RelationsAutomatically Spotting Cross-language Relations
Automatically Spotting Cross-language RelationsFederico Tomassetti
 
You Don't Need Lodash
You Don't Need Lodash You Don't Need Lodash
You Don't Need Lodash UpsideTravel
 
You will learn RxJS in 2017
You will learn RxJS in 2017You will learn RxJS in 2017
You will learn RxJS in 2017名辰 洪
 
The Ring programming language version 1.5.4 book - Part 40 of 185
The Ring programming language version 1.5.4 book - Part 40 of 185The Ring programming language version 1.5.4 book - Part 40 of 185
The Ring programming language version 1.5.4 book - Part 40 of 185Mahmoud Samir Fayed
 
Universal JavaScript
Universal JavaScriptUniversal JavaScript
Universal JavaScript名辰 洪
 
Thoughts on MongoDB Analytics
Thoughts on MongoDB AnalyticsThoughts on MongoDB Analytics
Thoughts on MongoDB Analyticsrogerbodamer
 
Cukeup nyc ian dees on elixir, erlang, and cucumberl
Cukeup nyc ian dees on elixir, erlang, and cucumberlCukeup nyc ian dees on elixir, erlang, and cucumberl
Cukeup nyc ian dees on elixir, erlang, and cucumberlSkills Matter
 
Amir Salihefendic: Redis - the hacker's database
Amir Salihefendic: Redis - the hacker's databaseAmir Salihefendic: Redis - the hacker's database
Amir Salihefendic: Redis - the hacker's databaseit-people
 
HadoopとMongoDBを活用したソーシャルアプリのログ解析
HadoopとMongoDBを活用したソーシャルアプリのログ解析HadoopとMongoDBを活用したソーシャルアプリのログ解析
HadoopとMongoDBを活用したソーシャルアプリのログ解析Takahiro Inoue
 
MongoDB Aggregation Framework in action !
MongoDB Aggregation Framework in action !MongoDB Aggregation Framework in action !
MongoDB Aggregation Framework in action !Sébastien Prunier
 
Test driven game development silly, stupid or inspired?
Test driven game development   silly, stupid or inspired?Test driven game development   silly, stupid or inspired?
Test driven game development silly, stupid or inspired?Eric Smith
 
Desarrollo de módulos en Drupal e integración con dispositivos móviles
Desarrollo de módulos en Drupal e integración con dispositivos móvilesDesarrollo de módulos en Drupal e integración con dispositivos móviles
Desarrollo de módulos en Drupal e integración con dispositivos móvilesLuis Curo Salvatierra
 
The Ring programming language version 1.9 book - Part 48 of 210
The Ring programming language version 1.9 book - Part 48 of 210The Ring programming language version 1.9 book - Part 48 of 210
The Ring programming language version 1.9 book - Part 48 of 210Mahmoud Samir Fayed
 
Test Driven Cocos2d
Test Driven Cocos2dTest Driven Cocos2d
Test Driven Cocos2dEric Smith
 
Processing and Processing.js
Processing and Processing.jsProcessing and Processing.js
Processing and Processing.jsjeresig
 
Ruby Language - A quick tour
Ruby Language - A quick tourRuby Language - A quick tour
Ruby Language - A quick touraztack
 
TicketBEKA? Ticket booking
TicketBEKA? Ticket bookingTicketBEKA? Ticket booking
TicketBEKA? Ticket bookingLikhith Pujari
 

What's hot (20)

Automatically Spotting Cross-language Relations
Automatically Spotting Cross-language RelationsAutomatically Spotting Cross-language Relations
Automatically Spotting Cross-language Relations
 
You Don't Need Lodash
You Don't Need Lodash You Don't Need Lodash
You Don't Need Lodash
 
You will learn RxJS in 2017
You will learn RxJS in 2017You will learn RxJS in 2017
You will learn RxJS in 2017
 
The Ring programming language version 1.5.4 book - Part 40 of 185
The Ring programming language version 1.5.4 book - Part 40 of 185The Ring programming language version 1.5.4 book - Part 40 of 185
The Ring programming language version 1.5.4 book - Part 40 of 185
 
Universal JavaScript
Universal JavaScriptUniversal JavaScript
Universal JavaScript
 
Sensmon couchdb
Sensmon couchdbSensmon couchdb
Sensmon couchdb
 
Thoughts on MongoDB Analytics
Thoughts on MongoDB AnalyticsThoughts on MongoDB Analytics
Thoughts on MongoDB Analytics
 
Cukeup nyc ian dees on elixir, erlang, and cucumberl
Cukeup nyc ian dees on elixir, erlang, and cucumberlCukeup nyc ian dees on elixir, erlang, and cucumberl
Cukeup nyc ian dees on elixir, erlang, and cucumberl
 
Amir Salihefendic: Redis - the hacker's database
Amir Salihefendic: Redis - the hacker's databaseAmir Salihefendic: Redis - the hacker's database
Amir Salihefendic: Redis - the hacker's database
 
Python 1
Python 1Python 1
Python 1
 
HadoopとMongoDBを活用したソーシャルアプリのログ解析
HadoopとMongoDBを活用したソーシャルアプリのログ解析HadoopとMongoDBを活用したソーシャルアプリのログ解析
HadoopとMongoDBを活用したソーシャルアプリのログ解析
 
MongoDB Aggregation Framework in action !
MongoDB Aggregation Framework in action !MongoDB Aggregation Framework in action !
MongoDB Aggregation Framework in action !
 
Test driven game development silly, stupid or inspired?
Test driven game development   silly, stupid or inspired?Test driven game development   silly, stupid or inspired?
Test driven game development silly, stupid or inspired?
 
Desarrollo de módulos en Drupal e integración con dispositivos móviles
Desarrollo de módulos en Drupal e integración con dispositivos móvilesDesarrollo de módulos en Drupal e integración con dispositivos móviles
Desarrollo de módulos en Drupal e integración con dispositivos móviles
 
The State of JavaScript
The State of JavaScriptThe State of JavaScript
The State of JavaScript
 
The Ring programming language version 1.9 book - Part 48 of 210
The Ring programming language version 1.9 book - Part 48 of 210The Ring programming language version 1.9 book - Part 48 of 210
The Ring programming language version 1.9 book - Part 48 of 210
 
Test Driven Cocos2d
Test Driven Cocos2dTest Driven Cocos2d
Test Driven Cocos2d
 
Processing and Processing.js
Processing and Processing.jsProcessing and Processing.js
Processing and Processing.js
 
Ruby Language - A quick tour
Ruby Language - A quick tourRuby Language - A quick tour
Ruby Language - A quick tour
 
TicketBEKA? Ticket booking
TicketBEKA? Ticket bookingTicketBEKA? Ticket booking
TicketBEKA? Ticket booking
 

Similar to Self-descriptive Ruby programs generate themselves

Migrating To Ruby1.9
Migrating To Ruby1.9Migrating To Ruby1.9
Migrating To Ruby1.9tomaspavelka
 
The Art Of Readable Code
The Art Of Readable CodeThe Art Of Readable Code
The Art Of Readable CodeBaidu, Inc.
 
PostgreSQL as seen by Rubyists (Kaigi on Rails 2022)
PostgreSQL as seen by Rubyists (Kaigi on Rails 2022)PostgreSQL as seen by Rubyists (Kaigi on Rails 2022)
PostgreSQL as seen by Rubyists (Kaigi on Rails 2022)Андрей Новиков
 
RubyEnRails2007 - Dr Nic Williams - DIY Syntax
RubyEnRails2007 - Dr Nic Williams - DIY SyntaxRubyEnRails2007 - Dr Nic Williams - DIY Syntax
RubyEnRails2007 - Dr Nic Williams - DIY SyntaxDr Nic Williams
 
GC in Ruby. RubyC, Kiev, 2014.
GC in Ruby. RubyC, Kiev, 2014.GC in Ruby. RubyC, Kiev, 2014.
GC in Ruby. RubyC, Kiev, 2014.Timothy Tsvetkov
 
React Native Evening
React Native EveningReact Native Evening
React Native EveningTroy Miles
 
Groovy presentation
Groovy presentationGroovy presentation
Groovy presentationManav Prasad
 
A Recovering Java Developer Learns to Go
A Recovering Java Developer Learns to GoA Recovering Java Developer Learns to Go
A Recovering Java Developer Learns to GoMatt Stine
 
Blocks by Lachs Cox
Blocks by Lachs CoxBlocks by Lachs Cox
Blocks by Lachs Coxlachie
 
Helvetia
HelvetiaHelvetia
HelvetiaESUG
 
TechDays - IronRuby
TechDays - IronRubyTechDays - IronRuby
TechDays - IronRubyBen Hall
 
Ruby - Uma Introdução
Ruby - Uma IntroduçãoRuby - Uma Introdução
Ruby - Uma IntroduçãoÍgor Bonadio
 
3D Design with OpenSCAD
3D Design with OpenSCAD3D Design with OpenSCAD
3D Design with OpenSCADVickyTGAW
 
Hacking with ruby2ruby
Hacking with ruby2rubyHacking with ruby2ruby
Hacking with ruby2rubyMarc Chung
 
SDPHP - Percona Toolkit (It's Basically Magic)
SDPHP - Percona Toolkit (It's Basically Magic)SDPHP - Percona Toolkit (It's Basically Magic)
SDPHP - Percona Toolkit (It's Basically Magic)Robert Swisher
 
Esoteric, Obfuscated, Artistic Programming in Ruby
Esoteric, Obfuscated, Artistic Programming in RubyEsoteric, Obfuscated, Artistic Programming in Ruby
Esoteric, Obfuscated, Artistic Programming in Rubymametter
 
Logic programming a ruby perspective
Logic programming a ruby perspectiveLogic programming a ruby perspective
Logic programming a ruby perspectiveNorman Richards
 
スマートフォン勉強会@関東 #11 どう考えてもdisconなものをiPhoneに移植してみた
スマートフォン勉強会@関東 #11 どう考えてもdisconなものをiPhoneに移植してみたスマートフォン勉強会@関東 #11 どう考えてもdisconなものをiPhoneに移植してみた
スマートフォン勉強会@関東 #11 どう考えてもdisconなものをiPhoneに移植してみたTaro Matsuzawa
 

Similar to Self-descriptive Ruby programs generate themselves (20)

Method::Signatures
Method::SignaturesMethod::Signatures
Method::Signatures
 
Migrating To Ruby1.9
Migrating To Ruby1.9Migrating To Ruby1.9
Migrating To Ruby1.9
 
The Art Of Readable Code
The Art Of Readable CodeThe Art Of Readable Code
The Art Of Readable Code
 
PostgreSQL as seen by Rubyists (Kaigi on Rails 2022)
PostgreSQL as seen by Rubyists (Kaigi on Rails 2022)PostgreSQL as seen by Rubyists (Kaigi on Rails 2022)
PostgreSQL as seen by Rubyists (Kaigi on Rails 2022)
 
RubyEnRails2007 - Dr Nic Williams - DIY Syntax
RubyEnRails2007 - Dr Nic Williams - DIY SyntaxRubyEnRails2007 - Dr Nic Williams - DIY Syntax
RubyEnRails2007 - Dr Nic Williams - DIY Syntax
 
GC in Ruby. RubyC, Kiev, 2014.
GC in Ruby. RubyC, Kiev, 2014.GC in Ruby. RubyC, Kiev, 2014.
GC in Ruby. RubyC, Kiev, 2014.
 
React Native Evening
React Native EveningReact Native Evening
React Native Evening
 
Groovy presentation
Groovy presentationGroovy presentation
Groovy presentation
 
A Recovering Java Developer Learns to Go
A Recovering Java Developer Learns to GoA Recovering Java Developer Learns to Go
A Recovering Java Developer Learns to Go
 
Blocks by Lachs Cox
Blocks by Lachs CoxBlocks by Lachs Cox
Blocks by Lachs Cox
 
An introduction to Ruby
An introduction to RubyAn introduction to Ruby
An introduction to Ruby
 
Helvetia
HelvetiaHelvetia
Helvetia
 
TechDays - IronRuby
TechDays - IronRubyTechDays - IronRuby
TechDays - IronRuby
 
Ruby - Uma Introdução
Ruby - Uma IntroduçãoRuby - Uma Introdução
Ruby - Uma Introdução
 
3D Design with OpenSCAD
3D Design with OpenSCAD3D Design with OpenSCAD
3D Design with OpenSCAD
 
Hacking with ruby2ruby
Hacking with ruby2rubyHacking with ruby2ruby
Hacking with ruby2ruby
 
SDPHP - Percona Toolkit (It's Basically Magic)
SDPHP - Percona Toolkit (It's Basically Magic)SDPHP - Percona Toolkit (It's Basically Magic)
SDPHP - Percona Toolkit (It's Basically Magic)
 
Esoteric, Obfuscated, Artistic Programming in Ruby
Esoteric, Obfuscated, Artistic Programming in RubyEsoteric, Obfuscated, Artistic Programming in Ruby
Esoteric, Obfuscated, Artistic Programming in Ruby
 
Logic programming a ruby perspective
Logic programming a ruby perspectiveLogic programming a ruby perspective
Logic programming a ruby perspective
 
スマートフォン勉強会@関東 #11 どう考えてもdisconなものをiPhoneに移植してみた
スマートフォン勉強会@関東 #11 どう考えてもdisconなものをiPhoneに移植してみたスマートフォン勉強会@関東 #11 どう考えてもdisconなものをiPhoneに移植してみた
スマートフォン勉強会@関東 #11 どう考えてもdisconなものをiPhoneに移植してみた
 

More from mametter

error_highlight: User-friendly Error Diagnostics
error_highlight: User-friendly Error Diagnosticserror_highlight: User-friendly Error Diagnostics
error_highlight: User-friendly Error Diagnosticsmametter
 
TRICK 2022 Results
TRICK 2022 ResultsTRICK 2022 Results
TRICK 2022 Resultsmametter
 
クックパッド春の超絶技巧パンまつり 超絶技巧プログラミング編 資料
クックパッド春の超絶技巧パンまつり 超絶技巧プログラミング編 資料クックパッド春の超絶技巧パンまつり 超絶技巧プログラミング編 資料
クックパッド春の超絶技巧パンまつり 超絶技巧プログラミング編 資料mametter
 
Enjoy Ruby Programming in IDE and TypeProf
Enjoy Ruby Programming in IDE and TypeProfEnjoy Ruby Programming in IDE and TypeProf
Enjoy Ruby Programming in IDE and TypeProfmametter
 
TypeProf for IDE: Enrich Development Experience without Annotations
TypeProf for IDE: Enrich Development Experience without AnnotationsTypeProf for IDE: Enrich Development Experience without Annotations
TypeProf for IDE: Enrich Development Experience without Annotationsmametter
 
Ruby 3の型解析に向けた計画
Ruby 3の型解析に向けた計画Ruby 3の型解析に向けた計画
Ruby 3の型解析に向けた計画mametter
 
emruby: ブラウザで動くRuby
emruby: ブラウザで動くRubyemruby: ブラウザで動くRuby
emruby: ブラウザで動くRubymametter
 
Type Profiler: Ambitious Type Inference for Ruby 3
Type Profiler: Ambitious Type Inference for Ruby 3Type Profiler: Ambitious Type Inference for Ruby 3
Type Profiler: Ambitious Type Inference for Ruby 3mametter
 
型プロファイラ:抽象解釈に基づくRuby 3の静的解析
型プロファイラ:抽象解釈に基づくRuby 3の静的解析型プロファイラ:抽象解釈に基づくRuby 3の静的解析
型プロファイラ:抽象解釈に基づくRuby 3の静的解析mametter
 
Ruby 3の型推論やってます
Ruby 3の型推論やってますRuby 3の型推論やってます
Ruby 3の型推論やってますmametter
 
マニアックなRuby 2.7新機能紹介
マニアックなRuby 2.7新機能紹介マニアックなRuby 2.7新機能紹介
マニアックなRuby 2.7新機能紹介mametter
 
A Static Type Analyzer of Untyped Ruby Code for Ruby 3
A Static Type Analyzer of Untyped Ruby Code for Ruby 3A Static Type Analyzer of Untyped Ruby Code for Ruby 3
A Static Type Analyzer of Untyped Ruby Code for Ruby 3mametter
 
A Plan towards Ruby 3 Types
A Plan towards Ruby 3 TypesA Plan towards Ruby 3 Types
A Plan towards Ruby 3 Typesmametter
 
Ruby 3 の型解析に向けた計画
Ruby 3 の型解析に向けた計画Ruby 3 の型解析に向けた計画
Ruby 3 の型解析に向けた計画mametter
 
A Type-level Ruby Interpreter for Testing and Understanding
A Type-level Ruby Interpreter for Testing and UnderstandingA Type-level Ruby Interpreter for Testing and Understanding
A Type-level Ruby Interpreter for Testing and Understandingmametter
 
本番環境で使える実行コード記録機能
本番環境で使える実行コード記録機能本番環境で使える実行コード記録機能
本番環境で使える実行コード記録機能mametter
 
Transcendental Programming in Ruby
Transcendental Programming in RubyTranscendental Programming in Ruby
Transcendental Programming in Rubymametter
 
Cookpad Hackarade #04: Create Your Own Interpreter
Cookpad Hackarade #04: Create Your Own InterpreterCookpad Hackarade #04: Create Your Own Interpreter
Cookpad Hackarade #04: Create Your Own Interpretermametter
 
Ruby 3のキーワード引数について考える
Ruby 3のキーワード引数について考えるRuby 3のキーワード引数について考える
Ruby 3のキーワード引数について考えるmametter
 
TRICK 2018 results
TRICK 2018 resultsTRICK 2018 results
TRICK 2018 resultsmametter
 

More from mametter (20)

error_highlight: User-friendly Error Diagnostics
error_highlight: User-friendly Error Diagnosticserror_highlight: User-friendly Error Diagnostics
error_highlight: User-friendly Error Diagnostics
 
TRICK 2022 Results
TRICK 2022 ResultsTRICK 2022 Results
TRICK 2022 Results
 
クックパッド春の超絶技巧パンまつり 超絶技巧プログラミング編 資料
クックパッド春の超絶技巧パンまつり 超絶技巧プログラミング編 資料クックパッド春の超絶技巧パンまつり 超絶技巧プログラミング編 資料
クックパッド春の超絶技巧パンまつり 超絶技巧プログラミング編 資料
 
Enjoy Ruby Programming in IDE and TypeProf
Enjoy Ruby Programming in IDE and TypeProfEnjoy Ruby Programming in IDE and TypeProf
Enjoy Ruby Programming in IDE and TypeProf
 
TypeProf for IDE: Enrich Development Experience without Annotations
TypeProf for IDE: Enrich Development Experience without AnnotationsTypeProf for IDE: Enrich Development Experience without Annotations
TypeProf for IDE: Enrich Development Experience without Annotations
 
Ruby 3の型解析に向けた計画
Ruby 3の型解析に向けた計画Ruby 3の型解析に向けた計画
Ruby 3の型解析に向けた計画
 
emruby: ブラウザで動くRuby
emruby: ブラウザで動くRubyemruby: ブラウザで動くRuby
emruby: ブラウザで動くRuby
 
Type Profiler: Ambitious Type Inference for Ruby 3
Type Profiler: Ambitious Type Inference for Ruby 3Type Profiler: Ambitious Type Inference for Ruby 3
Type Profiler: Ambitious Type Inference for Ruby 3
 
型プロファイラ:抽象解釈に基づくRuby 3の静的解析
型プロファイラ:抽象解釈に基づくRuby 3の静的解析型プロファイラ:抽象解釈に基づくRuby 3の静的解析
型プロファイラ:抽象解釈に基づくRuby 3の静的解析
 
Ruby 3の型推論やってます
Ruby 3の型推論やってますRuby 3の型推論やってます
Ruby 3の型推論やってます
 
マニアックなRuby 2.7新機能紹介
マニアックなRuby 2.7新機能紹介マニアックなRuby 2.7新機能紹介
マニアックなRuby 2.7新機能紹介
 
A Static Type Analyzer of Untyped Ruby Code for Ruby 3
A Static Type Analyzer of Untyped Ruby Code for Ruby 3A Static Type Analyzer of Untyped Ruby Code for Ruby 3
A Static Type Analyzer of Untyped Ruby Code for Ruby 3
 
A Plan towards Ruby 3 Types
A Plan towards Ruby 3 TypesA Plan towards Ruby 3 Types
A Plan towards Ruby 3 Types
 
Ruby 3 の型解析に向けた計画
Ruby 3 の型解析に向けた計画Ruby 3 の型解析に向けた計画
Ruby 3 の型解析に向けた計画
 
A Type-level Ruby Interpreter for Testing and Understanding
A Type-level Ruby Interpreter for Testing and UnderstandingA Type-level Ruby Interpreter for Testing and Understanding
A Type-level Ruby Interpreter for Testing and Understanding
 
本番環境で使える実行コード記録機能
本番環境で使える実行コード記録機能本番環境で使える実行コード記録機能
本番環境で使える実行コード記録機能
 
Transcendental Programming in Ruby
Transcendental Programming in RubyTranscendental Programming in Ruby
Transcendental Programming in Ruby
 
Cookpad Hackarade #04: Create Your Own Interpreter
Cookpad Hackarade #04: Create Your Own InterpreterCookpad Hackarade #04: Create Your Own Interpreter
Cookpad Hackarade #04: Create Your Own Interpreter
 
Ruby 3のキーワード引数について考える
Ruby 3のキーワード引数について考えるRuby 3のキーワード引数について考える
Ruby 3のキーワード引数について考える
 
TRICK 2018 results
TRICK 2018 resultsTRICK 2018 results
TRICK 2018 results
 

Recently uploaded

Call Girls in Nashik Bhavna 7001305949 Independent Escort Service Nashik
Call Girls in Nashik Bhavna 7001305949 Independent Escort Service NashikCall Girls in Nashik Bhavna 7001305949 Independent Escort Service Nashik
Call Girls in Nashik Bhavna 7001305949 Independent Escort Service Nashikranjana rawat
 
(DIVYA) Dhanori Call Girls Just Call 7001035870 [ Cash on Delivery ] Pune Esc...
(DIVYA) Dhanori Call Girls Just Call 7001035870 [ Cash on Delivery ] Pune Esc...(DIVYA) Dhanori Call Girls Just Call 7001035870 [ Cash on Delivery ] Pune Esc...
(DIVYA) Dhanori Call Girls Just Call 7001035870 [ Cash on Delivery ] Pune Esc...ranjana rawat
 
Kolkata Call Girls Service +918240919228 - Kolkatanightgirls.com
Kolkata Call Girls Service +918240919228 - Kolkatanightgirls.comKolkata Call Girls Service +918240919228 - Kolkatanightgirls.com
Kolkata Call Girls Service +918240919228 - Kolkatanightgirls.comKolkata Call Girls
 
5* Hotel Call Girls In Goa 7028418221 Call Girls In Calangute Beach Escort Se...
5* Hotel Call Girls In Goa 7028418221 Call Girls In Calangute Beach Escort Se...5* Hotel Call Girls In Goa 7028418221 Call Girls In Calangute Beach Escort Se...
5* Hotel Call Girls In Goa 7028418221 Call Girls In Calangute Beach Escort Se...Apsara Of India
 
Vip Udaipur Call Girls 9602870969 Dabok Airport Udaipur Escorts Service
Vip Udaipur Call Girls 9602870969 Dabok Airport Udaipur Escorts ServiceVip Udaipur Call Girls 9602870969 Dabok Airport Udaipur Escorts Service
Vip Udaipur Call Girls 9602870969 Dabok Airport Udaipur Escorts ServiceApsara Of India
 
Call Girls in Faridabad 9000000000 Faridabad Escorts Service
Call Girls in Faridabad 9000000000 Faridabad Escorts ServiceCall Girls in Faridabad 9000000000 Faridabad Escorts Service
Call Girls in Faridabad 9000000000 Faridabad Escorts ServiceTina Ji
 
Call Girls Nikol 7397865700 Ridhima Hire Me Full Night
Call Girls Nikol 7397865700 Ridhima Hire Me Full NightCall Girls Nikol 7397865700 Ridhima Hire Me Full Night
Call Girls Nikol 7397865700 Ridhima Hire Me Full Nightssuser7cb4ff
 
VIP Call Girls Bara Bazar - Phone No 8250192130 For Ultimate Sexual Urges
VIP Call Girls Bara Bazar - Phone No 8250192130 For Ultimate Sexual UrgesVIP Call Girls Bara Bazar - Phone No 8250192130 For Ultimate Sexual Urges
VIP Call Girls Bara Bazar - Phone No 8250192130 For Ultimate Sexual Urgesanamikaraghav4
 
Kolkata Call Girl Kalyani 👉 8250192130 ❣️💯 Available With Room 24×7
Kolkata Call Girl Kalyani 👉 8250192130 ❣️💯 Available With Room 24×7Kolkata Call Girl Kalyani 👉 8250192130 ❣️💯 Available With Room 24×7
Kolkata Call Girl Kalyani 👉 8250192130 ❣️💯 Available With Room 24×7Riya Pathan
 
Hi Class Call Girls In Goa 7028418221 Call Girls In Anjuna Beach Escort Services
Hi Class Call Girls In Goa 7028418221 Call Girls In Anjuna Beach Escort ServicesHi Class Call Girls In Goa 7028418221 Call Girls In Anjuna Beach Escort Services
Hi Class Call Girls In Goa 7028418221 Call Girls In Anjuna Beach Escort ServicesApsara Of India
 
Pallawi ❣ 💓 Pallawi 09167673311 💓Call Girl in Thane Near Hiranandani Estate ...
Pallawi ❣ 💓 Pallawi  09167673311 💓Call Girl in Thane Near Hiranandani Estate ...Pallawi ❣ 💓 Pallawi  09167673311 💓Call Girl in Thane Near Hiranandani Estate ...
Pallawi ❣ 💓 Pallawi 09167673311 💓Call Girl in Thane Near Hiranandani Estate ...Pooja Nehwal
 
Hifi Laxmi Nagar Call Girls Service WhatsApp -> 9999965857 Available 24x7 ^ D...
Hifi Laxmi Nagar Call Girls Service WhatsApp -> 9999965857 Available 24x7 ^ D...Hifi Laxmi Nagar Call Girls Service WhatsApp -> 9999965857 Available 24x7 ^ D...
Hifi Laxmi Nagar Call Girls Service WhatsApp -> 9999965857 Available 24x7 ^ D...srsj9000
 
5* Hotel Call Girls In Goa 7028418221 Call Girls In North Goa Escort Services
5* Hotel Call Girls In Goa 7028418221 Call Girls In North Goa Escort Services5* Hotel Call Girls In Goa 7028418221 Call Girls In North Goa Escort Services
5* Hotel Call Girls In Goa 7028418221 Call Girls In North Goa Escort ServicesApsara Of India
 
Fun Call Girls In Goa 7028418221 Call Girl Service In Panaji Escorts
Fun Call Girls In Goa 7028418221 Call Girl Service In Panaji EscortsFun Call Girls In Goa 7028418221 Call Girl Service In Panaji Escorts
Fun Call Girls In Goa 7028418221 Call Girl Service In Panaji EscortsApsara Of India
 
Hot Call Girls In Goa 7028418221 Call Girls In Vagator Beach EsCoRtS
Hot Call Girls In Goa 7028418221 Call Girls In Vagator Beach EsCoRtSHot Call Girls In Goa 7028418221 Call Girls In Vagator Beach EsCoRtS
Hot Call Girls In Goa 7028418221 Call Girls In Vagator Beach EsCoRtSApsara Of India
 
Authentic No 1 Amil Baba In Pakistan Authentic No 1 Amil Baba In Karachi No 1...
Authentic No 1 Amil Baba In Pakistan Authentic No 1 Amil Baba In Karachi No 1...Authentic No 1 Amil Baba In Pakistan Authentic No 1 Amil Baba In Karachi No 1...
Authentic No 1 Amil Baba In Pakistan Authentic No 1 Amil Baba In Karachi No 1...First NO1 World Amil baba in Faisalabad
 
Verified Call Girls Esplanade - [ Cash on Delivery ] Contact 8250192130 Escor...
Verified Call Girls Esplanade - [ Cash on Delivery ] Contact 8250192130 Escor...Verified Call Girls Esplanade - [ Cash on Delivery ] Contact 8250192130 Escor...
Verified Call Girls Esplanade - [ Cash on Delivery ] Contact 8250192130 Escor...anamikaraghav4
 
FULL ENJOY Call Girls In Mahipalpur Delhi Contact Us 8377087607
FULL ENJOY Call Girls In Mahipalpur Delhi Contact Us 8377087607FULL ENJOY Call Girls In Mahipalpur Delhi Contact Us 8377087607
FULL ENJOY Call Girls In Mahipalpur Delhi Contact Us 8377087607dollysharma2066
 
Kolkata Call Girl Bara Bazar 👉 8250192130 ❣️💯 Available With Room 24×7
Kolkata Call Girl Bara Bazar 👉 8250192130 ❣️💯 Available With Room 24×7Kolkata Call Girl Bara Bazar 👉 8250192130 ❣️💯 Available With Room 24×7
Kolkata Call Girl Bara Bazar 👉 8250192130 ❣️💯 Available With Room 24×7Riya Pathan
 
(KRITI) Pimpri Chinchwad Call Girls Just Call 7001035870 [ Cash on Delivery ]...
(KRITI) Pimpri Chinchwad Call Girls Just Call 7001035870 [ Cash on Delivery ]...(KRITI) Pimpri Chinchwad Call Girls Just Call 7001035870 [ Cash on Delivery ]...
(KRITI) Pimpri Chinchwad Call Girls Just Call 7001035870 [ Cash on Delivery ]...ranjana rawat
 

Recently uploaded (20)

Call Girls in Nashik Bhavna 7001305949 Independent Escort Service Nashik
Call Girls in Nashik Bhavna 7001305949 Independent Escort Service NashikCall Girls in Nashik Bhavna 7001305949 Independent Escort Service Nashik
Call Girls in Nashik Bhavna 7001305949 Independent Escort Service Nashik
 
(DIVYA) Dhanori Call Girls Just Call 7001035870 [ Cash on Delivery ] Pune Esc...
(DIVYA) Dhanori Call Girls Just Call 7001035870 [ Cash on Delivery ] Pune Esc...(DIVYA) Dhanori Call Girls Just Call 7001035870 [ Cash on Delivery ] Pune Esc...
(DIVYA) Dhanori Call Girls Just Call 7001035870 [ Cash on Delivery ] Pune Esc...
 
Kolkata Call Girls Service +918240919228 - Kolkatanightgirls.com
Kolkata Call Girls Service +918240919228 - Kolkatanightgirls.comKolkata Call Girls Service +918240919228 - Kolkatanightgirls.com
Kolkata Call Girls Service +918240919228 - Kolkatanightgirls.com
 
5* Hotel Call Girls In Goa 7028418221 Call Girls In Calangute Beach Escort Se...
5* Hotel Call Girls In Goa 7028418221 Call Girls In Calangute Beach Escort Se...5* Hotel Call Girls In Goa 7028418221 Call Girls In Calangute Beach Escort Se...
5* Hotel Call Girls In Goa 7028418221 Call Girls In Calangute Beach Escort Se...
 
Vip Udaipur Call Girls 9602870969 Dabok Airport Udaipur Escorts Service
Vip Udaipur Call Girls 9602870969 Dabok Airport Udaipur Escorts ServiceVip Udaipur Call Girls 9602870969 Dabok Airport Udaipur Escorts Service
Vip Udaipur Call Girls 9602870969 Dabok Airport Udaipur Escorts Service
 
Call Girls in Faridabad 9000000000 Faridabad Escorts Service
Call Girls in Faridabad 9000000000 Faridabad Escorts ServiceCall Girls in Faridabad 9000000000 Faridabad Escorts Service
Call Girls in Faridabad 9000000000 Faridabad Escorts Service
 
Call Girls Nikol 7397865700 Ridhima Hire Me Full Night
Call Girls Nikol 7397865700 Ridhima Hire Me Full NightCall Girls Nikol 7397865700 Ridhima Hire Me Full Night
Call Girls Nikol 7397865700 Ridhima Hire Me Full Night
 
VIP Call Girls Bara Bazar - Phone No 8250192130 For Ultimate Sexual Urges
VIP Call Girls Bara Bazar - Phone No 8250192130 For Ultimate Sexual UrgesVIP Call Girls Bara Bazar - Phone No 8250192130 For Ultimate Sexual Urges
VIP Call Girls Bara Bazar - Phone No 8250192130 For Ultimate Sexual Urges
 
Kolkata Call Girl Kalyani 👉 8250192130 ❣️💯 Available With Room 24×7
Kolkata Call Girl Kalyani 👉 8250192130 ❣️💯 Available With Room 24×7Kolkata Call Girl Kalyani 👉 8250192130 ❣️💯 Available With Room 24×7
Kolkata Call Girl Kalyani 👉 8250192130 ❣️💯 Available With Room 24×7
 
Hi Class Call Girls In Goa 7028418221 Call Girls In Anjuna Beach Escort Services
Hi Class Call Girls In Goa 7028418221 Call Girls In Anjuna Beach Escort ServicesHi Class Call Girls In Goa 7028418221 Call Girls In Anjuna Beach Escort Services
Hi Class Call Girls In Goa 7028418221 Call Girls In Anjuna Beach Escort Services
 
Pallawi ❣ 💓 Pallawi 09167673311 💓Call Girl in Thane Near Hiranandani Estate ...
Pallawi ❣ 💓 Pallawi  09167673311 💓Call Girl in Thane Near Hiranandani Estate ...Pallawi ❣ 💓 Pallawi  09167673311 💓Call Girl in Thane Near Hiranandani Estate ...
Pallawi ❣ 💓 Pallawi 09167673311 💓Call Girl in Thane Near Hiranandani Estate ...
 
Hifi Laxmi Nagar Call Girls Service WhatsApp -> 9999965857 Available 24x7 ^ D...
Hifi Laxmi Nagar Call Girls Service WhatsApp -> 9999965857 Available 24x7 ^ D...Hifi Laxmi Nagar Call Girls Service WhatsApp -> 9999965857 Available 24x7 ^ D...
Hifi Laxmi Nagar Call Girls Service WhatsApp -> 9999965857 Available 24x7 ^ D...
 
5* Hotel Call Girls In Goa 7028418221 Call Girls In North Goa Escort Services
5* Hotel Call Girls In Goa 7028418221 Call Girls In North Goa Escort Services5* Hotel Call Girls In Goa 7028418221 Call Girls In North Goa Escort Services
5* Hotel Call Girls In Goa 7028418221 Call Girls In North Goa Escort Services
 
Fun Call Girls In Goa 7028418221 Call Girl Service In Panaji Escorts
Fun Call Girls In Goa 7028418221 Call Girl Service In Panaji EscortsFun Call Girls In Goa 7028418221 Call Girl Service In Panaji Escorts
Fun Call Girls In Goa 7028418221 Call Girl Service In Panaji Escorts
 
Hot Call Girls In Goa 7028418221 Call Girls In Vagator Beach EsCoRtS
Hot Call Girls In Goa 7028418221 Call Girls In Vagator Beach EsCoRtSHot Call Girls In Goa 7028418221 Call Girls In Vagator Beach EsCoRtS
Hot Call Girls In Goa 7028418221 Call Girls In Vagator Beach EsCoRtS
 
Authentic No 1 Amil Baba In Pakistan Authentic No 1 Amil Baba In Karachi No 1...
Authentic No 1 Amil Baba In Pakistan Authentic No 1 Amil Baba In Karachi No 1...Authentic No 1 Amil Baba In Pakistan Authentic No 1 Amil Baba In Karachi No 1...
Authentic No 1 Amil Baba In Pakistan Authentic No 1 Amil Baba In Karachi No 1...
 
Verified Call Girls Esplanade - [ Cash on Delivery ] Contact 8250192130 Escor...
Verified Call Girls Esplanade - [ Cash on Delivery ] Contact 8250192130 Escor...Verified Call Girls Esplanade - [ Cash on Delivery ] Contact 8250192130 Escor...
Verified Call Girls Esplanade - [ Cash on Delivery ] Contact 8250192130 Escor...
 
FULL ENJOY Call Girls In Mahipalpur Delhi Contact Us 8377087607
FULL ENJOY Call Girls In Mahipalpur Delhi Contact Us 8377087607FULL ENJOY Call Girls In Mahipalpur Delhi Contact Us 8377087607
FULL ENJOY Call Girls In Mahipalpur Delhi Contact Us 8377087607
 
Kolkata Call Girl Bara Bazar 👉 8250192130 ❣️💯 Available With Room 24×7
Kolkata Call Girl Bara Bazar 👉 8250192130 ❣️💯 Available With Room 24×7Kolkata Call Girl Bara Bazar 👉 8250192130 ❣️💯 Available With Room 24×7
Kolkata Call Girl Bara Bazar 👉 8250192130 ❣️💯 Available With Room 24×7
 
(KRITI) Pimpri Chinchwad Call Girls Just Call 7001035870 [ Cash on Delivery ]...
(KRITI) Pimpri Chinchwad Call Girls Just Call 7001035870 [ Cash on Delivery ]...(KRITI) Pimpri Chinchwad Call Girls Just Call 7001035870 [ Cash on Delivery ]...
(KRITI) Pimpri Chinchwad Call Girls Just Call 7001035870 [ Cash on Delivery ]...
 

Self-descriptive Ruby programs generate themselves

  • 1. Esoteric, Obfuscated, Artistic Programming in Ruby Yusuke Endoh (@mametter) Cookpad Inc. Bath Ruby Conference 2018 (2018/03/23)
  • 2. And Now for Something Completely Different — in Ruby Yusuke Endoh (@mametter) Cookpad Inc. Bath Ruby Conference 2018 (2018/03/23)
  • 3. Yusuke Endoh (@mametter) • MRI committer – Was the release manager for 2.0 – Implemented coverage.so, keyword arguments, etc. • Branch coverage (Ruby 2.5) • Working at Cookpad Inc. – Cookpad employs two full-time Ruby committers (Koichi Sasada and me)
  • 4. • A recipe sharing platform service – Monthly Average Users: 90 million – https://cookpad.com/uk PR: Cookpad Inc.
  • 5. • A recipe sharing platform service – Monthly Average Users: 90 million – https://cookpad.com/uk PR: Cookpad Inc. We're hiring! HQ is in Bristol Aim to be No.1 in 100 countries (Now in 22 Languages and 68 Countries)
  • 6. Today's Topic • "Completely different" Ruby programs – Ruby can do anything! • Agenda – 1. Ruby with limited letters – 2. Funny, self-descriptive Ruby programs
  • 8. A Ruby program require "1234567890" 164494982952174876928097944808592 345203368399394864831728762954025 223544083864187912864887414172728 297936126807895282322033562499828 91940559064073941914244494205218
  • 9. Demo • "Hello, world!" program by using only numbers – You can encode not only Hello world, but also any Ruby programs $ ruby H3110.rb Hello, Bath & Bristol Ruby! $ Hello world only by numbers
  • 10. Internal • Gödel numbering • Ruby's black magic Hello world only by numbers
  • 11. Internal: Gödel numbering • A technique to encode any given string to a natural number – In: a byte array 𝑛1, 𝑛2, 𝑛3, 𝑛4, 𝑛5, … – Out:2 𝑛1 × 3 𝑛2 × 5 𝑛3 × 7 𝑛4 × 11 𝑛5 × ⋯ – To decode it, use prime factorization • The gem uses much easier way – Encoding: str.unpack("H*")[0].hex – Decoding: [num.to_s(16)].pack("H*") Hello world only by numbers
  • 12. Internal: Ruby's black magic • How to get the number – It is just placed at the toplevel of code • My answer: – ObjectSpace.each_object(Integer) • Unsure if this is portable, but it works anyway – Try to decode all enumerated integers, identify the desired Ruby code, and eval – See the source code (32 lines) in detail • https://github.com/mame/1234567890 Hello world only by numbers
  • 13. How to install Hello world only by numbers $ gem install 1234567890_ Don't forget underscore! (rubygems.org required at least one letter)
  • 14. Hello world only by "_" require "_" ____ _ _____ ____ __ ____ ____ __ ___ ____ __ __ _ ______ _____ ___ _ _ ___ _____ ______ ____ _ _ ____ _ _ ____ _ ____ __ __ ___ _ ______ ___ __ ______ _ ___ _____ __ ____ __ ___ ___ ______ ___ _ ______ ___ __ _ ___ _ ______ ___ __ ______ _ ____ __ _ ___ ______ ____ ____ __ __ ____ __ ___ ____ _ ____ ____ _ _ _ ______ ___ ___ __ _____ ____ __ ____ ___ _____ ___ ____ ___ __ _ ______ ____ _ ______ _____
  • 15. Demo • "Hello, world!" program written using only underscores $ ruby __hello__.rb Hello, Bath & Bristol Ruby! $ Hello world only by "_"
  • 16. Internal: Base-6 • Encode the Gödel number in Base-6 • Represent each digit with underscores – Use length (n+1) for digit n • Why base-6 is chosen? – To minimize the expected code length: log 𝑏 126 × ൗ𝑏 2 + 1 + 1 Hello world only by "_" 304313… ____ _ _____ ____ __ ____ …
  • 17. You can install $ gem install _ Hello world only by "_"
  • 18. Summary • Ruby beats letter limitation • More? – See my RubyConf 2017 talk begin begin begin public begin begin def each clear rescue begin begin begin end end end concat begin dup ensure concat begin clear concat concat concat concat concat concat size concat begin begin begin size end end end begin size end ensure begin clear end end end concat begin dup ensure concat begin clear begin concat concat size end until hex concat concat concat concat begin size end concat concat begin size end rescue upcase begin concat begin concat size end end begin size end ensure begin clear end end end concat begin dup ensure concat begin clear concat begin concat size end unless begin end begin concat concat concat begin size end end @_="_"=~/$/;_=@_+@_;$><<(""<<(_*_*_+@_)*_*_*_<< ((_+@_)*_*_*_+@_)*_*_+@_<<(((_+@_)*_*_+@_)*_+@_ )*_ *_ << ( ( (_+@_ )*_*_+ @_) * _+ + @_) * _*_ <<((((+ _+@_)*_ * _+ + +@_ )*_+@_)* _++ @_ )* _ ++@_ <<((_*_+@_ )*_ + + + @_)* _*_ <<_*_*_*_* _<< ( (_ * _ +@_) *_*_*_++@_ )*_<<(((_++@_)*_+@_)*_*_+@_)*_*_+@_<<((_+@_)*_* _*_*_ +@_)* _<<( ( (_+ +@_ )*_ ++ @_ ) *_+ @_) *_*_*_+ @_<< ( _* _ *_*_*_++ @_) *_+@_<< (((( _ ++ + +@_)* _*_ ++ @_ )* _ +@_)*_++ @_)*_ +@_<< (((( _+ + @_)*_*_+ @_)*_+@_)*_+@_)*_<<(((_+@_)*_*_*_+@_)*_+@_)*_<< _*_*_*_*_+@_<<(_*_+@_)*_)#_$`/^|:()[_-|?|_||:`/ Only symbols Only alphabets
  • 21. Self-descriptive FizzBuzz eval(s=s= %w@proc{| n|z=32.ch r;k="[#{n +=1}]";u= ":>==;<==?"[m=n**4 %-15,m+13]||"#{$f= k}";d="Y.E.#{c=64. chr}*'')";$f||d<<z +k;t="eval(s=s=%w# {c+s=s[0, 334]}#$f# ";25.time s{|y|m=u. bytes.map {|v|t<<s; (0..[62-v ,2].min). map{|x|"i f0zgl11p0 zghuhku744d8hzeg41qtfx7xs7t wflr".to_i(36)[x+32+v*3-y/5 *44]<1?z*9:t.slice!(0,9)}<< z}.join.rstrip;y>23&&m[-9,9 ]=d;puts(m)}}[1]#pY.E.@*'') eval(s=s=%w@proc{|n|z=32.ch r;k="[#{n+=1}]";u=":>==;<== ?"[m=n**4%-15,m+13]||"#{$f= k}";d="Y.E.#{c=64.chr}*'')" ;$f||d<<z+k;t="eval(s=s=%w# {c+s=s[0, 334]}#$f# ";25.time s{|y|m=u. bytes.map {|v|t<<s;(0..[62-v,2].min). map{|x|"if0zgl11p0zghuhku74 4d8hzeg41qtfx7xs7twflr".to_ i(36)[x+32+v*3-y/5*44]<1?z* 9:t.slice!(0,9)}<<z}.join.r strip;y>2 3&&m[-9,9 ]=d;puts( m)}}[2]#p roc{|n|z= 32.chr;k="[#{n+=1}]";u=":>= =;<==?"[m=n**4%-15,m+13]||" #{$f=k}";d="Y.E.#{c=64.chr} *'')";$f||d<<z+k;t="eval(s= s=%w#{c+s=s[0,334]Y.E.@*'') eval(s=s=%w@proc{|n|z=32.ch r;k="[#{n+=1}]";u=":>==;<== ?"[m=n**4%-15,m+13]||"#{$f= k}";d="Y.E.#{c=64.chr}*'')" ;$f||d<<z+k;t="eval(s=s=%w# {c+s=s[0, 334]}#$f# ";25.times{|y|m=u. bytes.map{|v|t<<s; (0..[62-v ,2].min). map{|x|"if0zgl11p0 zghuhku744d8hzeg41 qtfx7xs7t wflr".to_ i(36)[x+32+v*3-y/5 *44]<1?z*9:t.slice !(0,9)}<< z}.join.r strip;y>23&&m[-9,9 ]=d;puts(m)}}#proc {|n|z=32. chr;k="[# {n+=1}]";u=":>==;< ==?"[m=n**4%-15,m+ 13]||"#{$f=k}";d="Y.E.#{c=6 4.chr}*'' )";$f||d< <z+k;t="eval(s=s=%w#{c+s=s[ 0,334]}#$ f#";25.ti mes{|y|m=u.bytes.map{|v|t<< s;(0..[62 -v,2].min ).map{|x|"if0zgl11p0zghuhku 744d8hzeg 41qtfx7xs 7twflr".to_i(36)[x+32+v*3-y /5*44]<1? z*9:t.sli ce!(0,9)} <<z}.join .rstrip;y >23&&m[-9 ,9]=d;put s(m)}}pro c{|n|z=32 .chr;k="[ #{n+=1}]" ;u=":>==; <==?"[m=n **4%-15,m +13]||"#{ $f=k}";d= "Y.E.#{c= 64.chr}*' ')";$f||d <<z+k;t=" eval(s=s= %w#{c+s=s [0,334]}# $f#";25.t imes{|y|m=u.bytes. map{|v|t<<s;(0..[6 2-v,2].mi n).map{|x |"if0zgl11p0zghuhk u744d8hzeg41qtfx7x s7twflr". to_i(36)[ x+32+v*3-y/5*44]<1 ?z*9:t.slice!(0,9) }<<z}.joi n.rstrip; y>23&&m[-9,9]=d;pu ts(m)}}proc{|n|z=3 2.chr;k=" [#{n+=1}] ";u=":>==;<==?"[m= n**4%-15,Y.E.@*'') [3]
  • 22. Internal • Reconstruct self • Reshape itself as the next number – Embedded font data – Fizzbuzz – Shaping • Output the result • Make it "executable ASCII-art" Self-descriptive FizzBuzz eval(s=s= %w@proc{| n|z=32.ch r;k="[#{n +=1}]";u= ":>==;<==?"[m=n**4 %-15,m+13]||"#{$f= k}";d="Y.E.#{c=64. chr}*'')";$f||d<<z +k;t="eval(s=s=%w# {c+s=s[0, 334]}#$f# ";25.time s{|y|m=u. bytes.map {|v|t<<s; (0..[62-v ,2].min). map{|x|"i f0zgl11p0 zghuhku744d8hzeg41qtfx7xs7t wflr".to_i(36)[x+32+v*3-y/5 *44]<1?z*9:t.slice!(0,9)}<< z}.join.rstrip;y>23&&m[-9,9 ]=d;puts(m)}}[1]#pY.E.@*'')
  • 23. Quine • A program that outputs itself • Trick – Step 1. Reconstruct self as a string – Step 2. Print it • Additional step makes Quine "funny" eval s="puts('eval s='+s.inspect)" Self-descriptive FizzBuzz
  • 24. Embedded font data Self-descriptive FizzBuzz • Original data (165 bytes) • Replace spaces with "0", and "#" with "1" • Interpret each line as binary number (50 bytes) • Shorten them by to_s(36) (35 bytes) ### ## ### ### # # ### ### ### ### ### ### ## # # # # # # # # # # # # # # # # # # ## # # # ### ### ### ### ### # ### ### ### ## # # # # # # # # # # # # # # # # # # # ### ### ### ### # ### ### # ### ### # ## # ## 111 110 111 111 101 111 111 111 111 111 111 110 0 00 101 010 001 001 101 100 100 001 101 101 100 101 1 11 101 010 111 111 111 111 111 010 111 111 111 110 0 01 101 010 100 001 001 001 101 010 101 001 100 101 1 10 111 111 111 111 001 111 111 010 111 111 100 110 1 11 1073733623,2905756245,1063256021,2371130133,1063231487 0hr9u5z, 1c20fv9, 0hl19lh, 137pjpx, 0hl0qnz
  • 25. Executable ASCII-art • Write a code with no space and backslash • Wrap it with "eval(%w(" and ").join)" • You can shape your code as you like puts"Hello,world!" eval(%w(puts"Hello,world!").join) eval(%w(pu ls "H el lo ,w or ld!")*"")# #=> Hello,world!
  • 26. Quine-relay eval$s=%q(eval(%w(B=92.chr;g=32.chr;puts(eval(%q(N=10.chr;n=0;e=->s{Q[Q[s,B],?"].K(N,B+?n)};E=->s{'("'+e[s]+'")'};d=->s,t=?"{s.K(t){t+t}};def~f(s,n)s.K(/.{1,#{n*255}}/m){yield$S=E[$s=$&]}end;Q=->s,t=?${s.K(t){B+$&}};R=";return~0;";V=-> s,a,z{s.K(/(#{B*4})+/){a+"#{$&.size/2}"+z}};C=%w(System.Console~Write);$C=C*?.;$D="program~QR";$G="~contents~of"+$F="~the~mix!g~bowl";$L="public~static";rp=->s,r{v="";[r.!ject(s){|s,j|o={};m=n=0;s.size.times{|i|o[f=s[i,2]]||=0;c=o[f]+= 1;m<c&&(m=c;n=f)};v=n+v;s.K(n,(j%256).chr)},v]};%(fn~mX{Z`x21("{}",#{E["object~QR~extends~App{#{f(%((display~"#{e[%(Zf("1d;s/.//;s/1/~the~sum~of~a~son~and0/g;s/0/~twice/g;s/2/`x59ou~are~as~bad~as/g;s/3/~a~son`x21Speak~your~m!d`x21/g^n# The~Relay~of~Qu!e.^n#Ajax,~a~man.^n#Ford,~a~man.^n#Act~i:~Qu!e.^n#Scene~i:~Relay.^n#[Enter~Ajax~and~Ford]^n#Ajax:^n#");function[]=f(s);for~i=1:2:length(s),Zf("2%s3",part(dec2b!(hex2dec(part(s,i:i+1))),$:-1:2)),end;endfunction`n#{s,v=rp ["Transcript~show:~'#{d["Z"+E[%(fun~p~n=Z(Int.toSJ~n`x5e"~");p~0;p~0;p~130;List.tabulate(127,p);SJ.map(fn~c=>(p(3+ord~c);Z"-1~0~";c))#{E[%(puts~"#{Q[e[%(echo~'a::=`x7e#{Q[Q["let~s=#{E["!t~mX{Z#{d[E[%(module~QR;!itial~beg!~#{f("let~s=#{ E[%(Module~QR:Sub~MX:Dim~s,n,i,c~As~Object:n=Chr(10):For~Each~c~!"#{d["<?xml#{O="~version='1.0'"}?><?xml-#{I="stylesheet"}~type='text/xsl'href='QR.xslt'?><xsl:#{I+O}~xmlns:xsl='http://www.w3.org/1999/`x58SL/Transform'><xsl:output~metho d='text'/><#{U="xsl:template"}~match='/'><`x21[CDATA[#{%(sub~f(s$,n)Z(s$);:for~i=1to~n~Z("Y");:next:end~sub:f("#{V[e[%(H,format="#{y="";f("^H{-}{txt}{#{Q["echo~-E~$'#{Q[Q[E[%(with~Ada.Text_Io;procedure~qr~is~beg!~Ada.Text_Io.Put("#{d[% (!terp:library"afnix-sio"`ntrans~O(n){trans~o(afnix:sio:OutputTerm)`no:H(Byte(+~128~n))}`ntrans~f(v~n){`nO(+(/~n~64)107)`nO(n:mod~64)`nO~v}`ntrans~D(n){if(<~n~4){f(+(*~6~n)9)48}{if(n:odd-p){D(-~n~3)`nf~27~48`nf~36~11}{D(/~n~2)`nf~21~48 `nf~48~20}}}`ntrans~S"#{e[%W[STRINGz:=~226+~153,a:=z+~16 6,b:=a+"2 "+z+~160,c:=b+"8"+z+~165,t:="#!clude<iostream>"+~(10)+"!t"+~(32)+"mX{puts#{d[E[%(class~QR{#$L~void~ma!(SJ[]v){System.out.Z(#{E["H('#{Q[e["implement~ma!0()=Z"+E["BEGIN{ Z#{E[%(echo~'#{%(f(s){System.out.Z(s);}s="389 **6+44 *6+0 0p45*,"; for(c:#{E[(s="#!clude<iostream>`n!t~mX{std::cout<<#{E[%(class~Program{#$L~void~MX{#$C("Qu!e~Relay~Coffee.^n^nIngredients.^n");for(!t~i=9;i++<126;)#$C($"{i}~ g~caffe!e~{i}^n");#$C("^nMethod.^n");foreac h(c h ar~c~!#{E[%((doseq[s(lazy-cat["IDENTIFICATION~DIVISION.""PROGRAM-ID.~QR.""PROCEDURE~ DIVISION."'DISPLA`x59](map~#(str"~~~~^""(.replace~%1"^""" ^"^"")"^"&")(re-seq~#".{1,45}""#{e["(f=(n )- >Array(n+1).jo!~'Y');console.log('%s',#{V[E[%((H-l!e"#{e["impor t~std.stdio;void~mX{H(`x60#{%(method~MX{Z(@"#{d[" [#{%(class~QR:Application{void~f(SJ~con st~s,!t~n){for(Pr!t(s);n;n--)Pr!t("Y");}void~MX{#{f("IO.puts "+E[%((pr!c~"#{e["`nma!(_)->`nio:fH#{d[E['Zf n("""'+d[?"+"%option~noyywrap`n%%`n%%` n!t~mX{puts#{E["echo~'#{Q[Q[%(~:~A~."#{g*9}"~;~:~ B~A~."~WRITE(*,*)'"~A~;~:~C~B~T`x59PE~." ~'"~CR~;~:~D~S"~#$D"~C~S^"~Z~^"(&"~C~ S^"~#{e[%(Z"#{e["s:=OutputTextUser();Write All(s,#{E[%(Zf"#{e[d[f('set~Z"-";Z'+E [%(package~ma!;import"fmt";func~mX{ fmt.Pr!t#{E[%(236:j;{119:i;{206i-:i;.48<{ 71+}{[i]^48-*}if}%}:t;"algoritmo~Q R;!"[195][173]++'cio~imprima("'"0 1314 1"t"/12131"t~6*"/1:1918151:??62714 13/4=3626612/2 /353251215/`x5a0`x5a0R"t"#{e[%( show~"z=new~java.util.zip.G`x5aI POutp utStream(System.out);z.H('#{ "ma!=putStr"+E["class~QR{#$L ~function~mX{neko.Lib.Z#{E[%(p rocedure~mX;i:=c:=0;s:=#{E[%(.c lass ~public~QR`n.super~#{$T="ja va/io/Pr!tStream"}`n.method~#$L~ma!([L #{S="java/lang/S"}J;)V~;]`n. limit~stack~2`ngetstatic~#{S}ys tem/out~L#$T;`nldc~"#{ e[%(class~QR{#$L~void~ ma!(SJ[]v){SJ~c[]=new~SJ[99999],y="",z=y,s=" #{z=t=(0..r=q=126).map{|n| [n,[]]};a="";b=->n{a<<(n%78+55) %84+ 42};(%(P={0:'[+[]]',m:'((+[])'+(C= "['constructor']" )+"+[])['11']"};for(R~!~B=('`x21[]@`x21`x21[]@[][[ ]]@'+(A="[]['fill']")+"@( []+[])['fontcolor']([])@(+('11e20 ')+[])['split']([])@"+A+C+"('return~escape')()("+ A+')').split( '@'))for(E~!~D=eval(G='('+B[R]+'+[])'))P[T=D[E]]=P[T]| |G+"['"+E+"']";for(G='[ ',B=0;++B<36;)P[D=B.toSJ(36)]= B<10?(G+='+`x21+[]')+']':P[D]||"(+('"+B+"'))['to'+( []+[])"+C+"[ 'name']]('36')";A+=C+"('console.log(unescape(^"";for(E~!~G =#{E[%(A=Z;A("echo~'k` x60");[(A("`x60`x60s"`x5e8* "i");for~j=6:-1:0;x=(Int(c)>>j)%2+1;A("`x60"*"kki"[x:x+1 ])end)fo r~c~!~jo!(["Section`x48eader+name:=QR;SectionPublic-ma!<-(";[ "^"$(replace(replace( s,"Y","YY"),"^"","Y^""))^" .Z;"for~s=matchall(r".{1,99}",#{Q[E["console.log"+Q[E[%(@s=g loba l[#{i=(s=%(`x48AI~1.2`nVISIBLE~"#{"x=sJ.K(#{V[E["changequote(<@,@ >)`ndef!e(p,<@#{"all :`n`t@echo~'#{d["l!el:99 999;Z#{E["solve~satisfy;output~[#{E[%(.assembly~t{}.method~#$L~ vo id~MX{.entrypo!t~ldstr"#{e["m{{`x21:~x`nqr:~|-`n~:db`x60#{e[s="$Z#{E[%(#!clude< stdio.h>`nmodule~QR{ }implementation{!t~mX_ _attribute__((C,spontaneous)){puts#{E["Zf#{E["echo"+E["#import<stdi o.h>#{ N}!t~mX{puts#{E["Z_sJ"+E["s=toascii#{E["Z#{E["$console:l!e[#{"# $D(output);beg!~H(# {f((p="eval";%($_="#{ s,v=rp["$_='#{Q[%(<?php~$z=3+$w=strlen($s=#{Q[E["!t~mX{H#{E["(#{?_*11} )dup~=/s(|~~~~~.~~~|)def(#{Q["qr:-H('#{Q[e["!it{#{f (%(Z('cat("')`nfor ~c~!"".jo!(["echo~'s ay~''%s'''^n"%l~for~l~!#{E[d[d["eval$s=%q(#$s)",?'],?']]}.split("^n")]): Z('r=fput(char(%d))'%ord(c))`nZ('end^n")')#),6 ){"Zf#{d[$S,?%]};" }}}"],?']}').",B]}) {9~7{exch~dup~1~and~79~mul~32~add~exch~2~idiv~3~1~roll~s~exch~2~!dex~exch~p ut~1~sub~dup~6~eq{1~sub}if}repeat~s~=~pop ~pop}forall~=~quit "]+R}}"]]})*3;echo" ^x89PNG^r^n^x1a^n";$m="";$t="^xc0^0^xff";for($i=-1;++$i<128*$z;$m.=$c--?($w- $c||$i>$z)&&$i/$z<($c<$w?ord($s[(!t)( $c/3)]):$c--%3+2)? $t[2].$t[$c%3%2].$ t[$c%3]:"^0^0^0":"^0")$c=$i%$z;foreach(array("I`x48DR".pack("NNCV",$w+2,128,8,2 ),"IDAT".gzcompress($m),"IEND")as$ d)echo~pack("NA*N ",strlen($d)-4,$d, crc32($d));).K(B,"`x7f"),?']}';s:g/^x7f/Y/;Z~$_",128..287];s="$_='#{Q[s,c=/['Y]/ ]}';$n=32;$s='#{Q[v,c]}';$s=`x7 es{..}{$a=$&;$b=c hr(--$n&255);`x7e s/$b/$a/g;}eg;Z";(s+N*(-s.size%6)).unpack("B*")[0].K(/.{6}/){n=$&.to_i~2;((n+14)/2 6*6+n+47).chr}}";s|.|$n=ord $&;substr~unpack( B8,chr$n-!t($n/32 )*6-41),2|eg;eval~pack'B*',$_).scan(/[~,-:A-z]+|(.)/){p="s++#{$1?"chr~#{$1.ord}+e": $&+?+};"+p};p),1){"'#$s' ,"}}'')end.".K(/[: ;()]/){?`x5e+$&}} ]"]};quit"]};t=num2cell(b=11-ceil(s/13));for~n=1:9m={};for~i=1:141f=@(x,y,n)repmat ( ['Ook'~char(x)~'~Ook' ~char(y)~'~'],[1~a bs(n)]);m(i)=[f(z =46,63,n)~f(q=z-(i<13)*13,q,i-13)~f(33,z,1)~f(63,z,n)];end;t(x)=m(diff([0~s(x=b= =n )])+13);en d;Zf ('%%s',t{:})"]]+R} }"]]}`n"]};return~ 0;}~})]};"]}`x60` n~global~_start`n~_start:mov~edx,#{s.size}`n~mov~ecx,m`n~mov~ebx,1`n~mov~eax,4` n ~!t~128`n~mov ~ebx,0`n~mo v~eax,1`n~!t~12 8`nx:~|`n~}}{{{qr}} }"]}"call~void~[ms corlib]#{C*"::"}(sJ)ret})]}];"]};quit();",?$].K(?'){"'^''"}}'"}@>)`np"],?&,?& ] },'&(%d+)&',fu nction(s)retur n~sJ. rep('Y',tonu mber(s))end);Z(x)". K(/[:"]/,":^0")}"` n`x4bT`x48`x58B`x59E~B`x59E)).size+1}x~i8]c"#{s.K(/[^"`n`t]/){"^%02`x58"%$ &. ord}}^00"declare~i32@puts(i8*)d ef!e~i32@mX{ %1=call~i 32@puts(i8*getelemen tptr([#{i}x~i8],[#{ i}x~i8]*@s,i32~0,i32~0))ret~i32~0})],?#]]]})];");"],"^n")];[for~i=0:2:4; x=(( Int(c)%83-10)>>i)%4+1;A("ski`x60 "[x:x])end~for~c ~!"AG- `x48-`x48Fy.IlD==;=jd lAy=;=jldltldltl{lAu lAy=jtlldlAyFy=?=jdlAyGFyFyG2AFy>zlAFFBCjldGyGFy>GFy.AGy=G==n`x48==nl ldC=j@=j tlldltldlAut11"];A("'"))]})A+="' +`x21[]+'"+G.charCo deA t(E).toSJ(16);for(A+=" ^".replace(/'+`x21[] +'/g,^"%^")))')()",R=0;R<9;R++)A=A.replace(/'.*?'/g,function(B){T= [];for(E=1 ;B[E+1];)T.push(P[B[E++]]);return~T.jo!('+')});conso l e.log('"'+A+'"'))).byte s{|n|r,z=z[n]||(b[r/7 8];b[r];q<6083&&z[n]=[q+=1,[]];t[n])};b[r/78];b[r]}";!t~i=0,n=0 ,q=0;for(;++n< 126;)c[n]=""+(char)n;for(;i<#{a.size};){q=q*78+(s .charAt(i)-13)%84;if(i++ %2>0){y=q<n?c[q]:y;c[n ++]=z+y.charAt(0);System.out.Z(z=c[q]);q=0;}}}})]}"`n!vokevi rtual~#$T/Zln(L#{S }J;)V`nreturn`n.end~method)+N]};H("DO,1<-#"|| *s);s?while~t:=ord(move(1) )do{i+:=1;u:=-i;every~0t o~7do{u:=u*2+t%2;t/:=2};H("PLEASE")^(i%4/3);H("DO,1SUB# "||i||"<-#"||((c-u)%2 56));c:=u;};H("PLEASEREADOUT,1^nPLEASEG IVEUP");end)]};}}"].tr(?"+B ,"`x21`x7e")}'.tr('`x7e`x 21','YY^u0022')as~byte[]);z.close()"`n)]}"{"W""w"@j ~1+:j^-~118%1+*}%"/35512 416612G61913@921/17A331513"t'") ;fim')]};})],61){"Zn#$S`n"},? %]]}"`nquit)]});CloseStream (s);QUIT;"]}")]}"~DUP~A~."~DO~10~I=1,"~.~CR~S "~&A,&"~C~."~10~~~~~~CONTINU E"~CR~S^"~&A)^",&" ~C~0~DO~B~."~&char("~COUNT~.~." ~),&'"~CR~LOOP~S^"~&^"^""~C~S "~end~#$D"~C~A~."~STOP"~CR~A~."~END"~CR ~B`x59E~;~D~),B],?`x21].K(?',%('"' "'))}'"]};}".K(?"){'"34,"'}.K(N){ '"10,"'}+?",?%]+'~""")'],?`x7e] }."]}"))],15){"f(#{V[$S[1..-2] ,'",',');f("']},0);"}}}})}]pq"]}");})} `x60);}"]}"))].K(?`x60,"Yx60"),'#{f (',')}']})"]}"))["~~~~^"~^".""STO P~RUN."])](Zln( str"message(STATUS~^"~~~~~"(.replace(.replac e(str~s)"Y""YY")"^"""Y^"")"^")")))).re verse]})#$C($"Put~caffe!e~{(!t)c}~!t o#$F.^n");#$C("Liquify#$G.^nPour#$G~!to~the~bak!g~ dish.^n^nServes~1.^n");}})]};}/****//**** /";t={};b="";L="";n=i=0;D=->n{L<<(n+62) %92+35;D};s.bytes{|c|n>0?n-=1:(t[c]=(t[c]||[]).reject{|j| j<i-3560};x=[];t[c].map{|j|k=(0..90).f!d{|k|n ot~s[i+1+k]==s[j+k]}||91;k>4&&x<<[k,j]};x=x. max)?(n,j=x;x=b.size;(u=[x,3999].m!;D[u%87][u/87];L<<b[0,u];b[0,u ]="";x-=u)while~x>0;x=4001+i-j;D[x%87][x/87][n-5] ):b<<c;t[c]+=[i+=1]};"#!clude<stdio.h>`nchar*p=#{E [L]},s[999999],*q=s;!t~mX{!t~n,m;for(;*p;){n=(*p-5)%92+(p[1]-5)%92*87;p+=2;if(n >3999)for(m=(*p++-5)%92+6;m--;q++)*q=q[4000-n];else~for( ;n--;)*q++=*p++;}puts(s)#{R}}")]}){s+="00g,";for(m=1;m<256;m*=2)s+="00g,4,:"+(c/m%2>0?"4+":"")+",";f(s);s="4,:,";}f(s+s);for(c:Base64.getDecoder().decode("kaARERE`x58/I0ALn3n5ef6l/Pz8+fnz58/BOf5/7/hE`x58/O`x5azM5mC`x58/Oczm`x5azBPn5+`x 58/OczMznBL/nM5m`x5azBPu++fPPOc5zngnnO`x5azO`x5agnBMGAW7A==")){c=c<0?256+c:c;for(i=0;i++<3;c/=8)f(c%8);f("8*+8*+,");}f("@");).K(?',%('"'"'))}'|sed~-e's/Y/YY/g'~-e's/"/Yq/g'~-e's/.*/Z~"&"^nquit/')]}}"]],?']}');".K(B,?`x5e)]}.replace("`x 5e","Y"));}})]]};}";FORiTO`~UPBtDO`~INTn:=ABSt[i];Z(~(50+n%64)+c+~(50+n%8MOD8)+c+~(50+nMOD8)+b+"`x4a"+a)OD]*"REPR"]}"`ntrans~c~0`ndo{D(Integer(S:get~c))`nf~35~39}(<(c:++)(S:length))`nf~24~149)].K(N,'"&Character'+?'+'Val(10)&"')}");end; )]+"`nsys.exit~0",B],?']}'",/[^{}]/]}}",35){y<<",`n"+$S;"%s"}}")+y],'",','):f("']}",0))}]]></#{U}></xsl:#{I}>"].K~N,'"&~VbLf~&"'}":s="~~~":For~i=0To~7:s~&=Chr(32-(Asc(c)>>7-i~And~1)*23):Next:#$C(s~&n~&Chr(9)&n~&"~~"):Next:#$C(n~&n~&n): End~Sub:End~Module)]}`nput=s`nZ`nqa`x21",3){%($H("%s",#$S);)+N}}end~endmodule)],?%]+R}}"]},i=0,t='k';while(s[i])t='^x60.'+s[i++]+t;console.log(t)",B],?`x21].K(?',%('"'"'))}'"^n::=^na")],/[`[`]$]/]}")]};Z"0~0~-1";)],?']}';cr",127..255]; f(%(variable~s=`x60#{s.K(/.{1,234}/){$&.K("`x60",%(`x60+"`x60"+`x60))+"`x60+`n`x60"}}`x60,i;for(i=0;i<129;i++)s=strreplace(s,pack("C",255-i),substrbytes(`x60#{v[0,99]}`x60+`n`x60#{v[99..-1]}`x60,i*2+1,2));Zf("%s",s)),7){"f('%s')`n"%$s. unpack("`x48*")}}Zf("^n#[Exeunt]");quit)]}")),196){%(Z#$S;)}}}"]});})).gsub(/[!HJKXYZ^`~]/){[B*2,:write,B,:tring,:gsub,"ain()",B*4,:print,g,:in][$&.ord%47%12]})))*"")#_buffer_for_future_bug_fixes_#_buffer_for_future_bug_fixes_#_buffer_ ############################################################################## Quine Relay -- Copyright (c) 2013, 2014 Yusuke Endoh (@mametter), @hirekoke #############################################################################)
  • 27. Quine-relay • A Ruby code • that generates Rust code • that generates Scala code • … • that generates REXX code • that generates the original Ruby code 128 languages involved in total Quine-relay
  • 28. Quine-relay • A Ruby code • that generates Rust code • that generates Scala code • … • that generates REXX code • that generates the original Ruby code 128 languages involved in total Quine-relay
  • 30. Internal – Step 1. Reconstruct self as a string – Step 2. Wrap Python's Hello world – Step 3. Print it Quine-relay eval s="puts( 'eval s='+s.dump )" Ruby's Quine print( "Hello!" ) +Python's Hello world eval s="puts('print('+('eval s='+s.dump).dump+')')" ↓RubyPython Quine
  • 31. Internal • In theory: Repeat this process for 127 languages • In practical: The naïve approach explodes the size of intermediate code – To avoid this problem, it uses many tricks • compression algorithm • on-time code generation • etc. – See the generator in detail https://github.com/mame/quine-relay/blob/master/src/code-gen.rb Quine-relay
  • 32. Monumental Quine A column object 3D model data Ruby code is inscribed You can buy it at Shapeways! https://www.shapeways.com/shops/mametter Execute the code 3D printer
  • 33. Internal • The shorter is code, the cheaper ☺ – 3D printing fee: $15 per one line – The code does not contain complex-glyph letters ("3", "8", "g") to omit them from font data 33 eval(_=%[b='DEILMQTVY';eval((%[a=(-1)EE0.5;f=->EfVf.each_slice(2)Y;c=->wVz=->dVd.mapVd=d.rotate(1)YY ;Q=->k,l,mV((m-k)E(l-k).conT).arQ<0Y;y=[];x=0.99;o,T=w.partitionV|n|d=0;z[n].mapV|k,l|y<<f[k,x,k,1,l ,1,l,x];d+=k.conTElY;d.arQ<0Y;f[o,T,[[0,d=2IEa,d+15,15]],o.map(Dd=:reverse),T.map(Dd),[]].mapV|o,T|T .mapV|h|z[h].max_byV|u,|u.realY;Y.sort_byV|i,|-i.realY.mapV|h|i,=h;v=0;o.mapV|n|z[n].mapV|x|m,l,E,k= x;e=(i-m).arQEE2;v<eDD(d=Q[k,m,l])^(Q[k,m,i]^d|(Q[m,l,i]^d))DDo.allMV|n|z[n].allMV|k,l|[i,m,k,l].uni q.size<4||Q[i,k,l]==Q[m,k,l]||Q[i,m,k]==Q[i,m,l]YYDD(v=e;w=n;T=Ex,m,Eh,i)YY;w[0..-1]=TY;o.mapV|v|t,= s=z[v];n=->rVk,m,l=r;k=k[2],l,m[2];r[I]=Q[Ek]DDv.allMV|q|z[k].anyMV|k,l|q==k||Q[k,q,l]YYY;z[s].mapV| k,l,m|l[0,2]=k,m;n[l]Y;(s[I..-1].mapVt=t[1]until(t[I]);k,m=l=t;m[0],k[1]=t;n[m];n[t=k];lY<<t).mapV|k ,m,l|y<<f[k[2],x,l,x,m[2],x]YY;x=1Y;yY;e=0;%[`^Tx52t<^cd,7/w(kabvbEz5arIwIa17.=c'slxr=-'4|e)EwkMI,_^ pvMVhsnME.rLw_k)^tp>+TIEduE45u>mv%^Y=Vny-`zce)k`heIt%`Vzf;c2nk4d|Vp^D_,,|kDDL2r_sDy%%fiMV6cYE)5`,m/k YQ/;IEezMVv,QchILY|p%%i<vstDt)=M7vLcT>=4Q2(vwael61//<ck>-l67uQ;2Tq,c_'qEIcm1cL;i++2-tYdbenq%pxr;2'Vn (uDa)n)zf4w)%5vh;ssV5kI;)z;2=+Toe<VL_D0`VLu;ook_y+eT`>IeT9-(i<MiVdd)ib_y+x`s^_u>M1s/mYQvEY`vMxu%Y0u5 7Qaoh2<Mkd'vtkp^zTc`E->Ep+icop_u0%=-zv,omq`Qz/41DV'`f9L5`M'bVxx%/;qLtq12%q:V'9,fD,ovu%qr|+e+rudI`Ir0 5chVd+Q5`II76rY0laT%b(I>Y%EQ1xf^|r,1)%4--zQa'<qxL-7Y0+|'vvbIxso0usv;%.I:pLQbe5a),Vu|91(0EIv^T>c5Dmd: 9-I15%Lp/>>z57^,Th2>%la0;5`dE1<xvrd09^9zz<.t,LpofrTTsQi'u5;Lwp7+zmm`'>qy;f6)||Ikw_0wdMM5<hmn64wbQ_rD m'>so7b..4qy`nQrz%Vf7Ii^epY(x=|49Lh(=>sI_sbofb7|qM,unaD%^i:|;_tEEnb-DDt`t%I2h;0x5f^yhs,pbLf+m^e>yqzQ '%::|^=,5-b=^_1x1se`kp,%wq4T%;'E.:Dsp_V-0||,)=;.a|<%0QY:;t:fEmk:4|_%o-.:aooq/6mThdvz4`uQqY1r'em.5'z1 2p7e%%pp6ebMM,m`5QpYx'd`,`6a4T)6Q.k.E.YsdiE^ox9pyrsr%|(kfn=y9q`6;=V<z%9(0cf^yp=:Irw-c/y>%iie%)y-1i(y 'V-n^uTva%l0Q>,yz;E0:LbV'eTb6MIb``Da.__ihbacxY|fc6>pTtl;ivVt,q>/%w,=hnI+i90>10u59te,Ildw4p94x`iwvs`f +^)w1M>%wf^].bytesV|i|e=eE59+(i-5)%L9Y;Q=->iVk=e%i;e/=i;kY;d=VI2=>c[[]]Y;54.upto(1I0)V|h|d[h%L9+I7]= c[(0..Q[5]).mapVl=o=T=[];n=0;(-2..Q[17]).mapV[l=Q[2],o=Q[1I]+Q[21]Ea+1+a]Y.flat_mapV|m,n|E,(h,)=[[o, l],[(o+o=n)/2,0]][0..lDl=m]Y.mapV|o,l|n=l<1M((n==0ML:1).upto(L)V|k|T<<h+kE(n-h)/4+kEkE(o-2En+h)/64Y; h=o;0):oY;TY]Y;n=[];m=0;v=aEE0.04;z=15/v.arQ;w=-0.2I;h='eval(_=%['+_+'])';h.tr(b,']+b+%[').bytesV|o| q=-w+s=wEm+=1;r=vEp=vEEmEz;d[o].mapV|v|n<<v.mapV|v,l|T,k=v.rect;[(p+(r-p)ET/=15)El,q+wET-k]YY;m<101D Dn+=[f[p,q,r,s,E[r,0]E(m/100),r,2,p,2],f[p,2,r,2,k=rET=0.976,2,TE=p,2],f[T,2,k,2,k,x=-715,T,x],f[T,x ,k,x,r,x,p,x],f[p,x,r,x,r,s-l=690,p,q-l,E[p,x+2]E(1/m)]];Y;T=VY;k=VY;l=''<<I2;m=n.mapV|i|(p,q),(r,s) ,(t,u)=Ei;p-=r;r-=t;Mf+l+i.mapV|m|[[T,:v,Em],[k,:vn,(rE(q-s)-pE(s-u))Ea,(p.conTEr).imaQ]].mapV|T,o,p ,w|T[[o,E(p.rect<<w).mapV|p|(pE500).round/z/10Y]El]||=T.size+1YE'//'YElY;o=''<<I5;puts(%(Q%squine')% l,o+%V'+(eval(%[Y+h+%V]);exit);'Y,T.keys,k.keys,m,o+M');]).tr(b,'%)27>fiz|'.tr('x%-|','%-'<<125)));' [[[ Monumental Quine (c) 2015 Yusuke Endoh -- tested with ruby 2.2.1 -- built on 2015/04/01 ]]]']) Embedded TrueType Font Data + Renderer Triangulation Algorithm for Font Polygons 3D Model Generator Monumental Quine
  • 34. 15 quzzle • An interactive Quine eval$s=%w[b=0 x4160ab7de523 f8c9;i=(m=0.. 15).find{|i|1 >b&m=15<<4*i} ;t=m|n=m<<4*o =("AdABrBlBAu A"=~/(.)#{ARG V*''}¥1/||04| |0)-4;(n<1||n >1<<64||[255< <12]&[t>>040| |___________9 |__________12 |___________8 |__________15 |0,t>>16,t]!= [])?t=0:i+=o; ;s="eval$s=%% w[b=0x%016x"% (b^=t.&b|m&b> >o*4)+$s.gsub (/(¥|_+¥d+)+/ ,'')[/;.*/]+" ]*''||0"<<92| |1;z=s=s.scan (/.{13}/);3.t imes{|j|s[(i| |___________3 |___________2 |___________5 |__________14 |0)/4*8+i+j*4 ,0]=m=(z=32.c hr)*13};c=b;4 .times{puts(( 0..3.times{pu ts((s.slice!( 0,4)*z).rstri p)}).map{j=c% 16;c/=16;;(0| |0)<(j)?"|"+j .to_s.rjust(1 2,"_"):m}*(z| |__________13 |___________7 |__________11 |__________10 |0),z)};b==0x fedcba9876543 21&&("%b"%"1t v7c1th0wylel7 3ba35knw3t".t o_i(36)).tr(" 01",".#").sca n(/.{25}/){pu ts$&}]*''||0¥ |___________6 |___________1 |___________4
  • 35. Tiq-taq-toe • The world's first quine containing AI s="n=' '[0,2] d|=1<< $*[0]. to_i-1 ;m,i=[ f=proc {|b|a= [];[73 ,7,84, 273,56 ,146," proc{| t|[t*= "",s].map{|u|u.gsub!(35.chr,"")};d=0000000;eval(s+t)}[ %w(448,292].find{|m|b&m==m}?1:9.times{|i|b&(513<<i)<1& &a<<[-f[1<<i|b>>9|b<<9][0],i]}&&a.min||0}][0][d];s='s= "'+s.s plit*' '+'"pr oc{|t| [t*="" ,s].ma p{|u|u .gsub! (35.ch r,"")} ;d=0%0 6o;eva l(s+t) }[%%w( '%d|=$*[0]?0:512<<i;s<<t+")]";27.times{|y|i=y/10;y%=10 ;puts(y>6?s.slice!(0,54):(0..4).map{|x|x&1>0?(i+=3;s.s lice!(0,6)):62[y]<1?n*7:n+(y*5-5...y*5).map{|j|1105[j- 7]<1&& d[i]|d [i+9]> 0&&~j& 5981[j /2]^d[ i]>0?3 5.chr* 2:n;}* ""+n}* "")}|| __(C). YEndoh 2009)]
  • 36. qng and qif  qng – A png image file containing Ruby code that produces this image  qif – A gif version
  • 37. Lipogram Quine format= %%->{#({#){#.{#0{#1{#2{#3{#4{#5{#6{#7{#8{#9{#h{#k{#l{#p{#v{#w{#<{#*{#a{#b{#c{#d{#e{#f{; t=->s,x,y{->&u{u[s,x,y]}[&:tr]};z="!-{";->&u{u[y="().0123456789hklpvw<*abcdef¥¥",t["m~i",",-~", "$-{"]+t["$",z,"i-{"],t[t["YQUO@g=`@W='@ABCDEFGHIJKLMNOPQRSTUVWXYZ';g=^YQUO@g=`@^+g+^AA^;Y=?=;n =Y+OoWUO_Q UriUVOYsTY+Y;x=- >s{sBVyt Ys};q,=n[u =^ZormUt^]?@u =ZormUtA?[ DC,TFEBBDEI]-x[u +?`]:x[W +?`]-x[y]: n=~/=Z?o?r?m? U?t?=/?x[u ]-x[$&]:Y;z='ZormUt= C``->{H{Dt=- >s,x,y {Js,x, y]}[&: tr]};z=^!-{ ^;Jy=^I^,t [^m~iK,-~K$-{^]+t[^$ ^,z,^i-{^],t [t[^EK C^+$/, ^^],^G ^,t[^qntuz| yKm-|^,z]+ t[^;jmnrxy>,K&-{K$-{ ^]+t[^o;tK/- {^,z]] ]}[&Jt [^xjsi K&-{^,z]]}[ &:to_sym]] }[]`;DYQUO^@YQUO@@`R ``SS`R`F`T`` `ABPUW N@``MT `AAA^' BgsuV@/[C-L ]/A{[FEBWM r,$/,gBtr@'`^'+W,j=L IBWMrSSLGSSI GSSGHSSL CA,TgB unPUWN@^MT^ A,j,?#+WBW MUrsT^{#^,W+LEBWMrTE ,^->&u{u[^,' ^,^'][YQ UO$&]} ;GGBtimYs{| y|Print@@@ CBBLGABmUP{|x|^qZXzm uDHjtVOCuVnO ooCYHWIJyrnonDmE GtijRU oNFxGWXxuOm CmIEYRXsgZ EgqOKQMGHJOKQnYuuVYy IrCEmrPqVgno irYDnnxLDjZWCGyN nZmnIy zKXignRYPnz DuCYgMHyyM JjqWYD ODruUPCm DtqFqFDCrrJVxXJzOg MWQGNnUuio^Bt o_i@FIA[x/ E-D+@y +DA/ETGI ]>C?@FEBWMrA:@z[C] ==$/||!z[C]?? ;:zBsOiWY!@C,DAA}T^^+$/ABtr@@!$T[C]&&q||CABWMr,^^AA;z[C]==$/&&z[C]=^^};Yxit;;;;;;;AA"," "+$/,"" ],"`^@-Z",t["qntuz|y","m-|",z]+t[";jmnrxy>,","&-{","$-{"]+t["o;t","/-{",z]]]}[&->&u{u[t["xjsi", "&-{",z]]}[&:to_sym]]}[]%;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; eval"(eval((%w%%<<%w%566716c68276d3528236d3728292e20313233343536373839386b6c6076777c3a216263646 566672b376d322566716c68276d3528222b276b222929222b356d3f3d3b3e6d356b2c6f63616c6f5671627961626c65 637a256b256b387d3d2e337b737e22697475637d7b317c2d3e6b557d32266f627d6164722d5f38257d366f627d61647 92f3b51303c2a23323e2e2132363d5d287b557b2f352d5a387b536b2f352d5d287b597d5a3e6d3e7f2d366f3f6f327f 3d6f316f347f3d3f2f387b557d5d287b54262d5a356b3a7d37266f627d61647d3035252d2e3b753b71347d3d2e337c2 87c297b77337c287c297d5d7b562a34727d5d7b3a7d32212d2b722b37397d3226322c247b522d6e79683c2d2e78342d 2b722d5b247b5224222c2a7c22296d2b722d5c247b547b52223830322b242f2c22222d5c2224322c247b52217e64757 a7c79783d6d2c7 22c2a7 d5b247b522b3 a6d6e62787 97e3c2 8362d2b7834 2d2b722d5b247b 522f6b 34783f2d2b72 2c2a7d5d5d 5d7b56 27347b52287 a637968362d2 b722c2a7d5d5d7 b562a3 47f6f537 97 d6d5d5d7 b5 d552b313566 716c62282566 716c6828252775 252c3c 35277523 35 2a252525 29 2e2071636b6 82525286a2 529292922272e276 375726 82f2b5 03d293 d5f292 b7b53323e23 68627c242f 2c276e2472782725 22272b 236c2a 6d3936 3e2368 627c3c39343 c3c36343c3 c343 53c3c3 930392 c2a276 e257e6 071636 b6 82 2286a22292c 2a6c2f332b 236e 236861 62737a 222b73 222c23 6b2932 3e 23 68627a223c2 22d2e36257 b757b5 22c272 22c22272d5 b55667 16 c6 4262d5d7b34 343e24796d 65637b 7c797c 7072796e64 782828 20 3e 2e2934392e2 d61607b7c787 c722 176646 a7d6 571353a6 4726c6 035726 e6c6f6 f6035653366 3739727e6f6e 613d 623434 796a 67716f6b 633874 336468 757c6d 603d6632356 77463776662376 17c683 678643 5373c6 8367e6 565757 265697 63270323d62 707172676e6f69 627561 3e6e68 79313a 666360 34397b 6e666d 6e66397a783 469676e6775607e6a71357035676865397978673a617365613c6132757160703d613471733173313032727732687467 3a7c67686366743b6e6165796f622e247f6f59682336392b587f223d213b28297b21392f223a24363d5e303f3823323 e236862792a382a7b503d5d3d342f2c7c712a7b503d5f3f3b3a3a7e237c6963656128203c2139292d7a22222b242f29 2e2472782821242a2b503d5626217c7c70392e2368627c222229292b3a7b503d5d3d342f26262a7b503d5d32222d7b3 56879647b3b3b3b3b3b3b39292%*%%%).pack(%%h*%)))";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  • 38. Demo • Works as an ordinary Quine $ ruby lquine.rb > lquine2.rb $ diff –s lquine.rb lquine2.rb lquine.rb and lquine2.rb are identical Lipogram Quine
  • 39. "a" is removed from the world! format= %%->{#({#){#.{#0{#1{#2{#3{#4{#5{#6{#7{#8{#9{#h{#k{#l{#p{#v{#w{#<{#*{#a{#b{#c{#d{#e{#f{; t=->s,x,y{->&u{u[s,x,y]}[&:tr]};z="!-{";->&u{u[y="().0123456789hklpvw<*abcdef¥¥",t["m~i",",-~", "$-{"]+t["$",z,"i-{"],t[t["YQUO@g=`@W='@ABCDEFGHIJKLMNOPQRSTUVWXYZ';g=^YQUO@g=`@^+g+^AA^;Y=?=;n =Y+OoWUO_Q UriUVOYsTY+Y;x=- >s{sBVyt Ys};q,=n[u =^ZormUt^]?@u =ZormUtA?[ DC,TFEBBDEI]-x[u +?`]:x[W +?`]-x[y]: n=~/=Z?o?r?m? U?t?=/?x[u ]-x[$&]:Y;z='ZormUt= C``->{H{Dt=- >s,x,y {Js,x, y]}[&: tr]};z=^!-{ ^;Jy=^I^,t [^m~iK,-~K$-{^]+t[^$ ^,z,^i-{^],t [t[^EK C^+$/, ^^],^G ^,t[^qntuz| yKm-|^,z]+ t[^;jmnrxy>,K&-{K$-{ ^]+t[^o;tK/- {^,z]] ]}[&Jt [^xjsi K&-{^,z]]}[ &:to_sym]] }[]`;DYQUO^@YQUO@@`R ``SS`R`F`T`` `ABPUW N@``MT `AAA^' BgsuV@/[C-L ]/A{[FEBWM r,$/,gBtr@'`^'+W,j=L IBWMrSSLGSSI GSSGHSSL CA,TgB unPUWN@^MT^ A,j,?#+WBW MUrsT^{#^,W+LEBWMrTE ,^->&u{u[^,' ^,^'][YQ UO$&]} ;GGBtimYs{| y|Print@@@ CBBLGABmUP{|x|^qZXzm uDHjtVOCuVnO ooCYHWIJyrnonDmE GtijRU oNFxGWXxuOm CmIEYRXsgZ EgqOKQMGHJOKQnYuuVYy IrCEmrPqVgno irYDnnxLDjZWCGyN nZmnIy zKXignRYPnz DuCYgMHyyM JjqWYD ODruUPCm DtqFqFDCrrJVxXJzOg MWQGNnUuio^Bt o_i@FIA[x/ E-D+@y +DA/ETGI ]>C?@FEBWMrA:@z[C] ==$/||!z[C]?? ;:zBsOiWY!@C,DAA}T^^+$/ABtr@@!$T[C]&&q||CABWMr,^^AA;z[C]==$/&&z[C]=^^};Yxit;;;;;;;AA"," "+$/,"" ],"`^@-Z",t["qntuz|y","m-|",z]+t[";jmnrxy>,","&-{","$-{"]+t["o;t","/-{",z]]]}[&->&u{u[t["xjsi", "&-{",z]]}[&:to_sym]]}[]%;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; eval"(eval((%w%%<<%w%566716c68276d3528236d3728292e20313233343536373839386b6c6076777c3a216263646 566672b376d322566716c68276d3528222b276b222929222b356d3f3d3b3e6d356b2c6f63616c6f5671627961626c65 637a256b256b387d3d2e337b737e22697475637d7b317c2d3e6b557d32266f627d6164722d5f38257d366f627d61647 92f3b51303c2a23323e2e2132363d5d287b557b2f352d5a387b536b2f352d5d287b597d5a3e6d3e7f2d366f3f6f327f 3d6f316f347f3d3f2f387b557d5d287b54262d5a356b3a7d37266f627d61647d3035252d2e3b753b71347d3d2e337c2 87c297b77337c287c297d5d7b562a34727d5d7b3a7d32212d2b722b37397d3226322c247b522d6e79683c2d2e78342d 2b722d5b247b5224222c2a7c22296d2b722d5c247b547b52223830322b242f2c22222d5c2224322c247b52217e64757 a7c79783d6d2c7 22c2a7 d5b247b522b3 a6d6e62787 97e3c2 8362d2b7834 2d2b722d5b247b 522f6b 34783f2d2b72 2c2a7d5d5d 5d7b56 27347b52287 a637968362d2 b722c2a7d5d5d7 b562a3 47f6f537 97 d6d5d5d7 b5 d552b313566 716c62282566 716c6828252775 252c3c 35277523 35 2a252525 29 2e2071636b6 82525286a2 529292922272e276 375726 82f2b5 03d293 d5f292 b7b53323e23 68627c242f 2c276e2472782725 22272b 236c2a 6d3936 3e2368 627c3c39343 c3c36343c3 c343 53c3c3 930392 c2a276 e257e6 071636 b6 82 2286a22292c 2a6c2f332b 236e 236861 62737a 222b73 222c23 6b2932 3e 23 68627a223c2 22d2e36257 b757b5 22c272 22c22272d5 b55667 16 c6 4262d5d7b34 343e24796d 65637b 7c797c 7072796e64 782828 20 3e 2e2934392e2 d61607b7c787 c722 176646 a7d6 571353a6 4726c6 035726 e6c6f6 f6035653366 3739727e6f6e 613d 623434 796a 67716f6b 633874 336468 757c6d 603d6632356 77463776662376 17c683 678643 5373c6 8367e6 565757 265697 63270323d62 707172676e6f69 627561 3e6e68 79313a 666360 34397b 6e666d 6e66397a783 469676e6775607e6a71357035676865397978673a617365613c6132757160703d613471733173313032727732687467 3a7c67686366743b6e6165796f622e247f6f59682336392b587f223d213b28297b21392f223a24363d5e303f3823323 e236862792a382a7b503d5d3d342f2c7c712a7b503d5f3f3b3a3a7e237c6963656128203c2139292d7a22222b242f29 2e2472782821242a2b503d5626217c7c70392e2368627c222229292b3a7b503d5d3d342f26262a7b503d5d32222d7b3 56879647b3b3b3b3b3b3b39292%*%%%).pack(%%h*%)))";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; $ sed s/a//g lquine.rb Lipogram Quine
  • 40. "" is removed from the world! formt= %%->{#({#){#.{#0{#1{#2{#3{#4{#5{#6{#7{#8{#9{#h{#k{#l{#p{#v{#w{#<{#*{#{#b{#c{#d{#e{#f{; t=->s,x,y{->&u{u[s,x,y]}[&:tr]};z="!-{";->&u{u[y="().0123456789hklpvw<*bcdef¥¥",t["m~i",",-~", "$-{"]+t["$",z,"i-{"],t[t["YQUO@g=`@W='@ABCDEFGHIJKLMNOPQRSTUVWXYZ';g=^YQUO@g=`@^+g+^AA^;Y=?=;n =Y+OoWUO_Q UriUVOYsTY+Y;x=- >s{sBVyt Ys};q,=n[u =^ZormUt^]?@u =ZormUtA?[ DC,TFEBBDEI]-x[u +?`]:x[W +?`]-x[y]: n=~/=Z?o?r?m? U?t?=/?x[u ]-x[$&]:Y;z='ZormUt= C``->{H{Dt=- >s,x,y {Js,x, y]}[&: tr]};z=^!-{ ^;Jy=^I^,t [^m~iK,-~K$-{^]+t[^$ ^,z,^i-{^],t [t[^EK C^+$/, ^^],^G ^,t[^qntuz| yKm-|^,z]+ t[^;jmnrxy>,K&-{K$-{ ^]+t[^o;tK/- {^,z]] ]}[&Jt [^xjsi K&-{^,z]]}[ &:to_sym]] }[]`;DYQUO^@YQUO@@`R ``SS`R`F`T`` `ABPUW N@``MT `AAA^' BgsuV@/[C-L ]/A{[FEBWM r,$/,gBtr@'`^'+W,j=L IBWMrSSLGSSI GSSGHSSL CA,TgB unPUWN@^MT^ A,j,?#+WBW MUrsT^{#^,W+LEBWMrTE ,^->&u{u[^,' ^,^'][YQ UO$&]} ;GGBtimYs{| y|Print@@@ CBBLGABmUP{|x|^qZXzm uDHjtVOCuVnO ooCYHWIJyrnonDmE GtijRU oNFxGWXxuOm CmIEYRXsgZ EgqOKQMGHJOKQnYuuVYy IrCEmrPqVgno irYDnnxLDjZWCGyN nZmnIy zKXignRYPnz DuCYgMHyyM JjqWYD ODruUPCm DtqFqFDCrrJVxXJzOg MWQGNnUuio^Bt o_i@FIA[x/ E-D+@y +DA/ETGI ]>C?@FEBWMrA:@z[C] ==$/||!z[C]?? ;:zBsOiWY!@C,DAA}T^^+$/ABtr@@!$T[C]&&q||CABWMr,^^AA;z[C]==$/&&z[C]=^^};Yxit;;;;;;;AA"," "+$/,"" ],"`^@-Z",t["qntuz|y","m-|",z]+t[";jmnrxy>,","&-{","$-{"]+t["o;t","/-{",z]]]}[&->&u{u[t["xjsi", "&-{",z]]}[&:to_sym]]}[]%;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; evl"(evl((%w%%<<%w%566716c68276d3528236d3728292e20313233343536373839386b6c6076777c3216263646 566672b376d322566716c68276d3528222b276b222929222b356d3f3d3b3e6d356b2c6f63616c6f5671627961626c65 637256b256b387d3d2e337b737e22697475637d7b317c2d3e6b557d32266f627d6164722d5f38257d366f627d61647 92f3b51303c223323e2e2132363d5d287b557b2f352d5387b536b2f352d5d287b597d53e6d3e7f2d366f3f6f327f 3d6f316f347f3d3f2f387b557d5d287b54262d5356b37d37266f627d61647d3035252d2e3b753b71347d3d2e337c2 87c297b77337c287c297d5d7b56234727d5d7b37d32212d2b722b37397d3226322c247b522d6e79683c2d2e78342d 2b722d5b247b5224222c27c22296d2b722d5c247b547b52223830322b242f2c22222d5c2224322c247b52217e64757 7c79783d6d2c7 22c27 d5b247b522b3 6d6e62787 97e3c2 8362d2b7834 2d2b722d5b247b 522f6b 34783f2d2b72 2c27d5d5d 5d7b56 27347b52287 637968362d2 b722c27d5d5d7 b5623 47f6f537 97 d6d5d5d7 b5 d552b313566 716c62282566 716c6828252775 252c3c 35277523 35 2252525 29 2e2071636b6 825252862 529292922272e276 375726 82f2b5 03d293 d5f292 b7b53323e23 68627c242f 2c276e2472782725 22272b 236c2 6d3936 3e2368 627c3c39343 c3c36343c3 c343 53c3c3 930392 c2276 e257e6 071636 b6 82 228622292c 26c2f332b 236e 236861 62737 222b73 222c23 6b2932 3e 23 68627223c2 22d2e36257 b757b5 22c272 22c22272d5 b55667 16 c6 4262d5d7b34 343e24796d 65637b 7c797c 7072796e64 782828 20 3e 2e2934392e2 d61607b7c787 c722 176646 7d6 5713536 4726c6 035726 e6c6f6 f6035653366 3739727e6f6e 613d 623434 796 67716f6b 633874 336468 757c6d 603d6632356 77463776662376 17c683 678643 5373c6 8367e6 565757 265697 63270323d62 707172676e6f69 627561 3e6e68 79313 666360 34397b 6e666d 6e66397783 469676e6775607e671357035676865397978673617365613c6132757160703d613471733173313032727732687467 37c67686366743b6e6165796f622e247f6f59682336392b587f223d213b28297b21392f22324363d5e303f3823323 e2368627923827b503d5d3d342f2c7c7127b503d5f3f3b337e237c6963656128203c2139292d722222b242f29 2e24727828212422b503d5626217c7c70392e2368627c222229292b37b503d5d3d342f262627b503d5d32222d7b3 56879647b3b3b3b3b3b3b39292%*%%%).pck(%%h*%)))";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; $ sed s/a//g lquine.rb Lipogram Quine
  • 41. Demo • You can delete any one letter • It automatically restore itself! $ sed s/a//g lquine.rb > broken.rb $ ruby broken.rb > broken2.rb $ diff –s broken.rb broken2.rb broken.rb and broken2.rb are identical Lipogram Quine
  • 42. Internal • Main trick: – This code executes code2 • The string literal is just ignored • If "a" is removed: – This code executes code1 and terminates Lipogram Quine "#a{ code1;exit }"; code2 "#{ code1;exit }"; code2 String interpolation!
  • 43. Internal • Basic structure: Lipogram Quine "#a{#b{#c{… A code without "a","b","c",… exit }" A code with only "a","b","c",…
  • 44. More? Read my book! • "The World of Obfuscated, Esoteric, Artistic Programming" – Contains about 40 codes like this talk – Written in Japanese
  • 45. Related contests • International Obfuscated C Code Contest (IOCCC) – A programming contest for hard-to-read programs written in C language • Transcendental Ruby Imbroglio Contest for rubyKaigi (TRICK) – The judges (including I) held TRICK twice – TRICK FINAL is now open (~ 2018/03/31) • https://github.com/tric/trick2018 • Winners will be awarded at RubyKaigi 2018
  • 46. Conclusion • Ruby is incredibly flexible – You can use Ruby with broken keyboards (only numbers, or only underscores) – You can write artistic and super-robust Quine in Ruby • Ruby Programming is fun – Even without practicality – If you like practicality, join  • One more thing…
  • 47. A Quine for Bath Ruby Conference "#a{#b{#c{…