from abc import abstractmethod
from typing import List, Dict, Union, Any
import sys
import os
from Lexer import runlexer
TAB = '  '  # two whitespaces

store = {}
class Node:
    def __init__(self, *args):
        self.height = int(args[0])  # the level of indentation required for current Node

    def __str__(self):
        return 'prog'

    @staticmethod
    def one_tab(line):
        """Formats the line of an argument from an expression."""
        return TAB + line + '\n'

    def final_print_str(self, print_str):
        """Adds height number of tabs at the beginning of every line that makes up the current Node."""
        return (self.height * TAB).join(print_str)

    @abstractmethod
    def accept(self, visitor):
        pass

class InstructionList(Node):
    """begin <instruction_list> end"""

    def __init__(self, *args):  # args = height, [Nodes in instruction_list]
        super().__init__(args[0])
        self.list = args[1]

    def __str__(self):
        print_str = ['[\n']
        for expr in self.list:
            print_str.append(self.one_tab(expr.__str__()))
        print_str.append(']')

        return self.final_print_str(print_str)
    def executa_instructiuni(self):
        for expr in self.list:
            visitor.visit(expr)
    def accept(self, visitor):
        return visitor.visit(self)

class Expr(Node):
    """<expr> + <expr> | <expr> > <expr> | <expr> == <expr> | <variable> | <integer>"""

    def __init__(self, *args):  # args = height, '+' | '>' | '==' | 'v' | 'i', left_side, *right_side
        super().__init__(args[0])
        self.type = args[1]
        self.left = args[2]
        if len(args) > 3:
            self.right = args[3]
        else:
            # variable and integer have no right_side
            self.right = None

    def __str__(self):
        name = 'expr'
        if self.type == 'v':
            name = 'variable'
        elif self.type == 'i':
            name = 'integer'
        elif self.type == '+':
            name = 'plus'
        elif self.type == '*':
            name = 'multiply'
        elif self.type == '-':
            name = 'minus'
        elif self.type == '>':
            name = 'greaterthan'
        elif self.type == '==':
            name = 'equals'

        print_str = [name + ' [\n', self.one_tab(str(self.left))]
        if self.right:
            print_str.append(self.one_tab(str(self.right)))
        print_str.append(']')

        return self.final_print_str(print_str)

    def get_variable(self) -> str:
       return self.left

    def get_expr(self) -> Union[int, Any]:
        if self.type == 'v':
            return store[self.left]
        if self.type == 'i':
            return int(self.left)
        if self.type == '+':
            suma = self.left.get_expr() + self.right.get_expr()
            return suma
        if self.type == '-':
            diferenta = self.left.get_expr() - self.right.get_expr()
            return diferenta
        if self.type == '*':
            produs = self.left.get_expr() * self.right.get_expr()
            return produs
        if self.type == '==':
            return self.left.get_expr() == self.right.get_expr()
        if self.type == '>':
            return self.left.get_expr() > self.right.get_expr()
    def accept(self, visitor):
        return visitor.visit(self)

class While(Node):
    """while (<expr>) do <prog> od"""

    def __init__(self, *args):  # args = height, Node_expr, Node_prog
        super().__init__(args[0])
        self.expr = args[1]
        self.prog = args[2]

    def __str__(self):
        print_str = ['while [\n',
                     self.one_tab(self.expr.__str__()),
                     self.one_tab('do ' + self.prog.__str__()),
                     ']']
        return self.final_print_str(print_str)
    def executa_while(self):
        while visitor.visit(self.expr) is True:
            visitor.visit(self.prog)
    def accept(self, visitor):
        return visitor.visit(self)

class If(Node):
    """if (<expr>) then <prog> else <prog> fi"""

    def __init__(self, *args):  # args = height, Node_expr, Node_then, Node_else
        super().__init__(args[0])
        self.expr = args[1]
        self.then_branch = args[2]
        self.else_branch = args[3]

    def __str__(self):
        print_str = ['if [\n',
                     self.one_tab(self.expr.__str__()),
                     self.one_tab('then ' + self.then_branch.__str__()),
                     self.one_tab('else ' + self.else_branch.__str__()),
                     ']']
        return self.final_print_str(print_str)

    def executa_conditie(self):
        if visitor.visit(self.expr) is True:
            visitor.visit(self.then_branch)
        else:
            visitor.visit(self.else_branch)

    def accept(self, visitor):
        return visitor.visit(self)

class Assign(Node):
    """<variable> '=' <expr>"""

    def __init__(self, *args):  # args = height, Node_variable, Node_expr
        super().__init__(args[0])
        self.variable = args[1]
        self.expr = args[2]

    def __str__(self):
        print_str = ['assign [\n',
                     self.one_tab(self.variable.__str__()),
                     self.one_tab(self.expr.__str__()),
                     ']']
        return self.final_print_str(print_str)
    def update_store(self):
        var = self.variable.get_variable()
        exp = int(visitor.visit(self.expr))
        store.update({var: exp})

    def accept(self, visitor):
        return visitor.visit(self)

class Visitor():
    """Abstract Vistor Class"""
    @abstractmethod
    def visit(self, item):
        pass
class CartVisitor(Visitor):
    def visit(self, item):
        if isinstance(item, Assign):
            item.update_store()
        if isinstance(item, Expr):
            return item.get_expr()
        if isinstance(item, InstructionList):
            return item.executa_instructiuni()
        if isinstance(item, If):
            return item.executa_conditie()
        if isinstance(item, While):
            return item.executa_while()

class NFA:
    def __init__(self, expr):
        if isinstance(expr, simbol):
            self.alphabet: List[str] = expr.x
            self.initialState: tuple = (0,)
            self.finalState: tuple = (1,)
            self.delta: Dict[tuple, Dict[str, tuple]] = {self.initialState: {self.alphabet[0]: self.finalState}}
            self.states = 2
        else:
            self.alphabet: List[str] = None
            self.initialState: tuple = None
            self.finalState: tuple = None
            self.delta: Dict[tuple, Dict[str, tuple]] = None
            self.states = 0

    def renumerotare(self, nr_stari: int) -> dict:
        x = self.delta
        z = {}
        for sursa in x.keys():
            for tranzitii in x[sursa].keys():
                if len(x[sursa][tranzitii]) > 1:
                    for i in range(0, len(x[sursa][tranzitii])):
                        x[sursa][tranzitii][i] = tuple(y + nr_stari for y in x[sursa][tranzitii][i])
                else:
                    x[sursa][tranzitii] = tuple(y + nr_stari for y in x[sursa][tranzitii])
            z[tuple(y + nr_stari for y in sursa)] = x[sursa]
        return z

    def epsilon_tranzitii(self, current_state: tuple, vizitat: List[tuple]) -> tuple:
        if type(current_state) is not tuple:
            current_state = (current_state,)
        states = current_state
        if current_state not in (self.delta.keys()) or 'ε' not in self.delta[current_state].keys() \
                or current_state in vizitat:
            return tuple(set(sorted(states)))
        else:
            vizitat.append(current_state)
            for state in self.delta[current_state]['ε']:
                states += self.epsilon_tranzitii(state, vizitat)
        return tuple(set(sorted(states)))

    def step(self, dfa_state: tuple, simbol: str) -> tuple:
        next_state = tuple()
        for x in dfa_state:
            if (x,) in (self.delta.keys()) and simbol in self.delta[(x,)].keys():
                nfa_step = self.delta[(x,)][simbol]
                next_state += self.epsilon_tranzitii(nfa_step, [])
        if next_state == ():
            next_state = ('S',)
        return tuple(set(sorted(next_state)))

class expr:
    def __init__(self, x, y):
        self.x = x
        self.y = y

    def __str__(self):
        return str(self.x) + ' ' + str(self.y)

class star(expr):
    def __init__(self, x, y):
        super().__init__(x, y)

    def __str__(self):
        return 'STAR ' + str(self.x)

    def get_NFA(self) -> NFA:
        nfa = NFA(self)
        nfa1 = self.x.get_NFA()
        nfa.alphabet = nfa1.alphabet + 'ε'
        nfa.states = nfa1.states + 2
        nfa.initialState = (0,)
        nfa.finalState = (nfa.states - 1,)
        nfa.delta = {}
        nfa.delta.update({nfa.initialState: {'ε': [tuple(y + 1 for y in nfa1.initialState), nfa.finalState]}})
        nfa.delta.update(nfa1.renumerotare(1))
        nfa.delta.update({tuple(y + 1 for y in nfa1.finalState):
                              {'ε': [nfa.finalState, tuple(y + 1 for y in nfa1.initialState)]}})
        return nfa

class plus(expr):
    def __init__(self, x, y):
        super().__init__(x, y)

    def __str__(self):
        return 'PLUS ' + str(self.x)

    def get_NFA(self) -> NFA:
        nfa = NFA(self)
        nfa1 = self.x.get_NFA()
        nfa.alphabet = nfa1.alphabet + 'ε'
        nfa.states = nfa1.states + 2
        nfa.initialState = (0,)
        nfa.finalState = (nfa.states - 1,)
        nfa.delta = {}
        nfa.delta.update({nfa.initialState: {'ε': tuple(y + 1 for y in nfa1.initialState)}})
        nfa.delta.update(nfa1.renumerotare(1))
        nfa.delta.update({tuple(y + 1 for y in nfa1.finalState):
                              {'ε': [nfa.finalState, tuple(y + 1 for y in nfa1.initialState)]}})

        return nfa

class union(expr):
    def __init__(self, x, y):
        super().__init__(x, y)

    def __str__(self):
        return 'UNION ' + str(self.x) + ' ' + str(self.y)

    def get_NFA(self) -> NFA:
        nfa = NFA(self)
        nfa1 = self.x.get_NFA()
        nfa2 = self.y.get_NFA()
        nfa.alphabet = (nfa1.alphabet + nfa2.alphabet + 'ε')
        nfa.states = nfa1.states + nfa2.states + 2
        nfa.initialState = (0,)
        nfa.finalState = (nfa.states - 1,)
        nfa.delta = {}
        nfa.delta.update({nfa.initialState: {'ε': [tuple(y + 1 for y in nfa1.initialState),
                                                   tuple(y + nfa1.states + 1 for y in nfa2.initialState)]}})
        nfa.delta.update(nfa1.renumerotare(1))
        nfa.delta.update(nfa2.renumerotare(nfa1.states + 1))
        nfa.delta.update({tuple(y + 1 for y in nfa1.finalState): {'ε': nfa.finalState}})
        nfa.delta.update({tuple(y + nfa1.states + 1 for y in nfa2.finalState): {'ε': nfa.finalState}})
        return nfa

class concat(expr):
    def __init__(self, x, y):
        super().__init__(x, y)

    def __str__(self):
        return 'CONCAT ' + str(self.x) + ' ' + str(self.y)

    def get_NFA(self) -> NFA:
        nfa1 = self.x.get_NFA()
        nfa2 = self.y.get_NFA()
        nfa = NFA(self)
        nfa.alphabet = (nfa1.alphabet + nfa2.alphabet + 'ε')
        nfa.initialState = nfa1.initialState
        nfa.finalState = tuple(x + nfa1.states for x in nfa2.finalState)
        nfa.delta = nfa1.delta
        nfa.delta.update({nfa1.finalState: {'ε': tuple(y + nfa1.states for y in nfa2.initialState)}})
        nfa.delta.update(nfa2.renumerotare(nfa1.states))
        nfa.states = nfa1.states + nfa2.states
        return nfa

class simbol(expr):
    def __init__(self, x, y):
        super().__init__(x, y)

    def __str__(self):
        return str(self.x)

    def get_NFA(self) -> NFA:
        nfa = NFA(self)
        return nfa

class DFA:
    def __init__(self):
        self.alphabet: List[str] = None
        self.initialState: tuple = None
        self.finalStates: List[tuple] = []
        self.delta: Dict[tuple, Dict[str, tuple]] = {}
        self.renumerotare_stari: Dict[tuple, int] = {}
        self.stari: int = 0

    def generate_delta(self, current_state: tuple, nfa: NFA):
        if current_state not in self.renumerotare_stari.keys():
            self.renumerotare_stari.update({current_state: self.stari})
            self.stari += 1
        if nfa.finalState[0] in current_state and current_state not in self.finalStates:
            self.finalStates.append(current_state)
        for x in self.alphabet:
            next_state = nfa.step(current_state, x)
            if next_state == ('S',):
                if current_state in self.delta.keys():
                    self.delta[current_state].update({x: next_state})
                else:
                    self.delta.update({current_state: {x: next_state}})
                for y in self.alphabet:
                    if next_state in self.delta.keys():
                        self.delta[next_state].update({y: next_state})
                    else:
                        self.delta.update({next_state: {y: next_state}})
            elif current_state not in self.delta.keys() or x not in self.delta[current_state].keys() or \
                    self.delta[current_state][x] != next_state:
                if current_state in self.delta.keys():
                    self.delta[current_state].update({x: next_state})
                else:
                    self.delta.update({current_state: {x: next_state}})
                self.generate_delta(next_state, nfa)

    def NFA_to_DFA(self, nfa: NFA):
        self.alphabet = nfa.alphabet
        if 'ε' in self.alphabet:
            self.alphabet.remove('ε')
        self.initialState = nfa.epsilon_tranzitii((0,), [])
        self.generate_delta(self.initialState, nfa)

        if ('S',) in self.delta.keys():
            self.renumerotare_stari.update({('S',): self.stari})
            self.stari += 1

