Ejemplo n.º 1
0
def p_term_2op(p):
    '''
    term_2op    : term TIMES    factor
                | term DIVIDE   factor
                | term POW      factor
                | term PERC     factor
                | term EQUAL    factor
                | term NEQ      factor
                | term GEQ      factor
                | term LEQ      factor
                | term GT       factor
                | term LT       factor
                | term IS       factor
    '''
    p[0] = p[1] + p[3]
    if p[2] == '*': p[0] += ['MUL']
    elif p[2] == '/': p[0] += ['DIV']
    elif p[2] == '**': p[0] += ['POW']
    elif p[2] == '%': p[0] += ['LD', 'mod', 'CALL', 2]
    elif p[2] == '==': p[0] += ['EQ']
    elif p[2] == '!=': p[0] += ['NEQ']
    elif p[2] == '>=': p[0] += ['GEQ']
    elif p[2] == '<=': p[0] += ['LEQ']
    elif p[2] == '>': p[0] += ['GT']
    elif p[2] == '<': p[0] += ['LT']
    elif p[2] == 'is': p[0] += ['IS']

    if len(p[1]) == 2 and len(
            p[3]) == 2 and p[1][0] == 'LDC' and p[3][0] == 'LDC':
        v = eval([], [G], p[0] + ['STOP'], 0, [], [])
        p[0] = ['LDC', v[-1]]
Ejemplo n.º 2
0
def p_expression_2op(p):
    '''
    expression_2op  : expression PLUS expression
                    | expression MINUS expression
                    | expression ID expression
    '''
    #print(p)
    p[0] = p[1] + p[3]
    if p[2] == '+': p[0] += ['ADD']
    elif p[2] == '-': p[0] += ['SUB']
    elif p[2] in G:  #2項演算子系のマクロを展開する
        c = G[p[2]]
        #print(c)
        if isinstance(c, list) and c[0] == 'MACRO_CL':
            p[0] = macrofunction_expand(c, [p[1], p[3]])
            return
        p[0] += ['LD', p[2], 'CALL', 2]
    else:
        p[0] += ['LD', p[2], 'CALL', 2]

    if len(p[1]) == 2 and len(
            p[3]) == 2 and p[1][0] == 'LDC' and p[3][0] == 'LDC':
        v = eval([], [G], p[0] + ['STOP'], 0, [], [])
        p[0] = ['LDC', v[-1]]
        return

    if len(p[3]) == 2 and p[3][0] == 'LDC' and p[3][1] == 1:
        if p[2] == '+': p[0] = p[1] + ['INC']
        elif p[2] == '-': p[0] = p[1] + ['DEC']
Ejemplo n.º 3
0
def p_term_1op(p):
    '''
    term_1op    : MINUS factor
                | NOT factor
    '''
    if p[1] == '-': p[0] = p[2] + ['MINUS']
    elif p[1] == '!': p[0] = p[2] + ['NOT']
    # 定数の畳み込み
    if len(p[2]) == 2 and p[2][0] == 'LDC':
        v = eval([], [G], p[0] + ['STOP'], 0, [], [])
        p[0] = ['LDC', v[-1]]
Ejemplo n.º 4
0
def load(file_name):
    f = open(file_name)
    s = f.read()
    print(s)
    result = parser.parse(s)
    #c_time = time.time()
    v = eval([], [G], result + ['STOP'], 0, [], [])
    #e_time = time.time()
    if   type(v) == list and v != [] and v[0] == 'CL':print('Usser Function')
    elif type(v) == list and v != [] and v[0] == 'MACRO_CL':print ('User Macro')
    elif type(v) == list and v != [] and v[0] == 'CONT':print ('User Continueation')
    else:print(v)
    #print('c_time  : ', int((1000000 * (c_time - s_time))) / 1000000)
    #print('e_time  : ', int((1000000 * (e_time - c_time))) / 1000000)
    G['_'] = v
