Summary

From Esolang
Jump to navigation Jump to search

Summary is a list of numbers where the sum of consecutive numbers determines the command

Interpreter

def interpret(nums):
    stack = []
    i = 0
    while i < len(nums)-1:
        sum_ = nums[i]+nums[i+1]
        if sum_ == 1:
            if i+2 < len(nums):
                stack.append(nums[i+2])
                i += 1
        elif sum_ == 2:
            if stack: stack.pop()
        elif sum_ == 3:
            if stack: print(stack.pop())
        elif sum_ == 4:
            if len(stack) > 1: stack.append(stack.pop()+stack.pop())
        elif sum_ == 5:
            if len(stack) > 1: stack.append(stack.pop()-stack.pop())
        elif sum_ == 6:
            if i+2 < len(nums) and -1<nums[i+2]<len(nums):
                i = nums[i+2]-1
        elif sum_ == 7:
            if stack and stack.pop()==0 and i+2 < len(nums) and -1<nums[i+2]<len(nums):
                i = nums[i+2]-1
        elif sum_ == 8:
            if stack:
                stack.append(stack[-1])
        elif sum_ == 9:
            if stack and stack.pop()>0 and i+2 < len(nums) and -1<nums[i+2]<len(nums):
                i = nums[i+2]-1
        elif sum_ == 10:
            if stack and stack.pop()<0 and i+2 < len(nums) and -1<nums[i+2]<len(nums):
                i = nums[i+2]-1
        elif sum_ == 11:
            stack = stack[::-1]
        i += 1
nums = [0, 1, 1, 0, 1, 7, -4, 12, -1, 5, 1, 4]
interpret(nums)

Compiler

class Spec:
    def __init__(self, value):
        self.value = value
    def __repr__(self):
        return repr(self.value)
    def __rsub__(self, other):
        return other-self.value
def compile_(unassembled):
    code = [0]
    map_ = []
    gotos = []
    i = 0
    for x in unassembled.splitlines():
        print(code, i, code[i])
        commandlet = x.split()
        command = commandlet[0]
        arg = int(commandlet[1]) if len(commandlet) > 1 else None
        map_.append(i)
        if arg is not None:
            i += 2
            z = Spec(arg)
            if command == "push":
                code.append(1-code[-1])
                code.append(z)
            elif command == "branchp":
                gotos.append(z)
                code.append(9-code[-1])
                code.append(z)
            elif command == "branchn":
                gotos.append(z)
                code.append(10-code[-1])
                code.append(z)
            elif command == "goto":
                gotos.append(z)
                code.append(6-code[-1])
                code.append(z)
            elif command == "branchz":
                gotos.append(z)
                code.append(7-code[-1])
                code.append(z)
            else:
                gotos.remove(z)
        else:
            i += 1
            if command == "pop":
                code.append(2-code[-1])
            elif command == "print":
                code.append(3-code[-1])
            elif command == "add":
                code.append(4-code[-1])
            elif command == "sub":
                code.append(5-code[-1])
            elif command == "dup":
                code.append(8-code[-1])
            elif command == "flip":
                code.append(11-code[-1])
    for x in gotos:
        x.value = map_[x.value]
    return code
code = """push 1
push 1
dup
print
dup
flip
add
goto 2"""
print(compile_(code))