class DFA_simplificat:
    def __init__(self):
        self.alphabet: List[str] = None
        self.initialState: int = None
        self.finalStates: List[int] = []
        self.delta: Dict[int, Dict[str, int]] = {}
        self.stari: int = 0

    def simplifica_DFA(self, dfa: DFA):
        self.stari = dfa.stari
        self.alphabet = sorted(dfa.alphabet)
        self.initialState = dfa.renumerotare_stari[dfa.initialState]
        for x in dfa.finalStates:
            self.finalStates.append(dfa.renumerotare_stari[x])
        for sursa in dfa.delta.keys():
            for simbol in dfa.delta[sursa].keys():
                dest = dfa.renumerotare_stari[dfa.delta[sursa][simbol]]
                if dfa.renumerotare_stari[sursa] in self.delta.keys():
                    self.delta[dfa.renumerotare_stari[sursa]].update({simbol: dest})
                else:
                    self.delta.update({dfa.renumerotare_stari[sursa]: {simbol: dest}})

def afisare(dfa: DFA_simplificat, token:str, output: str):
    out = open(output, 'a')
    for x in dfa.alphabet:
        if x == '\n':
            out.write('\'' + '\\' + 'n' + '\'')
        else:
            out.write(x)
    out.write("\n")
    out.write(token + "\n")
    out.write(str(dfa.initialState) + "\n")
    for sursa in dfa.delta.keys():
        for simbol in dfa.delta[sursa].keys():
            dest = str(dfa.delta[sursa][simbol])
            if simbol == '\n':
                out.write(str(sursa) + ',' + '\'' + '\'' + '\\' + 'n' + '\'' + '\'' + ',' + dest + "\n")
            else:
                out.write(str(sursa) + ',' + '\'' + simbol + '\'' + ',' + dest + "\n")
    for x in dfa.finalStates:
        out.write(str(x) + " ")
    out.write("\n")
    out.write("\n")
    out.close()

def parsare(input: str) -> NFA:
    input = input.replace("   ","  ")
    lista = list(input.split(" "))
    if lista[len(lista) - 1] == '' and lista[len(lista) - 1] == '':
        lista.pop()
    expresii = ['CONCAT', 'UNION', 'STAR', 'PLUS']
    for i in range (0,len(lista)) :
        if lista[i] == '':
            lista[i] = ' '
    stack = []
    stack2 = []
    operanzi = 0
    operanzi_necesari = 0
    i = 0
    append = 0
    while append == 1 or i < len(lista):
        if append == 0:
            stack.append(lista[i])
            element = lista[i]
            i = i + 1
            if element not in expresii:
                stack2.append(simbol(element, None))
        else:
            element = stack[len(stack) - 1]

        if element == 'CONCAT' or element == 'UNION':
            operanzi_necesari = 2
            operanzi = 2
        elif element == 'STAR' or element == 'PLUS':
            operanzi_necesari = 1
            operanzi = 1
        elif element not in expresii:
            operanzi_necesari = operanzi_necesari - 1

        if operanzi_necesari == 0:
            if operanzi == 2:
                arg2 = stack.pop()
                arg1 = stack.pop()
                nume_expresie = stack.pop()
                expr2 = stack2.pop()
                expr1 = stack2.pop()
                if len(stack) > 0:
                    if stack[len(stack) - 1] not in expresii:
                        operanzi_necesari = 1
                        operanzi = 2
                    elif stack[len(stack) - 1] == 'CONCAT' or stack[len(stack) - 1] == 'UNION':
                        operanzi_necesari = 2
                        operanzi = 2
                    else:
                        operanzi_necesari = 1
                        operanzi = 1
                if nume_expresie == 'CONCAT':
                    stack.append(str(concat(arg1, arg2)))
                    stack2.append(concat(expr1, expr2))
                    append = 1
                elif nume_expresie == 'UNION':
                    stack.append(str(union(arg1, arg2)))
                    stack2.append(union(expr1, expr2))
                    append = 1
            else:
                arg1 = stack.pop()
                expr1 = stack2.pop()
                nume_expresie = stack.pop()
                if len(stack) > 0:
                    if stack[len(stack) - 1] not in expresii:
                        operanzi_necesari = 1
                        operanzi = 2
                    elif stack[len(stack) - 1] == 'CONCAT' or stack[len(stack) - 1] == 'UNION':
                        operanzi_necesari = 2
                        operanzi = 2
                    elif stack[len(stack) - 1] == 'STAR' or stack[len(stack) - 1] == 'PLUS':
                        operanzi_necesari = 1
                        operanzi = 1
                if nume_expresie == 'STAR':
                    stack.append(str(star(arg1, '')))
                    stack2.append(star(expr1, None))
                elif nume_expresie == 'PLUS':
                    stack.append(str(plus(arg1, '')))
                    stack2.append(plus(expr1, None))
                append = 1
        else:
            append = 0
    expr = stack2.pop()
    if str(expr) == '':
       expr = simbol(' ',None)
    nfa = expr.get_NFA()
    nfa.alphabet = set(nfa.alphabet)
    return nfa

def transf_in_prenex(regex: str) -> str:
    stack = []
    stack2 = []
    paranteze_deschise = 0
    parametrii = 2
    este_simbol = 0
    i = 0
    endline = 0
    lista = regex
    while i < len(lista):
        if lista[i] == '\'' and este_simbol == 1:
            este_simbol = 0
        elif lista[i] == '\'' and este_simbol == 0:
            este_simbol = 1
        if este_simbol == 1 and lista[i] != '\'' :
            if endline == 0 and lista[i] != "\\":
                stack.append(simbol(lista[i], None))
            if endline == 1:
                stack.append(simbol('\n', None))
                endline = 0
            if lista[i] == "\\":
                endline = 1
        if este_simbol == 0 and lista[i] != '\'':
            stack.append(lista[i])
        element = lista[i]
        if element == '(' and este_simbol == 0:
            paranteze_deschise += 1
        if element == ')' and este_simbol == 0:
            paranteze_deschise -= 1
            expr_intre_paranteze = []
            elem = stack.pop()
            while elem != '(':
                elem = stack.pop()
                if elem != '(':
                    expr_intre_paranteze.append(elem)
            if len(expr_intre_paranteze) == 1:
                stack.append(expr_intre_paranteze[0])
            if len(expr_intre_paranteze) == 2:
                stack.append(concat(expr_intre_paranteze[1], expr_intre_paranteze[0]))
            if len(expr_intre_paranteze) > 2:
                expr1 = expr_intre_paranteze[len(expr_intre_paranteze) - 1]
                j = len(expr_intre_paranteze) - 2
                while j >= 0:
                    if expr_intre_paranteze[j] == '|':
                        expr1 = union(expr1, expr_intre_paranteze[j - 1])
                        j -= 2
                    else:
                        expr1 = concat(expr1, expr_intre_paranteze[j])
                        j -= 1
                stack.append(expr1)

        if element == '+' and este_simbol == 0:
            arg1 = stack.pop()
            arg2 = stack.pop()
            stack.append(plus(arg2, None))
        if element == '*' and este_simbol == 0:
            arg1 = stack.pop()
            arg2 = stack.pop()
            stack.append(star(arg2, None))
        i += 1
    if len(stack) == 2:
        arg1 = stack.pop()
        arg2 = stack.pop()
        stack.append(concat(arg2, arg1))
    if len(stack) > 2:
        stack.reverse()
        expr = stack.pop()
        while stack:
            arg = stack.pop()
            if arg == '|':
                arg2 = stack.pop()
                expr = union(expr, arg2)
            else:
                expr = concat(expr, arg)
        stack.append(expr)
    return str(stack.pop())

def citire(fisier: str) -> list:
    with open(fisier, "r") as input:
        line = input.readlines()
    return line

def runcompletelexer(lexer: str, input:str, output:str):
    line = citire(lexer)
    tokens = []
    input_regex = []
    open("out", 'w').close()
    for i in range(0, len(line)):
        lista = line[i].split(' ', 1)
        tokens.append(lista[0])
        input_regex.append(lista[1].rstrip()[:-1])
    for i in range(0 ,len(tokens)):
        regex = transf_in_prenex(input_regex[i])
        nfa = parsare(regex)
        dfa = DFA()
        dfa.NFA_to_DFA(nfa)
        dfa_final = DFA_simplificat()
        dfa_final.simplifica_DFA(dfa)
        afisare(dfa_final, str(tokens[i]), "out")
    runlexer("out", input, output)
    open("out", 'w').close()

def runparser(fisier_input:str, fisier_output:str):
    open("tokens", 'w').close()
    runcompletelexer('specificatie.lex', fisier_input, 'tokens')
    with open('tokens', "r") as input:
        lines = input.readlines()
    stack = []
    indent = 0
    assigning = 0
    conditie = 0
    expresie_compusa = 0
    for x in lines:
        element = x.rstrip().split(' ', 1)
        if element[0] == 'KEYWORD':
            stack.append(element[1])
            if 'if' in element[1]:
                conditie = 1
                indent += 1
            if 'while' in element[1]:
                conditie = 1
                indent += 1
            if 'begin' in element[1]:
                indent += 1
            if 'then' in element[1] or 'do' in element[1]:
                conditie = 0
                arg_then = stack.pop()
                arg1 = stack.pop()
                arg2 = stack.pop()
                if expresie_compusa == 0:
                    arg3 = stack.pop()
                    stack.append(Expr(indent, arg2, arg3, arg1))
                else:
                    arg3 = stack.pop()
                    arg4 = stack.pop()
                    arg5 = stack.pop()
                    stack.append(Expr(indent, arg2,
                                      Expr(indent + 1, arg4, Expr(arg5.height + 1, arg5.type, str(arg5.left)),
                                           Expr(arg3.height + 1, arg3.type, str(arg3.left))), arg1))
                    expresie_compusa = 0
                stack.append(arg_then)
            if 'fi' in element[1]:
                lista_if = []
                elem = stack.pop()
                indent -= 1
                while 'if' not in str(elem):
                    lista_if.append(elem)
                    elem = stack.pop()
                if 'else' in lista_if:
                    stack.append(If(indent, lista_if[5], lista_if[3], lista_if[1]))
                else:
                    stack.append(If(indent, lista_if[3], lista_if[1]))
            if 'od' in element[1]:
                lista_do = []
                elem = stack.pop()
                indent -= 1
                while 'while' not in str(elem):
                    lista_do.append(elem)
                    elem = stack.pop()
                stack.append(While(indent, lista_do[3], lista_do[1]))
            if 'end' in element[1]:
                indent -= 1
                end = stack.pop()
                elem = stack.pop()
                lista_expresii = []
                while elem != 'begin':
                    lista_expresii.append(elem)
                    elem = stack.pop()
                lista_expresii.reverse()
                stack.append(InstructionList(indent, lista_expresii))

        if element[0] == 'COMPARATIE' or element[0] == 'OPERATIE':
            stack.append(element[1].split(' ')[1])
            if conditie == 1 and element[0] == 'OPERATIE':
                expresie_compusa = 1
        if element[0] == 'ASSIGN':
            assigning = 1
            stack.append(element[1].split(' ', 1)[0])
        if element[0] == 'INTEGER':
            stack.append(Expr(indent + 1, 'i', str(element[1])))
        if element[0] == 'VARIABLE':
            stack.append(Expr(indent + 1, 'v', str(element[1])))
        if element[0] == 'NEWLINE':
            if assigning == 1:
                arg1 = stack.pop()
                arg2 = stack.pop()
                if arg2 in ['+', '-', '*']:
                    arg3 = stack.pop()
                    arg4 = stack.pop()
                    stack.append(Assign(indent, Expr(indent + 1, 'v', arg4),
                                        Expr(indent + 1, arg2, Expr(arg3.height + 1, arg3.type, str(arg3.left)),
                                             Expr(arg1.height + 1, arg1.type, str(arg1.left)))))
                else:
                    stack.append(Assign(indent, Expr(indent + 1, 'v', arg2), arg1))
                assigning = 0

    arg = stack.pop()
    with open(fisier_output, 'w') as f:
        f.write(str(arg))
    return arg

if __name__ == "__main__":
    input_interpretor = 'tests/T3/prog/input/8.in'
    interpreter = runparser(input_interpretor, 'test')
    with open(input_interpretor, "r") as input:
        lines = input.readlines()
    for text in lines:
        print(text.rstrip())
    print()
    print(store)
    visitor = CartVisitor()
    interpreter.accept(visitor)
    print(store)

Lexer, Parser and Interpreter/Parser_and_Interpreter.py


"""Module for manipulating data."""