Ejemplo n.º 5
0
def add_expr(p):
    '''
    add_expr    : mul_expr
                | add_expr ADD mul_expr
                | add_expr SUB mul_expr
    '''
    if len(p) == 2:
        p[0] = p[1]
        return
    p[0] = p[1] + p[3]
    if   p[2] == '+': p[0] += ['ADD']
    elif p[2] == '-': p[0] += ['SUB']
    # 定数畳み込み
    if len(p[1]) == 2 and len(p[3]) == 2 and p[1][0] ==  'LDC' and p[3][0] ==  'LDC':
        v = eval([], [G], p[0] + ['STOP'],0,  [], [])
        p[0] = ['LDC', v]
Ejemplo n.º 6
0
def eq_expression(p):   
    '''
    eq_expr     : rel_expr
                | eq_expr IS rel_expr
                | eq_expr EQUAL rel_expr
                | eq_expr NEQ rel_expr
    '''
    if len(p) == 2:
        p[0] = p[1]
        return
    p[0] = p[1] + p[3]
    if   p[2] == 'is': p[0] += ['IS']
    elif p[2] == '==': p[0] += ['EQ']
    elif p[2] == '!=': p[0] += ['NEQ']
    # 定数畳み込み
    if len(p[1]) == 2 and len(p[3]) == 2 and p[1][0] ==  'LDC' and p[3][0] ==  'LDC':
        v = eval([], [G], p[0] + ['STOP'],0,  [], [])
        p[0] = ['LDC', v]
Ejemplo n.º 7
0
def p_factor_var(p):
    '''
    var : ID
    '''
    #p[0] = ['LD', p[1]]    # マクロの処置をしないならここまででOK

    if p[1] in G:
        c = G[p[1]]
        if isinstance(c, list) and c != [] and c[0] == 'MACRO':
            #p[0] = c[1]    # 解釈しないでそのまま出力すのも仕様としてあり
            try:  # 定数として解釈可能ならそれを返す
                v = eval([], [G], c[1] + ['STOP'], 0, [], [])
                p[0] = ['LDC', v[-1]]
            except:  # 定数として解釈できなければコードを残す
                p[0] = c[1]
            #p[0] = ['LDC', v]
        else:
            p[0] = ['LD', p[1]]  #
    else:
        p[0] = ['LD', p[1]]
Ejemplo n.º 8
0
def rel_expression(p):
    '''
    rel_expr    : add_expr
                | rel_expr GT add_expr
                | rel_expr GEQ add_e]pr
                | rel_expr LT add_expr
                | rel_expr LEQ add_expr
    '''
    if len(p) == 2:
        p[0] = p[1]
        return
    p[0] = p[1] + p[3]
    if   p[2] == '>': p[0] += ['GT']
    elif p[2] == '>=': p[0] += ['GEQ']
    elif p[2] == '<': p[0] += ['LT']
    elif p[2] == '<=': p[0] += ['LEQ']
    # 定数畳み込み
    if len(p[1]) == 2 and len(p[3]) == 2 and p[1][0] ==  'LDC' and p[3][0] ==  'LDC':
        v = eval([], [G], p[0] + ['STOP'],0,  [], [])
        p[0] = ['LDC', v]
Ejemplo n.º 9
0
def mul_expr(p):
    '''
    mul_exp     : uni_exper
                | mul_expr MUL uni_expr
                | mul_expr DIV uni_expr
                | mul_expr MOD uni_expr
                | mul_expr POW uni_expr
                | mul_expr IDIV uni_expr
    '''
    if len(p) == 2:
        p[0] = p[1]
        return
    p[0] = p[1] + p[3]
    if   p[2] == '*': p[0] += ['MUL']
    elif p[2] == '/': p[0] += ['DIV']
    elif p[2] == '%': p[0] += ['MOD']
    elif p[2] == '**': p[0] += ['POW']
    elif p[2] == '//': p[0] += ['IDIV']
    # 定数畳み込み
    if len(p[1]) == 2 and len(p[3]) == 2 and p[1][0] ==  'LDC' and p[3][0] ==  'LDC':
        v = eval([], [G], p[0] + ['STOP'],0,  [], [])
        p[0] = ['LDC', v]
