We are currently working on new rules for what content should and shouldn't be allowed on this website, and are looking for feedback! See Esolang:2026 topicality proposal to view and give feedback on the current draft.

One Command Programming Language(OCPL)/Implementation

From Esolang
Jump to navigation Jump to search

Back to One Command Programming Language(OCPL)

Python

#####################################################################
#            Implementation of OCPL, written in Python              #
#              Made by PrySigneToFry on Aug 26, 2026                #
# Note: The comments for each part in this interpreter are in       #
# Chinese. If you don't understand Chinese, you can use a           #
# translator. Sorry for the inconvenience, and thanks               #
# for understanding.                                                #
#####################################################################

import re
import operator

class OCPLInterpreter:
    def __init__(self):
        self.variables = {}
        self.functions = {}
        self.lists = {}
        self.output = []
    
    def eval_expr(self, expr):
        """计算表达式(支持算术运算和变量引用)"""
        if isinstance(expr, str):
            # 尝试解析为数字
            try:
                if '.' in expr:
                    return float(expr)
                return int(expr)
            except ValueError:
                pass
            
            # 变量引用
            if expr in self.variables:
                return self.variables[expr]
            
            # 算术表达式(简化版,支持 + - * /)
            if any(op in expr for op in ['+', '-', '*', '/']):
                # 替换变量名
                local_expr = expr
                for var, val in self.variables.items():
                    if var in local_expr and not isinstance(val, (list, dict)):
                        local_expr = local_expr.replace(var, str(val))
                try:
                    return eval(local_expr)
                except:
                    return expr
            
            return expr
        return expr
    
    def parse_args(self, args_str):
        """解析参数字符串,返回参数列表"""
        # 处理嵌套的 !() 调用
        args = []
        current = ""
        depth = 0
        i = 0
        
        while i < len(args_str):
            ch = args_str[i]
            if ch == '!' and i + 1 < len(args_str) and args_str[i+1] == '(':
                depth += 1
                current += ch
            elif ch == '(':
                depth += 1
                current += ch
            elif ch == ')':
                depth -= 1
                current += ch
            elif ch == ',' and depth == 0:
                args.append(current.strip())
                current = ""
            else:
                current += ch
            i += 1
        
        if current.strip():
            args.append(current.strip())
        
        return args
    
    def parse_value(self, val_str):
        """解析值(字符串、数字、列表、null、嵌套命令)"""
        val_str = val_str.strip()
        
        # null
        if val_str.lower() == 'null':
            return None
        
        # 字符串(带引号)
        if (val_str.startswith('"') and val_str.endswith('"')) or \
           (val_str.startswith("'") and val_str.endswith("'")):
            return val_str[1:-1]
        
        # 列表
        if val_str.startswith('[') and val_str.endswith(']'):
            items = val_str[1:-1].split(',')
            return [self.parse_value(item.strip()) for item in items if item.strip()]
        
        # 嵌套命令 !(...)
        if val_str.startswith('!(') and val_str.endswith(')'):
            inner = val_str[2:-1]
            return self.execute_command(inner)
        
        # 数字
        try:
            if '.' in val_str:
                return float(val_str)
            return int(val_str)
        except ValueError:
            pass
        
        # 变量引用
        return val_str
    
    def execute_command(self, args_str):
        """执行一个 !() 命令"""
        args = self.parse_args(args_str)
        arg_count = len(args)
        
        # 解析参数值
        parsed_args = [self.parse_value(arg) for arg in args]
        
        if arg_count == 1:
            # 打印
            self.output.append(str(parsed_args[0]))
            
        elif arg_count == 2:
            # 变量赋值
            name = args[0].strip()
            if name.startswith('"') and name.endswith('"'):
                name = name[1:-1]
            value = parsed_args[1]
            self.variables[name] = value
            
        elif arg_count == 3:
            # 函数定义
            name = args[0].strip()
            if name.startswith('"') and name.endswith('"'):
                name = name[1:-1]
            func_args = parsed_args[1]
            code = args[2]  # 保持为字符串,稍后执行
            self.functions[name] = {'args': func_args, 'code': code}
            
        elif arg_count == 4:
            # if 语句
            condition = parsed_args[0]
            true_branch = args[1]
            false_branch = args[2]
            finally_branch = args[3]
            
            # 执行 finally(总是执行)
            if finally_branch and finally_branch.strip().lower() != 'null':
                self.execute_command(finally_branch[2:-1])
            
            # 判断条件
            if self._is_true(condition):
                if true_branch and true_branch.strip().lower() != 'null':
                    self.execute_command(true_branch[2:-1])
            else:
                if false_branch and false_branch.strip().lower() != 'null':
                    self.execute_command(false_branch[2:-1])
            
        elif arg_count == 5:
            # while 循环
            condition = parsed_args[0]
            code = args[1]
            
            while self._is_true(condition):
                if code and code.strip().lower() != 'null':
                    self.execute_command(code[2:-1])
                # 重新计算条件(变量可能已更新)
                condition = self.parse_value(args[0])
            
        elif arg_count == 6:
            # 向列表添加元素
            list_name = args[0].strip()
            if list_name.startswith('"') and list_name.endswith('"'):
                list_name = list_name[1:-1]
            item = parsed_args[1]
            
            if list_name not in self.lists:
                self.lists[list_name] = []
            self.lists[list_name].append(item)
            
        elif arg_count == 7:
            # 调用函数
            func_name = args[0].strip()
            if func_name.startswith('"') and func_name.endswith('"'):
                func_name = func_name[1:-1]
            arg_val = parsed_args[1]
            
            if func_name in self.functions:
                func = self.functions[func_name]
                # 保存当前变量以便恢复
                old_vars = self.variables.copy()
                
                # 设置参数变量
                if func['args']:
                    arg_names = func['args']
                    if isinstance(arg_names, str) and arg_names.lower() != 'null':
                        # 简单参数传递
                        self.variables[arg_names] = arg_val
                
                # 执行函数体
                if func['code'] and func['code'].strip().lower() != 'null':
                    self.execute_command(func['code'][2:-1])
                
                # 恢复变量
                self.variables = old_vars
            else:
                raise ValueError(f"Undefined function: {func_name}")
        
        return None
    
    def _is_true(self, value):
        """判断条件是否为真"""
        if value is None:
            return False
        if isinstance(value, bool):
            return value
        if isinstance(value, (int, float)):
            return value != 0
        if isinstance(value, str):
            # 尝试解析比较表达式
            if '>' in value:
                parts = value.split('>')
                left = self.eval_expr(parts[0].strip())
                right = self.eval_expr(parts[1].strip())
                return left > right
            elif '<' in value:
                parts = value.split('<')
                left = self.eval_expr(parts[0].strip())
                right = self.eval_expr(parts[1].strip())
                return left < right
            elif '==' in value:
                parts = value.split('==')
                left = self.eval_expr(parts[0].strip())
                right = self.eval_expr(parts[1].strip())
                return left == right
            elif '!=' in value:
                parts = value.split('!=')
                left = self.eval_expr(parts[0].strip())
                right = self.eval_expr(parts[1].strip())
                return left != right
            elif '>=' in value:
                parts = value.split('>=')
                left = self.eval_expr(parts[0].strip())
                right = self.eval_expr(parts[1].strip())
                return left >= right
            elif '<=' in value:
                parts = value.split('<=')
                left = self.eval_expr(parts[0].strip())
                right = self.eval_expr(parts[1].strip())
                return left <= right
            # 非空字符串视为 True
            return bool(value)
        if isinstance(value, list):
            return len(value) > 0
        return bool(value)
    
    def run(self, code):
        """运行 OCPL 代码"""
        # 移除注释
        lines = code.split('\n')
        cleaned = []
        for line in lines:
            if '//' in line:
                line = line[:line.index('//')]
            if line.strip():
                cleaned.append(line)
        code = ' '.join(cleaned)
        
        # 查找所有顶级 !() 命令
        i = 0
        while i < len(code):
            if code[i] == '!' and i + 1 < len(code) and code[i+1] == '(':
                start = i
                depth = 0
                j = i
                while j < len(code):
                    if code[j] == '(':
                        depth += 1
                    elif code[j] == ')':
                        depth -= 1
                        if depth == 0:
                            break
                    j += 1
                if depth == 0:
                    cmd = code[start:j+1]
                    self.execute_command(cmd[2:-1])
                    i = j + 1
                else:
                    i += 1
            else:
                i += 1
        
        return '\n'.join(self.output)