import math
import random

import numpy as np
import scipy.interpolate

from sklearn.utils import check_random_state

# TODO numpy doc

def one_hot(array, n_classes=None):
    """Return one of k vectors for an array of class indices.

    :param array: 1D array containing N integers from 0 to k-1.
    :param classes: Amount of classes, k. If None, this will be inferred
        from array (and might take longer).
    :returns: A 2D array of shape (N, k).
    """
    if n_classes is None:
        n_classes = len(set(array.tolist()))
    n = array.shape[0]
    arr = np.zeros((n, n_classes), dtype=np.float32)
    arr[xrange(n), array] = 1.
    return arr

def shuffle(data):
    """Shuffle the first dimension of an indexable object in place."""
    for i in range(len(data) - 2):
        swappartner = random.randint(i + 1, len(data) - 1)
        a, b = data[swappartner][:], data[i][:]
        data[i][:], data[swappartner][:] = b, a

def shuffle_many(arrays, axes, random_state=None):
    rng = check_random_state(random_state)

    # We need to swap the axes of the arrays so that the axes along to shuffle
    # is the first for each. We don't need to swap back, since these will be
    # views.
    arrays = [i.swapaxes(0, j) for i, j in zip(arrays, axes)]

    assert all(i.shape[0] == arrays[0].shape[0] for i in arrays[1:])

    permutation = rng.permutation(arrays[0].shape[0])

    for old_index, new_index in enumerate(permutation):
        for a in arrays:
            a[old_index], a[new_index] = a[new_index], a[old_index]

def padzeros(lst, front=True, return_mask=False):
    # TODO add docs for ``front``
    """Given a list of arrays, pad every array with up front  zeros until they
    reach unit length.

    Each element of `lst` can have a different first dimension, but has to be
    equal on the other dimensions.
    """
    n_items = len(lst)
    # Get the longest item.
    maxlength = max(len(i) for i in lst)
    restshape = list(lst[0].shape)[1:]
    item_shape = [maxlength] + restshape
    total_shape = [n_items] + item_shape

    data = scipy.zeros(total_shape, dtype=lst[0].dtype)
    if return_mask:
        mask = scipy.zeros(total_shape, dtype=lst[0].dtype)
    for i in range(n_items):
        # Iterate over indices because we work in place of the list.
        thislength = lst[i].shape[0]
        if front:
            data[i][-thislength:] = lst[i]
            if return_mask:
                mask[i][-thislength:] = 1
        else:
            data[i][:thislength] = lst[i]
            if return_mask:
                mask[i][:thislength] = 1

    if return_mask:
        return data, scipy.asarray(mask)
    return data

def collapse_seq_borders(arr):
    """Given an array of ndim 3, return a view of ndim 2 where the first
    dimension is flattened out."""
    if not arr.ndim == 3:
        raise ValueError("only for arrays of ndim 3")
    arr2 = arr[:]
    arr2.shape = arr.shape[0] * arr.shape[1], arr.shape[2]
    return arr2

def uncollapse_seq_borders(arr, shape):
    """Return a view of ndim 3, given an array of ndim 2, where the first
    dimension is expanded to 2 dimensions of the given shape."""
    if not arr.ndim == 2:
        raise ValueError("only for arrays of ndim 2")
    arr2 = arr[:]
    arr2.shape = shape[0], shape[1], arr.shape[1]
    return arr2

def skip(X, n, d=1):
    """Return an array X with the same number of rows, but only each `n`'th
    block of `d` consecutive columns is kept.

    Crude way of reducing the dimensionality of time series."""
    X_ = X.reshape((X.shape[0], X.shape[1] / d, d))
    X_ = X_[:, ::n, :]
    return X_.reshape((X.shape[0], X_.size / X.shape[0]))

def interleave(lst):
    """Given a list of arrays, interleave the arrays in a way that the
    first dimension represents the first dimension of every array.

    This is useful for time series, where multiple time series should be
    processed in a single swipe."""
    arr = scipy.asarray(lst)
    return scipy.swapaxes(arr, 0, 1)

def uninterleave(lst):
    """Given an array of interleaved arrays, return an uninterleaved version of
    it."""
    arr = scipy.asarray(lst)
    return scipy.swapaxes(arr, 0, 1)

def interpolate(X, n_intermediates, kind='linear'):
    """Given an array of shape (j, k), return an array of size
    (j * n_intermediates, k) where each i * n_intermediated element refers to
    the i'th element in X while all the others are linearly interpolated."""
    X_ = scipy.empty((X.shape[0] * n_intermediates, X.shape[1]))
    grid = scipy.mgrid[0:X.shape[0]]

    finegrid = scipy.linspace(0, X.shape[0] - 1, X.shape[0] * n_intermediates)
    for i in range(X.shape[1]):
        f = scipy.interpolate.interp1d(grid, X[:, i], kind=kind)
        X_[:, i] = f(finegrid)
    return X_

def n_windows(X, size, offset):
    """Given an array `X` representing a sequence along its first axis, return
    the number of windows of `size` with `offset` that fit into it."""
    return max(int(math.ceil((X.shape[0] - size + 1.) / offset)), 0)

def windowify(X, size, offset=1):
    """Return a static array that represents a sliding window dataset of size
    `size` given by the list of arrays `."""
    windows = []
    for i, window in enumerate(iter_windows(X, size, offset)):
        windows.append(window[np.newaxis])

    return np.concatenate(windows)

def iter_windows(X, size, offset=1):
    """Return an iterator that goes over a sequential dataset with a sliding
    time window.

    `X` is expected to be a list of arrays, where each array represents a
    sequence along its first axis."""
    for seq in X:
        for j in [k * offset for k in range(n_windows(seq, size, offset))]:
            yield seq[j:j + size]

def split(X, maxlength):
    """Return a list of sequences where each sequence has a length of at most
    `maxlength`.

    Given a list of sequences `X`, the sequences are split accordingly."""
    new_X = []
    for seq in X:
        n_new_seqs, rest = divmod(seq.shape[0], maxlength)
        if rest:
            n_new_seqs += 1
        for i in range(n_new_seqs):
            new_X.append(seq[i * maxlength:(i + 1) * maxlength])
    return new_X

def collapse(X, n):
    """Return a list of sequences, where `n` consecutive timesteps have been
    collapsed into a single timestep by concatenation for each sequence.

    Timesteps are cut off to ensure divisibility by `n`."""
    dim = X[0].shape[1]
    new_X = []
    for seq in X:
        seq = scipy.ascontiguousarray(seq)
        length = seq.shape[0]
        keep = length / n * n
        seq = seq[:keep]
        seq.shape = length / n, dim * n
        new_X.append(seq)

    return new_X

def uncollapse(X, n):
    """Return a list of sequences, where each timestep is divided into `n`
    consecutive timesteps."""
    new_X = []
    dim = X[0].shape[1]
    for seq in X:
        length = seq.shape[0]
        new_X.append(seq.reshape((length * n, dim / n)))
    return new_X

def consecutify(seqs):
    """Given sequences of equal second dimension, put them into a consecutive
    memory block M and return it. Also return a list of views to that block that
    represent the given sequences."""
    n_rows = sum(i.shape[0] for i in seqs)
    n = seqs[0].shape[1]
    block = scipy.empty((n_rows, n))
    new_seqs = []
    start = 0
    for seq in seqs:
        stop = start + seq.shape[0]
        block[start:stop] = seq
        new_seqs.append(block[start:stop])
        start = stop
    return block, new_seqs

def sample(arr, n, axis=0, with_replacement=False):
    indices = range(arr.shape[axis])
    all_slice = slice(0, arr.shape[axis])
    sampled_indices = random.sample(indices, n)
    slices = tuple(all_slice if i != axis else sampled_indices
                   for i in range(arr.ndim))
    return arr[slices]


import pygame
import random
#################################################
# 기본 초기화 (반드시 해야하는 것들)
pygame.init()

# 화면 크기 설정 (480 x 640)
screen_width = 480 # 가로 크기
screen_height = 640 # 세로 크기
screen = pygame.display.set_mode((screen_width, screen_height))

# 화면 타이틀 설정
pygame.display.set_caption("Hee DDONG Game") # 게임 이름

# FPS
clock = pygame.time.Clock()
#################################################

# 1. 사용자 게임 초기화 (배경화면, 게임 이미지, 좌표, 속도, 폰트 등)
# 배경 만들기
background = pygame.image.load("C:\\Users\\wkdgm\\OneDrive\\Documents\\Python_Game\\pygame_ddong\\background.png")

# 캐릭터 만들기
character = pygame.image.load("C:\\Users\\wkdgm\\OneDrive\\Documents\\Python_Game\\pygame_ddong\\character.png")
character_size = character.get_rect().size
character_width = character_size[0]
character_height = character_size[1]
character_x_pos = (screen_width / 2) - (character_width / 2)
character_y_pos = screen_height - character_height

# 이동 위치
to_x = 0
character_speed = 10

# 똥 만들기 (적군)
ddong = pygame.image.load("C:\\Users\\wkdgm\\OneDrive\\Documents\\Python_Game\\pygame_ddong\\enemy.png")
ddong_size = ddong.get_rect().size
ddong_width = ddong_size[0]
ddong_height = ddong_size[1]
ddong_x_pos = random.randint(0, screen_width - ddong_width)
ddong_y_pos = 0
ddong_speed = 10

# Font 정의
game_font = pygame.font.Font(None, 40)
total_time = 10
start_ticks = pygame.time.get_ticks() # 시작 시간 정의

# 게임 종료 메시지
game_result = "Game Over"

running = True # 게임이 진행 중인가
while running:
    dt = clock.tick(30)

    # 2. 이벤트 처리 (키보드, 마우스 등)
    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            running = False

        if event.type == pygame.KEYDOWN:
            if event.key == pygame.K_LEFT:
                to_x -= character_speed
            elif event.key == pygame.K_RIGHT:
                to_x += character_speed

        if event.type == pygame.KEYUP:
            if event.key == pygame.K_LEFT or event.key == pygame.K_RIGHT:
                to_x = 0

    # 3. 게임 캐릭터 위치 정의
    character_x_pos += to_x

    if character_x_pos < 0:
        character_x_pos = 0
    elif character_x_pos > screen_width - character_width:
        character_x_pos = screen_width - character_width

    ddong_y_pos += ddong_speed # 똥이 떨어짐

    if ddong_y_pos > screen_height:
        ddong_y_pos = 0
        ddong_x_pos = random.randint(0, screen_width - ddong_width)

    # 4. 충돌 처리
    character_rect = character.get_rect()
    character_rect.left = character_x_pos
    character_rect.top = character_y_pos

    ddong_rect= ddong.get_rect()
    ddong_rect.left = ddong_x_pos
    ddong_rect.top = ddong_y_pos

    if character_rect.colliderect(ddong_rect):
        game_result = "Game Over"
        running = False

    # 5. 화면에 그리기
    screen.blit(background, (0, 0))
    screen.blit(character, (character_x_pos, character_y_pos))
    screen.blit(ddong, (ddong_x_pos, ddong_y_pos))

     # 경과 시간 계산
    elapsed_time = (pygame.time.get_ticks() - start_ticks) / 1000 # ms -> s
    timer = game_font.render("Time : {}".format(int(total_time - elapsed_time)), True, (255,255,255))
    screen.blit(timer, (10, 10))

    # 시간 초과 했다면
    if total_time-elapsed_time <= 0:
        game_result = "Mission Complete"
        running = False

    pygame.display.update() # 게임 화면을 다시 그리기(반드시 계속 호출 되어야 함)

# 게임 오버 메시지
msg = game_font.render(game_result, True, (255,255,0))  # 노란색
msg_rect = msg.get_rect(center=(int(screen_width/2), int(screen_height/2)))
screen.blit(msg, msg_rect)
pygame.display.update()

# 2초 대기
pygame.time.delay(2000)

# pygame 종료
pygame.quit()


from datetime import datetime, timedelta
import json
from airflow import DAG
from airflow.operators.python import PythonOperator
from airflow.operators.dummy_operator import DummyOperator
from sample_crawl_to_csv import crawl_to_csv

''''''''''''''''' START '''''''''''''''''''''
# DAG definition
default_args = {
    "owner": "airflow",
    "start_date": datetime(2021, 11, 10),
    "email": ["airflow@airflow.com"],
    "email_on_failure": False,
    "email_on_retry": False,
    "retries": 1,
    "retry_delay": timedelta(minutes=1),
}

dag = DAG(
    "dag_crawl_to_csv",
    default_args=default_args,
    schedule_interval="0 0 * * *",      # once a day
    max_active_runs=1,
)

end_of_data_pipeline = DummyOperator(task_id="end_of_data_pipeline", dag=dag)

crawl_to_csv = PythonOperator(
    dag=dag,
    task_id='crawl_to_csv',
    python_callable=crawl_to_csv
)

crawl_to_csv >> end_of_data_pipeline


from typing import Tuple

import cv2
import numba
import numpy as np
from vinbigdata import BoxCoordsFloat, BoxCoordsInt