Ejemplo n.º 10
0
def Eval(s):
    return eval([], [G], Compile(s), 0, [], [])
Ejemplo n.º 11
0
 # call_ccの処理
 #
 q = result + ['STOP']
 qq = q
 cc = search_nr(qq, '__CODE__')
 if cc != []:
     for (ccc, j) in cc:
         ccc[j] = ccc[j + 6:]
 # __DCL__を元に戻す
 replace(qq, ['__DCL__'], ['DCL'])
 if G['_code']: print(qq)
 c_time = time.time()
 #print( result)
 try:
     #v = eval([], [G], result + ['STOP'], 0, [], [])
     V = eval([], [G], qq, 0, [], [])
     e_time = time.time()
     for v in V:
         if type(v) == list and v != [] and v[0] == 'CL':
             print('User Function')
         elif type(v) == list and v != [] and v[0] == 'MACRO_CL':
             print('User Macro')
         elif type(v) == list and v != [] and v[0] == 'CONT':
             print('User Continueation')
         elif type(v) == str:
             print(repr(v))
         else:
             print(v)
     if G['_time']:
         print('c_time  : ',
               int((1000000 * (c_time - s_time))) / 1000000,
Ejemplo n.º 12
0
def uni_expr(p):
    '''
    uni_expr    : pfix_expr
                | MINUS uni_expr
                | NOT uni_expr
                | CALLCC LPAREN expr RPAREN
    '''
    if len(p) == 2: # 単純式または後置式
        p[0] = compile_pfix_expr(p[1])
        return
    if len(p) == 5: # call_cc
        p[0] = ['LDICT', '__CODE__'] + p[3] + ['CALL', 1]
        return
    # 単項演算子 '-'または'!'の場合
    p[0] = p[2]
    if p[1] == '-':p[0] += ['MINUS']
    elif p[1] == '!':p[0] += ['NOT']
    else
    # 定数の畳み込み
    if len(p[2]) == 2 and p[2][0] ==  'LDC' :
        v = eval([], [G], p[0] + ['STOP'],0,  [], [])
        p[0] = ['LDC', v]

NON_TYPE, INC_TYPE, DEC_TYPE, CALL_TYPE, APLY_TYPE = 0, 1, 2, 3, 4
def pfix_expr(p):
    '''
    pfix_expr   : prm_expr
                | pfix_expr LBRAK expr RBRAK
                | pfix_expr LPAREN args DOTS RPAREN
                | pfix_expr LPAREN args RPAREN
                | pfix_expr LPAREN RPAREN
                | pfix_expr INC
                | pfix_expr DEC
    '''
    if len(p) == 2:
        p[0] =  p[1]         # 後置表記なし
        return
    # 長さが2でないならp[1]がpfix_exprなのでまずそれをコンパイル
    p[1] = compile_pfix_expr(p[1])
    # 右辺式のコードを生成しp[0]に入れる
    if   p[2] == '++': p[0] = ['_PF_', INC_TYPE, p[1]]  # ++ の後置表記
    elif p[2] == '--': p[0] = ['_PF_', DEC_TYPE, p[1]]  # -- の後置表記
    elif p[2] == '(' :   # 関数呼び出し
        if len(p) == 4:  # 引数なしの関数呼び出し表記
            p[0] = ['_PF_', CALL_TYPE,[], p[1] ]
        elif len(p) == 5:
            p[0] = ['_PF_', CALL_TYPE, p[3], p[1]]
        elif len(p) == 6:
            p[0] = ['_PF_', APLY_TYPE, p[3], p[1]]
    elif p[2] == '[': p[0] = ['_PF_', REF_TYPE, p[3], p[1]]   # Vector参照表記

def prm_exp(p):     # primitive expression
    '''
    prm_expr    : atm
                | LPAREN expr RPAREN
                | var
                | vector
                | closure
                | macro_expr
    '''
    if len(p) == 2: p[0] = p[1]
    else:
        p[0] = p[2]

def atm(p):         # basic factor
    '''
    atm         : INT | FLOAT | E_FLOAT |FLOAT2 | FACT
                | TRUE | FALSE
                | STR
    '''
    p[0] = ['LDC', p[1]]

def var(p):
    '''
    var         : ID
    '''
    p[0] = ['LD', p[1]]
    # マクロ処理を追加すること

def vector(p):
    '''
    vector      : LBRAK args RBRAK
                | LBRAK RBRAK
    '''
    if len(p) == 2: p[0] = ['LDC', []]  # NULL vector
    else:
        n = len(p[1])
        C = []
        for c in p[1]:
            C = C + c
        p[0] = C + ['VEC', n]
# closure (LAMBDA式)
def closure(p):
    '''
    closure     : LAMBDA LPAREN id_list DOTS RPAREN expr
                | LAMBDA LPAREN id_list RPAREN expr
                | LAMBDA LPAREN RPAREN expr
    '''
    if len(p) == 5:
        p[0] = ['LDF', tail(p[4] + ['RTN']), []]
    if len(p) == 6:
        p[0] = ['LDF', tail(p[5] + ['RTN']), p[3]]
    if len(p) == 7:
        p[0] = ['LDF', tail(p[6] + ['RTN']), p[3], '..']
    
# 関数マクロ
def macro_expr(p):
    '''
    macro_expr  : MACRO LPAREN args DOTS RPAREN expression 
                | MACRO LPAREN args RPAREN expression
                | MACRO LPAREN RPAREN expression
                | MACRO expression
    '''
    if len(p) == 7:p[0] = ['LDM_CL', p[6], p[3], ['..']]
    elif len(p) == 6:p[0] = ['LDM_CL', p[5], p[3]]
    elif len(p) == 5:p[0] = ['LDM_CL', p[4], []]
    elif len(p) == 3:p[0] = ['LDM', p[2]]

def args(p):
    '''
    args        : expr
                | args CAMMA expr
    '''
    if   len(p) == 2: p[0] = [p[1]]
    elif len(p) == 4: p[0] = p[1] + [p[3]]

def id_list(p):
    '''
    id_list     : ID
                | id_list CAMMA ID
    '''
    if   len(p) == 2: p[0] = [p[1]]
    elif len(p) == 4: p[0] = p[1] + [p[3]]

#
# 構文エラー 
#
def p_error(p):     
    #print( "Syntax error in input")
    raise SyntaxError("SyntaxError: " + str(p))
# 構文解析器の構築 
parser = yacc.yacc() 
from eval_test import eval
import time
if __name__ == '__main__':
    load("lib.py")
    while True:
        try:
            s = input('pure> ')
        except EOFError:
            break
        if not s:
            continue
        s_time = time.time()
        try:
            result = parser.parse(s)
            #print(result)
        except (SyntaxError, ZeroDivisionError) as e:
            print(e)
            continue
        #
        # call_ccの処理
        #
        q = result + ['STOP']
        qq = q
        cc = search_nr(qq, '__CODE__')
        if cc != []: 
            for (ccc, j) in cc:
                ccc[j] = ccc[j + 6:]
        # __DCL__を元に戻す
        replace(qq, ['__DCL__'], ['DCL'])
        if G['_code']:print(qq)
        c_time = time.time()
        #print( result)
        try:
            #v = eval([], [G], result + ['STOP'], 0, [], [])
            v = eval([], [G], qq, 0, [], [])
            e_time = time.time()
            if type(v) == list and v != [] and v[0] == 'CL':print('Usser Function')
            elif type(v) == list and v != [] and v[0] == 'MACRO_CL':print ('User Macro')
            elif type(v) == list and v != [] and v[0] == 'CONT':print ('User Continueation')
            else:print(v)
            if G['_time']:print('c_time  : ', int((1000000 * (c_time - s_time))) / 1000000, '\te_time  : ', int((1000000 * (e_time - c_time))) / 1000000)
            G['_'] = v
        except (KeyError, IndexError, SyntaxError, TypeError, ZeroDivisionError) as e:
            print(e)
            continue