# -*- coding: utf-8 -*-
"""
Created on Mon May 07 21:52:59 2018
@author: renyi
"""
import numpy as np
import matplotlib.pyplot as plt
feature_score1=np.loadtxt('F:\\work\\predict_economics\\data\\model\\rf_top_feature_v2.txt')
block=np.loadtxt('F:\\work\\predict_economics\\data\\gdp\\gdp2block.txt')
feature=np.loadtxt('F:\\work\\predict_economics\\data\\model\\feature_new_3.0.txt')
feature_score2=np.unique(feature_score1, axis=0)
feature_score=feature_score2[np.lexsort(-feature_score2.T)]
List=list(feature_score[:,0])
#block
gdp1=block[:,[0,3]]
gdp=np.delete(gdp1,[4],axis=0)

top=feature_score[:41]
top_id=top[:,0].astype(int)
poi=top[top[:,0]<21,:]
trace1=top[top[:,0]<53,:]
trace=trace1[trace1[:,0]>20,:]
#app1=top[top[:,0]<309,:]
#app=app1[app1[:,0]>52,:]
#od=top[top[:,0]>308,:]
app1=top[top[:,0]<69,:]
app=app1[app1[:,0]>52,:]
od=top[top[:,0]>68,:]

feature_top=feature[:,top_id]
feature1=np.hstack((gdp,feature_top))
feature2=feature1[np.argsort(-feature1[:,1])]
feature_ana=feature2[[0,1,2,3,4,182,183,184,185,186],:]

#poi
poi_idx=[] #poi
for item in poi[:,0]:
    idx=List.index(item)
    poi_idx.append(idx)
poi_ana=np.column_stack((poi_idx,poi))

#trace_feature
trace_idx=[] #trace
for item in trace[:,0]:
    idx=List.index(item)
    trace_idx.append(idx)
trace_ana=np.column_stack((trace_idx,trace))

#app_feature
app_idx=[] #app
t_idx=[] #app
app_class=[]#app
for item in app[:,0]:
    idx1=List.index(item)
    app_idx.append(idx1)
    t=int((item-52)/16)+1
    t_idx.append(t)
    app_id=(item-52)
    app_class.append(app_id)
app_ana1=np.column_stack((app_idx,app))
app_ana2=np.column_stack((app_ana1,t_idx))
app_ana=np.column_stack((app_ana2,app_class))


r"""WMCS Openstack - Rolling reboot of all the cloudgw.

Usage example:
    cookbook wmcs.openstack.roll_reboot_cloudgws --cluster_name eqiad1

"""
from __future__ import annotations

import argparse
import logging

from spicerack import Spicerack
from spicerack.cookbook import ArgparseFormatter, CookbookBase

from cookbooks.wmcs.openstack.cloudgw.reboot_node import RebootNode
from cookbooks.wmcs.openstack.network.tests import NetworkTests
from wmcs_libs.common import CommonOpts, SALLogger, WMCSCookbookRunnerBase, add_common_opts, with_common_opts
from wmcs_libs.inventory import OpenstackClusterName
from wmcs_libs.openstack.common import get_gateway_nodes

LOGGER = logging.getLogger(__name__)

class RollRebootCloudgws(CookbookBase):
    """WMCS Openstack cookbook to rolling reboot all cloudgws."""

    title = __doc__

    def argument_parser(self):
        """Parse the command line arguments for this cookbook."""
        parser = argparse.ArgumentParser(
            prog=__name__,
            description=__doc__,
            formatter_class=ArgparseFormatter,
        )
        add_common_opts(parser)
        parser.add_argument(
            "--cluster-name",
            required=True,
            choices=list(OpenstackClusterName),
            type=OpenstackClusterName,
            help="Cluster/deployment to roll-reboot the cloudgws for.",
        )
        parser.add_argument(
            "--force",
            required=False,
            action="store_true",
            help="If passed, will continue even if the cluster is not in a healthy state.",
        )

        return parser

    def get_runner(self, args: argparse.Namespace) -> WMCSCookbookRunnerBase:
        """Get runner"""
        return with_common_opts(self.spicerack, args, RollRebootCloudgwsRunner,)(
            force=args.force,
            cluster_name=args.cluster_name,
            spicerack=self.spicerack,
        )

def check_network_ok(cluster_name: OpenstackClusterName, spicerack: Spicerack) -> None:
    """Run the network tests and check if they pass."""
    args = ["--cluster_name", str(cluster_name)]
    network_test_cookbook = NetworkTests(spicerack=spicerack)
    if network_test_cookbook.get_runner(args=network_test_cookbook.argument_parser().parse_args(args)).run() != 0:
        raise Exception("Network tests failed, see logs or run the cookbook for details.")

class RollRebootCloudgwsRunner(WMCSCookbookRunnerBase):
    """Runner for RollRebootCloudgws"""

    def __init__(
        self,
        common_opts: CommonOpts,
        force: bool,
        cluster_name: OpenstackClusterName,
        spicerack: Spicerack,
    ):
        """Init"""
        self.common_opts = common_opts
        self.force = force
        super().__init__(spicerack=spicerack, common_opts=common_opts)
        self.sallogger = SALLogger.from_common_opts(common_opts=common_opts)
        self.cluster_name = cluster_name
        self.cloudgw_hosts = get_gateway_nodes(cluster_name=cluster_name)
        if not self.force:
            LOGGER.info("Checking the current state of the network...")
            check_network_ok(cluster_name=self.cluster_name, spicerack=self.spicerack)
            LOGGER.info("Network up and running!")

    def run_with_proxy(self) -> None:
        """Main entry point"""
        self.sallogger.log(
            message=(
                f"Rebooting all the cloudgw nodes from the {self.cluster_name} cluster_name: "
                + ",".join(self.cloudgw_hosts)
            )
        )

        reboot_node_cookbook = RebootNode(spicerack=self.spicerack)
        for index, cloudgw_node in enumerate(self.cloudgw_hosts):
            LOGGER.info("Rebooting node %s, %d done, %d to go", cloudgw_node, index, len(self.cloudgw_hosts) - index)
            args = [
                "--fqdn-to-reboot",
                f"{cloudgw_node}",
                "--skip-checks",
            ] + self.common_opts.to_cli_args()

            reboot_node_cookbook.get_runner(args=reboot_node_cookbook.argument_parser().parse_args(args)).run()
            LOGGER.info(
                "Rebooted node %s, %d done, %d to go, waiting for cluster to stabilize...",
                cloudgw_node,
                index + 1,
                len(self.cloudgw_hosts) - index - 1,
            )
            if not self.force:
                LOGGER.info("Checking if the network is still up and running...")
                check_network_ok(cluster_name=self.cluster_name, spicerack=self.spicerack)
                LOGGER.info("Network up and running! Will continue.")

        self.sallogger.log(message=f"Finished rebooting the cloudgw nodes {self.cloudgw_hosts}")


from django.conf.urls import url

from . import views

locations_add_delete = views.UserLocationAddDeleteViewSet.as_view({
    'put': 'update',
    'delete': 'destroy'
})

urlpatterns = [
    url(r'^locations/all/$', views.LocationsView.as_view()),
    url(r'^locations/$', views.UserLocationsView.as_view()),
    url(r'^locations/(?P<pk>[0-9]+)/$', locations_add_delete),
    url(r'^forecasts/$', views.ForecastsView.as_view()),
]


import os
import time
import random
from time import sleep
from argparse import ArgumentParser
'''DEVIDO A ALGUNS TRECHOS DO CODIGO DO GA DO VALVAL EXECUTAREM FUNÇÃO COM O CONSTRUTOR,
É NECESSARIO TRAZER O TERMINAL PARA A PASTA DE TESTE, ANTES MESMO DOS IMPORTS DO GA '''

# ----------------------------------------- PASSAGEM DE PARAMETRO POR TERMINAL ----------------------------------------

parser = ArgumentParser(
    prog="MetaHeuristica Hibrida ABC + ANSGAII",
    #description=""
)
parser.add_argument('-QT_ABC', default=10, type=int, help='Quantidade de tempo em segundos que o ABC vai ficar em execução')
parser.add_argument('-QT_GA', default=10, type=int, help='Quantidade de tempo em segundos que o GA vai ficar em execução')
parser.add_argument('-TA_ABC', default=100, type=int, help='Quantidade de abelhas')
parser.add_argument('-Q_indv', default=15, type=int, help='Quantidade de individuos do abc que vão ser passados pro GA')
parser.add_argument('-N_teste', default=1, type=int, help='Qual o testes que está sendo executado')
args = parser.parse_args()

# ---------------------------------------------------------------------------------------------------------------------

print("----------------------- PARAMETROS UTILIZADOS ----------------------------")
print("Tempo limite execução ABC: ", args.QT_ABC)
print("Tempo limite execução GA: ", args.QT_GA)
print("Total de abelhas: ", args.TA_ABC)
print("Quantidade de individuos: ", args.Q_indv)
print("Numero do teste: ", args.N_teste)
print("--------------------------------------------------------------------------")

# MOVE O FOCO DESSE TERMINAL PARA A PASTA EM QUE O TESTE VAI SER EXECUTADO
caminho_pasta_teste = os.getcwd() + "/teste" + str(args.N_teste)
print("Camihno até a pasta de teste: ", caminho_pasta_teste)
os.chdir(caminho_pasta_teste)

from grafo_pronto import grafo
from helpers import *
from desenha_rede import *
from pasta_maluca.GA_correto import GA
import pasta_maluca.GA_correto as gra

print("Inicio Execução codigo!")