def is_interactive():
    import __main__ as main
    return not hasattr(main, '__file__')

@numba.jit
def compute_intersection_area(bbox1: BoxCoordsInt, bbox2: BoxCoordsInt) -> int:
    x1 = max(bbox1[0], bbox2[0])
    y1 = max(bbox1[1], bbox2[1])
    x2 = min(bbox1[2], bbox2[2])
    y2 = min(bbox1[3], bbox2[3])
    h = x2 - x1
    w = y2 - y1
    if h < 0:
        h = 0
    if w < 0:
        h = 0
    return h * w

@numba.jit
def compute_area(bbox: BoxCoordsInt) -> int:
    return (bbox[3] - bbox[1]) * (bbox[2] - bbox[0])

@numba.jit
def compute_union_area(bbox1: BoxCoordsInt, bbox2: BoxCoordsInt) -> int:
    x1 = min(bbox1[0], bbox2[0])
    y1 = min(bbox1[1], bbox2[1])
    x2 = max(bbox1[2], bbox2[2])
    y2 = max(bbox1[3], bbox2[3])
    h = x2 - x1
    w = y2 - y1
    if h < 0:
        h = 0
    if w < 0:
        h = 0
    return h * w

def resize(img: np.array, max_size: Tuple[int, int]) -> np.array:
    return cv2.resize(img, max_size, interpolation=cv2.INTER_LANCZOS4)

@numba.jit
def rel2abs(box: BoxCoordsFloat, img_shape: Tuple[int, int]) -> BoxCoordsFloat:
    return (box[0] * img_shape[0], box[1] * img_shape[1], box[2] * img_shape[0], box[3] * img_shape[1])

@numba.jit
def abs2rel(box: BoxCoordsFloat, img_shape: Tuple[int, int]) -> BoxCoordsFloat:
    return (box[0] / img_shape[0], box[1] / img_shape[1], box[2] / img_shape[0], box[3] / img_shape[1])


from netCDF4 import Dataset
import matplotlib.pyplot as plt
import matplotlib as mpl
from matplotlib.cm import get_cmap
import numpy as np
import os
import cartopy.crs as crs
from cartopy.feature import NaturalEarthFeature
from cartopy.mpl.gridliner import LONGITUDE_FORMATTER, LATITUDE_FORMATTER
import wrf
from wrf import (to_np, getvar, smooth2d, get_cartopy, cartopy_xlim,
                 cartopy_ylim, latlon_coords)

# Create a figure
def plot():
    fig = plt.figure(figsize=(10,8))
    # Set the GeoAxes to the projection used by WRF
    ax = plt.axes(projection=cart_proj)
    #--------------------------------------------------------------------------------------
    #--------------------------------------------------------------------------------------
    #--------------------------------------------------------------------------------------
    levels = range(1000,8000,500)

    contours = plt.contour(to_np(lons), to_np(lats), to_np(hgt), levels, colors="black",
                transform=crs.PlateCarree(),alpha=0.4)
    #plt.clabel(contours, inline=True, fontsize=8)
    plt.contourf(to_np(lons), to_np(lats), to_np(hgt), 10,
                transform=crs.PlateCarree(),
                cmap=get_cmap("gist_earth"))
    plt.clim(-6000,9000)
    # Add a color bar
    plt.colorbar(ax=ax, shrink=.98)

    plt.plot(ncop_lon,ncop_lat,'k*',markersize=12,transform=crs.PlateCarree())

    plt.plot(coord_x0,coord_y0,'o',markersize=4,transform=crs.PlateCarree())
    plt.plot(valley_lon,valley_lat,'-',transform=crs.PlateCarree())
    # Set the map bounds
    ax.set_xlim(cartopy_xlim(hgt))
    ax.set_ylim(cartopy_ylim(hgt))

    # Add the gridlines
    #ax.gridlines(color="black", linestyle="dotted")

    plt.title("Title")

    gl = ax.gridlines(crs=crs.PlateCarree(), draw_labels=True,
                      linewidth=2, color='gray', alpha=0.5, linestyle='--')
    gl.xlabels_top = False
    gl.ylabels_right = False
    gl.xformatter = LONGITUDE_FORMATTER
    gl.yformatter = LATITUDE_FORMATTER
    #plt.show()
    plt.savefig("defvalley.pdf")
    plt.savefig("defvalley.png")

# Open the NetCDF file
ncfile = Dataset("/home/local/mikkolaj/codes/nepal/wrfout_d04_2014-12-19_12:00:00")

# Get the sea level pressure
hgt = getvar(ncfile, "HGT")
LAP = getvar(ncfile, "LAP_HGT")
LON = getvar(ncfile, "XLONG")
LAT = getvar(ncfile, "XLAT")

# Get the latitude and longitude points
lats, lons = latlon_coords(hgt)

# NCO-P station coordinates
ncop_lat, ncop_lon = 27.95, 86.82

# Get the cartopy mapping object
cart_proj = get_cartopy(hgt)

#starting point for valley definition

#keskim. laakso
y_start, x_start = 174, 145

#ncop
#y_start, x_start = 117,165
#y_start, x_start = 109,177
#vasen
#y_start, x_start = 60,170

#oikea laakso
#y_start, x_start = 215, 140
#y_start, x_start = 170, 56

"""

"""

coord_x0, coord_y0 = LON[x_start,y_start], LAT[x_start,y_start]

valley_y = []
valley_x = []

x = x_start
y = y_start

a = 1
for n in range(0,20):
    hgt_tmp = []
    for i in [-a,0,a]:
        for j in [-a,0,a]:
            if i==0 and j==0:
                continue
            if n > 4:
                if valley_x[-3] == x+i or valley_x[-2] == x+i:
                    if valley_y[-3] == y+j or valley_y[-2] == y+j:
                        continue
                else:
                    hgt_tmp.append(hgt[x+i,y+j])
                    if min(hgt_tmp) == hgt_tmp[-1]:
                        x_tmp, y_tmp = x+i, y+j
            else:
                hgt_tmp.append(hgt[x+i,y+j])
                if min(hgt_tmp) == hgt_tmp[-1]:
                    x_tmp, y_tmp = x+i, y+j

    valley_x.append(x_tmp)
    valley_y.append(y_tmp)
    x, y = x_tmp, y_tmp

# f  = open("valley_east.txt","a")
# for i in range(0,len(valley_x)-1):
#     f.write(str(valley_x[i]) + " " + str(valley_y[i]) + "\n")
# f.close()

#convert valley xy to coordinates
valley_lon = []
valley_lat = []

valley_lat, valley_lon = wrf.xy_to_ll(ncfile,valley_y,valley_x)

plot()


import logging

from users.models import GitHubProfile, User

LOGGER = logging.getLogger(__name__)

def update_or_create_githubprofile(profile_data, user=None):
    """
    Accepts any mapping object that has field names of GitHubProfile in the keys
    """
    # Ensure that is a editable object and that `profile_data` is a mapping object
    profile_data = dict(profile_data)

    profile_id = profile_data.pop('id')
    profile_data['user'] = user or User.objects.get_or_create(username=profile_data['login'])[0]
    profile_data['name'] = profile_data['name'] or ''

    profile, profile_created = GitHubProfile.objects.update_or_create(
        github_id=profile_id,
        defaults=profile_data
    )

    LOGGER.info(f'GitHub profile "{profile}" {"created" if profile_created else "updated"}.')
    return profile


import json
import time
import os
from pymongo import MongoClient

############### 数据初始化，修改数据库链接后，直接运行本程序 ####################

############################## 工具配置 start ################################

# mongodb连接字符串
MONGODB_URI='mongodb://127.0.0.1:27017/'

############################## 工具配置 end ##################################

# 地区
LOCATION=["de-DE", "en-CA", "en-GB", "en-IN", "en-US", "fr-FR", "it-IT", "ja-JP", "zh-CN"]
# 必应接口
BINGAPI='https://cn.bing.com/HPImageArchive.aspx?n=1&format=js&idx=0'
# 必应URL
BINGURL='https://cn.bing.com'

'''
初始化连接
@mkt 地区，默认zh-CN
'''
def db_init(mkt="zh-CN"):
    URI = os.environ.get("MONGODB_URI")
    client = MongoClient(URI)
    db = client.bing
    if mkt=="zg-CN":
        return db['cn']
    if mkt=="ja-JP":
        return db['jp']
    if mkt=="it-IT":
        return db['it']
    if mkt=="fr-FR":
        return db['fr']
    if mkt=="en-US":
        return db['us']
    if mkt=="en-IN":
        return db['in']
    if mkt=="en-GB":
        return db['gb']
    if mkt=="en-CA":
        return db['ca']
    if mkt=="de-DE":
        return db['de']
    return db['cn']
    return collection

'''
根据地区插入多条json数据
@mkt 地区
@obj 插入数据
'''
def insert_many(mkt,obj):
    collection = db_init(mkt)
    collection.insert_many(obj)

def read_json(run_type):
    with open(f'{run_type}_all.json', 'r', encoding="utf-8") as f:
        return json.load(f)['data']

# 格式化必应接口数据
def format_data(lists):
    res=[]
    lists=lists[::-1]
    id=1
    for bing_json_data in lists:
        timearray=time.strptime(str(bing_json_data['datetime']),'%Y-%m-%d')
        datetime=time.strftime('%Y-%m-%d', timearray)
        json_data={}
        json_data['id']=id
        json_data['title']=bing_json_data.get("title","")
        json_data['url']=bing_json_data['url'].replace("&rf=LaDigue_1920x1080.jpg&pid=hp","")
        json_data['datetime']=datetime
        json_data['copyright']=bing_json_data.get("copyright","")
        json_data['copyrightlink']=bing_json_data.get("copyrightlink","")
        json_data['hsh']=bing_json_data.get("hsh","")
        json_data['created_time']=str(time.strftime('%Y-%m-%d', time.localtime()))
        res.append(json_data)
        id=id+1
    return res

# 初始化数据
def init_data():
    for mkt in LOCATION:
        print("初始化"+mkt)
        lists=read_json(mkt)
        lists=format_data(lists)
        insert_many(mkt,lists)
        print("初始化结束\n")

# 删除数据库，慎用
def del_database():
    URI = os.environ.get("MONGODB_URI")
    client = MongoClient(URI)
    client.drop_database('bing')

if __name__=='__main__':
    os.environ['MONGODB_URI']=MONGODB_URI
    del_database()
    init_data()


from collections import defaultdict
import sys

def parse_args(typ):
  args = sys.argv[1:]
  if (typ == "b"):
    args = args[1:]

  if len(args) > 0:
    filein = args[0]
  else:
    filein = input("Enter filename to transform: ")
  if len(args) > 1:
    fileout = args[1]
  else:
    fileout = "new_" + filein

  return filein, fileout

def get_max_dim(filein, typ=""):
  # determine max dimension
  midx = 0

  with open(filein, "r") as f:
    for line in f:
      if typ == "b":
        midx = max(midx, max([int(item) for item in line.strip().split()]))
      else:
        midx = max(midx, max([int(item.split(":")[0]) for item in line.strip().split()]))
  return midx

def transform(filein, fileout):
  midx = get_max_dim(filein)
  # print("max dim = ", midx)
  with open(fileout, "w") as fout:
    with open(filein, "r") as f:
      for line in f:
        dense_v = defaultdict(int)
        for pair in line.strip().split():
          idx, val = pair.split(":")
          dense_v[int(idx)] = float(val)

        outline = " ".join([str(dense_v[i]) for i in range(midx)])
        fout.write(outline + "\n")

def transform_binary(filein, fileout):
  midx = get_max_dim(filein, "b")
  with open(fileout, "w") as fout:
    with open(filein, "r") as f:
      for line in f:
        dense_v = defaultdict(int)
        for idx in line.strip().split():
          idx = int(idx)
          dense_v[idx] = 1

        outline = " ".join([str(dense_v[i]) for i in range(midx)])
        fout.write(outline + "\n")

def main():
  if len(sys.argv) > 1:
    typ = sys.argv[1]

  filein, fileout = parse_args(typ)

  if typ == "b":
    transform_binary(filein, fileout)
  else:
    transform(filein, fileout)

main()


import pandas as pd
import boto3

#######################
## world cities data ##
########################

# read dataset
world_cities = pd.read_csv("/Users/keenzarate/Documents/data/ds4a/new_raw_data/worldcities.csv")

# subset data to only countries we want
sub_world_cities = world_cities[world_cities['country'].isin(['China', 'India','United States', 'Brazil'])]

# aggregate -- count number
ven = sub_world_cities.groupby(['country'])['city'].nunique().reset_index(name='number_of_cities')

# calculate total population
sum_pop = sub_world_cities.groupby(['country'])['population'].sum().reset_index(name='total_population')

# merge the two dataframes
country_info = pd.merge(ven, sum_pop, on = 'country')

######################
### cereal data    ###
######################

# read cereal dt
raw_cereal = pd.read_csv("/Users/keenzarate/Documents/data/ds4a/new_raw_data/cereal_new.csv")

