Exemple #1
0
def quasiquote(ast):
    #print ("quasiquote with", printer.pr_str(ast, True))
    if not is_pair(ast):
        #print("step i: ast is not pair", ast)
        return parser.LispList([parser.StrSymbol('quote'), ast])
    if (isinstance(ast.values[0], parser.StrSymbol)
            and ast.values[0].val == 'unquote'):
        #print("step ii : found 'unquote'")
        return ast.values[1]
    if is_pair(ast.values[0]):
        zz = ast.values[0].values[0]
        #print ("zz", zz)
        #print ("t(zz)", type(zz))
        if isinstance(zz, parser.StrSymbol) and zz.val == 'splice-unquote':
            #print("step iii : found 'splice-unquote'")
            return parser.LispList([
                parser.StrSymbol('concat'), ast.values[0].values[1],
                quasiquote(parser.LispList(ast.values[1:]))
            ])
    #print("step iv : else")
    return parser.LispList([
        parser.StrSymbol('cons'),
        quasiquote(ast.values[0]),
        quasiquote(parser.LispList(ast.values[1:]))
    ])
Exemple #2
0
def read_atom(readerInst):
    """ this function will look at the contents of the token and return the appropriate scalar (simple/single) data type value. Initially, you can just implement numbers(integers) and symbols. This will allow you to proceed through the next couple of steps before you will need to implement the other fundamental MAL types: nil, true, false, and string. The remaining MAL types: keyword, vector, hash-map, and atom do not need to be implemented until step 9 (but can be implemented at any point between this step and that). BTW, symbol types are just objects that contain a single string name value."""

    if not readerInst.has_token():
        raise SyntaxError('reached EOF')

    malItem = readerInst.next()

    try:
        intNum = int(malItem)
        return parser.IntSymbol(intNum)
    except ValueError:
        #print ("malItem:", malItem)
        #print ("len:", len(malItem))
        if ((len(malItem) > 1) and (malItem[0] == '"')
                and (malItem[-1] == '"')):
            s = printer.unescape(malItem[1:-1])
            #print ("making lisp string:", s)
            #for i,c in enumerate(s):
            #    print (i, c)
            return parser.LispString(s)

        if ((len(malItem) > 1) and (malItem[0] == ':')):
            s = malItem[1:]
            return parser.LispKeyword(s)
        if malItem == 'nil':
            return parser.NilSymbol()
        elif malItem == 'true':
            return parser.TrueSymbol()
        elif malItem == 'false':
            return parser.FalseSymbol()
        else:
            return parser.StrSymbol(malItem)
Exemple #3
0
def read_form(readerInst):
    """this function will peek at the first token in the Reader object
    and switch on the first character of that token.  If the character
    is a left paren then read_list is called with the Reader object.
    Otherwise, read_atom is called with the Reader Ojbect.  The return
    value from read_form is a MAL data type. You can likely just
    return a plain list of MAL types.
    """

    tok = readerInst.peek()

    if tok is '(':
        return parser.LispList(read_list(readerInst, ')'))
    elif tok is '[':
        return parser.LispVector(read_list(readerInst, ']'))
    elif tok is '{':
        return parser.LispHashMap(read_list(readerInst, '}'))
    elif tok is '@':
        atSign = readerInst.next()
        nextForm = read_form(readerInst)
        return parser.LispList([parser.StrSymbol('deref'), nextForm])
    elif tok is "'":
        readerInst.next()
        nextForm = read_form(readerInst)
        return parser.LispList([parser.StrSymbol('quote'), nextForm])
    elif tok is "`":
        readerInst.next()
        nextForm = read_form(readerInst)
        return parser.LispList([parser.StrSymbol('quasiquote'), nextForm])
    elif tok is "~":
        readerInst.next()
        nextForm = read_form(readerInst)
        return parser.LispList([parser.StrSymbol('unquote'), nextForm])
    elif tok == "~@":
        readerInst.next()
        nextForm = read_form(readerInst)
        return parser.LispList([parser.StrSymbol('splice-unquote'), nextForm])
    elif tok == "^":
        readerInst.next()
        nf = read_form(readerInst)
        nnf = read_form(readerInst)
        return parser.LispList([parser.StrSymbol('with-meta'), nnf, nf])
    else:
        return read_atom(readerInst)
Exemple #4
0
def func_symbol(arg):
    return parser.StrSymbol(arg.str)