G = gra._grafo_
random.seed(None)
class cromossomo:
    demanda_caminho = None
    fluxo_aresta = None
    custo = None
    soma_tam_caminhos= None

    def __gera_cromossomo(self):
        candidato = [0 for i in range(len(G.demandas))]
        while True:
            tam = len(G.demandas)
            for i in range(tam):
                candidato[i] = random.randint(0,len(G.caminhos[i])-1)
            a=[0.0 for i in range(len(G.arestas))]
            for i in range(tam):
                tam1 = len(G.caminhos[i][candidato[i]])
                for e in range(tam1):
                    if G.caminhos[i][candidato[i]][e] == 1:
                        a[e] += G.demandas[i].routing_value
            deu = True
            for e in range(len(G.arestas)):
                if a[e] > G.array_max_cap[e]:
                    deu = False
                    break
            if deu:
                self.demanda_caminho= [[] for i in range(tam)]
                for i in range(tam):
                    caminho = []+G.caminhos[i][candidato[i]]
                    tam1 = len(caminho)
                    for j in range(tam1):
                        if caminho[j] == 1:
                            self.demanda_caminho[i].append(j)
                self.fluxo_aresta = a
                break

    def __calcula_custo(self):
        tam = len(G.arestas)
        self.custo = 0.0
        for e in range(len(G.arestas)):
            self.custo+=G.arestas[e].pre_installed_capacity_cost
            if self.fluxo_aresta == 0 or self.fluxo_aresta[e]<=G.arestas[e].pre_installed_capacity:
                continue
            val = 100000000000.0
            for k in range(len(G.arestas[e].module_list)):
                if G.arestas[e].module_list[k].capacidade+G.arestas[e].pre_installed_capacity >= self.fluxo_aresta[e]:
                    val = min(val,G.arestas[e].module_list[k].cost)
            self.custo += val

    def __calcula_custo_dif(self,fluxo_aresta):
        tam = len(G.arestas)
        custo = 0.0
        for e in range(len(G.arestas)):
            custo+=G.arestas[e].pre_installed_capacity_cost
            if fluxo_aresta[e] == 0 or fluxo_aresta[e]<=G.arestas[e].pre_installed_capacity:
                continue
            val = 100000000000.0
            for k in range(len(G.arestas[e].module_list)):
                if G.arestas[e].module_list[k].capacidade +G.arestas[e].pre_installed_capacity >= fluxo_aresta[e]:
                    val = min(val, G.arestas[e].module_list[k].cost)
            custo += val
        return custo

    def __calcula_soma_tamanho_caminhos(self):
        tam = len(self.demanda_caminho)
        self.soma_tam_caminhos=0
        for i in range(tam):
            self.soma_tam_caminhos+=len(self.demanda_caminho[i])

    def __imprime_cromossomo(self):
        print('-------------')
        for d in range(len(self.demanda_caminho)):
            for e in range(len(self.demanda_caminho[d])):
                print(self.demanda_caminho[d][e],end=' ')
            print()
        print('-------------')

    def busca_local(self, pos, lista_limites):
        continua = 1
        while continua:
            tt = len(self.demanda_caminho)
            demanda_idx = 0
            continua = 0

            while demanda_idx < len(self.demanda_caminho):
                demanda_caminho = [] + self.demanda_caminho
                fluxo_aresta = [] + self.fluxo_aresta
                custo = 0.0
                soma_tam_caminho = 0
                conjunto_caminho = [] + G.caminhos[demanda_idx]

                for e in demanda_caminho[demanda_idx]:#remove fluxo do caminho atual
                    fluxo_aresta[e] -= G.demandas[demanda_idx].routing_value

                ref_fluxo_aresta = [] + fluxo_aresta

                '''Para cada caminho, dentro dos caminhos, e verifica quais arestas estão sendo utilizadas,
                Coloca a aresta que está utilizada na lista de caminho formatado'''
                for cmh in conjunto_caminho:#para cada caminho do conjunto de caminhos
                    cmh_formatado = []
                    for i in range(len(cmh)):
                        if cmh[i] == 1:
                            cmh_formatado.append(i)

                    # Troca o caminho da variavel auxiliar
                    demanda_caminho[demanda_idx] = [] + cmh_formatado

                    # Soma o fluxo do novo caminho, no fluxo_aresta
                    for e in cmh_formatado:
                        fluxo_aresta[e] += G.demandas[demanda_idx].routing_value

                    # Calcula o custo
                    custo = self.__calcula_custo_dif(fluxo_aresta)
                    # Calcula a soma dos tamanhos dos caminhos
                    for c in demanda_caminho:
                        soma_tam_caminho += len(c)

                    # Verifica de melhorou, atraves da dominancia de pareto
                    if (custo < self.custo and soma_tam_caminho <= self.soma_tam_caminhos) or (custo<=self.custo and soma_tam_caminho<self.soma_tam_caminhos):
                    #if custo < self.custo:
                        self.demanda_caminho = [] + demanda_caminho
                        self.fluxo_aresta = [] + fluxo_aresta
                        self.custo = custo
                        self.soma_tam_caminhos = soma_tam_caminho
                        continua = 1
                    fluxo_aresta = [] + ref_fluxo_aresta
                demanda_idx += 1

        return self.demanda_caminho, self.fluxo_aresta, self.custo

    def __lt__(self,other):
        return (self.custo < other.custo and self.soma_tam_caminhos <= other.soma_tam_caminhos) or (self.custo <= other.custo and self.soma_tam_caminhos < other.soma_tam_caminhos)

    def __eq__(self, other):
        return (self.custo == other.custo and self.soma_tam_caminhos == other.soma_tam_caminhos)

    def eh_aceitavel(self,demanda_caminho):
        fluxo_aresta = [0.0 for i in range(len(self.fluxo_aresta))]
        for cmh in range(len(demanda_caminho)):
            for e in demanda_caminho[cmh]:
                fluxo_aresta[e] += G.demandas[cmh].routing_value
        for e in range(len(fluxo_aresta)):
            if fluxo_aresta[e] > G.array_max_cap[e]+G.arestas[e].pre_installed_capacity:
                return None
        return fluxo_aresta

    def __add__(self, other):
        while True:
            filho1 = []
            filho2 = []
            sz = len(self.demanda_caminho)
            p1 = random.randint(1,int(sz/2))
            p2 = random.randint(int(sz/2+1),sz-2)
            ord = []
            for i in range(len(self.demanda_caminho)):
                if i <= p1 or i > p2:
                    ord.append(0)
                elif i<= p2:
                    ord.append(1)

            for c in range(len(self.demanda_caminho)):
                if ord[c] == 1:
                    filho1.append(self.demanda_caminho[c])
                    filho2.append(other.demanda_caminho[c])
                else:
                    filho2.append(self.demanda_caminho[c])
                    filho1.append(other.demanda_caminho[c])
            prole = []
            f1 = self.eh_aceitavel(filho1)
            f2 = self.eh_aceitavel(filho2)
            if f1 != None:
                prole.append(cromossomo(tipo='receber',demanda_caminho=filho1,fluxo_aresta=f1))
            if f2 != None:
                prole.append(cromossomo(tipo='receber',demanda_caminho=filho2,fluxo_aresta=f2))
            return prole

    def mutacao(self):
        return cromossomo()

    def __init__(self,tipo='gerar',demanda_caminho=None,fluxo_aresta=None,item=None):
        if tipo == 'gerar':
            self.__gera_cromossomo()
        if tipo == 'receber':
            self.demanda_caminho = demanda_caminho
            self.fluxo_aresta = fluxo_aresta
        if tipo == 'atribuir':
            self.demanda_caminho = item.demanda_caminho
            self.fluxo_aresta = item.fluxo_aresta
            self.custo = item.custo
            self.soma_tam_caminhos = item.soma_tam_caminhos
            return

        self.__calcula_custo()
        self.__calcula_soma_tamanho_caminhos()