# clean up column
raw_cereal.columns = raw_cereal.columns.str.replace(' ','_')
raw_cereal.columns = raw_cereal.columns.str.lower()

# drop column we don't need so we can stack it with the rest of the weather data
sub_raw_cereal = raw_cereal.drop(['year_code', 'flag', 'flag_description', 'domain_code', 'domain'], axis = 1)

# change usa to us to match other dataset
sub_raw_cereal['area'] = sub_raw_cereal['area'].replace(['United States of America'],'United States')

# rename columns
final_cereal_data = sub_raw_cereal.rename({'area_code_(fao)': 'country_id', 'area': 'country','item_code_(fao)': 'item_id'}, axis = 1)

######################
### greenhouse gas ###
######################

# read dataset
greenhouse_gas = pd.read_csv("/Users/keenzarate/Documents/data/ds4a/new_raw_data/historical_emissions.csv")

# update column names
greenhouse_gas.columns = greenhouse_gas.columns.str.replace(' ','_')
greenhouse_gas.columns = greenhouse_gas.columns.str.lower()

long_greenhouse_gas = pd.DataFrame(pd.melt(greenhouse_gas, id_vars = ['country', 'data_source', 'sector', 'gas', 'unit'], value_name = 'measure_value', var_name = 'year'))

# drop column we don't need so we can stack it with the rest of the weather data
final_greenhouse_gas = long_greenhouse_gas.drop(['data_source'], axis = 1)

##########################################
###     NOAA DATA CLEANING FUNCTION    ###
##########################################

# create function to clean temperature and precipitation data
def clean_temp_precip(path_usa, path_bra, path_chn, path_ind, measure_name, unit):

    # read csv files
    read_usa = pd.read_csv(path_usa, skiprows = 1)
    read_bra = pd.read_csv(path_bra, skiprows = 1)
    read_chn= pd.read_csv(path_chn,  skiprows = 1)
    read_ind = pd.read_csv(path_ind, skiprows = 1)

    # add a column country so we can have an indicator when data is stacked in the end
    read_usa['country'] = 'United States'
    read_bra['country'] = 'Brazil'
    read_chn['country'] = 'China'
    read_ind['country'] = 'India'

    # update the unnamed column to "year" to make it more clear
    read_usa.rename( columns={'Unnamed: 0' :'year'}, inplace=True )
    read_bra.rename( columns={'Unnamed: 0' :'year'}, inplace=True )
    read_chn.rename( columns={'Unnamed: 0' :'year'}, inplace=True )
    read_ind.rename( columns={'Unnamed: 0' :'year'}, inplace=True )

    # make the data long so we can stack it later on our other datasets
    long_usa = pd.DataFrame(pd.melt(read_usa, id_vars = ['year', 'country'], value_name = 'measure_value', var_name = 'location'))
    long_bra = pd.DataFrame(pd.melt(read_bra, id_vars = ['year', 'country'], value_name = 'measure_value', var_name = 'location'))
    long_chn = pd.DataFrame(pd.melt(read_chn, id_vars = ['year', 'country'], value_name = 'measure_value', var_name = 'location'))
    long_ind = pd.DataFrame(pd.melt(read_ind, id_vars = ['year', 'country'], value_name = 'measure_value', var_name = 'location'))

    # stack all of the individual country dataframes
    stacked_data = pd.concat([long_usa, long_bra, long_chn, long_ind])

    # add a column measure name so we know what this data is about
    stacked_data['measure_name'] = measure_name

    stacked_data['unit'] = unit

    # sort col so we can stack it later
    stacked_data.sort_index(axis=1)

    return stacked_data

#################################
### CLEAN TEMPERATURE DATA    ###
#################################

# dataset paths
temp_usa = "/Users/keenzarate/Documents/data/ds4a/new_raw_data/tas_timeseries_annual_cru_1901-2020_USA.csv"
temp_bra = "/Users/keenzarate/Documents/data/ds4a/new_raw_data/tas_timeseries_annual_cru_1901-2020_BRA.csv"
temp_chn = "/Users/keenzarate/Documents/data/ds4a/new_raw_data/tas_timeseries_annual_cru_1901-2020_CHN.csv"
temp_ind = "/Users/keenzarate/Documents/data/ds4a/new_raw_data/tas_timeseries_annual_cru_1901-2020_IND.csv"

# clean mean temperature data
clean_mean_temp = clean_temp_precip(temp_usa, temp_bra, temp_chn, temp_ind, 'Mean Temperature', 'Tonnes')

#################################
### CLEAN PRECIPITATION DATA ###
#################################

# load the dataset skip the extra headers cause we dont need it.
precip_usa = "/Users/keenzarate/Documents/data/ds4a/new_raw_data/pr_timeseries_annual_cru_1901-2020_USA.csv"
precip_bra = "/Users/keenzarate/Documents/data/ds4a/new_raw_data/pr_timeseries_annual_cru_1901-2020_BRA.csv"
precip_chn = "/Users/keenzarate/Documents/data/ds4a/new_raw_data/pr_timeseries_annual_cru_1901-2020_CHN.csv"
precip_ind = "/Users/keenzarate/Documents/data/ds4a/new_raw_data/pr_timeseries_annual_cru_1901-2020_IND.csv"

test = pd.read_csv(precip_usa)

# clean precipitation data
clean_precip = clean_temp_precip(precip_usa, precip_bra, precip_chn, precip_ind, 'Precipitation', 'Celcius')

clean_precip.loc[((clean_precip['location'] == 'Brazil') & (clean_precip['year'] == 2018))]

# stack mean temperature, carbon emissions, precipitation
final_temp_precip = pd.concat([clean_mean_temp, clean_precip])

final_cereal_data.to_csv('/Users/keenzarate/Documents/data/ds4a/clean_data/clean_cereal_data.csv',   index = False)
final_temp_precip.to_csv('/Users/keenzarate/Documents/data/ds4a/clean_data/clean_climate_indicator_data.csv', index = False)
final_greenhouse_gas.to_csv('/Users/keenzarate/Documents/data/ds4a/clean_data/clean_greenhouse_data.csv', index = False)
country_info.to_csv('/Users/keenzarate/Documents/data/ds4a/clean_data/clean_country_info.csv', index = False)

# data
final_cereal_data = '/Users/keenzarate/Documents/data/ds4a/clean_cereal_data.csv'
final_temp_precip = '/Users/keenzarate/Documents/data/ds4a/clean_climate_indicator_data.csv'
final_greenhouse_gas = '/Users/keenzarate/Documents/data/ds4a/clean_greenhouse_data.csv'
country_info = '/Users/keenzarate/Documents/data/ds4a/clean_country_info.csv'

#############################
###   LOAD DATA TO S3     ###
#############################

# create a client to access resources with
s3_client = boto3.client('s3', aws_access_key_id = "null", aws_secret_access_key = "null")

# upload the applications to the bucket created earlier
# we have a try/except clause to see if it fails
try:
    s3_client.upload_file(final_cereal_data, 'null' ,"clean/clean_cereal_data.csv")
    print('File successfully loaded')
except Exception as e:
    print(f'{e} Client error: file could not be uploaded to S3')

# load weather data to s3
try:
    s3_client.upload_file(final_greenhouse_gas, 'null' ,"clean/clean_weather_data.csv")
    print('File successfully loaded')
except Exception as e:
    print(f'{e} Client error: file could not be uploaded to S3')

# load weather data to s3
try:
    s3_client.upload_file(final_temp_precip, 'null' ,"clean/clean_weather_data.csv")
    print('File successfully loaded')
except Exception as e:
    print(f'{e} Client error: file could not be uploaded to S3')

# load weather data to s3
try:
    s3_client.upload_file(country_info, 'null' ,"clean/clean_weather_data.csv")
    print('File successfully loaded')
except Exception as e:
    print(f'{e} Client error: file could not be uploaded to S3')


from w13.num import num
from w13.sym import sym
from w13.sample import sample
from texttable import Texttable
import re,csv

class table:

    def __init__(self):
        """
        A table object to represent rows that holds and works with
        both num and sym instance
        """
        self.use = {}
        self.w={}
        self.syms = {}
        self.nums = {}
        self.clazz = None
        self.rows = {}
        self.name = {}
        self. indeps = {}

    def row(self,cells):
          """
         Adds a row to this table instance
          :param cells:
          :return:
          """
          r= len(self.rows) + 1
          self.rows[r] = {}
          for c,c0 in self.use.items():
            x = cells[c0]
            if x != '?':
              if c0 in self.nums.keys():
                x = float(x)
                self.nums[c].numInc(x)
              else:
                self.syms[c].symInc(x)
            self.rows[r][c] = x

    def dep(self, c):
        """
        Check if this column is a dependent column
        :param c:
        :return: True/False
        """
        return not self.indep(c)

    def indep(self,c):
        """
        Check if this column is an independent column
        :param c:
        :return: True/False
        """
        return not self.w[c] and self.clazz != c

    def printReport(self, fileName):
        """
        Pretty print the table instance for a given csv input
        :param fileName:
        :return:
        """

        t = Texttable()
        t.add_rows([[' ', ' ', 'n' , 'mode' ,'frequency']])
        print("-------------- ",str(fileName)," ---------------------------\n")
        for key, symVal in self.syms.items():
            t.add_row([str(key), self.name[key], symVal.n, symVal.mode, symVal.most])

        print (t.draw())

        t = Texttable()
        t.add_rows([[' ', ' ', 'n', 'mu', 'sd']])

        for key, numVal in self.nums.items():
            t.add_row([str(key), self.name[key], numVal.n, numVal.mu, numVal.sd])

        print(t.draw())

def header(cells):
  """
   To read and process special symbols for input rows
  :param cells:
  :return:
  """

  t = table()
  for c0,x in enumerate(cells):
    if "?" not in x:
      c = len(t.use)
      t.use[c] = c0
      t.name[c] = x
      if re.search("[<>$]", x):
        t.nums[c] = num(1000)
      else :
          t.syms[c] = sym()
      if     "<" in x :
         t.w[c]  = -1
      elif ">" in x:
        t.w[c]  =  1
      elif "!" in x:
        t.clazz =  c
      else:
          t.indeps[ len(t.indeps) + 1 ] = c

  return t

def createTable(fileName):
    """
    Reads csv from disk using fileName
    :param fileName: csv relative file path
    :return: a table object with only header or all data rows.
    """

    newTable = table()
    lineNumber = 1
    with open(fileName) as csv_file:
        csvRows = ''
        readerElements = csv.reader(csv_file, delimiter=',')
        for row in readerElements:
            cells = row #row.split(",")
            if lineNumber > 1:
                 newTable.row(cells)
            else :
                lineNumber += 1
                newTable = header(cells)

    return newTable

if __name__ == "__main__":

    """
    Prints the statistics for each csv
    """
    autoTable = createTable("data/auto.csv")
    autoTable.printReport("auto.csv")

    weatherTable = createTable("data/weather.csv")
    weatherTable.printReport("weather.csv")

    weatherLongTable = createTable("data/weatherLong.csv")
    weatherLongTable.printReport("weatherLong.csv")


from django.http import HttpResponse, JsonResponse
from .models import Weapon
from django.forms.models import model_to_dict
from .db_script import push_all_weapons

def weapon_search(request):
    weapon_list = request.GET.get('weapon')
    weapon_obj = request.GET.get('object')
    payload = list()

    if weapon_list:
        query_result = Weapon.objects.filter(name__icontains=weapon_list)

        for weapon_result in query_result:
            payload.append(weapon_result.name)
        return JsonResponse({'status':200, 'data' : payload})
    elif weapon_obj:
        try:
            query_result = Weapon.objects.get(name=weapon_obj)
        except Weapon.DoesNotExist:
            return JsonResponse({'status':404, 'data' : 'Weapon not found'})
        return JsonResponse({'status':200, 'data' : model_to_dict(query_result)})
    else:
        return JsonResponse({'status':404, 'data' : 'Weapon not found'})

def push_db(request):
    if not Weapon.objects.exists():
        push_all_weapons(push_db=True)
    return HttpResponse('')


from __future__ import absolute_import
from __future__ import division
from __future__ import print_function

from absl.testing import parameterized

import tensorflow as tf
from tensorflow_privacy.privacy.estimators import test_utils
from tensorflow_privacy.privacy.estimators.v1 import head as head_lib
from tensorflow_privacy.privacy.optimizers.dp_optimizer import DPGradientDescentGaussianOptimizer

def make_model_fn(head, optimizer, feature_columns):
  """Constructs and returns a model_fn using supplied head."""

  def model_fn(features, labels, mode, params, config=None):  # pylint: disable=unused-argument
    feature_layer = tf.keras.layers.DenseFeatures(feature_columns)
    inputs = feature_layer(features)
    hidden_layer = tf.keras.layers.Dense(units=3, activation='relu')
    hidden_layer_values = hidden_layer(inputs)
    logits_layer = tf.keras.layers.Dense(
        units=head.logits_dimension, activation=None)
    logits = logits_layer(hidden_layer_values)
    return head.create_estimator_spec(
        features=features,
        labels=labels,
        mode=mode,
        logits=logits,
        optimizer=optimizer)

  return model_fn

