コード例 #1
0
 def add(node: ASTNode, _):
     isatLeastOneString = Types.isStrictlyString(
         node.left) or Types.isStrictlyString(node.right)
     if isatLeastOneString:
         node.value = str(node.left.value) + str(node.right.value)
         node.dataType = Types.STRING
     else:
         node.value = node.left.value + node.right.value
         node.dataType = Types.NUMERIC
コード例 #2
0
    def logicalOp(node: ASTNode, _):
        left = node.left.value
        right = node.right.value
        if node.nodeType == ASTNode.AND:
            node.value = left and right
        else:
            node.value = left or right

        node.dataType = Types.BOOLEAN
コード例 #3
0
 def binaryArithmeticOp(node: ASTNode, _):
     left = node.left.value
     right = node.right.value
     if node.nodeType == ASTNode.MULT:
         node.value = left * right
     elif node.nodeType == ASTNode.SUB:
         node.value = left - right
     elif node.nodeType == ASTNode.DIV:
         if right == 0:
             raise ZeroDivisionError("cannot divide with zero")
         node.value = left / right
     else:
         node.value = left**right
     node.dataType = Types.NUMERIC
コード例 #4
0
 def reverse_string(node: ASTNode):
     left = node.left
     if TypeChecker.isStrictlyString(left):
         node.dataType = TypeChecker.STRING
         return Result(True)
     else:
         return Result(False, getUniaryOpTypeErr(node))
コード例 #5
0
 def negate(node: ASTNode):
     left = node.left
     if TypeChecker.isLooselyNumeric(left):
         node.dataType = TypeChecker.NUMERIC
         return Result(True)
     else:
         return Result(False, getUniaryOpTypeErr(node))
コード例 #6
0
 def not_op(node: ASTNode):
     left = node.left
     if TypeChecker.isLooselyNumeric(left) or TypeChecker.isStrictlyBoolean(
             left):
         node.dataType = TypeChecker.BOOLEAN
         return Result(True)
     else:
         return Result(False, getUniaryOpTypeErr(node))
コード例 #7
0
 def relationOp(node: ASTNode):
     left = node.left
     right = node.right
     if not TypeChecker.isEqual(left, right):
         return Result(
             False,
             f'incomparables types: {left.dataType} and {right.dataType}')
     else:
         node.dataType = TypeChecker.BOOLEAN
         return Result(True)
コード例 #8
0
    def array(node: ASTNode, _):

        if Types.isAtomic(node.left):
            node.left.value = [node.left.value]
        node.value = node.left.value
        node.value.append(node.right.value)
        isLooselyNumeric = lambda type: type == Types.NUMERICARRAY or type == Types.INTARRAY
        isNumericBool = lambda type: type == Types.INTARRAY or type == Types.NUMERICARRAY or type == Types.BOOLEANARRAY or type == Types.NUMERIC_BOOL_ARR
        if Types.isAtomic(node.left):
            ltype = Types.getArrayTypeBasedOnAtomic(node.left)
        else:
            ltype = node.left.dataType
        rtype = Types.getArrayTypeBasedOnAtomic(node.right)
        if ltype == rtype:
            node.dataType = ltype
        elif isLooselyNumeric(ltype) and isLooselyNumeric(rtype):
            node.dataType = Types.NUMERICARRAY
        elif isNumericBool(ltype) and isNumericBool(rtype):
            node.dataType = Types.NUMERIC_BOOL_ARR
コード例 #9
0
    def logical_op(node: ASTNode):
        left = node.left
        right = node.right
        valid = lambda node: TypeChecker.isStrictlyBoolean(
            node) or TypeChecker.isLooselyNumeric(node)
        if valid(left) and valid(right):
            node.dataType = TypeChecker.BOOLEAN
            return Result(True)

        else:
            return Result(False, getBinaryOpTypeErr(node))
コード例 #10
0
 def hybridAdd(node: ASTNode):
     left = node.left
     right = node.right
     validType = lambda node: TypeChecker.isStrictlyString(
         node) or TypeChecker.isLooselyNumeric(node)
     if validType(left) and validType(right):
         node.dataType = TypeChecker.NUMERIC if TypeChecker.isLooselyNumeric(
             left) and TypeChecker.isLooselyNumeric(
                 right) else TypeChecker.STRING
         return Result(True)
     else:
         return Result(False, getBinaryOpTypeErr(node))