class ABC:
    def __init__(self, nome_instancia='', tempo_max_execucao=0,quant_abelhas=100):
        self.ciclos = 0
        self.todos_fluxos = []
        self.total_abelhas = quant_abelhas
        self.tempo_max_execucao = tempo_max_execucao
        self.quantidade_abelhas_empregadas = int(self.total_abelhas / 2)
        self.tamanho_populacao = int(self.total_abelhas / 2)
        self.limite_tentativas_por_solucao = 20
        self.quantidade_abelhas_observadoras = self.quantidade_abelhas_empregadas
        self.quantidade_abelhas_exploradoras = self.quantidade_abelhas_empregadas
        self.populacao, self.ranks = [], []
        self.melhor_solucao_global = None
        self.lista_limites = [0 for i in range(self.tamanho_populacao)]
        self.melhores_solucoes = None

    def monta_vetor_ranks(self):
        self.ranks = [ 1 for i in range(len(self.populacao))]
        vis = [0 for i in range(len(self.populacao))]
        r = 1
        while True:
            qt = [0 for i in range(len(self.populacao))]
            for x in range(len(self.populacao)):
                if vis[x] == 1:
                    continue
                for y in range(len(self.populacao)):
                    if vis[y] == 1:
                        continue
                    if self.populacao[x] < self.populacao[y]:
                        qt[y] +=1
            para = True
            for i in range(len(self.populacao)):
                if qt[i] == 0 and vis[i]==0:
                    self.ranks[i] = r
                    vis[i]=1
                    para = False
            if para == True:
                break
            r += 1
        self.frente = []
        for i in range(len(self.populacao)):
            if self.ranks[i] == 1:
                self.frente.append(cromossomo(tipo='atribuir',item=self.populacao[i]))

    def gera_populacao_inicial(self):
        print('gerando populacao')
        for i in range(self.tamanho_populacao):
            self.populacao.append(cromossomo())

        print('Populacao gerada')

    def imprime_populacao(self):
        for i in range(len(self.populacao)):
            po = self.populacao[i]
            print("Custo: ", po.custo)
            print("Ranks: ", self.ranks[i])
            print("soma_tam_caminhos: ", po.soma_tam_caminhos)

    def imprime_custo_e_soma_caminho_solucao(self):
        linha()
        for i in range(len(self.melhores_solucoes)):
            print("SOLUÇÃO, Custo: ", self.melhores_solucoes[i].custo)
            print("SOLUÇÃO, soma_tam_caminhos: ", self.melhores_solucoes[i].soma_tam_caminhos)
        linha()

    def imprime_apenas_um_cromosso(self, cromo, pos):
        print("Custo: ", cromo.custo)
        print("Ranks: ", self.ranks[pos])
        print("soma_tam_caminhos: ", cromo.soma_tam_caminhos)

    def get_frente_pareto_geracao_atual(self):
        lista_posicao_frente_geracao = []
        for i in range(len(self.ranks)):
            if self.ranks[i] == 1:
                ''' Adiciona a posição dos ranks que possuem valor 1,
                esses são a frente de pareto da geração atual. '''
                lista_posicao_frente_geracao.append(self.populacao[i])

        return lista_posicao_frente_geracao

    def get_maior_rank(self):
        return max(self.ranks)

    def calcula_somatorio_fitness(self):
        return sum(self.ranks)

    def calcula_pis(self, somatorio_ranks):
        pis = []
        menor_rank = 1
        maior_rank = self.get_maior_rank()

        # Monta o vetor com todas as probabilidades
        for i in range(len(self.populacao)):
            ''' Para evitar a indefinição matematica, de divisão por 0. Onde o menor_rank, e o maior_rank ficam iguais
            sendo por exemplo, ambos igual a 1.'''
            if menor_rank == maior_rank:
                pis.append(1)
                continue

            pis.append( ((self.ranks[i] - menor_rank) / (maior_rank - menor_rank)) )

        return pis

    def fase_abelha_empregadas(self):
        '''Executa a fase das abelhas empregadas, aplicando uma busca local em cada fonte de elemento.'''
        for i in range(self.quantidade_abelhas_empregadas):

            self.populacao[i].demanda_caminho, self.populacao[i].fluxo_aresta,self.populacao[i].custo = self.populacao[i].busca_local(i, self.lista_limites)

    def fase_abelha_observadoras(self, pis):
        for i in range(self.quantidade_abelhas_observadoras):
            # Probabilidade
            pi, prob = pis[i], random.random()
            if prob < pi:
                #print(" !DENTRO DO IF! ")
                # Faz a escolha desse fonte de alimento, e envia uma abelha observadora dela
                self.populacao[i].demanda_caminho, self.populacao[i].fluxo_aresta, self.populacao[i].custo= self.populacao[i].busca_local(i, self.lista_limites)

    def verifica_existe(self, obj, lista):
        '''Verifica se um objeto, já existe em uma determinada lista de obj, da classe cromossomo.'''
        for obj_lista in lista:
            if obj == obj_lista:
                return True

        return False

    def fase_abelha_exploradoras(self):
        for i in range(self.quantidade_abelhas_exploradoras):
            '''Caso essa fonte de alimento tenha se esgotado, envia uma abelha exploradora,
            onde ela substitui essa fonte, por uma fonte de alimento aletoria'''
            #if self.lista_limites[i] == self.limite_tentativas_por_solucao:
            self.populacao[i] = cromossomo()

    def armazena_melhores_solucao(self, frente_pareto_solucao_atual):
        '''Caso a lista de melhores soluções esteja vazia, significa que está na primeira iteração,
        logo a primeira frente de pareto gerada, são as melhores soluções.'''
        if len(self.melhores_solucoes) == 0:
            # Evita a inserção de objs repetidos
            for obj_frente in frente_pareto_solucao_atual:
                if self.verifica_existe(obj_frente, self.melhores_solucoes):
                    self.melhores_solucoes.append(obj_frente)
            return

        for sol in frente_pareto_solucao_atual:
            '''Verifica, se a solução domina alguma das soluções que estão como melhores soluções até então,
            caso isso ocorra, remove as soluções que são dominadas, e então insere essa nova solução a lista
             de melhores soluções.'''

            # Evita inserção de objetos repetidos
            if self.verifica_existe(sol, self.melhores_solucoes):
                continue

            dominada = False
            lista_aux = []
            for m_sol in self.melhores_solucoes:
                if not sol < m_sol:
                    # Não domina uma das melhores soluções
                    lista_aux.append(m_sol)
                elif m_sol < sol:
                    # Domina a sol
                    dominada = True
                    break

            if not dominada:
                lista_aux.append(sol)
                ''' Substitui a lista de melhores soluções, por um nova lista,
                que contenha a nova solução que foi adicionada.'''
                self.melhores_solucoes = [] + lista_aux

    def salva_fluxos(self, name_algoritmo, GA_=False, grande_frente_pareto_GA_=None):

        if GA_:
            self.melhores_solucoes = grande_frente_pareto_GA_

        aux = ''
        arq = open("fluxos_" + name_algoritmo + ".txt", "w")
        for m_sol in self.melhores_solucoes:
            aux += str(m_sol.custo) + "\n"
            aux += str(m_sol.soma_tam_caminhos) + "\n"
            aux += str(m_sol.fluxo_aresta) + "\n"
            self.todos_fluxos.append(m_sol.fluxo_aresta)

        arq.write(aux)
        arq.close()

    def get_fluxos(self):
        return self.todos_fluxos

    def salva_parametros_usados(self, tempo_max_execucaoGA, quant_indv, num_pasta):
        string = 'rede utilizada: message.txt\n'
        string += 'pasta teste número: ' + str(num_pasta) + '\n'
        string += 'ciclos: ' + str(self.ciclos) + '\n'
        string += 'total_abelhas: ' + str(self.total_abelhas) + '\n'
        string += 'tempo_max_execucao: ' + str(self.tempo_max_execucao) + '\n'
        string += 'quantidade_abelhas_empregadas: ' + str(self.quantidade_abelhas_empregadas) + '\n'
        string += 'tamanho_populacao: ' + str(self.tamanho_populacao) + '\n'
        string += 'limite_tentativas_por_solucao: ' + str(self.limite_tentativas_por_solucao) + '\n'
        string += 'quantidade_abelhas_observadoras: ' + str(self.quantidade_abelhas_observadoras) + '\n'
        string += 'quantidade_abelhas_exploradoras: ' + str(self.quantidade_abelhas_exploradoras) + '\n'
        string += 'tempo_max_execucao GA: ' + str(tempo_max_execucaoGA) + '\n'
        string += 'quant_indv_do_abc_para_GA: ' + str(quant_indv) + '\n'

        arq = open('parametros_utilizados.txt', 'w')
        arq.write(string)
        arq.close()

    def salva_custos_e_soma_caminho_ordenado(self, GA_=False, grande_frente_pareto_GA_=None):

        nome_arq = "custos_e_soma_caminho_ABC.txt"
        if GA_:
            self.melhores_solucoes = grande_frente_pareto_GA_
            nome_arq = "custos_e_soma_caminho_GA.txt"

        string = ''
        lista_aux = []
        for i in range(len(self.melhores_solucoes)):
            lista_aux.append([self.melhores_solucoes[i].custo, self.melhores_solucoes[i].soma_tam_caminhos, i])

        lista_aux.sort()
        for pos in lista_aux:
            string += "SOLUÇÃO " + str(pos[2]) + ", Custo: " + str(pos[0]) + '\n'
            string += "SOLUÇÃO " + str(pos[2]) + ", soma_tam_caminhos: " + str(pos[1]) + '\n'

        arq = open(nome_arq, 'w')
        arq.write(string)
        arq.close()

    def gambiarra_suprema_sinistra_verifica_chegou14(self):
        for sol in self.melhores_solucoes:
            aux___ = str(sol.custo)
            if aux___[0] == '1' and aux___[1] == '4':
                return True

        return False

    def execute_abc(self):
        time_ini = time.time()
        self.gera_populacao_inicial()
        self.monta_vetor_ranks()
        self.imprime_populacao()
        # Cada cromossomo já possui o seu fitness embutido, logo não é necessario fazer a etapa de fitness da geração
        self.monta_vetor_ranks()
        self.melhores_solucoes = self.get_frente_pareto_geracao_atual()

        Tinicio = time.time()
        while (time.time() - Tinicio) < self.tempo_max_execucao:
            print(f"------------------ ciclo -> {self.ciclos} ------------------")
            print("FASE DAS ABELHAS EMPREGADAS")
            self.fase_abelha_empregadas()
            # Monta o vetor de propabilidades
            print("FASE DAS ABELHAS CALCULA VETOR DE PIS")
            lista_pis = self.calcula_pis(self.calcula_somatorio_fitness())
            print("FASE DAS ABELHAS OBERSADORAS")
            self.fase_abelha_observadoras(lista_pis)
            self.monta_vetor_ranks()
            print("vetor ranks: ", self.ranks)
            frente_pareto_atual = self.get_frente_pareto_geracao_atual()
            self.armazena_melhores_solucao(frente_pareto_atual)
            print("FASE DAS ABELHAS EXPLORADORAS")
            self.fase_abelha_exploradoras()
            print("-------------------------------------------------")
            self.ciclos += 1

            # if self.gambiarra_suprema_sinistra_verifica_chegou14():
            #     print("Inicio: ", Tinicio)
            #     print("Final: ", time.time() - Tinicio)
            #     break

        print(" !FIM DA EXECUÇÃO!\nMELHORES SOLUÇÕES ENCONTRADAS: ")
        self.imprime_custo_e_soma_caminho_solucao()

'''
--------------------------------- PARAMETROS DO ABC ---------------------------------

SN -> Total de abelhas na população, sendo que, metade delas conehcem a fonte de alimento,
e a outra metade fará escolha de acordo com a qualidade da fonte. Logo, metade são abelhas
campeiras, e a outra metade são abelhas observadoras.

tamanho da população inicial -> SN/2

Cada solução xi é um vetor D-dimensional, sendo D o número de variáveis de projeto do problema

C -> Quantidade de ciclos que algoritmo vai repetir

MP -> Tamanho da população

Número de abelhas empregadas é igual ao número de soluções na população
-> total_abelhas = SN
-> tam_populacao_inicial = SN/2
-> limite_tentativas_por_solucao = Quantas vezes uma abelha tanta melhorar a solução até abandonar ela
->
'''

# Teste feitos com limitação de execução de no maximo 1h(3600s)
quant_tempo_duracao = args.QT_ABC

total_abelhas = args.TA_ABC

obj = ABC("message.txt", tempo_max_execucao=quant_tempo_duracao,quant_abelhas=total_abelhas)
obj.execute_abc()
print("Quantidade de ciclos executados: ", obj.ciclos)

name = 's'
while name != 'n' and name != 's':
    name = input("Plotar o gráfico?(s/n)").lower()
    print(name)

nome_pasta = ''

quant_indv = args.Q_indv
if len(obj.melhores_solucoes) < quant_indv:
    quant_indv = len(obj.melhores_solucoes)

total_tempo_execucaoAG = args.QT_GA

if name == 's':
    # Cria a pasta que irá armazenar os plots
    caminho_pasta_resultado = seleciona_nome_pasta_e_cria_pasta(args.N_teste)
    # Salva os fluxos no arquivo de texto, e preenche lista de fluxos
    obj.salva_fluxos(name_algoritmo="ABC", GA_=False, grande_frente_pareto_GA_=None)
    # Salva os parametro utilizados
    obj.salva_parametros_usados(total_tempo_execucaoAG, quant_indv, args.N_teste)
    # Salva os custos e soma caminhos das soluções
    obj.salva_custos_e_soma_caminho_ordenado()
    # Desenha o grafico de todos os fluxos das soluções encontradas
    desenha_grafico_fluxo(G, obj.get_fluxos())

obj.melhores_solucoes.sort(key=lambda x:x.custo)

print("Tipo da variavel obj: ", type(obj))
lista_com_melhores_solucoes = obj.melhores_solucoes
print("Tipo da posição da lista: ", type(lista_com_melhores_solucoes[0]))
print("--------------------------------------")
for obj_j in lista_com_melhores_solucoes:
    print(obj_j.custo)
print("--------------------------------------")

print("Enviando população para o GA!")
obj_GA = GA(populacaoABC=lista_com_melhores_solucoes, quant_indv=quant_indv)
frente_de_pareto_GA = obj_GA.Executa(total_tempo_execucaoAG)
#print("Frente de Pareto do GA: ", frente_de_pareto_GA)
print("SALVANDO FRENTE DE PARETO DO GA")
obj.salva_custos_e_soma_caminho_ordenado(GA_=True, grande_frente_pareto_GA_=frente_de_pareto_GA)
obj.salva_fluxos(name_algoritmo="GA", GA_=True, grande_frente_pareto_GA_=frente_de_pareto_GA)


# -*- coding: utf-8 -*-
"""
Created on Thu May 18 09:28:06 2017

@author: Trail1
"""

import os, os.path
from PIL import Image
from os import walk
from datetime import datetime
import pandas as pd
import numpy as np

rgbcode_dict = { (99, 214, 104, 255) : "G",
                 (255, 151, 77, 255) : "O",
                 (242, 60, 50, 255)  : "R",
                 (129, 31, 31, 255)  : "D",
                 (255, 255, 255, 255): "W"}

def str2tuple(tuple_str):
    r, g, b, alpha = tuple_str.replace("(","").replace(")","").split(",")
    return tuple([int(r), int(g), int(b), int(alpha)])
#rgb_df1 = pd.read_csv("rgb_traffic.csv")
#rgb_df1["rgb_code"] = rgb_df1["RGB"].apply(lambda x : str2tuple(x))

png_file_dir = r"""./screenshots_cropped_DC"""

png_flielist = []
for root, dirs, files in walk(png_file_dir):
    for file in files:
        if file.endswith('.png'):
            png_flielist.append(file)

png_flielist = png_flielist[:]

rgb_collection = []
unique_rgb_collection = []
for i, png in enumerate(png_flielist[:]):
    png_datetime_str = png.split(".")[0].split("_")[1]+"_"+png.split(".")[0].split("_")[2]
    png_datetime = datetime.strptime(png_datetime_str, "%Y%m%d_%H%M%S")
    print(png, i+1, "/", len(png_flielist))
    img1 = Image.open(os.path.join(png_file_dir,r"""DC_{0}.png""".format(png_datetime_str)))

    newimdata = []
    for color in img1.getdata():
        if color in [(99, 214, 104, 255), (255, 151, 77, 255), (242, 60, 50, 255), (129, 31, 31, 255)]:
            # G, O, R, D
            # D: (145, 59, 59, 255) - (R, G, B, alpha)
            #    (137, 45, 45, 255)
            #
        #if color in [(132, 202, 80, 255), (222, 241, 208, 255), (165, 216, 127, 255)]:
            #print("XXX")
            newimdata.append(color)
        else:
            newimdata.append((255, 255, 255, 255))

    img2 = Image.new(img1.mode,img1.size)
    img2.putdata(newimdata)
    #img2.save(r"""test_ATL_{0}.png""".format(png_datetime_str))

    df1 = pd.DataFrame({"rgb" : newimdata})
    df1["DROG"] = df1["rgb"].apply(lambda x : rgbcode_dict[x])
    df1["datetime"] = png_datetime_str
    df2 = pd.pivot_table(df1, values="rgb", index="datetime", columns="DROG", aggfunc="count").reset_index()
    rgb_collection.append(df2)