class DPHeadTest(tf.test.TestCase, parameterized.TestCase):
  """Tests for DP-enabled heads."""

  # Parameters for testing: n_classes.
  @parameterized.named_parameters(
      ('Binary', 2),
      ('MultiClass 3', 3),
      ('MultiClass 4', 4),
  )
  def testCreateTPUEstimatorSpec(self, n_classes):
    """Tests that an Estimator built with a binary head works."""

    train_features, train_labels = test_utils.make_input_data(256, n_classes)
    feature_columns = []
    for key in train_features:
      feature_columns.append(tf.feature_column.numeric_column(key=key))

    head = head_lib._binary_logistic_or_multi_class_head(
        n_classes=n_classes,
        weight_column=None,
        label_vocabulary=None,
        loss_reduction=tf.compat.v1.losses.Reduction.NONE)
    optimizer = DPGradientDescentGaussianOptimizer(
        learning_rate=0.5,
        l2_norm_clip=1.0,
        noise_multiplier=0.0,
        num_microbatches=2)
    model_fn = make_model_fn(head, optimizer, feature_columns)
    classifier = tf.estimator.Estimator(model_fn=model_fn)

    classifier.train(
        input_fn=test_utils.make_input_fn(train_features, train_labels, True),
        steps=4)

    test_features, test_labels = test_utils.make_input_data(64, n_classes)
    classifier.evaluate(
        input_fn=test_utils.make_input_fn(test_features, test_labels, False),
        steps=4)

    predict_features, predict_labels = test_utils.make_input_data(64, n_classes)
    classifier.predict(
        input_fn=test_utils.make_input_fn(predict_features, predict_labels,
                                          False))

if __name__ == '__main__':
  tf.test.main()


# -*- coding: utf-8 -*-
"""
Created on Wed Jun 13 11:07:08 2018

@author: Peeyush Goyal
"""

import pandas as pd
import matplotlib.pyplot as plt

data=pd.read_csv("crime_data.csv")
df=data.iloc[:,[1,2,4]]
"""from sklearn.preprocessing import LabelEncoder
labelencoder=LabelEncoder()
df["State"]=labelencoder.fit_transform(df["State"])

from sklearn.preprocessing import StandardScaler
sc=StandardScaler()
df=sc.fit_transform(df)
"""
from sklearn.decomposition import PCA
pca= PCA(n_components=2)
df= pca.fit_transform(df)

from sklearn.cluster import KMeans
"""wcss=[]
for i in range(3):
    kmeans=KMeans(n_clusters=i, init='k-means++',random_state=0)
    kmeans.fit(df)
    wcss.append(kmaens.inertia_)
"""
kmeans=KMeans(n_clusters=3, init='k-means++',random_state=0)
y_kmeans=kmeans.fit_predict(df)

plt.scatter(df[y_kmeans==0,0],df[y_kmeans==0,1],s=100,c='red')
plt.scatter(df[y_kmeans==1,0],df[y_kmeans==1,1],s=100,c='blue')
plt.scatter(df[y_kmeans==2,0],df[y_kmeans==2,1],s=100,c='green')
plt.legend()
plt.xlabel('Crimes')
plt.ylabel('cities')
plt.show()


import os
from argparse import ArgumentParser
from ASRCAISim1.viewer.GodViewLoader import GodViewLoader

def parse_args():
    parser = ArgumentParser()
    parser.add_argument('--movie-dir', default='./log')
    parser.add_argument('--as-video', type=int, default=1)

    return parser.parse_args()

def main():
    args = parse_args()
    matches = os.listdir(args.movie_dir)
    for match in matches:
        ext = os.path.splitext(match)[-1]
        if ext == ".dat":
            print(match)
            loader=GodViewLoader({
                "globPattern":os.path.join(args.movie_dir, match),
                "outputPrefix":os.path.join(args.movie_dir, "movie"),
                "asVideo":args.as_video, # Trueだと動画(mp4)、Falseだと連番画像（png）として保存
                "fps":60
            })
            loader.run()

if __name__ == "__main__":
    main()


# -*- coding: utf-8 -*-
"""
Created on Sun Dec  3 21:31:21 2017

@author: gxk19
"""

import matplotlib.pyplot as plt
import numpy as np

a=np.arange(10)

plt.ylabel('y')
plt.xlabel('x')
plt.title("Grade")

plt.plot(a,a*1,'go-',a,a*2,'rx',a,a*3,'*',a,a*4,'b-.')
plt.savefig("4",dpi=600)
plt.show()


import db
from flask_restful import Resource
from utils import get_jwt, return_auth_err

class CurrentUser(Resource):
    def get(self):
        try:
            jwt = get_jwt()
            role = jwt['role']
            person_id = jwt['id']
        except Exception:
            return return_auth_err()
        if role in ['manager', 'admin']:
            manager = db.Manager.query \
                .filter(db.Manager.id == person_id) \
                .one_or_none()
            manager_schema = db.ManagerSchema()
            return manager_schema.dump(manager)
        elif role == 'student':
            student = db.Student.query \
                .filter(db.Student.id == person_id) \
                .one_or_none()
            student_schema = db.StudentSchema()
            return student_schema.dump(student)
        return None


from mmengine import Config

from mmagic.registry import MODELS
from mmagic.utils import register_all_modules

import os
import torch
from pathlib import Path
import datetime
from mmagic.models.editors.animatediff import save_videos_grid

register_all_modules()

cfg = Config.fromfile('configs/animatediff/animatediff_ToonYou.py')
animatediff = MODELS.build(cfg.model).cuda()
prompts = ["(masterpiece, best quality), wasteland, wrecked train, moss, scenery, landscape, nature"
]

negative_prompts = [
    "worst quality, low quality, letterboxed",
    "badhandv4,easynegative,ng_deepnegative_v1_75t,verybadimagenegative_v1.3, bad-artist, bad_prompt_version2-neg, teeth",
    "",
    "",
]

sample_idx = 0
random_seeds = cfg.randomness['seed']
random_seeds = [random_seeds] if isinstance(random_seeds, int) else list(random_seeds)
samples = []
time_str = datetime.datetime.now().strftime("%Y-%m-%dT%H-%M-%S")
savedir = f"samples/{Path(cfg.model['dream_booth_lora_cfg']['type']).stem}-{time_str}"
os.makedirs(savedir)
for prompt_idx, (prompt, n_prompt, random_seed) in enumerate(zip(prompts, negative_prompts, random_seeds)):
    output_dict = animatediff.infer(prompt,negative_prompt=n_prompt, video_length=16, height=256, width=256, seed=random_seed,num_inference_steps=cfg.model['dream_booth_lora_cfg']['steps'])
    sample = output_dict['samples']
    prompt = "-".join((prompt.replace("/", "").split(" ")[:10]))
    save_videos_grid(sample, f"{savedir}/sample/{sample_idx}-{prompt}.gif")
    print(f"save to {savedir}/sample/{prompt}.gif")
    samples.append(sample)
    sample_idx += 1

samples = torch.concat(samples)
save_videos_grid(samples, f"{savedir}/sample.gif", n_rows=4)


import pandas as pd
import numpy as np
import random
import matplotlib.pyplot as plt

def sigmoid(x):
    return 1 / (1 + np.exp(-x))

def logistic_loss(y_true, y_pred):
    return - (y_true * np.log(y_pred) + (1 - y_true) * np.log(1 - y_pred))

def train_newton(X, y, theta):
    losses = []
    while True:
        p = np.array(sigmoid(X.dot(theta[:, 0])), ndmin=2).T
        W = np.diag((p * (1 - p))[:, 0])
        hessian = X.T.dot(W).dot(X)
        grad = X.T.dot(y - p)
        step = np.dot(np.linalg.inv(hessian), grad)

        if np.linalg.norm(grad) < 0.01:
            break
        theta = theta + step

        loss = logistic_loss(y, p)
        losses.append(loss[0])

    return losses

def train_gd(X, y, theta, learning_rate=0.001):
    losses = []
    while True:
        p = np.array(sigmoid(X.dot(theta[:, 0])), ndmin=2).T
        grad = X.T.dot(y - p)
        if np.linalg.norm(grad) < 0.1:
            break
        step = learning_rate * grad
        theta = theta + step

        loss = logistic_loss(y, p)
        losses.append(loss[0])

    return losses

def main():
    data = pd.read_csv("q4data.csv")

    X = data.iloc[:, :-1]
    y = data.iloc[:, -1]

    X = np.c_[np.ones((X.shape[0], 1)), X]
    y = y[:, np.newaxis]

    theta = np.zeros((4,1))

    gd_losses = train_gd(X, y, theta)
    newton_losses = train_newton(X, y, theta)

    fig, (ax1, ax2) = plt.subplots(1, 2, figsize=(12, 5))

    ax1.plot(gd_losses, label="Gradient Descent Loss")
    ax1.set_xlabel("Iteration")
    ax1.set_ylabel("Loss")
    ax1.set_title("Gradient Descent")
    ax1.legend()

    ax2.plot(newton_losses, label="Newton's Method Loss")
    ax2.set_xlabel("Iteration")
    ax2.set_ylabel("Loss")
    ax2.set_title("Newton's Method")
    ax2.legend()

    plt.tight_layout()
    plt.show()

main()


import numpy as np
import cv2
import pygame
import time

# pygame color values
white = (255,255,255)
black = (0,0,0)

# establishing width and height for pygame screen
width = 800
height = 800

# establishing starting position for the ball
x_ball = width/2
y_ball = height/2

#initiating steps for ball
a = True
b, c, d, e, f, g = False, False, False, False, False, False

# initiating pygame
pygame.init()
screen = pygame.display.set_mode((width,height)) #creating screen
pygame.draw.circle(screen, white, (x_ball,y_ball), 5) #drawing ball
pygame.display.update()

#classifier for face detector
face_cascade = cv2.CascadeClassifier('/usr/share/opencv/haarcascades/haarcascade_frontalface_alt.xml')

#starts video capture
cap = cv2.VideoCapture(0)

# Init video
ret, frame = cap.read()

faces = face_cascade.detectMultiScale(frame, scaleFactor=1.2, minSize=(20,20))
for (x,y,w,h) in faces:
	cv2.rectangle(frame,(x,y),(x+w,y+h),(0,0,255))

# Display the resulting frame
cv2.imshow('frame',frame)

while(True):

	# update ball location
	screen.fill(black)
	pygame.draw.circle(screen, white, (x_ball,y_ball), 5)
	pygame.display.update()

	# Capture frame-by-frame
	ret, frame = cap.read()

	# Face detecting and drawing rectangle around face
	faces = face_cascade.detectMultiScale(frame, scaleFactor=1.2, minSize=(20,20))
	for (x,y,w,h) in faces:
		cv2.rectangle(frame,(x,y),(x+w,y+h),(0,0,255))

	# Display the resulting frame
	cv2.imshow('frame',frame)
	if cv2.waitKey(1) & 0xFF == ord('q'):
		break

	# move ball for next round
	if a:
		if x_ball < width:
			x_ball+= 1
		else:
			a =False
			b = True
	if b:
		if x_ball>0:
			x_ball-=1
		else:
			b = False
			c = True
	if c:
		if x_ball < width/2:
			x_ball+=1
		else:
			c= False
			d = True
	if d:
		if y_ball < height:
			y_ball+= 1
		else:
			d =False
			e = True
	if e:
		if y_ball>0:
			y_ball-=1
		else:
			d = False
			f = True
	if g:
		if y_ball < height/2:
			y_ball+=1
		else:
			g= False
			a = True

# When everything done, release the capture
cap.release()
cv2.destroyAllWindows()


# I wrote this code

from django.test import TestCase
from rest_framework.test import APITestCase

from .model_factories import *
from .serializers import *

from django.shortcuts import get_object_or_404

class ProteinsSerializerTest(APITestCase):

    protein1 = None
    proteinSerializer = None

    def setUp(self) -> None:
        self.protein1 = ProteinFactory.create(proteinId="A0A014PQC0")
        self.proteinsSerializer = ProteinSerializer(instance=self.protein1)

        self.validated_data = {
            'protein_id': 'A0A014PQC0',
            'sequence': 'SAMPLE_SEQUENCE',
            'length': 100
        }

    def tearDown(self) -> None:
        Protein.objects.all().delete()
        ProteinFactory.reset_sequence(0)

    def test_proteinsListSerializer(self):
        data = self.proteinsSerializer.data
        self.assertEqual(set(data.keys()), set(['protein_id', 'sequence', 'length']))

    def test_proteinSerializer_create(self):
        serializer = ProteinSerializer(data=self.validated_data)

        is_valid = serializer.is_valid()
        if not is_valid:
            print(serializer.errors)
        self.assertTrue(is_valid)

