Programming Puzzles & Code Golf Stack Exchange is a question and answer site for programming puzzle enthusiasts and code golfers. It's 100% free, no registration required.

Sign up
Here's how it works:
  1. Anybody can ask a question
  2. Anybody can answer
  3. The best answers are voted up and rise to the top

Given an input of any valid Glypho program, output its "human-readable" counterpart.

Glypho is an interesting esolang idea:

The instruction reference is given here. For each instruction, the characters abcd represent the symbols composing each instruction. a refers to the first unique symbol, b refers to the second unique symbol, etc.

aaaa ..... n NOP - no operation; do nothing
aaab ..... i Input - push input onto top of stack
aaba ..... > Rot - pops top stack element and pushes to bottom of stack
aabb ..... \ Swap - swaps top two stack elements
aabc ..... 1 Push - pushes a 1 onto the top of stack (creates new element)
abaa ..... < RRot - pops bottom element and pushes to top of stack
abab ..... d Dup - Duplicates top stack element
abac ..... + Add - pops top two elements and pushes their sum
abba ..... [ L-brace - skip to matching ] if top stack element is 0
abbb ..... o Output - pops and outputs top stack element
abbc ..... * Multiply - pops top two elements and pushes their product
abca ..... e Execute - Pops four elements and interprets them as an instruction
abcb ..... - Negate - pops value from stack, pushes -(value)
abcc ..... ! Pop - pops and discards top stack element
abcd ..... ] R-brace - skip back to matching [

(credit: Brian Thompson aka Wildhalcyon)

So, for example, PPCG would represent the Push instruction—PPCG matches the pattern aabc, where a represents P, b represents C, and c represents G.

The input will be a single string consisting of only printable ASCII characters. It will always have a length divisible by four (duh).

The output is each group of four characters in the input string replaced by which instruction they designate. Use the single-letter instruction names (the ones right after the five dots in the table quoted above).

Since this is , the shortest code in bytes will win.

Test cases:

In                                Out
------------------------------------------------
Programming Puzzles & Code Golof  ]!]!]]]+
nananananananana batman!          dddd]]
;;;;;;;:;;:;;;::                  ni>\
llamas sleep                      1-*
8488133190003453                  <[oe
<empty string>                    <empty string>
share|improve this question
1  
Ah yes Code Golof. My favorite sporot. – KoreanwGlasses Feb 2 at 17:18
up vote 5 down vote accepted

Pyth, 37 35 34 bytes

The code contains unprintable characters, so here is the xxd hexdump:

0000000: 5663 7a34 7040 2e22 216f d78c 40bf d4f0  Vcz4p@."!o..@...
0000010: 38d6 7dfe 7312 3ff8 ea22 6958 4e7b 4e55  8.}.s.?.."iXN{NU
0000020: 5433                                     T3

Here's a printable version at 36 bytes:

Vcz4p@"ni >\\1   <d+[o*e-!]"iXN{NUT3

Try it online. Test suite.

Explanation

Vcz4p@."…"iXN{NUT3       implicit: z = input
  z                      input
 c 4                     split to 4-character blocks
V                        loop over that in N
           X               replace...
            N                in current part
             {N              unique chars in current part, in order
               UT            with numbers 0-9
          i      3         interpret as base 3
     @                     take that item of
      ."…"                   string "ni >\\1   <d+[o*e-!]"
    p                      and print without newline
share|improve this answer

CJam, 42 39 35 bytes

Saved 4 bytes borrowing user81655's idea of using base 3 instead of base 4.

l4/{__&f#3b"ni >\1   <d+[o*e-!]"=}%

Run all test cases.

There's gotta be a better way to compress the lookup table of commands...

share|improve this answer

JavaScript (ES6), 97

For each block of 4 characters, I substitute each symbol with its position in the block, getting a base 4 number. For instance 'aabc' -> '0023'. The possibile numbers are in the range 0..0123, that is 0..27 in decimal. I use the number as an index to find the right instruction character from a 28 chars string.

s=>s.replace(/.{4}/g,s=>'n..i....>.\\1....<d.+[o.*e-!]'[[...s].map(c=>n=n*4+s.indexOf(c),n=0),n])

Test

F=s=>s.replace(/.{4}/g,s=>'n..i....>.\\1....<d.+[o.*e-!]'[[...s].map(c=>n=n*4+s.indexOf(c),n=0),n])

function test() { O.textContent=F(I.value) }

test();
#I { width:90% }
<input id=I value="nananananananana batman!" oninput="test()">
<br><span id=O></span>

share|improve this answer

JavaScript (ES6), 115 101 bytes

s=>s.replace(/..../g,g=>"ni >\\1   <d+[o*e-!]"[[...g].map(c=>r=r*3+(m[c]=m[c]||++i)-1,i=r=0,m={})|r])

Saved 14 bytes thanks to @edc65!

Explanation

Stores the list of instructions in a string with each character at it's base-3 index. For example, + corresponds to abac which can be represented in base-3 as 0102, or 11 in decimal. The only instruction that cannot be represented in base-3 is ], but with the algorithm used to compute the base-3 number, it conveniently ends up needing to be at position 18 at the end of the string.

s=>
  s.replace(/..../g,g=>    // replace each four-character group with it's instruction
    "ni >\\1   <d+[o*e-!]" // list of instructions at their base-3 index
    [
      [...g].map(c=>       // for each character c
        r=r*3+(m[c]=m[c]   // shift r left and add the number associated with c to r
          ||++i)-1,        // if nothing is associated, associate the next number to c
                           // save i + 1 to m[c] so that it is truthy for 0
        i=                 // i = current number to assign to the next unique character
        r=0,               // r = 4-character group as a base-3 number
        m={}               // m = map of numbers assigned to each character
      )
      |r                   // return r
    ]
  )

Test

var solution = s=>s.replace(/..../g,g=>"ni >\\1   <d+[o*e-!]"[[...g].map(c=>r=r*3+(m[c]=m[c]||++i)-1,i=r=0,m={})|r])
<input type="text" id="input" value="Programming Puzzles & Code Golof" />
<button onclick="result.textContent=solution(input.value)">Go</button>
<pre id="result"></pre>

share|improve this answer
    
You can save many bytes not using parseInt and computing the number with repeated sum and multiply. This avoid the problem with '0123' that is invalid in base 3 but gives 1*9+2*6+3==18 that is a good position. Result: F=s=>s.replace(/..../g,g=>"ni]>\\1 <d+[o*e-!]"[[...g].map(c=>r=r*3+(m[c]=m[c]||++i)-1,r=i=0,m={})|r]) – edc65 Feb 1 at 11:13
    
@edc65 Great suggestion. Thanks! – user81655 Feb 1 at 11:52

MATLAB, 291 bytes

I hesitated for quite a long time if I should commit my answer. I was just playing around with MATLAB. I am aware that it's not really possible to generate dense code (a low number of instructions/bytes; about 3 times larget than your ~100 byte solutions) and that MATLAB might not be too suitable for code golf and I am new to code golf. But I simply wanted to try, and the code works (newline characters kept). Any hints welcome. :P

i=input('','s');
l=reshape(i,4,length(i)/4)';
m=']!- e';m(9)='*';m(12:22)='o[   + d  <';m(33:34)='1\';m(39)='>';m(57)='i';m(64)='n';
s='';
for k = 1:size(l,1)
n=l(k,:);
c=combvec(n,n);
t=triu(reshape(c(1,:)==c(2,:),4,4),1);
t=sum(t([5,9:10,13:15]).*2.^[5:-1:0]);
s=[s,m(t+1)];
end
display(s)
share|improve this answer
1  
Welcome to Programming Puzzles & Code Golf! All answers are welcome, even if they get outgolfed by a ridiculous amount (has definitely happened to me before). ;) Nice first answer! – Doorknob Feb 2 at 12:15

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

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