df3 = pd.concat(rgb_collection)

df3.to_csv("DC_screenshots_cropped_DROG_Counts.csv")


import os
import sqlite3
from sqlite3 import Error

############## Conxão com Banco de Dados ##############
dbfile = 'C:\\Users\\magal\\Desktop\\input\\mysite\\db.sqlite3'
con = sqlite3.connect(dbfile)
cur = con.cursor()

############## Variavel global ##############
idPessoal = ""

############## Criar tabela para dados Pessoais - PESSOAL ##############
def createTable():
    try:
        cur.execute('''CREATE TABLE PESSOAL (
                        ID_PESSOAL INTEGER PRIMARY KEY AUTOINCREMENT,
                        NAME       VARCHAR (10, 200),
                        TELEFONE   VARCHAR (10, 11),
                        EMAIL      VARCHAR (10, 200),
                        NASCIMENTO VARCHAR (10, 100)
                    )''')
        con.commit()
    except Error as er:
        print(er)

############## Inserir Dados Pessoais na Tabela ##############
def insertData():
    flag = "n"
    while flag!="s":
        try:
            nome = input("Digite seu nome: ")
            telefone = input("Digite seu telefone: ")
            email = input("Digite seu email: ")
            nasc = input("Digite sua data de nascimento: ")
            dadosPessoais = "INSERT INTO PESSOAL (NAME, TELEFONE, EMAIL, NASCIMENTO) VALUES('"+nome+"', '"+telefone+"', '"+email+"', '"+nasc+"')"
            os.system('cls')
            print("Cadastro efetuado com sucesso!")
            flag = input("Deseja parar de cadastrar dados? [s/n]")
            cur.execute(dadosPessoais)
            os.system('cls')
            con.commit()
        except Error as er:
            print(er)

############## Consultar perfis de Dados Pessoais na Tabela ##############
def viewData():
    try:
        allData = "SELECT * FROM PESSOAL"
        registros = cur.execute(allData)
        for r in registros:
            print(r)
        con.commit()
    except Error as er:
        print(er)

############## Atualizar Dados Pessoais na Tabela ##############
def updateData():
    try:
        idPessoal = input("Escolha qual perfil deseja editar: ")
        newName = input("Digite o novo nome: ")
        newTel = input("Digite o novo telefone: ")
        newMail = input("Digite o novo email: ")
        newBorn = input("Digite a nova dota de nascimento: ")

        att = "UPDATE PESSOAL SET NAME = '"+newName+"', TELEFONE = '"+newTel+"', EMAIL = '"+newMail+"', NASCIMENTO = '"+newBorn+"' WHERE ID_PESSOAL = "+idPessoal+""
        cur.execute(att)
        con.commit()
    except Error as er:
        print(er)

############## Deletar Dados Pessoais na Tabela ##############
def delData():
    try:
        idPessoal = input("Escolha qual perfil deseja excluir: ")
        deletarPessoal = "DELETE FROM PESSOAL WHERE ID_PESSOAL="+idPessoal+""
        deletado = "SELECT * FROM PESSOAL WHERE ID_PESSOAL="+idPessoal+""
        deleted = cur.execute(deletado)
        for d in deleted:
            print(" O perfil: " + str(d) + " foi deletado com sucesso!")
        cur.execute(deletarPessoal)
        con.commit()
        os.system('pause')
    except Error as er:
        print(er)

############## Executar funções para teste ##############
createTable()
#insertData()
#updateData()
#viewData()
#con.commit()
#con.close()


#!/usr/bin/env python3
import contextlib
import logging
import os
import sys

import boto3
import requests
import retrying
from botocore import exceptions

log = logging.getLogger(__name__)
logging.basicConfig(format='[%(levelname)s] %(message)s', level='INFO')

def is_rate_limit_error(exception):
    if exception in [exceptions.ClientError, exceptions.WaiterError]:
        if isinstance(exception, exceptions.ClientError):
            error_code = exception.response['Error']['Code']
        elif isinstance(exception, exceptions.WaiterError):
            error_code = exception.last_response['Error']['Code']
        if error_code in ['Throttling', 'RequestLimitExceeded']:
            print('AWS rate-limit encountered!')
            return True
    return False

@contextlib.contextmanager
def _remove_env_vars(*env_vars):
    environ = dict(os.environ)

    for env_var in env_vars:
        try:
            del os.environ[env_var]
        except KeyError:
            pass

    try:
        yield
    finally:
        os.environ.clear()
        os.environ.update(environ)

@retrying.retry(
    wait_exponential_multiplier=1000,
    wait_exponential_max=300 * 1000,
    stop_max_delay=1800 * 1000,
    retry_on_exception=is_rate_limit_error)
def delete_ec2_volume(name, timeout=600):
    """Delete an EC2 EBS volume by its "Name" tag

    Args:
        timeout: seconds to wait for volume to become available for deletion

    """
    def _force_detach_volume(volume):
        log.info("Force detaching all volume attachments.")
        for attachment in volume.attachments:
            try:
                log.info("Volume has attachment: {}".format(attachment))
                log.info("Detaching volume from instance: {}".format(attachment['InstanceId']))
                volume.detach_from_instance(
                    DryRun=False,
                    InstanceId=attachment['InstanceId'],
                    Device=attachment['Device'],
                    Force=True)
            except exceptions.ClientError as exc:
                log.exception("Failed to detach volume")
                # See the following link for the structure of the exception:
                # https://github.com/boto/botocore/blob/4d4c86b2bdd4b7a8e110e02abd4367f07137ca47/botocore/exceptions.py#L346
                err_message = exc.response['Error']['Message']
                err_code = exc.response['Error']['Code']
                # See the following link for details of the error message:
                # https://jira.mesosphere.com/browse/DCOS-37441?focusedCommentId=156163&page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel#comment-156163
                available_msg = "is in the 'available' state"
                if err_code == 'IncorrectState' and available_msg in err_message:
                    log.info("Ignoring benign exception")
                    return
                raise

    @retrying.retry(wait_fixed=30 * 1000, stop_max_delay=timeout * 1000,
                    retry_on_exception=lambda exc: isinstance(exc, exceptions.ClientError))
    def _delete_volume(volume):
        log.info("Trying to delete volume...")
        _force_detach_volume(volume)
        try:
            log.info("Issuing volume.delete()")
            volume.delete()  # Raises ClientError (VolumeInUse) if the volume is still attached.
        except exceptions.ClientError:
            log.exception("volume.delete() failed.")
            raise

    def _get_current_aws_region():
        try:
            return requests.get('http://169.254.169.254/latest/meta-data/placement/availability-zone').text.strip()[:-1]
        except requests.RequestException as ex:
            print("Can't get AWS region from instance metadata: {}".format(ex))
            return None

    # Remove AWS environment variables to force boto to use IAM credentials.
    with _remove_env_vars('AWS_ACCESS_KEY_ID', 'AWS_SECRET_ACCESS_KEY'):
        volumes = list(boto3.session.Session(
            # We assume we're running these tests from a cluster node, so we
            # can assume the region for the instance on which we're running is
            # the same region in which any volumes were created.
            region_name=_get_current_aws_region(),
        ).resource('ec2').volumes.filter(Filters=[{'Name': 'tag:Name', 'Values': [name]}]))

    if len(volumes) == 0:
        raise Exception('no volumes found with name {}'.format(name))
    elif len(volumes) > 1:
        raise Exception('multiple volumes found with name {}'.format(name))
    volume = volumes[0]
    log.info("Found volume {}".format(volume))

    try:
        _delete_volume(volume)
    except retrying.RetryError as ex:
        raise Exception('Operation was not completed within {} seconds'.format(timeout)) from ex

if __name__ == '__main__':
    log.info("Deleting volume {}".format(sys.argv[1]))
    delete_ec2_volume(sys.argv[1])


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

import argparse
import configparser
import re
import os
import sys
import pathlib as pl

import datetime as dt

from nrc_spifpy.input import DMTMonoFile
from nrc_spifpy.input import DMTGreyFile
from nrc_spifpy.input import SPECFile
from nrc_spifpy.input import TwoDFile
from nrc_spifpy.spif import SPIFCore

inst_dict = {'2DC': TwoDFile,
             '2DP': TwoDFile,
             'CIP': DMTMonoFile,
             'CIPGS': DMTGreyFile,
             'PIP': DMTMonoFile,
             '2DS': SPECFile,
             'HVPS': SPECFile}

def extract():

     # Get the parser and grab the args

     parser = get_parser()
     args = parser.parse_args()

     # Check the args, make sure everything is OK before using
     # the arguments to do anything with them

     args_checker = ArgsChecker(args)
     args_checker.check_args()

     # Do some more detailed checking of the times

     time_checker = SPIFStartEndTimeChecker(args.filename, args.config)
     time_checker.check_time_args(args.start, args.end)

     # Transform the arguments to the proper forms for smooth processing

     args_transformer = ArgsTransformer(args)
     transformed_args = args_transformer.transform_args()

     spif_core = call_spifcore(transformed_args)
     spif_core.process(processors=transformed_args['nproc'])

def get_parser():
    parser = argparse.ArgumentParser(description='Processes raw OAP data to' +
                                                 ' SPIF formatted NetCDF file')
    parser.add_argument('filename',
                        type=str,
                        help= 'path to raw instrument file to process.')

    parser.add_argument('config',
                        type=str,
                        help= 'path to config file to use for processing')

    parser.add_argument('-o',
                        dest='output',
                        type=str,
                        help='Filename to use for SPIF output',
                        default=None)

    parser.add_argument('--start',
                        dest='start',
                        type=str,
                        help='The start time in the file to begin processing.',
                        default=None)

    parser.add_argument('--end',
                        dest='end',
                        type=str,
                        help='The end time in the file to begin processing.',
                        default=None)

    parser.add_argument('-n',
                        dest='nproc',
                        type=int,
                        help='number of processors to use in processing',
                        default=None)

    return parser

def call_spifcore(transformed_args):
     inst_name = get_inst_name(transformed_args)
     filename = transformed_args['filename']
     outfile = transformed_args['output']
     config = transformed_args['config']
     start_time = transformed_args['start']
     end_time = transformed_args['end']

     spif_core = SPIFCore(
          inst_dict[inst_name],
          filename,
          outfile,
          config,
          start_time = start_time,
          end_time = end_time
     )

     return spif_core

def get_inst_name(transformed_args):
     config = configparser.ConfigParser(allow_no_value=True)

     config.read(transformed_args['config'])
     inst_name = config['instrument'].get('instrument_name', None)

     return inst_name