コード例 #11
0
 def array_sep(node: ASTNode):
     left, right = node.left, node.right
     status, err = None, None
     isLooselyNumeric = lambda type: type == TypeChecker.NUMERICARRAY or type == TypeChecker.INTARRAY
     isNumericBool = lambda type: type == TypeChecker.INTARRAY or type == TypeChecker.NUMERICARRAY or type == TypeChecker.BOOLEANARRAY or type == TypeChecker.NUMERIC_BOOL_ARR
     if TypeChecker.isAtomic(left):
         ltype = TypeChecker.getArrayTypeBasedOnAtomic(left)
     else:
         ltype = left.dataType
     rtype = TypeChecker.getArrayTypeBasedOnAtomic(right)
     if ltype == rtype:
         node.dataType = ltype
         status = True
     elif isLooselyNumeric(ltype) and isLooselyNumeric(rtype):
         node.dataType = TypeChecker.NUMERICARRAY
         status = True
     elif isNumericBool(ltype) and isNumericBool(rtype):
         node.dataType = TypeChecker.NUMERIC_BOOL_ARR
         status = True
     else:
         status = False
         err = f"Array cannot hold different types: {TypeChecker.getAtomicTypeBasedOnArray(ltype)} and {TypeChecker.getAtomicTypeBasedOnArray(rtype)}"
     return Result(status, err)
コード例 #12
0
 def strictArithmeticBinaryOp(node: ASTNode):
     """
      Apply type system rules for '*', '/', '-', '^'
     :param node:
     :return:
     """
     left = node.left
     right = node.right
     if TypeChecker.isLooselyNumeric(left) and TypeChecker.isLooselyNumeric(
             right):
         node.dataType = TypeChecker.NUMERIC
         return Result(True)
     else:
         return Result(False, getBinaryOpTypeErr(node))
コード例 #13
0
 def binaryComparisonOp(node: ASTNode, _):
     left = node.left.value
     right = node.right.value
     if node.nodeType == ASTNode.EQ:
         node.value = left == right
     elif node.nodeType == ASTNode.NE:
         node.value = left != right
     elif node.nodeType == ASTNode.GT:
         node.value = left > right
     elif node.nodeType == ASTNode.LT:
         node.value = left < right
     elif node.nodeType == ASTNode.GTE:
         node.value = left >= right
     else:
         node.value = left <= right
     node.dataType = Types.BOOLEAN
コード例 #14
0
 def undefined(node: ASTNode):
     node.dataType = TypeChecker.UNDEFINED
     return Result(True)
コード例 #15
0
 def var(node: ASTNode, env):
     #DATABASE QUERY THAT CHECKS IF VAR EXISTS
     node.dataType = env(node)
     return Result(True)
コード例 #16
0
 def enum(node: ASTNode, env):
     node.dataType = TypeChecker.ENUM
     return Result(True)
コード例 #17
0
 def string(node: ASTNode):
     node.dataType = TypeChecker.STRING
     return Result(True)
コード例 #18
0
    def integer(node: ASTNode):

        node.dataType = TypeChecker.INTEGER
        return Result(True)
コード例 #19
0
 def boolconstant(node: ASTNode):
     node.dataType = TypeChecker.BOOLEAN
     return Result(True)
コード例 #20
0
 def integer(node: ASTNode, _):
     node.dataType = Types.INTEGER
コード例 #21
0
 def negate(node: ASTNode, _):
     node.value = -node.left.value
     node.dataType = Types.NUMERIC
コード例 #22
0
 def reverse_string(node: ASTNode, _):
     node.value = node.left.value[::-1]
     node.dataType = Types.STRING
コード例 #23
0
 def notOp(node: ASTNode, _):
     node.value = not node.left.value
     node.dataType = Types.BOOLEAN
コード例 #24
0
 def undefined(node: ASTNode, _):
     node.dataType = Types.UNDEFINED
コード例 #25
0
 def boolConst(node: ASTNode, _):
     node.dataType = Types.BOOLEAN
コード例 #26
0
 def string(node: ASTNode, _):
     node.dataType = Types.STRING