class ProteinGetSerializerTest(APITestCase):
    '''
    Part of ProteinGetSerializerTest:
        ProteinGetSerializer
        TaxonomyProteinSerializer
        ProteinDomainLinkGetSerializer

    '''
    protein1 = None
    protein2 = None
    proteinSerializer = None
    domain1= None
    domain2=None
    domain_link1 = None
    domain_link2 = None
    taxonomy = None
    taxaonmoylink1 = None
    taxaonmoylink2 = None

    def setUp(self):

        self.taxonomy = TaxonomyFactory.create(taxaId='55661')
        self.protein1 = ProteinFactory.create(proteinId='A0A014PQC0')
        # self.protein2 = ProteinFactory.create(proteinId='A0A134567')

        self.taxaonmoylink1 = TaxonomyProteinLinkFactory.create(protein=self.protein1, taxonomy=self.taxonomy)
        # self.taxaonmoylink2 = TaxonomyProteinLinkFactory.create(protein=self.protein2, taxonomy=self.taxonomy)

        self.domain1 = PfamFactory(domainId='PF01650', domain_description='PeptidaseC13family')
        self.domain2 = PfamFactory(domainId='PF12345', domain_description='AnotherDomain')

        self.domain_link1 = ProteinDomainLinkFactory(protein=self.protein1, pfam=self.domain1)
        self.domain_link2 = ProteinDomainLinkFactory(protein=self.protein1, pfam=self.domain2)

        self.proteinSerializer = ProteinGetSerializer(self.protein1)

    def tearDown(self):
        Protein.objects.all().delete()
        ProteinDomainLink.objects.all().delete()
        TaxonomyProteinLink.objects.all().delete()
        ProteinFactory.reset_sequence(0)
        ProteinDomainLinkFactory.reset_sequence(0)
        TaxonomyProteinLinkFactory.reset_sequence(0)

    def test_proteinGetSerializer(self):
        data = self.proteinSerializer.data
        self.assertEqual(set(data.keys()), set(['protein_id', 'sequence', 'taxonomy', 'length', 'domains']))

    def test_proteinGetSerializerHasCorrectData(self):
        data = self.proteinSerializer.data
        self.assertEqual(data['protein_id'], 'A0A014PQC0')

        # Additional assertions for the fields 'sequence', 'length', 'taxonomy', and 'domains'
        self.assertEqual(data['sequence'], self.protein1.sequence)
        self.assertEqual(data['length'], self.protein1.length)
        self.assertEqual(len(data['taxonomy']), 4)
        self.assertEqual(len(data['domains']), 2)  # Assuming 2 domain entries for this protein

class TaxonomyProteinSerializerTest(TestCase):

    taxonomy_data = None

    def setUp(self):
        ''' not using factory boy, this serializer is part of create protein '''
        self.taxonomy_data = {
            'taxaId': '55661',
            'clade': 'Sample Clade',
            'genus': 'Sample Genus',
            'species': 'Sample Species'
        }

    def tearDown(self):
        Taxonomy.objects.all().delete()
        ProteinDomainLink.objects.all().delete()
        TaxonomyProteinLink.objects.all().delete()
        ProteinFactory.reset_sequence(0)
        ProteinDomainLinkFactory.reset_sequence(0)
        TaxonomyProteinLinkFactory.reset_sequence(0)

    def test_taxonomyProteinSerializer(self):

        protein_data = {
            'taxonomy': self.taxonomy_data
        }

        serializer = TaxonomyProteinSerializer(protein_data)

        self.assertEqual(set(serializer.data.keys()), set(['taxa_id', 'clade', 'genus', 'species']))
        self.assertEqual(serializer.data['taxa_id'], '55661')
        self.assertEqual(serializer.data['clade'], 'Sample Clade')
        self.assertEqual(serializer.data['genus'], 'Sample Genus')
        self.assertEqual(serializer.data['species'], 'Sample Species')

class TaxonomyProteinLinkSerializerTest(TestCase):

    def setUp(self):
        self.taxonomy = TaxonomyFactory.create(taxaId='55661')
        self.protein1 = ProteinFactory.create(proteinId='A0A014PQC0')
        self.taxaonmoylink1 = TaxonomyProteinLinkFactory.create(protein=self.protein1, taxonomy=self.taxonomy)
        self.serializer = TaxonomyProteinLinkSerializer(instance=self.taxaonmoylink1)

    def tearDown(self):
        Taxonomy.objects.all().delete()
        ProteinDomainLink.objects.all().delete()
        TaxonomyProteinLink.objects.all().delete()
        ProteinFactory.reset_sequence(0)
        ProteinDomainLinkFactory.reset_sequence(0)
        TaxonomyProteinLinkFactory.reset_sequence(0)

    def test_taxonomyProteinLinkSerializer(self):
        data = self.serializer.data
        self.assertEqual(set(data.keys()), set(['taxonomy', 'protein']))

class GetPfamOnTaxaIdSerializerTest(TestCase):

    def setUp(self):
        self.domain1 = PfamFactory(domainId='PF01650', domain_description='PeptidaseC13family')
        self.protein1 = ProteinFactory.create(proteinId='A0A04PQC0')
        self.domain_link1 = ProteinDomainLinkFactory(protein=self.protein1, pfam=self.domain1)

        self.serializer = GetPfamOnTaxaIdSerializer(instance=self.domain_link1)

    def tearDown(self):
        Taxonomy.objects.all().delete()
        ProteinDomainLink.objects.all().delete()
        TaxonomyProteinLink.objects.all().delete()
        ProteinFactory.reset_sequence(0)
        ProteinDomainLinkFactory.reset_sequence(0)
        TaxonomyProteinLinkFactory.reset_sequence(0)

    def test_getPfamOnTaxaIdSerializer(self):
        data = self.serializer.data
        self.assertEqual(set(data.keys()), set(['id', 'pfam_id']))
        self.assertEqual(data['id'], str(self.domain_link1.pk))
        self.assertEqual(data['pfam_id']['domain_id'], self.domain1.domainId)
        self.assertEqual(data['pfam_id']['domain_description'], self.domain1.domain_description)

class ProteinDomainLinkGetSerializerTest(TestCase):

    def setUp(self):
        self.domain1 = PfamFactory(domainId='PF01650', domain_description='PeptidaseC13family')
        self.protein1 = ProteinFactory(proteinId='A0A04PQC0')
        self.domain_link1 = ProteinDomainLinkFactory(protein=self.protein1, pfam=self.domain1)

        self.serializer = ProteinDomainLinkGetSerializer(instance=self.domain_link1)

    def tearDown(self):
        Taxonomy.objects.all().delete()
        ProteinDomainLink.objects.all().delete()
        TaxonomyProteinLink.objects.all().delete()
        ProteinFactory.reset_sequence(0)
        ProteinDomainLinkFactory.reset_sequence(0)
        TaxonomyProteinLinkFactory.reset_sequence(0)

    def test_proteinDomainLinkGetSerializer(self):
        data = self.serializer.data

        self.assertEqual(set(data.keys()), set(['pfam_id', 'description', 'start', 'stop']))
        self.assertEqual(data['pfam_id']['domain_id'], self.domain1.domainId)
        self.assertEqual(data['pfam_id']['domain_description'], self.domain1.domain_description)

class ProteinDomainLinkSerializerTest(TestCase):

    def setUp(self):
        self.protein1 = ProteinFactory(proteinId='A0A04PQC0')
        self.data = {
            'protein': self.protein1.pk,
            'pfam_id': {
                'domain_id': 'PF01650',
                'domain_description': 'self.pfam.domain_description'
            },
            'description': 'Sample description',
            'start': 1,
            'stop': 10
        }
        self.serializer = ProteinDomainLinkSerializer(data=self.data)

    def tearDown(self):
        Taxonomy.objects.all().delete()
        ProteinDomainLink.objects.all().delete()
        TaxonomyProteinLink.objects.all().delete()
        ProteinFactory.reset_sequence(0)
        ProteinDomainLinkFactory.reset_sequence(0)
        TaxonomyProteinLinkFactory.reset_sequence(0)

    def test_proteinDomainLinkSerializer_create(self):
        is_valid = self.serializer.is_valid()
        if not is_valid:
            print(self.serializer.errors)
        self.assertTrue(is_valid)

        link = self.serializer.save()

        self.assertEqual(link.protein, self.protein1)

class TaxonomySerializerTest(TestCase):

    def setUp(self):
        self.data = {
            'taxa_id': '55661',
            'clade': 'Sample Clade',
            'genus': 'Sample Genus',
            'species': 'Sample Species'
        }
        self.serializer = TaxonomySerializer(data=self.data)

    def tearDown(self):
        Taxonomy.objects.all().delete()
        ProteinDomainLink.objects.all().delete()
        TaxonomyProteinLink.objects.all().delete()
        ProteinFactory.reset_sequence(0)
        ProteinDomainLinkFactory.reset_sequence(0)
        TaxonomyProteinLinkFactory.reset_sequence(0)

    def test_taxonomySerializer(self):
        self.assertTrue(self.serializer.is_valid())
        data = self.serializer.data

        self.assertEqual(set(data.keys()), set(['taxa_id', 'clade', 'genus', 'species']))
        self.assertEqual(data['taxa_id'], '55661')
        self.assertEqual(data['clade'], 'Sample Clade')
        self.assertEqual(data['genus'], 'Sample Genus')
        self.assertEqual(data['species'], 'Sample Species')

#end of code I wrote


#!/usr/bin/python
# -*- coding: utf-8 -*-

import gettext
import config
import web

translations = web.storage()
supported_languages = ['ko', 'en', 'ru']
def get_translations(lang='ko'):
    if translations.has_key(lang):
        translation = translations[lang]
    elif lang is None:
        translation = gettext.NullTranslations()
    else:
        try:
            translation = gettext.translation('messages',
                    config.i18n_path, languages=[lang],)
        except IOError:
            translation = gettext.NullTranslations()
    return translation

def load_translations(lang):
    lang = str(lang)
    translation = translations.get(lang)
    if translation is None:
        translation = get_translations(lang)
        translations[lang] = translation

        for lk in translations.keys():
            if lk != lang:
                del translations[lk]
    return translation

def get_language():
    # 로그인한 경우에는 사용자가 선호하는 언어로 변경.
    # 로그인하지 않은 경우에는 Accept-Language 헤더의 가장 높은 q 언어를 사용.
    # 둘 다 해당하지 않으면 한국어.
    lang_header = ''
    lang = web.ctx.session.get('lang')
    if lang:
        return lang
    try:
        lang_header = web.ctx.environ.get('HTTP_ACCEPT_LANGUAGE')
        lang_header = [x.split(';q=') for x in lang_header.split(',')]
        for x in lang_header:
            if len(x) == 1:
                x.append(1)
            else:
                x[1] = float(x[1])
        lang_header.sort(key = lambda x: x[1], reverse = True)
        ret = lang_header[0][0]
        if ret in supported_languages:
            return ret
        if ret[0:ret.find('-')] in supported_languages:
            return ret[0:ret.find('-')]
        return lang
    except:
        pass
    return 'ko'

def custom_gettext(string):
    translation = load_translations(get_language())
    if translation is None:
        return unicode(string)
    return translation.ugettext(string)

def custom_ngettext(single, plural, n):
    translation = load_translations(get_language())
    if translation is None:
        if n:
            return unicode(plural)
        return unicode(single)
    return translation.ungettext(single, plural, n)


# coding:utf8
"""
参考django进行日志配置, 利用LOGGERS来添加日志配置
"""

import logging
import logging.config
import os

BASE_DIR = os.path.dirname(os.path.dirname(os.path.realpath(__file__)))
# 是否DEBUG
DEBUG = False

# 日志配置
LOGGING = {
    'version': 1,
    'disable_existing_loggers': True,
    'formatters': {
        'verbose': {
            'format': ("%(levelname)s %(asctime)s %(module)s "
                       "%(filename)s:%(lineno)s "
                       "%(process)d %(thread)d %(message)s")
        },
    },
    'filters': {},
    'handlers': {},
    'loggers': {},
}

# 自定义 Logger 配置, 之后可以在代码的任何地方添加如下代码进行日志记录:
# my_logger = logging.getLogger('name-1')
# my_logger.error('message')
LOGGERS = ["common", "error", "info"]
for name in LOGGERS:
    handler = {
        'level': 'INFO',
        # 利用TimedRotatingFileHandler来按照日期切割
        'class': 'logging.handlers.TimedRotatingFileHandler',
        'filename': os.path.join(BASE_DIR, 'logs/%s.log' % name),
        'formatter': 'verbose',
        'when': 'M',
    }
    logger = {
        'handlers': [name],
        'level': 'INFO',
        'propagate': True,
    }
    LOGGING['handlers'][name] = handler
    LOGGING['loggers'][name] = logger

# 是否开启调试
if DEBUG:
    LOGGING['handlers']['console'] = {
        'level': 'DEBUG',
        'class': 'logging.StreamHandler',
        'formatter': 'verbose'
    }
    for logger in LOGGING['loggers']:
        LOGGING['loggers'][logger]['handlers'] = ['console']