class ArgsChecker:
     def __init__(self, args):
          self.args = args

     def check_args(self):
          self.check_filename(self.args.filename)
          self.check_config(self.args.config)

          if self.args.output is not None : self.check_output(self.args.output)
          if self.args.start is not None : self.check_time_args(self.args.start)
          if self.args.end is not None : self.check_time_args(self.args.end)
          if self.args.nproc is not None : self.check_nproc(self.args.nproc)

     def check_filename(self, filename):

          try:
               assert pl.Path(filename).is_file()
          except AssertionError:
               print(f"ERROR : The file {filename} is not a valid file")
               raise

          try:
               assert pl.Path(filename).stat().st_size
          except AssertionError:
               print(f"ERROR : The file {filename} is an empty file")
               raise

     def check_config(self, config_file):
          config = configparser.ConfigParser(allow_no_value=True)

          config.read(config_file)
          inst_name = config['instrument'].get('instrument_name', None)

          try:
               assert inst_name in inst_dict
          except AssertionError:
               print(f"ERROR : The provided instrument type {inst_name} from config file {config} is invalid. Please provide a valid instrument from the following list {' | '.join([k for k in inst_dict.keys()])}")
               raise

     def check_output(self, output):

          try:
               open(output, 'w')
          except OSError:
               print(f"ERROR : The provided output filename {output} is not a valid filename.")
               raise

          try:
               assert pl.Path(output).suffix == '.nc'
          except AssertionError:
               print(f"ERROR : The provided filename {output} does not have a .nc file ending")
               raise

     def check_time_args(self, time):
          try:
               assert re.match('[0-9]{2}:[0-9]{2}:[0-9]{2}', time)
          except AssertionError:
               print(f"ERROR : The provided time {time} does not match the required format of HH:MM:SS")

          split_time = [int(x) for x in time.split(':')]

          try:
               assert split_time[0] < 24 and split_time[0] >= 0
               assert split_time[1] < 60 and split_time[0] >= 0
               assert split_time[2] < 60 and split_time[0] >= 0
          except AssertionError:
               print(f"ERROR : The provided time {time} does not have proper digits")
               raise

     def check_nproc(self, nproc):
          try:
               assert isinstance(nproc, int)
          except AssertionError:
               print(f"ERROR : The provided argument for nproc {nproc} is not a number.")
               raise

          try:
               assert nproc > 0
          except AssertionError:
               print(f"ERROR : The provided argument nproc {nproc} is less than one")
               raise

class SPIFStartEndTimeChecker:

     def __init__(self, filename, config_file):
          self.filename = filename
          self.config_file = config_file

          self.start_time = None
          self.end_time = None

          self.get_start_end_time()

     def get_start_end_time(self):
          config = configparser.ConfigParser(allow_no_value=True)

          config.read(self.config_file)
          inst_name = config['instrument'].get('instrument_name', None)

          inst_class = inst_dict[inst_name]

          self.inst_file = inst_class(
               self.filename,
               config['instrument']['instrument_name'],
               config['resolution']['value']
          )

          self.inst_file.read()

          file_datetimes = self.inst_file.datetimes

          self.file_time_start = self.inst_file.start_date - file_datetimes[0].replace(microsecond = 0)
          self.file_time_end = file_datetimes[-1].replace(microsecond = 0) - self.inst_file.start_date

     def check_time_args(self, start_time, end_time):
          if start_time is not None:
               start_time_sec = [int(x) for x in start_time.split(':')]
               start_time_sec = dt.timedelta(
                    seconds = start_time_sec[0]*3600 + start_time_sec[1]*60 + start_time_sec[2]
               )

          if end_time is not None:
               end_time_sec = [int(x) for x in end_time.split(':')]
               end_time_sec = dt.timedelta(
                    seconds = end_time_sec[0]*3600 + end_time_sec[1]*60 + end_time_sec[2]
               )

          if (start_time is not None) and (end_time is not None):
               try:
                    assert start_time_sec < end_time_sec
               except AssertionError:
                    print(f"ERROR : Start time {start_time} is greater than end time {end_time}")
                    raise

          if start_time is not None:
               try:
                    self.check_time_in_file(start_time_sec)
               except AssertionError:
                    print(f"ERROR : Start time {start_time} is not in the file time range")
                    raise

          if end_time is not None:
               try:
                    self.check_time_in_file(end_time_sec)
               except AssertionError:
                    print(f"ERROR : End time {end_time} is not in the file time range")
                    raise

     def check_time_in_file(self, time):
          assert time >= self.file_time_start
          assert time <= self.file_time_end

class ArgsTransformer:

     def __init__(self, args) -> None:
         self.args = args

         self.transformed_args = {
              'filename':None,
              'config':None,
              'output':None,
              'start':None,
              'end':None,
              'nproc':None,
              'aux_file':None,
              'aux_config':None,
         }

     def transform_args(self):
          self.transform_filename()
          self.transform_config()
          self.transform_output()
          self.transform_start()
          self.transform_end()
          self.transform_nproc()

          return self.transformed_args

     def transform_filename(self):
          self.transformed_args['filename'] = pl.Path(self.args.filename)

     def transform_config(self):
          self.transformed_args['config'] = self.args.config

     def transform_output(self):
          if self.args.output == None:
               input = pl.Path(self.args.filename)
               self.transformed_args['output'] = input.parent / (input.name.replace('.','_') + '.nc')
          else:
               self.transformed_args['output'] = pl.Path(self.args.output)

     def transform_start(self):
          if self.args.start is None:
               self.transformed_args['start'] = None
          else:
               start = [int(x) for x in self.args.start.split(':')]
               start = start[0]*3600 + start[1]*60 + start[2]
               self.transformed_args['start'] = dt.timedelta(seconds = start)

     def transform_end(self):
          if self.args.end is None:
               self.transformed_args['end'] = None
          else:
               end = [int(x) for x in self.args.end.split(':')]
               end = end[0]*3600 + end[1]*60 + end[2]
               self.transformed_args['end'] = dt.timedelta(seconds = end)

     def transform_nproc(self):
          self.transformed_args['nproc'] = self.args.nproc


# ActivitySim
# See full license in LICENSE.txt.
import itertools
import logging
import multiprocessing
import os
from builtins import range
from contextlib import contextmanager

import numpy as np
import pandas as pd
import psutil

from activitysim.core import config, inject, simulate, util

logger = logging.getLogger(__name__)

RAWARRAY = False
DTYPE_NAME = "float32"
RESCALE = 1000

DYNAMIC = "dynamic"
STATIC = "static"
TRACE = "trace"

MEMO_STACK = []

@contextmanager
def memo(tag, console=False, disable_gc=True):
    yield  # make this a noop for performance
    # t0 = time.time()
    #
    # MEMO_STACK.append(tag)
    #
    # gc_was_enabled = _gc.isenabled()
    # if gc_was_enabled:
    #     _gc.collect()
    #     if disable_gc:
    #         _gc.disable()
    #
    # previous_mem = psutil.Process().memory_info().rss
    # try:
    #     yield
    # finally:
    #     elapsed_time = time.time() - t0
    #
    #     current_mem = psutil.Process().memory_info().rss
    #     marginal_mem = current_mem - previous_mem
    #     mem_str = f"net {util.GB(marginal_mem)} ({util.INT(marginal_mem)}) total {util.GB(current_mem)}"
    #
    #     if gc_was_enabled and disable_gc:
    #         _gc.enable()
    #     if _gc.isenabled():
    #         _gc.collect()
    #
    #     if console:
    #         print(f"MEMO {tag} Time: {util.SEC(elapsed_time)} Memory: {mem_str} ")
    #     else:
    #         logger.debug(f"MEM  {tag} {mem_str} in {util.SEC(elapsed_time)}")
    #
    #     MEMO_STACK.pop()

class TVPBCache(object):
    """
    Transit virtual path builder cache for three zone systems
    """

    def __init__(self, network_los, uid_calculator, cache_tag):

        # lightweight until opened

        self.cache_tag = cache_tag

        self.network_los = network_los
        self.uid_calculator = uid_calculator

        self.is_open = False
        self.is_changed = False
        self._data = None

    @property
    def cache_path(self):
        file_type = "mmap"
        return os.path.join(config.get_cache_dir(), f"{self.cache_tag}.{file_type}")

    @property
    def csv_trace_path(self):
        file_type = "csv"
        return os.path.join(config.get_cache_dir(), f"{self.cache_tag}.{file_type}")

    def cleanup(self):
        """
        Called prior to
        """
        if os.path.isfile(self.cache_path):
            logger.debug(f"deleting cache {self.cache_path}")
            try:
                os.unlink(self.cache_path)
            except PermissionError:
                # windows may complain if the cache was not completely closed
                # in an earlier run, so let's just cache in a new file
                n = 0
                while True:
                    n += 1
                    candidate = os.path.join(
                        config.get_cache_dir(), f"{self.cache_tag}.{n}.mmap"
                    )
                    if not os.path.isfile(candidate):
                        self.cache_tag = f"{self.cache_tag}.{n}"
                        break

    def write_static_cache(self, data):

        assert not self.is_open
        assert self._data is None
        assert not self.is_changed

        data = data.reshape(self.uid_calculator.fully_populated_shape)

        # np.savetxt(self.csv_trace_path, data, fmt='%.18e', delimiter=',')

        logger.debug(f"#TVPB CACHE write_static_cache df {data.shape}")

        mm_data = np.memmap(
            self.cache_path, shape=data.shape, dtype=DTYPE_NAME, mode="w+"
        )
        np.copyto(mm_data, data)
        mm_data._mmap.close()
        del mm_data

        logger.debug(
            f"#TVPB CACHE write_static_cache wrote static cache table "
            f"({data.shape}) to {self.cache_path}"
        )

    def open(self):
        """
        open STATIC cache and populate with cached data

        if multiprocessing
            always STATIC cache with data fully_populated preloaded shared data buffer
        """
        # MMAP only supported for fully_populated_uids (STATIC)
        # otherwise we would have to store uid index as float, which has roundoff issues for float32

        assert not self.is_open, f"TVPBCache open called but already open"
        self.is_open = True

        if self.network_los.multiprocess():
            # multiprocessing usex preloaded fully_populated shared data buffer
            with memo("TVPBCache.open get_data_and_lock_from_buffers"):
                data, _ = self.get_data_and_lock_from_buffers()
            logger.info(
                f"TVPBCache.open {self.cache_tag} STATIC cache using existing data_buffers"
            )
        elif os.path.isfile(self.cache_path):
            # single process ought have created a precomputed fully_populated STATIC file
            data = np.memmap(self.cache_path, dtype=DTYPE_NAME, mode="r")

            # FIXME - why leave memmap open - maybe should copy since it will be read into memory when accessed anyway
            # mm_data = np.memmap(self.cache_path, dtype=DTYPE_NAME, mode='r')
            # data = np.empty_like(mm_data)
            # np.copyto(data, mm_data)
            # mm_data._mmap.close()
            # del mm_data

            logger.info(
                f"TVPBCache.open {self.cache_tag} read fully_populated data array from mmap file"
            )
        else:
            raise RuntimeError(
                f"Pathbuilder cache not found. Did you forget to run initialize tvpb?"
                f"Expected cache file: {self.cache_path}"
            )

        # create no-copy pandas DataFrame from numpy wrapped RawArray or Memmap buffer
        column_names = self.uid_calculator.set_names
        with memo("TVPBCache.open data.reshape"):
            data = data.reshape(
                (-1, len(column_names))
            )  # reshape so there is one column per set

        # data should be fully_populated and in canonical order - so we can assign canonical uid index
        with memo("TVPBCache.open uid_calculator.fully_populated_uids"):
            fully_populated_uids = self.uid_calculator.fully_populated_uids

        # check fully_populated, but we have to take order on faith (internal error if it is not)
        assert data.shape[0] == len(fully_populated_uids)

        self._data = data
        logger.debug(f"TVPBCache.open initialized STATIC cache table")

    def close(self, trace=False):
        """
        write any changes, free data, and mark as closed
        """

        assert self.is_open, f"TVPBCache close called but not open"

        self.is_open = False
        self._data = None
        self.cache_type = None

    @property
    def data(self):
        assert self._data is not None
        return self._data

    def allocate_data_buffer(self, shared=False):
        """
        allocate fully_populated_shape data buffer for cached data

        if shared, return a multiprocessing.Array that can be shared across subprocesses
        if not shared, return a numpy ndarrray

        Parameters
        ----------
        shared: boolean

        Returns
        -------
            multiprocessing.Array or numpy ndarray sized to hole fully_populated utility array
        """

        assert not self.is_open
        assert shared == self.network_los.multiprocess()

        dtype_name = DTYPE_NAME
        dtype = np.dtype(DTYPE_NAME)

        # multiprocessing.Array argument buffer_size must be int, not np.int64
        shape = self.uid_calculator.fully_populated_shape
        buffer_size = util.iprod(self.uid_calculator.fully_populated_shape)

        csz = buffer_size * dtype.itemsize
        logger.info(
            f"TVPBCache.allocate_data_buffer allocating data buffer "
            f"shape {shape} buffer_size {util.INT(buffer_size)} total size: {util.INT(csz)} ({util.GB(csz)})"
        )

        if shared:
            if dtype_name == "float64":
                typecode = "d"
            elif dtype_name == "float32":
                typecode = "f"
            else:
                raise RuntimeError(
                    "allocate_data_buffer unrecognized dtype %s" % dtype_name
                )

            if RAWARRAY:
                with memo("TVPBCache.allocate_data_buffer allocate RawArray"):
                    buffer = multiprocessing.RawArray(typecode, buffer_size)
                logger.info(
                    f"TVPBCache.allocate_data_buffer allocated shared multiprocessing.RawArray as buffer"
                )
            else:
                with memo("TVPBCache.allocate_data_buffer allocate Array"):
                    buffer = multiprocessing.Array(typecode, buffer_size)
                logger.info(
                    f"TVPBCache.allocate_data_buffer allocated shared multiprocessing.Array as buffer"
                )

        else:
            buffer = np.empty(buffer_size, dtype=dtype)
            np.copyto(buffer, np.nan)  # fill with np.nan

            logger.info(
                f"TVPBCache.allocate_data_buffer allocating non-shared numpy array as buffer"
            )

        return buffer

    def load_data_to_buffer(self, data_buffer):
        # 1) we are called before initialize_los, there is a saved cache, and it will be honored
        # 2) we are called before initialize_los and there is no saved cache yet
        # 3) we are resuming after initialize_los and so there must be a saved cache

        assert not self.is_open

        # wrap multiprocessing.Array (or RawArray) as a numpy array
        with memo("TVPBCache.load_data_to_buffer frombuffer"):
            if RAWARRAY:
                np_wrapped_data_buffer = np.ctypeslib.as_array(data_buffer)
            else:
                np_wrapped_data_buffer = np.ctypeslib.as_array(data_buffer.get_obj())

        if os.path.isfile(self.cache_path):
            with memo("TVPBCache.load_data_to_buffer copy memmap"):
                data = np.memmap(self.cache_path, dtype=DTYPE_NAME, mode="r")
                np.copyto(np_wrapped_data_buffer, data)
                data._mmap.close()
                del data
            logger.debug(
                f"TVPBCache.load_data_to_buffer loaded data from {self.cache_path}"
            )
        else:
            np.copyto(np_wrapped_data_buffer, np.nan)
            logger.debug(f"TVPBCache.load_data_to_buffer - saved cache file not found.")

    def get_data_and_lock_from_buffers(self):
        """
        return shared data buffer previously allocated by allocate_data_buffer and injected mp_tasks.run_simulation
        Returns
        -------
        either multiprocessing.Array and lock or multiprocessing.RawArray and None according to RAWARRAY
        """
        data_buffers = inject.get_injectable("data_buffers", None)
        assert self.cache_tag in data_buffers  # internal error
        logger.debug(f"TVPBCache.get_data_and_lock_from_buffers")
        data_buffer = data_buffers[self.cache_tag]
        if RAWARRAY:
            data = np.ctypeslib.as_array(data_buffer)
            lock = None
        else:
            data = np.ctypeslib.as_array(data_buffer.get_obj())
            lock = data_buffer.get_lock()

        return data, lock

