62
\$\begingroup\$

I recently created a new language called ;# (pronounced "Semicolon Hash") which only has two commands:

; add one to the accumulator

# modulo the accumulator by 127, convert to ASCII character and output without a newline. After this, reset the accumulator to 0. Yes, 127 is correct.

Any other character is ignored. It has no effect on the accumulator and should do nothing.

Your task is to create an interpreter for this powerful language!

It should be either a full program or a function that will take a ;# program as input and produce the correct output.

Examples

Output: Hello, World!
Program: ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#

Output: ;#
Program: ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#

Output: 2d{ (unprintable characters here; should have 4 `\000` bytes between the `d` and the `{` and 3 after the `{`)
Program: ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;hafh;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;f;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;###ffh#h#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;ffea;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;aa;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#au###h;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;h;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;o

Output: Fizz Buzz output
Program: link below

Output: !
Program: ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#

Fizz Buzz up to 100

\$\endgroup\$
  • 1
    \$\begingroup\$ Is it acceptable if an interpreter doesn't terminate its execution at the end of the input but instead keeps looping indefinitely without producing extra output? \$\endgroup\$ – Leo May 22 '17 at 9:26
  • 5
    \$\begingroup\$ The second example makes me wonder about a program to encode a program to produce an output... recursive compilation! \$\endgroup\$ – frarugi87 May 22 '17 at 9:29
  • \$\begingroup\$ @Leo yes that's fine \$\endgroup\$ – caird coinheringaahing May 22 '17 at 14:46
  • 1
    \$\begingroup\$ @iamnotmaynard Semicolon Hash \$\endgroup\$ – caird coinheringaahing May 23 '17 at 15:09
  • 2
    \$\begingroup\$ Maybe Wink Hash would be easier to say \$\endgroup\$ – James Waldby - jwpat7 May 23 '17 at 17:42

105 Answers 105

2
\$\begingroup\$

Befunge-98, 38 bytes

v+1$>';-!#;_
>~:;|-#';#:_@
^   >$' %,

Try it online!

Note that the input is terminated with a null byte and there is an unprintable (ASCII 127) on the third line after '

\$\endgroup\$
2
\$\begingroup\$

Perl 6, 49 bytes

{S:g/(<-[#]>*)(\#)?/{chr($0.comb(';')%127)x?$1}/}
\$\endgroup\$
2
\$\begingroup\$

QBIC, 48 66 57 bytes

[_l;||D=_sA,a,1|┘b=b-(D=@;`)~D=@#`|b=b%127?chr$(b)';`┘b=0

Explanation:

[    |           FOR
 _l;|              the length of the cmd line arg A$
 D=_sA,a,1|      Take the next character out of the string as D$
┘                Syntactic linebreak
b=b-(D=@;`)      If D$ == ";", this yields -1. Subtracting this from ACC reverses the sign
~D=@#`|          And if D$ == "#"
b=b%127          Do the Modulo-print thingy
?chr$(b)';`
┘b=0             And reset the acc
\$\endgroup\$
2
\$\begingroup\$

Go, 104 102 bytes

Yeeeeaaaaaaaaaah, Go.

import."fmt"
func f(c string){i:=0;for _,r:=range c{if';'==r{i++};if'#'==r{Print(string(i%127));i=0}}}

Try it online!

\$\endgroup\$
2
\$\begingroup\$

C#, 110 108 103 101 98 bytes

-2 bytes by removing braces, where unnecessary

-5 bytes by removing else, from else if

-2 bytes, thanks to TheLethalCoder

-3 bytes, thanks to Andrew Piliser

a=>{var b=0;var d="";foreach(var c in a){if(c==59)b++;if(c==35){d+=(char)(b%127);b=0;}}return d;};

Anonymous function, returns the output.

\$\endgroup\$
  • 1
    \$\begingroup\$ Compare c to an int to save 2 bytes. \$\endgroup\$ – TheLethalCoder May 22 '17 at 8:17
  • 1
    \$\begingroup\$ I don't think you need the +"", it works without it for me. \$\endgroup\$ – Andrew Piliser May 22 '17 at 17:54
2
\$\begingroup\$

Brainfuck, 135 bytes

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

Ungolfed

Memory layout
0   1   2   3   4   5   6   7
1   f1  f2  in  tmp acc d   acc%d   

flag1 indicates hash
flag2 indicates semicolon

+[      infinite loop
    >+      set flag1
    >>,     input
    >+++++[<------->-]<     subtract 35 (hash)

    [       not hash
        <+> set flag2
        >++++[<------>-]<   subtract 24 more (semicolon)
        [   not semicolon
            <-> clear flag2
            [-] clear input
        ]
        <   goto flag2
        [   semicolon
            >>>+<<<-    inc acc and clear flag2
        ]
        <-  clear flag1
        >>[-]   clear input
    ]
    <<      goto flag1
    [       hash
        >>>--[>>+<<--]> set d 127 and goto acc
        [>->+<[>]>[<+>-]<<[<]>-]    mod
        >[-]>       clear d and goto acc%d 
        .[-]        print and clear result
        <<<<<<- clear flag1
    ]
<]
\$\endgroup\$
2
\$\begingroup\$

Chip, 179 bytes

 HGFEDCB
,\\///\/A
`--v~.
   |z^.
 ,\#xZ<
a^xx/'`.
 ,\#xZ~<
b^xx/' |
 ,\#xZ~<
c^xx/' |
 ,\#xZ~<
d^xx/' |
 ,\#xZ~<
e^xx/' |
 ,\#xZ~<
f^xx/' |
 ,\#xZ~'
g^x-/'HGFEDCB
S÷^---\\/\\\/A

(UTF8, so ÷ is \xc3\xb7)

Try it online!

The upper block with A-H and the slashes is detecting the semicolon character, and the similar lower block is detecting the hash. If other bogus characters needn't be handled, the whole thing would be somewhere around 133 bytes.

The middle block does the following:

Z's are the registers, one for each of the seven bits.

The half-adders # allow for incrementing by 1 in case of a semicolon. If not a semicolon, increment by 0.

If we get a hash, send the current register values to a-g, which outputs the desired character, and then reset the values to zero with the switches \.

If the registers are 0b1111110 (126), as determined by the right two columns, the next increment results in zero due to the switches /.

\$\endgroup\$
2
\$\begingroup\$

R, 66 bytes

intToUtf8(nchar(gsub("[^;]","",el(strsplit(scan(,""),"#"))))%%127)

Test:

> intToUtf8(nchar(gsub("[^;]","",el(strsplit(scan(,""),"#"))))%%127)
1: ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;... <truncated>
2: 
Read 1 item
[1] "Hello, World!"
\$\endgroup\$
2
\$\begingroup\$

Cubix, 53 bytes

#..Wc.@n.!0i?\?;u...'u;.'\.U;.\w;;U.;).;'%o;c;.!;.U;

Contains one non-printable character, DEL, which is ASCII 127. If the accumulator is 0 and an ignored character is read in, an additional 0 is added to the stack so this runs the risk of stack overflow.

Try it online! and Watch it online

Cubified:

      # . .
      W c .
      @ n .
! 0 i ? \ ? ; u . . . '
u ; . ' \ . U ; . \ w ;
; U . ; ) . ; '   % o ;
      c ; .
      ! ; .
      U ; .
\$\endgroup\$
2
\$\begingroup\$

JavaScript (ES6), 91 85 bytes

ETH beat me to the punch with a variation on the Japt solution I was working on (that'll learn me to check the answers first!) so here's the JS solution I was using as the basis for it:

s=>s.split`#`.slice(0,-1).map(x=>String.fromCharCode(--x.split`;`.length%127)).join``

Try it

f=
s=>s.split`#`.slice(0,-1).map(x=>String.fromCharCode(--x.split`;`.length%127)).join``
oninput=_=>o.innerText=f(i.value)
o.innerText=f(i.value=";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#")
<input id=i><pre id=o>

\$\endgroup\$
  • \$\begingroup\$ You could use ~-x.split`;`.length%127 to get rid of the ||0 and the extra parens \$\endgroup\$ – ETHproductions May 22 '17 at 14:32
  • \$\begingroup\$ Good thinking, @ETHproductions; thanks. I was so focused on golfing down the Japt version, I forgot to golf this version before posting it. \$\endgroup\$ – Shaggy May 22 '17 at 14:38
  • \$\begingroup\$ You've done --x.split rather than ~-x.split. Is this intentional or a mistake? \$\endgroup\$ – caird coinheringaahing May 22 '17 at 15:04
  • \$\begingroup\$ It was a misreading of what ETH posted without my glasses on, @RandomUser, but the result is the same, as you can see in the Snippet. \$\endgroup\$ – Shaggy May 22 '17 at 15:07
  • \$\begingroup\$ Actually I can't see in the Snippet (on mobile) \$\endgroup\$ – caird coinheringaahing May 22 '17 at 15:13
2
\$\begingroup\$

Haskell, 70 bytes (-7 thanks to BWO)

n#(o:p)|o==';'=(n+1)#p|o=='#'=toEnum(mod n 127):0#p|1>0=n#p
_#p=p
(0#)

Try it online!

\$\endgroup\$
  • \$\begingroup\$ Huh, I always thought you had to use a space to call a function. \$\endgroup\$ – mrFoobles Aug 12 '18 at 16:00
  • 1
    \$\begingroup\$ n#(o:p)|o=='#'=toEnum(mod n 127):0#p|o/=';'=n#p|w<-n+1=w#p works for 69 bytes. \$\endgroup\$ – ovs Aug 12 '18 at 17:22
2
\$\begingroup\$

Shakespeare Programming Language, 447 439 404 bytes

,.Ajax,.Ford,.Act I:.Scene I:.[Exeunt][Enter Ajax and Ford]Ajax:Open mind.Ford:Am I as big as the sum ofa pig twice twice the sum ofa pig a big big big big cat?If soyou be the sum ofyou a cat.Be you worse the sum ofa pig twice the cube ofa big big cat?If notyou zero.Am I as big as the sum ofa cat twice the sum ofa cat a big big big big cat?If soSpeak thy.If soYou zero.Am I nicer zero?If soLet usAct I.

Try it online!

-35 bytes thanks to Joe King!

\$\endgroup\$
  • \$\begingroup\$ 404 bytes with proper termination \$\endgroup\$ – Jo King Sep 10 '18 at 0:51
  • \$\begingroup\$ Y'know, I should've thought about wrapping the accumulator manually. \$\endgroup\$ – JosiahRyanW Sep 10 '18 at 1:37
2
\$\begingroup\$

F# (.NET Core), 71 bytes

Seq.fold(fun a->function|';'->a+1|'#'->printf"%c"(a%127|>char);0|_->a)0

Try it online!

\$\endgroup\$
2
\$\begingroup\$

Awk, 57 bytes

BEGIN{RS="#"}RT=="#"{printf("%c",gsub(";","")%127)}

Explanation:

  • BEGIN{RS="#"}: make # record delimeter
  • RT=="#": ignore the record without ending #
  • gsub(";","")%127: count ; and mod 127
  • printf("%c",_): print as ASCII
\$\endgroup\$
1
\$\begingroup\$

C, 74 72 70 bytes

a;f(char*s){for(;*s;s++){if(*s==59)a++;if(*s==35)putchar(a%127),a=0;}}

Test cases:

Output: Hello, World!
f(";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#");

Output: ;#
f(";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#");

Output: 2d{ (unprintable characters here; should have 4 `\000` bytes between the `d` and the `{` and 3 after the `{`)
f(";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;hafh;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;f;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;###ffh#h#;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;ffea;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;aa;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#au###h;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;h;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;o");

Output: !
f(";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;#");
\$\endgroup\$
1
\$\begingroup\$

C (gcc), 66 bytes

a;f(char*c){for(a=0;*c;a+=*c==59,a=*c++==35&&putchar(a%127)?0:a);}

Try it online!

\$\endgroup\$
1
\$\begingroup\$

shortC, 51 bytes

a;f(C*s){O;*s;s++){F*s==59)a++;F*s==35)Pa%127),a=0;
\$\endgroup\$
1
\$\begingroup\$

J, 29 bytes

[:u:127|[:+/"1[:';'&=;.1'#',]

Try it online!

\$\endgroup\$
  • \$\begingroup\$ The third test case outputs 2┴d{I, but I think it might be because of J's alphabet a. \$\endgroup\$ – miles May 23 '17 at 2:33
1
\$\begingroup\$

C, 56 54 bytes

a;f(char*s){a+=*s-35?*s==59:-putch(a%127);*s&&f(s+1);}

Solution is based on Dennis's one ("C (gcc), 58 bytes"), but with elimination of two characters a=

Two more symbols can be taken off with substitution putchar with putch

\$\endgroup\$
  • 1
    \$\begingroup\$ a= is required to make the function reusable; since a is global, it has to be reset to 0. \$\endgroup\$ – Dennis May 23 '17 at 4:08
  • \$\begingroup\$ putch is not standard C. \$\endgroup\$ – MD XF May 23 '17 at 21:19
1
\$\begingroup\$

Cheddar, 57 bytes

@.split("#").head(-1).map(s->@"(s.count(";")%127)).join()

Try it online!

\$\endgroup\$
1
\$\begingroup\$

Aceto, 38 31 bytes

The program reads and processes one character at a time, so it will work with infinite ;# programs. Run with -F if you want immediate results (because buffering), but it works without it if the program is long enough.

  Ox%-12
  =_cpF7
d'#'O
,;=|xIO

, reads a character. We duplicate it and compare it with ;. If it's equal, we mirror to the right side (=|), drop (x) the duplicate, Increment the value on the stack (implicitly zero), and go back to the Origin.

If it's not equal, we compare the copy with #. If that is equal, we mirror upwards (=_; somewhere in empty space above, but the next non-nop we read will be the 2). We push a 2 and a 7, compute 2^7 (F), and substract 1 (1-). We then do a modulo operation (%) convert it to a character, print it (without a newline) and go back to the Origin.

If it's none of those characters, we drop the value on the stack (x) and go back to the Origin.

\$\endgroup\$
1
\$\begingroup\$

Gema, 63 characters

\A=@set{a;0}
\;=@incr{a}
\#=@int-char{@mod{$a;127}}@set{a;0}
?=

Sample run:

bash-4.4$ gema '\A=@set{a;0};\;=@incr{a};\#=@int-char{@mod{$a;127}}@set{a;0};?=' < '2d{.;#' | od -tad1
0000000    2  etb    d  nul  nul  nul  nul    {  nul  nul  nul
          50   23  100    0    0    0    0  123    0    0    0
0000013
\$\endgroup\$
  • \$\begingroup\$ I do so love Gema answers. \$\endgroup\$ – Jordan May 24 '17 at 2:01
1
\$\begingroup\$

APL (Dyalog) , 25 bytes

⎕UCS 127|+/¨';'='#'(≠⊂⊢)⍞

Try it online! Some of the longer test cases seem to have problems on TIO, but work fine offline.

 get text input

'#'() apply the following tacit function with hash as left argument:

 the inequality

 partitions*

 the right argument (all the semicolons and hashes)

';'= equality to semicolon

+/¨ sum each

127| mod-127

⎕UCS Convert to corresponding Unicode character


in versions up to 15.0, providing that ⎕ML←3 which is default on many systems. In version 16.0 and higher, just use .

\$\endgroup\$
1
\$\begingroup\$

Pyth, 16 bytes

smC%/d\;127Pcw\#

Try it!

explanation

smC%/d\;127Pcw\#
            cw\#    ## split the input on '#'
           P        ## remove the last element (everything after the last #)
 m                  ## map over this list of strings (variable: d)
    /d\;            ## count the semicolons
   %    127         ## modulo 127
  C                 ## the character with that number
s                   ## concat the list of characters

imperative version I did for fun: J0FHwIqH\;=+J1)IqH\#pC%J127=J0

\$\endgroup\$
1
\$\begingroup\$

PHP, 61 Bytes

for(;~$c=a^$argn[$i++];)$n+=$c^r?$c==Z:-$n*print chr($n%127);

Try it online!

PHP, 68 Bytes

for(;a&$c=$argn[$i++];)$c!=";"?$c!="#"?:$n=1-print chr($n%127):++$n;

Try it online!

\$\endgroup\$
  • 2
    \$\begingroup\$ Doesn't work with 0. Fixed and slightly golfed: for(;~$c=a^$argn[$i++];)$c^r?$n+=$c==Z:print~$n=~chr($n%127);. \$\endgroup\$ – user63956 May 22 '17 at 6:10
  • \$\begingroup\$ @user63956 It tooks a long time to understand how this works. Nice Thank You \$\endgroup\$ – Jörg Hülsermann May 22 '17 at 10:21
  • 1
    \$\begingroup\$ Yields warnings A non-numeric value encountered in PHP 7.1. Use $n+=$c^r?$c==Z:-$n*print chr($n%127); (same length) to fix. \$\endgroup\$ – Titus May 22 '17 at 13:47
  • \$\begingroup\$ @Titus Done Thank You \$\endgroup\$ – Jörg Hülsermann May 22 '17 at 14:05
1
\$\begingroup\$

Clojure, 71 bytes

#(for[i(re-seq #"[^#]*#"%)](print(char(mod(count(filter #{\;}i))127))))

Splits into chunks by regex, counts how many ;s there are in each chunk.

\$\endgroup\$
1
\$\begingroup\$

Haxe, 145 136 bytes

function(s){var a=0;for(i in 0...s.length){var c=s.charAt(i);if(c==';')a++;else if(c=='#'){Sys.print(String.fromCharCode(a%127));a=0;}}}

-9 bytes thanks to Haxe's "inline function" (lambda) feature

Don't think I've ever seen an answer given in Haxe before, probably because it's not very golfy, and not that well known.

The code's really quite self-explanatory, here's the un-golfed version:

function(s) {
    var a=0;
    for(i in 0...s.length) {
        var c=s.charAt(i);
        if(c==';') {
            a++;
        }
        else if(c=='#') {
            Sys.print(String.fromCharCode(a%127));
            a=0;
        }
    }
}
\$\endgroup\$
1
\$\begingroup\$

Rust, 109 bytes

Rust was not created for golfing...

fn f(s:&str){let mut a=0u8;for c in s.chars(){if c==';'{a+=1;}if c=='#'{a%=127;print!("{}",a as char);a=0;}}}
\$\endgroup\$
1
\$\begingroup\$

jq, 54 characters

(49 characters code + 5 characters command line options)

[scan(".*?#")|gsub("[^;]";"")|length%127]|implode

Sample run:

bash-4.4$ jq -Rrj '[scan(".*?#")|gsub("[^;]";"")|length%127]|implode' < '2d{.;#' | od -tad1
0000000    2  etb    d  nul  nul  nul  nul    {  nul  nul  nul
          50   23  100    0    0    0    0  123    0    0    0
0000013

On-line test

\$\endgroup\$
1
\$\begingroup\$

Mathematica, 81 bytes

StringReplace[a=0;#,{";":>(a++;""),"#":>FromCharacterCode@Mod[a,a=0;127],_:>""}]&

Pure function expecting a string argument.

Explanation

The basic evaluation procedure (it can be more complicated) for an expression in Mathematica is to evaluate the head of the epxression, then evaluate each of its arguments in order, then apply any definitions, then evaluate the entire expression again until nothing changes.

So first we evaluate StringReplace (no-op). The first argument is a=0;#, which sets the accumulator a to 0 and returns the first argument (denoted #) to the function. The second argument is a list of string replacement rules, which are applied in order starting at the beginning of the string.

If we encounter the substring ";", we replace it with (a++;""). Since we used :> instead of ->, this replacement expression is only evaluated whenever we actually find a match for ";". It (post-)increments a and returns the empty string, so finding a match for ";" effectively increments the accumulator and deletes the semicolon. In the case of a match, we move to the next position in the string, otherwise we check the next rule in the list.

If we encounter the substring "#", we replace it with FromCharacterCode@Mod[a,a=0;127]. FromCharacterCode does what you expect, but Mod[a,a=0;127] can be tricky if you don't understand Mathematica's evaluation procedure. We evaluate Mod (no-op), then evaluate the first argument a to get the value of the accumulator. When we evaluate the second argument a=0;127, we reset the accumulator to 0 and return 127. Thus we end up with Mod[<a>,127], where <a> is whatever the value of a was before the expression started evaluating. The only way I can think of to get this to work by resetting the accumulator after calculating the modulus without introducing additional variables is something like "#":>Reap[Sow[FromCharacterCode[Mod[a,127]]];a=0][[2,1,1]]. Introducing another variable I could do something like "#":>(b=a;a=0;FromCharacterCode[b~Mod~127]).

If we reach the last replacement rule, we replace any single character _ with the empty string "".

\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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