# 启动配置
logging.config.dictConfig(LOGGING)
logger_error = logging.getLogger('error')
logger_info = logging.getLogger('info')


import random
import re
import time
from selenium import webdriver
from selenium.webdriver import ActionChains
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.common.keys import Keys

from Board import Board

class WebOperator(object):
    def __init__(self):
        options = Options()
        options.add_argument("--disable-notifications")#--headless
        self.chrome = webdriver.Chrome('./chromedriver', chrome_options=options)
        self.chrome.get("https://play2048.co/")
        self.newNum = {2: 0, 4: 0}

    def IsGameOver(self):
        isGameOver=self.chrome.find_elements_by_css_selector(".game-over")
        return True if len(isGameOver)>0 else False

    def ResetGame(self):
        restartButton=self.chrome.find_element_by_css_selector(".restart-button")
        restartButton.click()

    def GetScore(self):
        scoreInfo = self.chrome.find_element_by_css_selector(".score-container")
        matches = re.match(r".*", scoreInfo.text)
        return (matches.group(0))

    def GetRawInfo(self):
        rawInfo = self.chrome.find_elements_by_css_selector(".tile-container .tile")
        return rawInfo

    def GetBoardInfo(self):
        rawInfo = self.GetRawInfo()
        board = Board()
        for r in rawInfo:
            className = str(r.get_attribute("class"))
            matches = re.match(r"tile tile-(?P<num>\d+) tile-position-(?P<px>\d)-(?P<py>\d)( (?P<misc>.+))?", className)
            misc = ""
            if matches.group("misc") is not None:
                misc = str(matches.group("misc"))
                if "tile-new" == misc:
                    self.newNum[int(matches.group("num"))] += 1
            # print(misc)
            board.title[int(matches.group("py")) - 1][int(matches.group("px")) - 1] = int(matches.group("num"))
        return board

    def RandomMove(self):
        d = random.randint(0, 4)
        actions = ActionChains(self.chrome)
        if (0 == d):
            actions.send_keys(Keys.ARROW_UP).perform()
        elif (1 == d):
            actions.send_keys(Keys.ARROW_DOWN).perform()
        elif (2 == d):
            actions.send_keys(Keys.ARROW_LEFT).perform()
        elif (3 == d):
            actions.send_keys(Keys.ARROW_RIGHT).perform()

    def Move(self,cmd):
        actions = ActionChains(self.chrome)
        if ("UP" == cmd):
            actions.send_keys(Keys.ARROW_UP).perform()
        elif ("DOWN" == cmd):
            actions.send_keys(Keys.ARROW_DOWN).perform()
        elif ("LEFT" == cmd):
            actions.send_keys(Keys.ARROW_LEFT).perform()
        elif ("RIGHT" == cmd):
            actions.send_keys(Keys.ARROW_RIGHT).perform()

        #

if __name__ == "__main__":
    webOperator = WebOperator()
    i = 0
    while ("Game over!" not in webOperator.chrome.page_source):
        time.sleep(1)
        webOperator.GetBoardInfo()
        webOperator.RandomMove()
        i += 1
    print(webOperator.newNum)


# Loading useful libraries/packages
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
from amplpy import AMPL,Environment

# Plotting the VMC capacity envelope
print('Plotting the VMC  and the IMC capacity envelopes...')
x_vmc = [0,17,24,28,28] # Intersecting points in x
y_vmc = [30,30,24,15,0] # Intersecting points in y
plt.plot(x_vmc,y_vmc)

# Plotting the IMC capacity envelope
x_imc = [0,12,17,20,20] # Intersecting points in x
y_imc = [22,22,17,11,0] # Intersecting points in y
plt.plot(x_imc,y_imc)
plt.legend(['VMC','IMC'])
plt.xlabel('Arrivals')
plt.ylabel('Departures')
plt.show()
print('Done.\n')

# Loading data
print('Loading data...')
demand_data = pd.read_excel("demand.xlsx", index_col = 0) # Demand information
print('Done.')

# Total number of time slots
N = len(demand_data)

# Arrival priority
alpha = 2

# Initial queue
a_0 = 0 # Initial arrival queue
d_0 = 0 # Initial departure queue

# Optimal values list
opt_values = []

# Optimization for different scenarios
episodes = 1000

for eps in range(episodes):

    a_t = a_0
    d_t = d_0
    z = 0
    arr = {}
    dep = {}
    plt.plot(x_vmc,y_vmc)
    plt.plot(x_imc,y_imc)
    plt.legend(['VMC','IMC'])
    plt.xlabel('Arrivals')
    plt.ylabel('Departures')

    for t in range(N):

        # Updating the demand queue
        a_t += demand_data['Arrival Demand'][t]
        d_t += demand_data['Departure Demand'][t]

        # Probability of IMC
        IMC_prob = demand_data['IMC Probability'][t]

        # Determining the current state
        wc = np.random.choice(['IMC','VMC'],p = [IMC_prob,1 - IMC_prob])

        # Determining the constraints
        p = []
        q = []
        r = []
        if wc == 'VMC':
            p.append(1)
            q.append(0)
            r.append(np.max(y_vmc))
            for i in range(1,len(x_vmc)-2):
                dy = y_vmc[i+1] - y_vmc[i]
                dx = x_vmc[i+1] - x_vmc[i]
                p.append(1)
                q.append(-dy/dx)
                r.append(y_vmc[i] - dy/dx*x_vmc[i])
            p.append(0)
            q.append(1)
            r.append(np.max(x_vmc))
        elif wc == 'IMC':
            p.append(1)
            q.append(0)
            r.append(np.max(y_imc))
            for i in range(1,len(x_imc)-2):
                dy = y_imc[i+1] - y_imc[i]
                dx = x_imc[i+1] - x_imc[i]
                p.append(1)
                q.append(-dy/dx)
                r.append(y_imc[i] - dy/dx*x_imc[i])
            p.append(0)
            q.append(1)
            r.append(np.max(x_imc))

        # Solving with AMPL
        ampl = AMPL(Environment(r'C:\Users\lucas\Desktop\ampl.mswin64'))
        ampl.eval(r"""
            param a_t;
            param d_t;
            param alpha;
            param p{i in 1..4};
            param q{i in 1..4};
            param r{i in 1..4};
            var u integer >= 0;
            var v integer >= 0;
            minimize delay:
                alpha*(a_t - u)^2 + (d_t - v)^2;
            s.t. c1:
                p[1]*v + q[1]*u <= r[1];
            s.t. c2:
                p[2]*v + q[2]*u <= r[2];
            s.t. c3:
                p[3]*v + q[3]*u <= r[3];
            s.t. c4:
                p[4]*v + q[4]*u <= r[4];
            s.t. c5:
                u <= a_t;
            s.t. c6:
                v <= d_t;
        """)
        ampl.param['alpha'] = alpha
        ampl.param['a_t'] = int(a_t)
        ampl.param['d_t'] = int(d_t)
        ampl.param['p'] = p
        ampl.param['q'] = q
        ampl.param['r'] = r
        ampl.option['solver'] = 'knitro'
        ampl.option['knitro_options'] = 'ms_enable=1 ms_num_to_save=5 ms_savetol=0.01 ms_maxsolves=10'
        ampl.solve()
        #assert ampl.get_value('solve_result') == 'solved'
        sol = ampl.get_value('alpha*(a_t - u)^2 + (d_t - v)^2')
        arr[t] = round(ampl.get_value('u'))
        dep[t] = round(ampl.get_value('v'))
        print('Optimal solution for episode '+str(eps+1)+', step '+str(t+1)+': '+str(round(sol,2))+', x = ['+str(arr[t])+', '+str(dep[t])+']')
        plt.plot(arr[t],dep[t],'o',color='grey')

        # Updating the queues
        a_t -= arr[t]
        d_t -= dep[t]

        # Calculating the total solution
        z += sol

    opt_values.append(round(z,2))
    print('Optimal value for episode '+str(eps+1)+': '+str(round(z,2)))
    plt.show()

# Plotting the results
plt.plot([i+1 for i in range(episodes)],opt_values,'o')
plt.plot([i+1 for i in range(episodes)],[round(np.average(opt_values),2) for i in range(episodes)],'--')
plt.xlabel('Episodes')
plt.ylabel('Delay/Cost')
plt.show()
print('Optimal value (average): '+str(round(np.average(opt_values),2)))


from PyQt5.QtWidgets import QApplication, QWidget, QInputDialog, QLineEdit, QFileDialog

class dialogsGUI(QWidget):

    def __init__(self):
        super().__init__()
        self.title = 'Choose File'
        self.left = 10
        self.top = 10
        self.width = 640
        self.height = 480
        self.initUI()

    def initUI(self):
        self.setWindowTitle(self.title)
        self.setGeometry(self.left, self.top, self.width, self.height)

    def openFileNameDialog(self):
        options = QFileDialog.Options()
        fileName, _ = QFileDialog.getOpenFileName(self, "Open File", "",
                                                  "PCAP (*.pcap);;PCAPNG (*.pcapng)", options=options)
        self.hide()
        return fileName,_

    def saveFileDialog(self):
        options = QFileDialog.Options()
        fileName, _ = QFileDialog.getSaveFileName(self, "Save As", "",
                                                  "PCAP (*.pcap);;PCAPNG (*.pcapng)", options=options)
        self.hide()
        return fileName,_


from os.path import join, getsize, split
from os import remove
from zlib import crc32
from shutil import copyfile
from platformio.util import get_systype

lod_header = bytes("""#$mode=flsh_spi32m
#$sectormap=(16 x 4k, 57 x 64k, 96 x 4k)
#$base=0x08000000
#$spacesize=0x08000000
#$XCV_MODEL=xcv_8955
#$PA_MODEL=pasw_rda6625
#$FLSH_MODEL=flsh_spi32m
#$FLASH_SIZE=0x400000
#$RAM_SIZE=0x00400000
#$RAM_PHY_SIZE=0x00400000
#$RAM_EXTAPP_SIZE=0
#$FLASH_EXTAPP_SIZE=0x40000
#$CALIB_BASE=0x3FA000
#$FACT_SETTINGS_BASE=0x3F4000
#$CODE_BASE=0x00000000
#$USER_DATA_BASE=0x3F6000
#$USER_DATA_SIZE=0x4000
#$BOOT_SECTOR=0x10000
#$PM_MODEL=pmu_8955
#$FM_MODEL=rdafm_8955
""", 'utf8')

def gen_lod_file(target, source, env):
    (target_lod, ) = target
    (source_elf, ) = source

    cmd = ["$OBJCOPY"]
    (source_path, source_name) = split(source_elf.get_abspath())
    tmp_bin = join(source_path, source_name + '.bin')

    cmd.extend(["-O", "binary"])
    cmd.append(source_elf.get_abspath())
    cmd.append(tmp_bin)
    env.Execute(env.VerboseAction(" ".join(cmd), " "))

    # fix bin size to sector boundary (0x10000)
    binsz = getsize(tmp_bin)
    f_binsz = (binsz + 0xFFFF) & ~0xFFFF
    # print("Binary size: %d" % binsz)
    f = open(tmp_bin, "rb")
    f_bin = bytearray(f.read())
    f.close()
    f_bin += bytes(b'\xff' * (f_binsz - binsz))
    # Fix header size
    f_bin[4:8] = f_binsz.to_bytes(4, "little")
    # Fix checksum
    f_bin[8:0xC] = crc32(f_bin).to_bytes(4, "little")
    # write final binary
    f = open(tmp_bin, "wb")
    f.write(f_bin)
    f.close()

    # write final lod file
    f = open(target_lod.get_abspath(), "wb")
    f.write(lod_header)
    address = 0x8250000
    for i in range(int(f_binsz / 4)):
        if address % 0x10000 == 0:
            f.write(bytes('@%08x\n' % address, "utf8"))
        x = i*4
        f.write(bytes('%08x\n' % int.from_bytes(f_bin[x:x+4], 'little'), "utf8"))
        address = address + 4
    f.close()
    remove(tmp_bin)

def gen_fota_file(target, source, env):
    if "darwin" in get_systype():
        print("Fota generate is only available on Windows/Linux.\n")
        return

    FRAMEWORK_DIR = env.PioPlatform().get_package_dir("framework-logicromsdk")
    (target_bin, ) = target
    (source_lod, ) = source
    (source_path, source_name) = split(source_lod.get_abspath())
    tmp_lod = join(source_path, 'tmp_' + source_name)
    empty_lod = join(FRAMEWORK_DIR, 'lib', 'rda8955', 'empty.lod')
    copyfile(empty_lod, tmp_lod)
    f_tmp = open(tmp_lod, "ab")
    with open(source_lod.get_abspath(), "rb") as src:
        src.seek(len(lod_header))
        f_tmp.write(src.read())
        src.close()
    f_tmp.close()
    env.Execute(env.VerboseAction(" ".join([
        '$FOTACREATE',
        '0x24F000',
        empty_lod,
        tmp_lod,
        target_bin.get_abspath()
    ]), " "))
    remove(tmp_lod)