class TapTapUidCalculator(object):
    """
    Transit virtual path builder TAP to TAP unique ID calculator for three zone systems
    """

    def __init__(self, network_los):

        self.network_los = network_los

        # ensure that tap_df has been loaded
        # (during multiprocessing we are initialized before network_los.load_data is called)
        assert network_los.tap_df is not None
        self.tap_ids = network_los.tap_df["TAP"].values

        self.segmentation = network_los.setting(
            "TVPB_SETTINGS.tour_mode_choice.tap_tap_settings.attribute_segments"
        )

        # e.g. [(0, 'AM', 'walk'), (0, 'AM', 'walk')...]) for attributes demographic_segment, tod, and access_mode
        self.attribute_combination_tuples = list(
            itertools.product(*list(self.segmentation.values()))
        )

        # ordinalizers - for mapping attribute values to canonical ordinal values for uid computation
        # (pandas series of ordinal position with attribute value index (e.g. map tod value 'AM' to 0, 'MD' to 1,...)
        # FIXME dict might be faster than Series.map() and Series.at[]?
        self.ordinalizers = {}
        for k, v in self.segmentation.items():
            self.ordinalizers[k] = pd.Series(range(len(v)), index=v)
        # orig/dest go last so all rows in same 'skim' end up with adjacent uids
        self.ordinalizers["btap"] = pd.Series(
            range(len(self.tap_ids)), index=self.tap_ids
        )
        self.ordinalizers["atap"] = self.ordinalizers["btap"]

        # for k,v in self.ordinalizers.items():
        #     print(f"\ordinalizer {k}\n{v}")

        spec_name = self.network_los.setting(
            f"TVPB_SETTINGS.tour_mode_choice.tap_tap_settings.SPEC"
        )
        self.set_names = list(simulate.read_model_spec(file_name=spec_name).columns)

    @property
    def fully_populated_shape(self):
        # (num_combinations * num_orig_zones * num_dest_zones, num_sets)
        num_combinations = len(self.attribute_combination_tuples)
        num_orig_zones = num_dest_zones = len(self.tap_ids)
        num_rows = num_combinations * num_orig_zones * num_dest_zones
        num_sets = len(self.set_names)
        return (num_rows, num_sets)

    @property
    def skim_shape(self):
        # (num_combinations, num_od_rows, num_sets)
        num_combinations = len(self.attribute_combination_tuples)
        num_orig_zones = num_dest_zones = len(self.tap_ids)
        num_od_rows = num_orig_zones * num_dest_zones
        num_sets = len(self.set_names)
        return (num_combinations, num_od_rows, num_sets)

    @property
    def fully_populated_uids(self):
        num_combinations = len(self.attribute_combination_tuples)
        num_orig_zones = num_dest_zones = len(self.tap_ids)
        return np.arange(num_combinations * num_orig_zones * num_dest_zones)

    def get_unique_ids(self, df, scalar_attributes):
        """
        compute canonical unique_id for each row in df
        btap and atap will be in dataframe, but the other attributes may be either df columns or scalar_attributes

        Parameters
        ----------
        df: pandas DataFrame
            with btap, atap, and optionally additional attribute columns
        scalar_attributes: dict
            dict of scalar attributes e.g. {'tod': 'AM', 'demographic_segment': 0}
        Returns
        -------
        ndarray of integer uids
        """
        uid = np.zeros(len(df), dtype=int)

        # need to know cardinality and integer representation of each tap/attribute
        for name, ordinalizer in self.ordinalizers.items():

            cardinality = ordinalizer.max() + 1

            if name in df:
                # if there is a column, use it
                if name == "tod" and df[name].dtype.kind == "i":
                    # when time of day is an integer, assume it is already ordinalized
                    ticker = np.asanyarray(df[name])
                else:
                    ticker = np.asanyarray(df[name].map(ordinalizer))
                uid = uid * cardinality + ticker
            else:
                # otherwise it should be in scalar_attributes
                assert (
                    name in scalar_attributes
                ), f"attribute '{name}' not found in df.columns or scalar_attributes."
                ticker = ordinalizer.at[scalar_attributes[name]]
                uid = uid * cardinality + ticker

        return uid

    def get_od_dataframe(self, scalar_attributes):
        """
        return tap-tap od dataframe with unique_id index for 'skim_offset' for scalar_attributes

        i.e. a dataframe which may be used to compute utilities, together with scalar or column attributes

        Parameters
        ----------
        scalar_attributes: dict of scalar attribute name:value pairs

        Returns
        -------
        pandas.Dataframe
        """

        # create OD dataframe in ROW_MAJOR_LAYOUT
        num_taps = len(self.tap_ids)
        od_choosers_df = pd.DataFrame(
            data={
                "btap": np.repeat(self.tap_ids, num_taps),
                "atap": np.tile(self.tap_ids, num_taps),
            }
        )
        od_choosers_df.index = self.get_unique_ids(od_choosers_df, scalar_attributes)
        assert not od_choosers_df.index.duplicated().any()

        return od_choosers_df

    def get_skim_offset(self, scalar_attributes):
        # return ordinal position of this set of attributes in the list of attribute_combination_tuples
        offset = 0
        for name, ordinalizer in self.ordinalizers.items():
            cardinality = ordinalizer.max() + 1
            if name in scalar_attributes:
                offset = offset * cardinality + ordinalizer.at[scalar_attributes[name]]
        return offset

    def each_scalar_attribute_combination(self):
        # iterate through attribute_combination_tuples, yielding dict of scalar attribute name:value pairs

        # attribute names as list of strings
        attribute_names = list(self.segmentation.keys())
        for attribute_value_tuple in self.attribute_combination_tuples:

            # attribute_value_tuple is an tuple of attribute values - e.g. (0, 'AM', 'walk')
            # build dict of attribute name:value pairs - e.g. {'demographic_segment': 0, 'tod': 'AM', })
            scalar_attributes = {
                name: value
                for name, value in zip(attribute_names, attribute_value_tuple)
            }

            yield scalar_attributes

    def scalar_attribute_combinations(self):
        attribute_names = list(self.segmentation.keys())
        attribute_tuples = self.attribute_combination_tuples
        x = [list(t) for t in attribute_tuples]
        df = pd.DataFrame(data=x, columns=attribute_names)
        df.index.name = "offset"
        return df


import numpy as np
import scipy.sparse as sp
from time import time
from Dataset import Dataset
import subprocess as sub
import pandas as pd
import sys,pdb