# ============ 测试示例 ============

if __name__ == "__main__":
    interpreter = OCPLInterpreter()
    
    # 示例 1: Hello World
    print("=== Example 1: Hello World ===")
    interpreter.run('!("Hello, World!")')
    print(interpreter.output[-1])
    
    # 示例 2: 变量和列表
    print("\n=== Example 2: Variables and Lists ===")
    interpreter = OCPLInterpreter()
    interpreter.run('!("x", 4)')
    interpreter.run('!("List", [0, 1, 2])')
    interpreter.run('!("x", "x + 1")')
    print(f"x = {interpreter.variables.get('x')}")
    print(f"List = {interpreter.variables.get('List')}")
    
    # 示例 3: 函数
    print("\n=== Example 3: Function ===")
    interpreter = OCPLInterpreter()
    interpreter.run('!("HelloWorld", null, !("Hello, World!"))')
    interpreter.run('!("HelloWorld", 1, null, null, null, null, null)')
    print(interpreter.output[-1])
    
    # 示例 4: if 语句
    print("\n=== Example 4: If Statement ===")
    interpreter = OCPLInterpreter()
    interpreter.run('!("x", 5)')
    interpreter.run('!("x>0", !("x is bigger than 0"), !("x is not bigger than 0"), !("this always shows"))')
    for line in interpreter.output:
        print(line)
    
    # 示例 5: while 循环(乘法表)
    print("\n=== Example 5: Multiplication Table (from spec) ===")
    interpreter = OCPLInterpreter()
    code = '''
    !("x", 1)
    !("x<10", 
      !("y", 1),
      !("y<10",
        !("y + " * " + x + " = " + x*y),
        !("y", "y + 1"),
        null,
        null,
        null
      ),
      !("x", "x + 1"),
      null,
      null
    )
    '''
    interpreter.run(code)
    for line in interpreter.output:
        print(line)