class ItemView_Dataset(Dataset):
    def __init__(self,args):
        Dataset.__init__(self,args)

        self.same_entity_list       = eval(args.same_entity)
        assert len(self.same_entity_list) == args.num_views, 'length of same_entity and num_views should be same.'

        self.item_view_matrix,self.num_row,self.num_col,self.adjacency_view_matrix = [],[],[],[]
        for view in range(args.num_views):
            num_row, num_col = self.get_row_column_count(self.embed_path + ".view_matrix" + str(view+1))
            self.num_row.append(num_row) # this is only for test purpose. self.num_item is used instead
            self.num_col.append(num_col)

            if self.same_entity_list[view] == -1: #-1 means entities are different
                self.item_view_matrix.append(self.load_rating_file_as_matrix_for_views(self.embed_path + ".view_matrix" + str(view+1),self.num_row[view],self.num_col[view]))
                self.adjacency_view_matrix.append(self.get_adjacency_matrix_sparse(self.item_view_matrix[view],self.item_view_matrix[view].T)) # Note num_items is used
            else: # 1 or other number means it is same entity both side
                self.item_view_matrix.append(self.load_rating_file_as_matrix_for_views(self.embed_path + ".view_matrix" + str(view+1), max(self.num_row[view],self.num_col[view]),max(self.num_row[view],self.num_col[view])))
                _A_obs = self.item_view_matrix[view] + self.item_view_matrix[view].T # Note num_items is used
                _A_obs[_A_obs > 1] = 1
                self.adjacency_view_matrix.append(_A_obs) # Note num_items is used

    def get_row_column_count(self, filename):
        num_users, num_items = 0, 0
        with open(filename, "r") as f:
            line = f.readline().strip()
            while line != None and line != "":
                arr         = line.split("\t")
                u, i        = int(arr[0]), int(arr[1])
                num_users   = max(num_users, u)
                num_items   = max(num_items, i)
                line = f.readline()
        return num_users+1, num_items+1

    def load_rating_file_as_matrix_for_views(self, filename, num_row, num_col):
        mat     = sp.dok_matrix((num_row,num_col), dtype=np.float32)
        with open(filename, "r") as f:
            line = f.readline()
            while line != None and line != "":
                arr = line.split("\t")
                user, item = (int(arr[0]), int(arr[1]))
                mat[user, item] = 1.0
                line = f.readline()
        return mat

    def get_adjacency_matrix_sparse(self,mat1,mat2): ## exactly same as param
        num_row,num_col = (mat1.shape[0] + mat2.shape[0], mat1.shape[1] + mat2.shape[1])
        mat = sp.lil_matrix((num_row,num_col),dtype=np.float32)
        assert num_row == num_col, 'In adj matrix conv. row and col should be equal.'
        mat[0:mat1.shape[0],mat1.shape[0]:] = mat1.astype(np.float32).tolil()
        mat[mat1.shape[0]:,0:mat1.shape[0]] = mat2.astype(np.float32).tolil()
        return mat.tocsr()

    def get_num_social(self,fname):
        df = pd.read_csv(fname,delimiter='\t',header=None)
        return df[1].max()+1

    def load_item_embed_as_mat(self, filename, zero_flag=False):
        # Construct matrix
        mat = np.zeros((self.num_item,self.item_attr_dim),dtype=np.float32)
        item_set = set()
        with open(filename, "r") as f:
            line = f.readline()
            while line != None and line != "":
                toks    = line.replace("\n","").split("::")
                itemid  = int(toks[0])
                embed   = np.array(toks[1].split(" ")).astype(np.float)
                mat[itemid] = embed
                line = f.readline()
                item_set.add(itemid)
            avg = np.mean(mat,axis=0)
            if zero_flag == False:
                for itemid in range(self.num_item):
                    if itemid not in item_set:
                        mat[itemid] = avg
        return mat


import numpy as np
import matplotlib.pyplot as plt
from tueplots import bundles

from Python_Code.definitions import load_caracteristics_csv, load_places_csv, load_holidays_csv, load_users_csv, \
    load_vehicles_csv

plt.rcParams.update(bundles.neurips2021(usetex=False))

test = np.array((8, 1, 10, -5, -4, 7))
plt.plot(test)
plt.show()

data_characteristics = load_caracteristics_csv()
data_places = load_places_csv()
data_holidays = load_holidays_csv()
data_users = load_users_csv()
data_vehicles = load_vehicles_csv()

print(data_places.head())
print(data_characteristics.head())
print(data_users.head())
print(data_vehicles.head())
print(data_holidays.head())
print(data_characteristics['an'].value_counts())

data_characteristics['an'].value_counts().sort_index().plot(kind='bar')
plt.savefig('..//Plots//Accidents_per_an.pdf', format='pdf')
plt.show()

print(data_users['catu'].value_counts(normalize=True).sort_index())

print(data_places['vosp'].value_counts().sort_index())


import tempfile

from pathlib import Path

from gpt_engineer.core.files_dict import FilesDict

class FileStore:
    def __init__(self, path: str | Path | None = None):
        if path is None:
            path = Path(tempfile.mkdtemp(prefix="gpt-engineer-"))

        self.working_dir = Path(path)
        self.working_dir.mkdir(parents=True, exist_ok=True)
        self.id = self.working_dir.name.split("-")[-1]

    def upload(self, files: FilesDict):
        for name, content in files.items():
            path = self.working_dir / name
            path.parent.mkdir(parents=True, exist_ok=True)
            with open(path, "w") as f:
                f.write(content)
        return self

    def download(self) -> FilesDict:
        files = {}
        for path in self.working_dir.glob("**/*"):
            if path.is_file():
                with open(path, "r") as f:
                    try:
                        content = f.read()
                    except UnicodeDecodeError:
                        content = "binary file"
                    files[str(path.relative_to(self.working_dir))] = content
        return FilesDict(files)


# mediapipeのposeお試しプログラム
# 鼻、左手、右手、左足、右足の場所に○を表示します
# 例外処理をしていないので体全体が全て写っているという前提で安定動作する感じです(入っていないパーツは荒ぶるカモ)

import sys
sys.dont_write_bytecode = True
import cv2
import mediapipe as mp

cap = cv2.VideoCapture(int(sys.argv[1])) # キャプチャ開始(複数カメラはIDを追加)

mp_pose = mp.solutions.pose # ポーズの初期化(変数はこのままでいいかな？)
pose = mp_pose.Pose(min_detection_confidence = 0.7, min_tracking_confidence = 0.5)

posName = [0, 19, 20, 31, 32] # 鼻、左手、右手、左足、右足
# https://google.github.io/mediapipe/solutions/pose.html

while True:
    ret, frame = cap.read() # キャプチャ
    if not ret: continue # キャプチャできていなければ再ループ
    cam_height, cam_width, _ = frame.shape # フレームサイズ取得(一回やればほんとうはいいのだけど)

    results = pose.process(cv2.cvtColor(frame, cv2.COLOR_BGR2RGB)) # mediapipeに処理を渡す
    if results.pose_landmarks is None: continue # 未検出なら再ループ

    pl = results.pose_landmarks
    for n in range(len(posName)): # 上記で設定したパーツ分ループする
        x = int(pl.landmark[posName[n]].x * cam_width)
        y = int(pl.landmark[posName[n]].y * cam_height)
        cv2.circle(frame, (x, y), 15, (0, 255, 0), thickness = 2)
        # print(x, y) # デバッグ用

    cv2.imshow("Frame pose", frame) # 円描画した結果の表示

    k = cv2.waitKey(1)
    if k == 27: break # escキーでプログラム終了

cap.release() # 後処理
cv2.destroyAllWindows()


class Solution:
    def islandPerimeter(self, grid: List[List[int]]) -> int:
        perimeter = 0
        adjacent = 0
        for i in range(len(grid)):
            for j in range(len(grid[i])):
                if grid[i][j] == 1:
                    perimeter += 4
                if (i > 0) and (grid[i][j] == 1):
                    if grid[i - 1][j] == 1:
                        adjacent += 1
                if (j > 0) and (grid[i][j] == 1):
                    if grid[i][j - 1] == 1:
                        adjacent += 1
            perimeter -= (2 * adjacent)
            adjacent = 0

        return perimeter


# author: YANG CUI
"""
Given a string containing digits from 2-9 inclusive,
return all possible letter combinations that the number could represent.

A mapping of digit to letters (just like on the telephone buttons) is given
 below. Note that 1 does not map to any letters.

This program uses backtracking
"""

def digitMapsLetter(digit):
    if digit == "2":
        result = ["a", "b", "c"]
    elif digit == "3":
        result = ["d", "e", "f"]
    elif digit == "4":
        result = ["g", "h", "i"]
    elif digit == "5":
        result = ["j", "k", "l"]
    elif digit == "6":
        result = ["m", "n", "o"]
    elif digit == "7":
        result = ["p", "q", "r", "s"]
    elif digit == "8":
        result = ["t", "u", "v"]
    elif digit == "9":
        result = ["w", "x", "y", "z"]
    return result

def letter_combo_aux(inputString):
    if inputString == "":
        return []
    letterList = []
    resultString = ""
    letter_combo(inputString, resultString, letterList)
    return letterList

def letter_combo(inputString, resultString, letterList):
    # base case
    if inputString == "":
        letterList.append(resultString)
    # choose/explore/unchoose
    else:
        # choose digit
        letter = inputString[0]
        letters = digitMapsLetter(letter)

        for j in range(len(letters)):
            # choose letter
            letterChosen = letters[j]
            resultString = resultString + letters[j]
            letters.__delitem__(j)
            inputString = inputString[1:]

            # explore
            letter_combo(inputString, resultString, letterList)

            # unchoose
            resultString = resultString[:len(resultString) - 1]
            letters.insert(j,letterChosen)
            inputString = letter + inputString
    return

print(letter_combo_aux(""))


class Solution:
    def setZeroes(self, matrix: List[List[int]]) -> None:
        """
        Do not return anything, modify matrix in-place instead.
        """
        vertical = {}
        horizontal=  {}

        rowSize = len(matrix)
        colSize = len(matrix[0])
        for row in range(rowSize):
            for col in range(colSize):
                if matrix[row][col] == 0:
                    vertical[col] = 1
                    horizontal[row] = 1
        for row in range(rowSize):
            for col in range(colSize):
                if row in horizontal:
                    matrix[row][col] = 0
                if col in vertical:
                    matrix[row][col] = 0


import pandas as pd
from matplotlib import pyplot as plt
import numpy as np

from relax import relaxation_fit, single_step_relaxation, two_step_relaxation, second_step_linear, linear, michaelis_menten

### CONSTANTS
color_set = [(0.2,0.6,0.2), (1,0.55,0.15)]
CONCENTRATION = 0.001
CYCLE_NUMBER_INDEX = 65 #quantared
# CYCLE_NUMBER_INDEX = 73 #quantablu
# INITIAL_GUESS = [2000, 0.0001, 0.1, 100]
INITIAL_GUESS = [2000, 0.0001, 100]
# INITIAL_GUESS = [0.2, 100]
### LOAD IN DATA

FILENAME = "/Users/benjaminbarad/Desktop/xlsx/ChitO_Test_1_20190425_092146.xlsx"
# FILENAME = "/Users/benjaminbarad/Desktop/xlsx/ChitO_Test_1_20190521_081704.xlsx"
# FILENAME = "/Users/benjaminbarad/Desktop/xlsx/ChitO_QuantaBlu_20190321_051503.xlsx"

data = pd.read_excel(FILENAME, index_col=0, nrows=96, header=CYCLE_NUMBER_INDEX, skiprows=[CYCLE_NUMBER_INDEX+1]).transpose()
# data = data.loc[data.index > 500]
data = data.loc[data.index<30000]
### SORT DATA BY FUNCTION
wt = ["B","C"]
mut = ["E","D"]
no_enzyme = ["G"]
# wt = ["B","C"]
# mut = ["F","D","E"]
# no_enzyme = ["A", "G"]
std = [["H{}".format(i+6)] for i in range(1,7)] #"H{}".format(i),
conc = [0.25*(2/3)**i for i in range(11)] + [0]
std_conc = [50 / 2**i for i in range(5)] + [0]

wt_results = []
mut_results = []
fig,ax = plt.subplots()
initial_rates_wt = []
initial_std_wt = []
initial_rates_mut = []
initial_std_mut = []

std_vals = []
std_stds = []
for index, concentration in enumerate(std_conc):
	standard_letters = std[index]
	standard = data[standard_letters].loc[data.index>10000].loc[data.index<15000].mean(axis=1)
	standard_std = standard.std()
	standard = standard.mean()
	# standard_std = data[standard_letters].mean(axis=0).std(axis=2)
	std_vals.append(standard)
	std_stds.append(standard_std)

adjuster, covariances, y_calc = relaxation_fit(std_vals[1:], std_conc[1:], relaxation_function=linear, initial_guess=(100, 100), sigma=std_stds[1:])
# adjuster = [ 0.00729535, -1.2748655 ] # from another run, since the standards failed on this one
slope = adjuster[0]
intercept = adjuster[1]
print(adjuster)

fig1, ax1 = plt.subplots()
ax1.plot(std_conc, std_vals ,".")
ax1.plot(y_calc, std_vals[1:])
ax1.set_xlabel(r"Standard Concentration ($\mu M$)")
ax1.set_ylabel("Fluorescence (RFU)")
plt.tight_layout()
fig1.savefig("standard_series.png")

for index, concentration in enumerate(conc):

	no_enzyme_letters = ["{0}{1}".format(i, index+1) for i in no_enzyme]
	no_enzyme_control = data[no_enzyme_letters].mean(axis=1)
	# ax.plot(no_enzyme_control.index.values, no_enzyme_control)

	wt_letters = ["{0}{1}".format(i, index+1) for i in wt]
	wt_unadjusted = data[wt_letters].mean(axis=1)
	wt_adjusted = wt_unadjusted - no_enzyme_control
	wt_std = data[wt_letters].mean(axis=1)

	rates, covariances, y_calc = relaxation_fit(wt_adjusted.index.values, wt_adjusted, relaxation_function=single_step_relaxation, initial_guess = INITIAL_GUESS, maxfev=30000)
	initial_rates_wt.append(rates[2]*slope)
	initial_std_wt.append(np.sqrt(covariances[0][0]/(rates[0]**2) + covariances[1][1]/(rates[1]**2) + 2*covariances[0][1]/(rates[0]*rates[1]))*rates[0]*rates[1]*slope)

	mut_letters = ["{0}{1}".format(i, index+1) for i in mut]
	mut_unadjusted = data[mut_letters].mean(axis=1)
	mut_adjusted = mut_unadjusted - no_enzyme_control
	mut_std = data[mut_letters].mean(axis=1)

	rates, covariances, y_calc = relaxation_fit(mut_adjusted.index.values, mut_adjusted, relaxation_function=single_step_relaxation, initial_guess = INITIAL_GUESS, maxfev=30000)
	initial_rates_mut.append(rates[2]*slope) #*rates[1]
	print(rates[0])
	initial_std_mut.append(np.sqrt(covariances[0][0]/(rates[0]**2) + covariances[1][1]/(rates[1]**2) + 2*covariances[0][1]/(rates[0]*rates[1]))*rates[0]*rates[1]*slope)
	if index>5:
		ax.plot(wt_adjusted.index.values, wt_adjusted)
		ax.plot(mut_adjusted.index.values, mut_adjusted)
		ax.plot(mut_adjusted.index.values, y_calc)

	# ax.plot(mut_adjusted.index.values, mut_adjusted)
	# ax.plot(mut_adjusted.index.values, y_calc)

ax.set_ylabel("Fluorescence (RFU)")
ax.set_xlabel("Time (s)")
plt.tight_layout()
fig.savefig("adjusted.png")

### Check that the data load actually worked
fig2,ax2 = plt.subplots()
ax2.plot(data.loc[0:,"H1":"H12"])
fig2.savefig("pandas_sanity_check.png")

### Michaelis Menten Plot
fig3,ax3 = plt.subplots()

values, covar, y_calc = relaxation_fit(conc[4:11], initial_rates_wt[4:11], relaxation_function=michaelis_menten, initial_guess=(0.05,20), maxfev=30000) #, absolute_sigma=True)
print (values)
ax3.plot(conc[4:11], initial_rates_wt[4:11], '.', label="WT", color=color_set[0]) #yerr=initial_std_wt[3:11]
ax3.plot(conc[4:11], y_calc, color=color_set[0])

values_mut, covar_mut, y_calc = relaxation_fit(conc[4:11], initial_rates_mut[4:11],  relaxation_function=michaelis_menten, initial_guess=(0.05,20), maxfev=30000) #, absolute_sigma=True)
print(values_mut)
ax3.plot(conc[4:11], initial_rates_mut[4:11], '.', label = "Mut", color=color_set[1]) # , yerr=initial_std_mut[3:11]
ax3.plot(conc[4:11], y_calc, color=color_set[1])

ax3.legend(loc=4)
ax3.set_ylabel(r"Calculated Initial Rate ($\mu M/s$)")
ax3.set_xlabel("Chitin Concentration (% w/v)")
plt.tight_layout()
fig3.savefig("MM_chito.png")

print("WT")
print("Vmax: {} ± {}".format(values[0], np.sqrt(covar[0][0])))
print("kcat: {} ± {}".format(values[0]/CONCENTRATION, np.sqrt(covar[0][0])/CONCENTRATION))
print("Km: {} ± {}".format(values[1], np.sqrt(covar[1][1])))
wt_rel_act = values[0]/values[1]/CONCENTRATION
wt_rel_act_dev = wt_rel_act*np.sqrt(covar[0][0]/(values[0]**2)+covar[1][1]/(values[1]**2)-2*covar[0][1]/(values[0]*values[1]))
print(wt_rel_act, wt_rel_act_dev)

print("Mut")
print("Vmax: {} ± {}".format(values_mut[0], np.sqrt(covar_mut[0][0])))
print("kcat: {} ± {}".format(values_mut[0]/CONCENTRATION, np.sqrt(covar_mut[0][0])/CONCENTRATION))
print("Km: {} ± {}".format(values_mut[1], np.sqrt(covar_mut[1][1])))
mut_rel_act = values_mut[0]/values_mut[1]/CONCENTRATION
mut_rel_act_dev = mut_rel_act*np.sqrt(covar_mut[0][0]/(values_mut[0]**2)+covar_mut[1][1]/(values_mut[1]**2)-2*covar_mut[0][1]/(values_mut[0]*values_mut[1]))
print(mut_rel_act, mut_rel_act_dev)

## Bar Plot
fig4,ax4=plt.subplots()
x = [0,1]
y = [wt_rel_act, mut_rel_act]
y_tick_labels = ["AMCase", "Mut"]
# y = [i/wt_rel_act for i in y]
yerr = [wt_rel_act_dev, mut_rel_act_dev]
# yerr = [i/wt_rel_act for i in yerr]
color_set = [(0.2,0.6,0.2), (1,0.55,0.15)]
ax4.set_xticks(x)
ax4.set_xticklabels(y_tick_labels)
ax4.bar(x, y, 0.8, yerr=yerr, color=color_set)
ax4.set_ylabel(r"kcat/Km $(s•\mu M)^{-1}$")
fig4.savefig("ChitO_Ratio.png")


from dataclasses import dataclass, field
from typing import Optional
from ojp.extension_type import ExtensionType

__NAMESPACE__ = "http://datex2.eu/schema/2_0RC1/2_0"

@dataclass
class Visibility:
    minimum_visibility_distance: Optional[int] = field(
        default=None,
        metadata={
            "name": "minimumVisibilityDistance",
            "type": "Element",
            "namespace": "http://datex2.eu/schema/2_0RC1/2_0",
            "required": True,
        }
    )
    visibility_extension: Optional[ExtensionType] = field(
        default=None,
        metadata={
            "name": "visibilityExtension",
            "type": "Element",
            "namespace": "http://datex2.eu/schema/2_0RC1/2_0",
        }
    )


# -*- coding: utf-8 -*-
"""
Created on Fri Oct  8 00:10:36 2021

@author: Mangesh

"""
import datetime as dt
import pandas as pd
import psycopg2
import time
import os
import numpy as np
import json
from playsound import playsound
from selenium import webdriver
from sqlalchemy import create_engine
from io import BytesIO
import requests
connection = psycopg2.connect(
            host="",
            database="",
            user="",
            password="")
engine = create_engine('')
with open(r"",'r',encoding = 'utf-8') as f:
    current_date=f.readline()
date = dt.datetime.strptime(current_date,'%Y-%m-%d').date()
date += dt.timedelta(days=1)
def getindexfile():
    print("indexfile")
    result = requests.get("https://archives.nseindia.com/content/indices/ind_close_all_"+date.strftime("%d%m%Y").
                          upper()+".csv",timeout=5)
    data = pd.read_csv(BytesIO(result.content), header=0, sep=',', quotechar='"')
    data.to_sql('stageindexfile',engine,'bhav_copy_raw',if_exists='append')
def getbhavcopy():
    print(date)
    print("bhavcopy")
    result = requests.get("https://archives.nseindia.com/content/historical/EQUITIES/"+str(date.year)+"/"+date.strftime("%b").upper()+"/cm"+date.strftime("%d%b%Y").upper()+"bhav.csv.zip",timeout=5)
    df = pd.read_csv(BytesIO(result.content),compression='zip', header=0, sep=',', quotechar='"')
    df.to_sql('stagebhavcopy',engine,'bhav_copy_raw',if_exists='append')
while date <= dt.date.today():
    try:
        getbhavcopy()
        getindexfile()
    except:
        print('data not found for'+ str(date))
    date += dt.timedelta(days=1)
ddl_cursor=connection.cursor()
connection.rollback()
ddl_cursor.execute('ALTER TABLE bhav_copy_raw.stagebhavcopy ALTER COLUMN "TIMESTAMP" TYPE date USING "TIMESTAMP"::date;')
ddl_cursor.execute('ALTER TABLE bhav_copy_raw.stagebhavcopy DROP COLUMN "ISIN";')
ddl_cursor.execute('ALTER TABLE bhav_copy_raw.stagebhavcopy DROP COLUMN "Unnamed: 13";')
ddl_cursor.execute('delete from bhav_copy_raw.stageindexfile where '+'"Open Index Value"'+" = '-';")
ddl_cursor.execute('ALTER TABLE bhav_copy_raw.stageindexfile ALTER COLUMN "Index Date" TYPE date USING "Index Date"::date;')
ddl_cursor.execute('ALTER TABLE bhav_copy_raw.stageindexfile ALTER COLUMN "Open Index Value" TYPE float8 USING "Open Index Value"::float8;')
ddl_cursor.execute('ALTER TABLE bhav_copy_raw.stageindexfile ALTER COLUMN "High Index Value" TYPE float8 USING "High Index Value"::float8;')
ddl_cursor.execute('ALTER TABLE bhav_copy_raw.stageindexfile ALTER COLUMN "Low Index Value" TYPE float8 USING "Low Index Value"::float8;')
ddl_cursor.execute('insert into bhav_copy_raw.bhavcopy select * from bhav_copy_raw.stagebhavcopy ')
ddl_cursor.execute('insert into bhav_copy_raw.index_file select * from bhav_copy_raw.stageindexfile')
ddl_cursor.execute("delete from bhav_copy_raw.bhavcopy where"+ '"SERIES"'+" <> 'EQ';")
ddl_cursor.execute('update bhav_copy_raw.index_file set "Index Name"  = upper("Index Name" );')
connection.commit()
with open(r"",'w',encoding = 'utf-8') as text_file:
    text_file.write(str(dt.date.today()))