import os
import sys;
from pathlib import Path

sys.path.extend('../')
import networkx as nx
from src.graph_stats import GraphStats
from src.parallel import parallel_async
from src.utils import load_pickle, get_imt_input_directory, walker, ColorPrint, get_imt_output_directory

def stats_computation(dataset, model, trial, filename, stats):
    path = Path(get_imt_output_directory()) / 'pickles' / dataset / model / filename
    graph_list = load_pickle(path)
    assert isinstance(graph_list, list), f'Expected type "list" and got type {type(graph_list)}.'
    assert all(isinstance(g, nx.Graph) for g in graph_list), f'Expected a list of nx.Graph and got disappointed instead.'

    # ColorPrint.print_orange(f'{filename} has length {len(graph_list)}')

    for idx, G in enumerate(graph_list):
        gs_obj = GraphStats(graph=G, dataset=dataset, model=model, trial=trial, iteration=idx)
        gs_obj.write_stats_jsons(stats=stats)

    return None

if __name__ == '__main__':
    stat = ['pagerank', 'degree_dist', 'pgd_graphlet_counts', 'laplacian_eigenvalues', 'b_matrix']#[-1:]
    datasets, models, trials, filenames = walker()
    #datasets, models, trials, filenames = ['eucore']*10, ['BTER']*10, [str(x) for x in range(1, 11)], [f'list_20_{x}.pkl.gz' for x in range(1, 11)]

    args = [(dataset, model, trial, filename, stat)
            for dataset, model, trial, filename in zip(datasets, models, trials, filenames)
            if dataset != 'enron']

    parallel_async(stats_computation, args, num_workers=8)


# -*- coding: utf-8 -*-
#
# Author: François Rossigneux <francois.rossigneux@inria.fr>
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.

"""Set up the ACL to access the API."""

import flask
import keystoneclient.middleware.auth_token as auth_token
from oslo.config import cfg

from kwstandby.openstack.common import policy

_ENFORCER = None
OPT_GROUP_NAME = 'keystone_authtoken'

def register_opts(conf):
    """Registers keystoneclient middleware options."""
    conf.register_opts(auth_token.opts,
                       group=OPT_GROUP_NAME,
                       )
    auth_token.CONF = conf

register_opts(cfg.CONF)

def install(app, conf):
    """Installs ACL check on application."""
    app.wsgi_app = auth_token.AuthProtocol(app.wsgi_app,
                                           conf=dict(conf.get(OPT_GROUP_NAME)))
    app.before_request(check)

def check():
    """Checks application access."""
    headers = flask.request.headers
    global _ENFORCER
    if not _ENFORCER:
        _ENFORCER = policy.Enforcer()
    if not _ENFORCER.enforce('context_is_admin',
                             {},
                             {'roles': headers.get('X-Roles', "").split(",")}):
        return "Access denied", 401


'''
문제
온라인 저지에 가입한 사람들의 나이와 이름이 가입한 순서대로 주어진다.
이때, 회원들을 나이가 증가하는 순으로,
나이가 같으면 먼저 가입한 사람이 앞에 오는 순서로 정렬하는 프로그램을 작성하시오.

입력
첫째 줄에 온라인 저지 회원의 수 N이 주어진다. (1 ≤ N ≤ 100,000)

둘째 줄부터 N개의 줄에는 각 회원의 나이와 이름이 공백으로 구분되어 주어진다.
나이는 1보다 크거나 같으며, 200보다 작거나 같은 정수이고,
이름은 알파벳 대소문자로 이루어져 있고, 길이가 100보다 작거나 같은 문자열이다.
입력은 가입한 순서로 주어진다.

출력
첫째 줄부터 총 N개의 줄에 걸쳐 온라인 저지 회원을 나이 순,
나이가 같으면 가입한 순으로 한 줄에 한 명씩 나이와 이름을 공백으로 구분해 출력한다.
'''

import sys

def merge_sort(arr) :
    if len(arr) < 2 :
        return arr

    mid = len(arr)//2
    low_arr = merge_sort(arr[:mid])
    high_arr = merge_sort(arr[mid:])

    merged_arr = []

    l = h = 0

    while l < len(low_arr) and h < len(high_arr) :
        if low_arr[l][0] < high_arr[h][0] :
            merged_arr.append(low_arr[l])
            l += 1

        elif low_arr[l][0] == high_arr[h][0] :
            if low_arr[l][1] < high_arr[h][1] :
                merged_arr.append(low_arr[l])
                l += 1
            else :
                merged_arr.append(high_arr[h])
                h += 1

        else :
            merged_arr.append(high_arr[h])
            h += 1

    merged_arr += low_arr[l:]
    merged_arr += high_arr[h:]

    return merged_arr

num = int(input())
nlist = list()

for i in range (num) :
    member = sys.stdin.readline().split()
    nlist.append([int(member[0]), i, member[1]])

nlist = merge_sort(nlist)
for i in nlist :
    print("{0} {1}".format(i[0], i[2]))


from django.contrib import admin
from django.urls import path, include
from django.conf import settings
from django.conf.urls.static import static
from django.contrib.staticfiles.urls import staticfiles_urlpatterns
from news.views import IndexView,MessageViewHome
from django.views.generic import TemplateView
from exceptionsapp.views import error_404,error_500,error_403,error_400

handler404 = 'exceptionsapp.views.error_404'
handler403 = 'exceptionsapp.views.error_403'
handler400 = 'exceptionsapp.views.error_400'
handler400 = 'exceptionsapp.views.error_500'

urlpatterns = [
    path("", include("contracts.urls")),
    path("user/", include("users.urls")),
    path("", include("news.urls")),
    path("", include("company.urls")),
    path("", include("construction.urls")),
    path("", include("dam.urls")),
    path("", include("damknowledge.urls")),

    # home
    path("", IndexView.as_view(), name="index"),
    path('message/<slug:slug>/', MessageViewHome.as_view(), name='message'),
    #list of apps
    path('admin/', admin.site.urls),
    path("", include('django.contrib.auth.urls')),
    #external package
    path('ckeditor/', include('ckeditor_uploader.urls')),

]

urlpatterns += staticfiles_urlpatterns()

urlpatterns += static(settings.STATIC_URL,document_root = settings.STATIC_ROOT)
urlpatterns += static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT)


class Node:
    def __init__(self, elm):
        self.elm = elm
        self.left = None
        self.right = None

class BST:
    def __init__(self):
        self.size = 0
        self.root = None

    def insert_recursive(self, node, elm):
        if node is None:
            new_node = Node(elm)
            if self.size == 0:
                self.root = new_node
            self.size += 1
            return new_node
        if elm < node.elm:
            node.left = self.insert_recursive(node.left, elm)
        else:
            node.right = self.insert_recursive(node.right, elm)
        return node

    def findMin(self, node):
        current = node
        while(current.left is not None):
            current = current.left
        return current

    def delete_recursive(self, root, elm):
        if root is None:
            return root
        if elm < root.elm:
            root.left = self.delete_recursive(root.left, elm)
        elif(elm > root.elm):
            root.right = self.delete_recursive(root.right, elm)
        else:
            if root.left is None:
                temp = root.right
                root = None
                return temp
            elif root.right is None:
                temp = root.left
                root = None
                return temp
            temp = self.findMin(root.right)
            root.elm = temp.elm
            root.right = self.delete_recursive(root.right, temp.elm)
        return root

    def search_recursive(self, root, elm):
        if root is None or root.elm == elm:
            return root
        if elm < root.elm:
            return self.search_recursive(root.left, elm)
        else:
            return self.search_recursive(root.right, elm)

    # User functions
    def insert(self, elm):
        self.insert_recursive(self.root, elm)

    def delete(self, elm):
        self.size -= self.search(elm)
        self.root = self.delete_recursive(self.root, elm)

    def search(self, elm):
        return self.search_recursive(self.root, elm) != None


from abc import ABC, abstractmethod
import re

from backend.tools.dao.entity_dao import DemographicDAO, LocationLookupDAO

class Validator:
    def is_valid(self, row_map):
        error_msg = []
        for attribute in row_map:
            if not self.check_blank(row_map[attribute]):
                error_msg.append(attribute + " is blank")
        if len(error_msg) != 0:
            return error_msg
        else:
            for attribute in row_map:
                if attribute != "name":
                    if not getattr(self, "check_" + attribute)(row_map[attribute]):
                        error_msg.append("Invalid " + attribute)
            # if len(error_msg) != 0:
            #     print(row_map)
            #     print(error_msg)
            return error_msg

    def check_mac_address(self, mac_address):
        pattern = "[a-fA-F0-9]{40}$"
        is_matched = re.match(pattern, mac_address)
        if is_matched:
            return True
        else:
            return False

    def check_blank(self, attribute):
        if attribute == "":
            return False
        else:
            return True

class DemographicValidator(Validator):
    def check_email(self, email_address):
        pattern = "([a-zA-Z0-9]+(\\.){1})+[0-9]{4}(@){1}(business|accountancy|sis|economics|law|socsc){1}(\\.smu\\.edu\\.sg){1}"
        is_matched = re.match(pattern, email_address)
        if is_matched:
            return True
        else:
            return False

    def check_gender(self, gender):
        potential_gender_value = ["F", "M", "f", "m"]
        if gender in potential_gender_value:
            return True
        else:
            return False

    def check_password(self, password):
        if " " not in password and len(password) >= 8:
            return True
        else:
            return False

class LocationLookupValidator(Validator):
    def check_location_id(self, location_id):
        try:
            int(location_id)
            return True
        except:
            return False

    def check_semantic_place(self, semantic_place):
        pattern = "(SMUSISL|SMUSISB)([1-5]{1})(.+)"
        is_matched = re.match(pattern, semantic_place)
        if is_matched:
            return True
        else:
            return False

class LocationValidator(Validator):
    def check_timestamp(self, timestamp):
        pattern = "(\\d){4}-(\\d){2}-(\\d){2} (\\d){2}:(\\d){2}:(\\d){2}"
        is_matched = re.match(pattern, timestamp)
        if is_matched:
            return True
        else:
            return False

    def check_location_id(self, location_id):
        if location_id in LocationLookupDAO.valid_location_ids:
            return True
        else:
            return False


'''
MACD
2011年〜2018年の最適な組み合わせを使って2019年〜2020年の取引を行う。
'''
import os
import datetime
import pandas as pd
import pandas_datareader
import matplotlib.pyplot as plt
import japanize_matplotlib
import talib
from backtesting import Backtest, Strategy
from backtesting.lib import crossover

START_DATE = datetime.date(2019, 1, 1)
END_DATE = datetime.date(2020, 12, 31)
TICKER = '^N225'
INIT_CASH = 1000000

def get_stock(ticker, start_date, end_date):
    '''
    get stock data from Yahoo Finance
    '''
    dirname = '../data'
    os.makedirs(dirname, exist_ok=True)
    period = f"{start_date.strftime('%Y%m%d')}_{end_date.strftime('%Y%m%d')}"
    fname = f'{dirname}/{ticker}_{period}.pkl'
    if os.path.exists(fname):
        df_stock = pd.read_pickle(fname)
    else:
        df_stock = pandas_datareader.data.DataReader(
            ticker, 'yahoo', start_date, end_date)
        df_stock.to_pickle(fname)
    return df_stock

class MacdStrategy(Strategy):
    '''
    MACD Strategy
    '''
    fastperiod = 9
    slowperiod = 48
    signalperiod = 5

    def init(self):
        close = self.data['Adj Close']
        self.macd, self.macdsignal, _ = self.I(
            talib.MACD, close,
            fastperiod=self.fastperiod,
            slowperiod=self.slowperiod,
            signalperiod=self.signalperiod)

    def next(self):
        '''
        MACDとMACDシグナルのゴールデンクロスで買い
        MACDとMACDシグナルのデッドクロスで売り
        MACDがマイナスからプラスになったら買い
        MACDがプラスからマイナスになったら売り
        '''
        if crossover(self.macd, self.macdsignal):
            self.buy()
        elif crossover(self.macd, self.macdsignal):
            self.sell()
        elif crossover(self.macd, 0):
            self.buy()
        elif crossover(0, self.macd):
            self.sell()

def main():
    df = get_stock(TICKER, START_DATE, END_DATE)

    bt = Backtest(
        df,
        MacdStrategy,
        cash=INIT_CASH,
        trade_on_close=False,
        exclusive_orders=True
    )

    output = bt.run()
    print(output)
    bt.plot()

if __name__ == '__main__':
    main()


"""empty message

Revision ID: cdbf41aea838
Revises:
Create Date: 2019-03-09 19:54:02.333712

"""
from alembic import op
import sqlalchemy as sa

# revision identifiers, used by Alembic.
revision = 'cdbf41aea838'
down_revision = None
branch_labels = None
depends_on = None

def upgrade():
    # ### commands auto generated by Alembic - please adjust! ###
    op.create_table('areas',
    sa.Column('id', sa.Integer(), nullable=False),
    sa.Column('area_name', sa.String(), nullable=False),
    sa.Column('label', sa.String(), nullable=False),
    sa.PrimaryKeyConstraint('id')
    )
    op.create_table('candidates',
    sa.Column('id', sa.Integer(), nullable=False),
    sa.Column('candname', sa.String(), nullable=False),
    sa.Column('label', sa.String(), nullable=False),
    sa.PrimaryKeyConstraint('id')
    )
    op.create_table('users',
    sa.Column('id', sa.Integer(), nullable=False),
    sa.Column('username', sa.String(length=10), nullable=False),
    sa.Column('full_name', sa.String(length=120), nullable=False),
    sa.Column('password', sa.String(), nullable=False),
    sa.PrimaryKeyConstraint('id'),
    sa.UniqueConstraint('username')
    )
    op.create_table('candidate_areas',
    sa.Column('candidate_id', sa.Integer(), nullable=False),
    sa.Column('area_id', sa.Integer(), nullable=False),
    sa.Column('tfidf', sa.Float(), nullable=False),
    sa.ForeignKeyConstraint(['area_id'], ['areas.id'], ),
    sa.ForeignKeyConstraint(['candidate_id'], ['candidates.id'], ),
    sa.PrimaryKeyConstraint('candidate_id', 'area_id')
    )
    op.create_table('user_areas',
    sa.Column('user_id', sa.Integer(), nullable=False),
    sa.Column('area_id', sa.Integer(), nullable=False),
    sa.Column('rate', sa.Integer(), nullable=False),
    sa.ForeignKeyConstraint(['area_id'], ['areas.id'], ),
    sa.ForeignKeyConstraint(['user_id'], ['users.id'], ),
    sa.PrimaryKeyConstraint('user_id', 'area_id')
    )
    op.create_table('user_candidates',
    sa.Column('user_id', sa.Integer(), nullable=False),
    sa.Column('candidate_id', sa.Integer(), nullable=False),
    sa.Column('rate', sa.Integer(), nullable=False),
    sa.ForeignKeyConstraint(['candidate_id'], ['candidates.id'], ),
    sa.ForeignKeyConstraint(['user_id'], ['users.id'], ),
    sa.PrimaryKeyConstraint('user_id', 'candidate_id')
    )
    # ### end Alembic commands ###

def downgrade():
    # ### commands auto generated by Alembic - please adjust! ###
    op.drop_table('user_candidates')
    op.drop_table('user_areas')
    op.drop_table('candidate_areas')
    op.drop_table('users')
    op.drop_table('candidates')
    op.drop_table('areas')
    # ### end Alembic commands ###


import requests
import json
import pandas as pd
import os

def load_schools(length):
    school_list = []
    with open('schools.txt', 'r') as f:
        for row in f:
            school_list.append(row.rstrip("\n"))
    school_list = school_list[0:length]
    return school_list

def load_positions():
    position_list = []
    with open('positions.txt', 'r') as f:
        for row in f:
            position_list.append(row.rstrip("\n"))
    return position_list

def get_schools():
    url = "https://api.collegefootballdata.com/conferences"
    params = {"searchTerm": ""}
    response = requests.get(url, params=params)
    c = json.loads(response.content)
    for conference in c:
        print(conference)
        params = {"conference": conference['name']}
        response = requests.get(url, params=params)
        teams = json.loads(response)
        for t in teams:
            print(t)
    #result = list(map(lambda x: x['school'], dictionary))
    #with open('schools.txt', 'w') as f:
    #    for item in result:
    #        f.write('%s\n' % item)

def write_list_to_file(l, file_name):
    with open(file_name, 'w') as f:
        for item in l:
            f.write('%s\n' % item)

def get_positions():
    player_dict = {}
    url = "https://api.collegefootballdata.com/player/search"
    teams = ["Georgia", "Alabama", "Florida", "Pittsburgh", "Baylor", "Army", "Arizona", "BYU", "Iowa Wesleyan",
             "Ithaca"]  # has to be a wide enough net
    # a through c in alphabet
    letters = [chr(i) for i in range(ord('a'), ord('c') + 1)]

    positions = set()
    for team in teams:
        for letter in letters:
            params = {"team": team, "searchTerm": letter}
            response = requests.get(url, params=params)
            dictionary = json.loads(response.content)
            position_list = set(list(map(lambda x: x['position'], dictionary)))
            positions = positions.union(position_list)

    positions = list(positions)

    with open('positions.txt', 'w') as f:
        for item in positions:
            f.write('%s\n' % item)

def get_players(schools, years):

    if os.path.exists("raw_players.csv"):
        player_df = pd.read_csv("raw_players.csv")
    else:
        column_names = ["id", "first_name", "last_name", "weight", "height", "jersey", "year",
                        "position", "home_city", "home_state", "home_country", "school"]
        player_df = pd.DataFrame(columns=column_names)

    url = "https://api.collegefootballdata.com/roster"
    for school in schools:
        for year in years:
            params = {"team": school, "year": year}
            response = requests.get(url, params=params)
            temp_dict = json.loads(response.content)
            for value in temp_dict:
                value['school'] = school
                value['year'] = year
                df = pd.DataFrame([value], columns=value.keys())
                player_df = player_df.append(df, ignore_index=True)

    columns_order = ["id", "first_name", "last_name", "school", "year", "weight", "height", "jersey",
                     "position", "home_city", "home_state", "home_country"]

    player_df = player_df[columns_order]
    player_df = player_df[player_df["id"].notna()]
    player_df['id'] = player_df['id'].astype(int)
    player_df = player_df.where(player_df['id'] > 0)  # remove negative values (teams)
    player_df = player_df.sort_values('id', ascending=False)
    player_df.drop_duplicates(subset="id", keep="last", inplace=True)
    player_df = player_df[player_df["id"].notna()]
    player_df = player_df[player_df["last_name"].notna()]
    player_df['id'] = player_df['id'].astype(int)
    player_df['year'] = player_df['year'].astype(int)
    player_df.to_csv("raw_players.csv", index=False)

    return None  # end function

years = list(range(2010, 2012, 1))
print(years)
get_players(load_schools(738), years)


from django.http import HttpResponse
from django.template import loader
from django.shortcuts import render
from django.template import Template,Context
from Familiares.models import Familiar

# Create your views here.
def listado_familiares(request):
    familiar1=Familiar(nombre='Nicolas',parentesco='hermano',dni=30123456,fecha_nacimiento='1980-08-11')
    familiar1.save()

    familiar2=Familiar(nombre='Carolina',parentesco='hermana',dni=31256987,fecha_nacimiento='1980-10-25')
    familiar2.save()

    familiar3=Familiar(nombre='Roberto',parentesco='padre',dni=10235478,fecha_nacimiento='1956-12-20')
    familiar3.save()

    familiar4=Familiar(nombre='Beatriz',parentesco='madre',dni=11247985,fecha_nacimiento='1950-04-11')
    familiar4.save()

    plantilla=loader.get_template('template.html')
    familia= {'familia':[familiar1,familiar2,familiar3,familiar4]}
    vista = plantilla.render(familia)
    return HttpResponse(vista)


# -*- coding: utf-8 -*-
"""
Created on Mon Apr 26 14:44:18 2021

@author: sp3660
"""

import pandas as pd
import numpy as np
import sqlite3
from sqlite3 import Error

excelfile=r'C:\Users\sp3660\Desktop\ForMouseDatabase.xlsx'
databasefile=r'C:\Users\sp3660\Desktop\MouseDatabase.db'

#%%
Rooms_table = pd.read_excel(
    excelfile,
    sheet_name='Rooms',
    header=0)

Action_types_table = pd.read_excel(
    excelfile,
    sheet_name='Action Types',
    header=0)

Lines_table = pd.read_excel(
    excelfile,
    sheet_name='Lines',
    header=0)

Genes_table = pd.read_excel(
    excelfile,
    sheet_name='Genes',
    header=0)

Genotypes_table = pd.read_excel(
    excelfile,
    sheet_name='Genotypes',
    header=0)

Genotyping_status_table = pd.read_excel(
    excelfile,
    sheet_name='Genotypings',
    header=0)

Breeding_status_table = pd.read_excel(
    excelfile,
    sheet_name='Breeders',
    header=0)

Experimental_status_table = pd.read_excel(
    excelfile,
    sheet_name='Experimental',
    header=0)

Labels_table = pd.read_excel(
    excelfile,
    sheet_name='Labels',
    header=0)

Sex_table = pd.read_excel(
    excelfile,
    sheet_name='Sex',
    header=0)

Mice_table = pd.read_excel(
    excelfile,
    sheet_name='Mouse Table',
    header=0)

Mice_table.dtypes
Mice_table['Cage'] = Mice_table['Cage'].astype('Int64')
Mice_table.dtypes

Breedings_table = pd.read_excel(
    excelfile,
    sheet_name='Breedings',
    header=0)
Breedings_table.dtypes
Breedings_table['Cage'] = Breedings_table['Cage'].astype('Int64')
Breedings_table['Male'] = Breedings_table['Male'].astype('Int64')
Breedings_table['Female1'] = Breedings_table['Female1'].astype('Int64')
Breedings_table['Female2'] = Breedings_table['Female2'].astype('Int64')
Breedings_table['Male_Cage'] = Breedings_table['Male_Cage'].astype('Int64')
Breedings_table['Requires_Genotyping'] = Breedings_table['Requires_Genotyping'].astype('Int64')
Breedings_table.dtypes

Litters_table = pd.read_excel(
    excelfile,
    sheet_name='Litters',
    header=0)
Litters_table.dtypes
Litters_table['NumberDead'] = Litters_table['NumberDead'].astype('Int64')

Actions_table = pd.read_excel(
    excelfile,
    sheet_name='Actions',
    header=0)
Actions_table.dtypes
Actions_table['Mouse_2'] = Actions_table['Mouse_2'].astype('Int64')
Actions_table['Mouse_3'] = Actions_table['Mouse_3'].astype('Int64')
Actions_table['Mouse_4'] = Actions_table['Mouse_4'].astype('Int64')
Actions_table['Mouse_5'] = Actions_table['Mouse_5'].astype('Int64')
Actions_table.dtypes

#%%

db_conn = sqlite3.connect(databasefile)
c = db_conn.cursor()
#%%
c.execute(
    """
CREATE TABLE Sex_table (
    ID INTEGER PRIMARY KEY AUTOINCREMENT ,
    Sex_types TEXT
    );
"""
)

c.execute(
    """
CREATE TABLE Labels_table (
    ID INTEGER PRIMARY KEY AUTOINCREMENT ,
    Labels_types TEXT
    );
"""
)

c.execute(
    """
CREATE TABLE Experimental_table (
    ID INTEGER PRIMARY KEY AUTOINCREMENT ,
    Experimental_types TEXT
    );
"""
)

c.execute(
    """
CREATE TABLE Breeders_table (
    ID INTEGER PRIMARY KEY AUTOINCREMENT,
    Breeders_types TEXT
    );
"""
)

c.execute(
    """
CREATE TABLE Genotypings_table (
    ID INTEGER PRIMARY KEY AUTOINCREMENT ,
    Genotypings_types TEXT
    );
"""
)

c.execute(
    """
CREATE TABLE Genotypes_table (
    ID INTEGER PRIMARY KEY AUTOINCREMENT ,
    Genotypes_types TEXT
    );
"""
)

c.execute(
    """
CREATE TABLE Genes_table (
    ID INTEGER PRIMARY KEY AUTOINCREMENT ,
    Genes_types TEXT
    );
"""
)

c.execute(
    """
CREATE TABLE Lines_table (
    ID INTEGER PRIMARY KEY AUTOINCREMENT ,
    Line_Short TEXT,
    Line_Long TEXT
    );
"""
)

c.execute(
    """
CREATE TABLE Action_types_table (
    ID INTEGER PRIMARY KEY AUTOINCREMENT ,
    Action_types  TEXT
    );
"""
)

c.execute(
    """
CREATE TABLE Rooms_table (
    ID INTEGER PRIMARY KEY AUTOINCREMENT ,
    Room_types TEXT
    );
"""
)
#%%
c.execute(
    """
CREATE TABLE Breedings_table (
    ID INTEGER PRIMARY KEY AUTOINCREMENT ,
    Cage INTEGER,
    Male INTEGER,
    Female1 INTEGER,
    Female2 INTEGER,
    Line INTEGER NOT NULL,
    StartDate TEXT,
    EndDate TEXT,
    Male_Cage INTEGER,
    Breeding_Status INTEGER,
    Requires_Genotyping INTEGER,
    Notes TEXT,

    FOREIGN KEY (Line) REFERENCES Lines_table (ID)
    FOREIGN KEY (Male) REFERENCES MICE_table (ID)
    FOREIGN KEY (Female1) REFERENCES MICE_table (ID)
    FOREIGN KEY (Female2) REFERENCES MICE_table (ID)
    FOREIGN KEY (Breeding_Status) REFERENCES Breeders_table (ID)

    );
"""
)

c.execute(
    """
CREATE TABLE Litters_table (
    ID INTEGER PRIMARY KEY AUTOINCREMENT ,
    Cage INTEGER NOT NULL,
    Breeding_Parents INTEGER NOT NULL,
    Date_seen TEXT NOT NULL,
    Age INTEGER NOT NULL,
    Line INTEGER NOT NULL,
    Date_Weaned TEXT,
    NumberAlive INTEGER,
    NumberDead INTEGER,
    Notes TEXT,

    FOREIGN KEY (Line) REFERENCES Lines_table (ID)
    FOREIGN KEY (Breeding_Parents) REFERENCES Breedings_table(ID)

    );
"""
)

c.execute(
    """
CREATE TABLE Actions_table (
    ID INTEGER PRIMARY KEY AUTOINCREMENT,
    Date TEXT NOT NULL,
    Action_Type INTEGER NOT NULL,
    Cage_start INT,
    Cage_end INT,
    Mouse_1 INTEGER NOT NULL,
    Mouse_2 INTEGER,
    Mouse_3 INTEGER,
    Mouse_4 INTEGER,
    Mouse_5 INTEGER,
    Notes TEXT,

    FOREIGN KEY (Action_Type) REFERENCES Action_types_table (ID)
    FOREIGN KEY (Mouse_1) REFERENCES MICE_table(ID)
    FOREIGN KEY (Mouse_2) REFERENCES MICE_table(ID)
    FOREIGN KEY (Mouse_3) REFERENCES MICE_table(ID)
    FOREIGN KEY (Mouse_4) REFERENCES MICE_table(ID)
    FOREIGN KEY (Mouse_5) REFERENCES MICE_table(ID)

    );
"""
)

#%%
c.execute(
    """
CREATE TABLE MICE_table (
    ID INTEGER PRIMARY KEY AUTOINCREMENT ,
    Lab_Number  INTEGER NOT NULL,
    Sex INTEGER NOT NULL,
    Cage INTEGER,
    Breeding_status INTEGER NOT NULL,
    DOB TEXT,
    Label INTEGER NOT NULL,
    Parent_Breeding INTEGER NOT NULL,
    Ai14 INTEGER NOT NULL,
    Ai65 INTEGER NOT NULL,
    Ai75 INTEGER NOT NULL,
    Ai80 INTEGER NOT NULL,
    Ai148 INTEGER NOT NULL,
    Ai162 INTEGER NOT NULL,
    G2C INTEGER NOT NULL,
    VGC INTEGER NOT NULL,
    VRC INTEGER NOT NULL,
    PVF INTEGER NOT NULL,
    SLF INTEGER NOT NULL,
    Line INTEGER NOT NULL,
    Room INTEGER NOT NULL,
    Experimental_Status INTEGER NOT NULL,
    Genotyping_Status INTEGER NOT NULL,
    Alive INTEGER NOT NULL,
    Notes TEXT,

    FOREIGN KEY (Sex) REFERENCES Sex_table (ID)
    FOREIGN KEY (Breeding_status) REFERENCES Breeders_table (ID)
    FOREIGN KEY (Label) REFERENCES Labels_table (ID)
    FOREIGN KEY (Parent_Breeding) REFERENCES Breedings_table (ID)
    FOREIGN KEY (Ai14) REFERENCES Genotypes_table (ID)
    FOREIGN KEY (Ai65) REFERENCES Genotypes_table (ID)
    FOREIGN KEY (Ai75) REFERENCES Genotypes_table (ID)
    FOREIGN KEY (Ai80) REFERENCES Genotypes_table (ID)
    FOREIGN KEY (Ai148) REFERENCES Genotypes_table (ID)
    FOREIGN KEY (Ai162) REFERENCES Genotypes_table (ID)
    FOREIGN KEY (VGC) REFERENCES Genotypes_table (ID)
    FOREIGN KEY (VRC) REFERENCES Genotypes_table (ID)
    FOREIGN KEY (PVF) REFERENCES Genotypes_table (ID)
    FOREIGN KEY (SLF) REFERENCES Genotypes_table (ID)
    FOREIGN KEY (Line) REFERENCES Lines_table (ID)
    FOREIGN KEY (Room) REFERENCES Rooms_table (ID)
    FOREIGN KEY (Experimental_Status) REFERENCES Experimental_table (ID)
    FOREIGN KEY (Genotyping_Status) REFERENCES Genotypings_table (ID)

    );
"""
)
#%%

Sex_table.to_sql('Sex_table', db_conn, if_exists='append', index=False)
Rooms_table.to_sql('Rooms_table', db_conn, if_exists='append', index=False)
Action_types_table.to_sql('Action_types_table', db_conn, if_exists='append', index=False)
Lines_table.to_sql('Lines_table', db_conn, if_exists='append', index=False)
Genes_table.to_sql('Genes_table', db_conn, if_exists='append', index=False)
Genotypes_table.to_sql('Genotypes_table', db_conn, if_exists='append', index=False)
Genotyping_status_table.to_sql('Genotypings_table', db_conn, if_exists='append', index=False)
Breeding_status_table.to_sql('Breeders_table', db_conn, if_exists='append', index=False)
Experimental_status_table.to_sql('Experimental_table', db_conn, if_exists='append', index=False)
Labels_table.to_sql('Labels_table', db_conn, if_exists='append', index=False)
Breedings_table.to_sql('Breedings_table', db_conn, if_exists='append', index=False)
Litters_table.to_sql('Litters_table', db_conn, if_exists='append', index=False)
Actions_table.to_sql('Actions_table', db_conn, if_exists='append', index=False)
Mice_table.to_sql('MICE_table', db_conn, if_exists='append', index=False)

#%%
db_conn = sqlite3.connect(databasefile)
c = db_conn.cursor()
db_conn.close()

#%%

# query3="""
# SELECT
#     Lab_number,
#     Sex_types,
#     Cage,
#     round(julianday('now') - julianday(DOB)) AS DaysOld,
#     round(round(julianday('now') - julianday(DOB))/7) AS WeeksOld,
#     Breeders_types,
#     Labels_types,
#     Line_Short,
#     Genotypings_types

# FROM MICE_table

# LEFT JOIN Breeders_table ON Breeders_table.ID=MICE_table.Breeding_status
# LEFT JOIN Labels_table ON Labels_table.ID=MICE_table.Label
# LEFT JOIN Sex_table ON Sex_table.ID=MICE_table.Sex
# LEFT JOIN Experimental_table ON Experimental_table.ID=MICE_table.Experimental_Status
# LEFT JOIN Genotypings_table ON Genotypings_table.ID=MICE_table.Genotyping_Status
# LEFT JOIN Lines_table ON Lines_table.ID=MICE_table.Line
# LEFT JOIN Rooms_table ON Rooms_table.ID=MICE_table.Room

# WHERE Alive=1 AND (Experimental_Status=1 OR Experimental_Status=3)  AND Breeding_status=3

# """

# Alive_non_exp = pd.read_sql_query(query3,db_conn)

# Alive_non_exp.sort_values(by=['Sex_types'],ascending=False)
# new=    Alive_non_exp.sort_values(by=['Sex_types'],ascending=False)

# gk = new.groupby(['Breeders_types', 'Cage', 'Line_Short'])['Lab_Number'].apply(list)
# zz=gk.to_frame()
# tt=pd.DataFrame(zz.Lab_Number.values.tolist(),zz.index).add_prefix('Mouse_')
# %% changing the breeding mouse codes to indexes

# Breedings_table = pd.read_excel(
#     excelfile,
#     sheet_name='Breedings',
#     header=0)

# ChangeBreedings=Breedings_table
#%%

#             #%%
# unique=list(ChangeBreedings.Male.unique())
# list_to_replace=unique[:-2]
# list_to_replace.remove(np.nan)
# new_list=[Mice_table._get_value(Mice_table.index[Mice_table['Lab_Number'] == mouse].tolist()[0],  'ID') for  mouse in list_to_replace ]
# ChangeBreedings[['Male']]=ChangeBreedings[['Male']].replace(list_to_replace,new_list)

# unique=list(ChangeBreedings.Female1.unique())
# list_to_replace=unique[:-2]
# list_to_replace.remove(np.nan)
# new_list=[Mice_table._get_value(Mice_table.index[Mice_table['Lab_Number'] == mouse].tolist()[0],  'ID') for  mouse in list_to_replace ]
# ChangeBreedings[['Female1']]=ChangeBreedings[['Female1']].replace(list_to_replace,new_list)

# unique=list(ChangeBreedings.Female2.unique())
# list_to_replace=unique[:-2]
# list_to_replace.remove(np.nan)
# new_list=[Mice_table._get_value(Mice_table.index[Mice_table['Lab_Number'] == mouse].tolist()[0],  'ID') for  mouse in list_to_replace ]
# ChangeBreedings[['Female2']]=ChangeBreedings[['Female2']].replace(list_to_replace,new_list)

#%% change action lab number to codes

# Actions_table = pd.read_excel(
#     excelfile,
#     sheet_name='Actions',
#     header=0)

# unique=list(Actions_table.Mouse_1.unique())
# list_to_replace=unique
# new_list=[Mice_table._get_value(Mice_table.index[Mice_table['Lab_Number'] == mouse].tolist()[0],  'ID') for  mouse in list_to_replace ]
# Actions_table[['Mouse_1']]=Actions_table[['Mouse_1']].replace(list_to_replace,new_list)

# unique=list(Actions_table.Mouse_2.unique())
# list_to_replace=unique
# list_to_replace.pop(9)
# new_list=[Mice_table._get_value(Mice_table.index[Mice_table['Lab_Number'] == mouse].tolist()[0],  'ID') for  mouse in list_to_replace ]
# Actions_table[['Mouse_2']]=Actions_table[['Mouse_2']].replace(list_to_replace,new_list)

# unique=list(Actions_table.Mouse_3.unique())
# list_to_replace=unique
# list_to_replace.pop(3)
# new_list=[Mice_table._get_value(Mice_table.index[Mice_table['Lab_Number'] == mouse].tolist()[0],  'ID') for  mouse in list_to_replace ]
# Actions_table[['Mouse_3']]=Actions_table[['Mouse_3']].replace(list_to_replace,new_list)

# unique=list(Actions_table.Mouse_4.unique())
# list_to_replace=unique
# list_to_replace.pop(2)
# new_list=[Mice_table._get_value(Mice_table.index[Mice_table['Lab_Number'] == mouse].tolist()[0],  'ID') for  mouse in list_to_replace ]
# Actions_table[['Mouse_4']]=Actions_table[['Mouse_4']].replace(list_to_replace,new_list)

# unique=list(Actions_table.Mouse_5.unique())
# list_to_replace=unique
# list_to_replace.pop(0)
# new_list=[Mice_table._get_value(Mice_table.index[Mice_table['Lab_Number'] == mouse].tolist()[0],  'ID') for  mouse in list_to_replace ]
# Actions_table[['Mouse_5']]=Actions_table[['Mouse_5']].replace(list_to_replace,new_list)

# Actions_table['Mouse_2'] = Actions_table['Mouse_2'].astype('Int64')
# Actions_table['Mouse_3'] = Actions_table['Mouse_3'].astype('Int64')
# Actions_table['Mouse_4'] = Actions_table['Mouse_4'].astype('Int64')
# Actions_table['Mouse_5'] = Actions_table['Mouse_5'].astype('Int64')


import argparse
import json
import codecs
import numpy as np
import h5py
import matplotlib.pyplot as plt

parser = argparse.ArgumentParser()
parser.add_argument('--reddit', default='../Data/Reddit/Sequences.txt')
parser.add_argument('--redditSequences', default='../Data/Reddit/Sequences.json')
parser.add_argument('--wikipedia', default='../Data/Wikipedia/Summaries.txt')
parser.add_argument('--wikipediaSentences', default='../Data/Wikipedia/Sentences.json')
parser.add_argument('--padding', action='store_true', default=True)
parser.add_argument('--alignedSentences', default=20)
parser.add_argument('--redditOutput', default='../Aligned-Dataset/reddit.h5')
parser.add_argument('--wikipediaOutput', default='../Aligned-Dataset/wikipedia.h5')
parser.add_argument('--dictionary', default='../Aligned-Dataset/dictionary.json')
parser.add_argument('--validate', type=float, default=0.1)
parser.add_argument('--test', type=float, default=0.1)
parser.add_argument('--encoding', default='utf-8')
args = parser.parse_args()

id2word = {}
word2id = {}
word2count = {}
vocab_length = 0
id2element = {}
element2id = {}
elements_length = 0

with codecs.open(args.wikipedia, 'r', 'utf-8') as wikipedia:
    wikipedia_dataset = wikipedia.read().split()
    wikipedia.close()

    with codecs.open(args.reddit, 'r', 'utf-8') as reddit:
        reddit_dataset = reddit.read().split()
        reddit.close()
        dataset = wikipedia_dataset + reddit_dataset

        wikipedia_size = len(wikipedia_dataset)
        reddit_size = len(reddit_dataset)
        size = len(dataset)
        print ('Total number of words included in the Wikipedia dataset: %d' % (wikipedia_size))
        print ('Total number of words included in the reddit dataset: %d' % (reddit_size))
        print ('Total number of words included in the aggregated dataset: %d' % (size))

        vocab_length = vocab_length + 1
        word2id['NaN'.decode('utf-8')] = vocab_length
        id2word[vocab_length] = 'NaN'.decode('utf-8')

        # Remove infrequent words from the sequences of comments.

        for i in range(0, wikipedia_size):
             if wikipedia_dataset[i] not in word2count:
                word2count[wikipedia_dataset[i]] = 1
             else:
                 word2count[wikipedia_dataset[i]] = word2count[wikipedia_dataset[i]] + 1
                 if wikipedia_dataset[i] not in word2id:
                     vocab_length = vocab_length + 1
                     word2id[wikipedia_dataset[i]] = vocab_length
                     id2word[vocab_length] = wikipedia_dataset[i]
        print ('Size of the vocabulary after processing the Wikipedia dataset: %d' % (vocab_length))

        for i in range(0, reddit_size):
            if reddit_dataset[i] not in word2count:
                word2count[reddit_dataset[i]] = 1
            elif word2count[reddit_dataset[i]] <= 2:
                word2count[reddit_dataset[i]] = word2count[reddit_dataset[i]] + 1
            else:
                word2count[reddit_dataset[i]] = word2count[reddit_dataset[i]] + 1
                if reddit_dataset[i] not in word2id:
                    vocab_length = vocab_length + 1
                    word2id[reddit_dataset[i]] = vocab_length
                    id2word[vocab_length] = reddit_dataset[i]

if args.padding:
    vocab_length = vocab_length + 1
    word2id['<PAD>'.decode('utf-8')] = vocab_length
    id2word[vocab_length] = '<PAD>'.decode('utf-8')

print ('Size of the vocabulary: %d' % (vocab_length))

# Load Wikipedia sentences along with their corresponding lengths.

with open (args.wikipediaSentences, 'r') as f:
    sentences = json.load(f, 'utf-8')
    f.close()

wiki_sentences = sentences['wiki_sentences']
wiki_elements = sentences['wiki_elements']
wiki_sentences_length = sentences['wiki_sentences_length']
num_wiki_sentences = len(wiki_sentences)

max_tokens = 0
for i in range(0, num_wiki_sentences):
    if len(wiki_sentences[i]) > max_tokens:
        max_tokens = len(wiki_sentences[i])

print ('Max sentence length is: %d' % (max_tokens))

for i in range(0, len(wiki_sentences)):
    if wiki_elements[i] not in element2id:
        elements_length = elements_length + 1
        element2id[wiki_elements[i]] = elements_length
        id2element[elements_length] = wiki_elements[i]

# Load reddit sequences.

with open (args.redditSequences, 'r') as f:
    sequences = json.load(f, 'utf-8')
    f.close()

tmpSequences = []
tmpElements = []
sequences_length = []
num_sequences = 0

for element in sequences:
    for j in range(0, len(sequences[element])):
        tmpSequences.append(sequences[element][j])
        tmpElements.append(element)
        sequences_length.append(len(sequences[element][j].split()))
        num_sequences = num_sequences + 1

reddit_lengths = np.asarray(sequences_length)
reddit_mean = np.mean(reddit_lengths)
reddit_std = np.std(reddit_lengths)
reddit_maximum = np.amax(reddit_lengths)

# Disregard sequences whose length exceeds a specific threshold.
threshold = reddit_mean + 1.0 * reddit_std

deleted = 0
tmpSequencesLength = sequences_length[:]
for i in range(0, num_sequences):
    if tmpSequencesLength[i] > threshold:
        del tmpSequences[i - deleted]
        del tmpElements[i - deleted]
        del sequences_length[i - deleted]
        deleted = deleted + 1

reddit_lengths = np.asarray(sequences_length)
reddit_mean = np.mean(reddit_lengths)
reddit_std = np.std(reddit_lengths)
reddit_maximum = np.amax(reddit_lengths)

print ('Mean sequence length is: %d' % (reddit_mean))
print ('Max sequence length is: %d' % (reddit_maximum))
print ('Standard deviation of the lengths of the sampled sequences is: %d' % (reddit_std))

reddit_validate_sequences = np.floor(args.validate * len(tmpSequences))
reddit_test_sequences = np.floor(args.test * len(tmpSequences))
reddit_train_sequences = len(tmpSequences) - reddit_validate_sequences - reddit_test_sequences

aligned_train_dataset = []
aligned_validate_dataset = []
aligned_test_dataset = []

# The flagElement corresponds to the position of the last sentence that has been aligned with an already processed sequence of comments.
flagElement = {}

for key in element2id:
    flagElement[key] = 0
totalSequences = [0, 0, 0]

while len(tmpSequences) > 0:

    sequence = np.random.randint(0, len(tmpSequences))

    if totalSequences[1] < reddit_validate_sequences and totalSequences[2] < reddit_test_sequences:
        random = np.random.randint(0, 3)
    elif totalSequences[1] >= reddit_validate_sequences and totalSequences[2] < reddit_test_sequences:
        random = np.random.randint(0, 2)
        if random == 1:
            random = random + 1
    elif totalSequences[2] >= reddit_test_sequences and totalSequences[1] < reddit_validate_sequences:
        random = np.random.randint(0, 2)
    else:
        random = 0

    if random == 1 and totalSequences[1] < reddit_validate_sequences:
        aligned_validate_dataset.append({'sentences': [], 'sequence': tmpSequences[sequence].split()})
        totalSequences[1] = totalSequences[1] + 1
        find = 0
        while wiki_elements[find] != tmpElements[sequence]:
            find = find + 1
        included = 0
        while included < args.alignedSentences:
            if find + flagElement[tmpElements[sequence]] + included < len(wiki_sentences):
                if wiki_elements[find + flagElement[tmpElements[sequence]] + included] == tmpElements[sequence]:
                    aligned_validate_dataset[len(aligned_validate_dataset) - 1]['sentences'].append(wiki_sentences[find + flagElement[tmpElements[sequence]] + included])
                    included = included + 1
                else:
                    flagElement[tmpElements[sequence]] = 0
            else:
                flagElement[tmpElements[sequence]] = 0
                print('Resetting end-flag for the Element: %s...' % (tmpElements[sequence]))
        flagElement[tmpElements[sequence]] = flagElement[tmpElements[sequence]] + included
        tmpSequences.pop(sequence)
        tmpElements.pop(sequence)
        sequences_length.pop(sequence)

    elif random == 2 and totalSequences[2] < reddit_test_sequences:
        aligned_test_dataset.append({'sentences': [], 'sequence': tmpSequences[sequence].split()})
        totalSequences[2] = totalSequences[2] + 1
        find = 0
        while wiki_elements[find] != tmpElements[sequence]:
            find = find + 1
        included = 0
        while included < args.alignedSentences:
            if find + flagElement[tmpElements[sequence]] + included < len(wiki_sentences):
                if wiki_elements[find + flagElement[tmpElements[sequence]] + included] == tmpElements[sequence]:
                    aligned_test_dataset[len(aligned_test_dataset) - 1]['sentences'].append(wiki_sentences[find + flagElement[tmpElements[sequence]] + included])
                    included = included + 1
                else:
                    flagElement[tmpElements[sequence]] = 0
            else:
                flagElement[tmpElements[sequence]] = 0
                print('Resetting end-flag for the Element: %s...' % (tmpElements[sequence]))
        flagElement[tmpElements[sequence]] = flagElement[tmpElements[sequence]] + included
        tmpSequences.pop(sequence)
        tmpElements.pop(sequence)
        sequences_length.pop(sequence)

    else:
        #reddit_train_dataset = reddit_train_dataset + tmpSequences[sequence]
        aligned_train_dataset.append({'sentences': [], 'sequence': tmpSequences[sequence].split()})
        totalSequences[0] = totalSequences[0] + 1
        find = 0
        while wiki_elements[find] != tmpElements[sequence]:
            find = find + 1
        included = 0
        while included < args.alignedSentences:
            if find + flagElement[tmpElements[sequence]] + included < len(wiki_sentences):
                if wiki_elements[find + flagElement[tmpElements[sequence]] + included] == tmpElements[sequence]:
                    aligned_train_dataset[len(aligned_train_dataset) - 1]['sentences'].append(wiki_sentences[find + flagElement[tmpElements[sequence]] + included])
                    included = included + 1
                else:
                    flagElement[tmpElements[sequence]] = 0
            else:
                flagElement[tmpElements[sequence]] = 0
                print('Resetting end-flag for the Element: %s...' % (tmpElements[sequence]))
        flagElement[tmpElements[sequence]] = flagElement[tmpElements[sequence]] + included
        tmpSequences.pop(sequence)
        tmpElements.pop(sequence)
        sequences_length.pop(sequence)

aligned_reddit_train = np.zeros((len(aligned_train_dataset), reddit_maximum), dtype=np.uint32)
aligned_reddit_validate = np.zeros((len(aligned_validate_dataset), reddit_maximum), dtype=np.uint32)
aligned_reddit_test = np.zeros((len(aligned_test_dataset), reddit_maximum), dtype=np.uint32)

aligned_wiki_train = np.zeros((args.alignedSentences * len(aligned_train_dataset), max_tokens), dtype=np.uint32)
aligned_wiki_validate = np.zeros((args.alignedSentences * len(aligned_validate_dataset), max_tokens), dtype=np.uint32)
aligned_wiki_test = np.zeros((args.alignedSentences * len(aligned_test_dataset), max_tokens), dtype=np.uint32)

for i in range(0, len(aligned_train_dataset)):
    for j in range(0, len(aligned_train_dataset[i]['sequence'])):
        if aligned_train_dataset[i]['sequence'][j] in word2id:
            aligned_reddit_train[i][j] = word2id[aligned_train_dataset[i]['sequence'][j]]
        else:
            aligned_reddit_train[i][j] = word2id['NaN']
    for z in range(len(aligned_train_dataset[i]['sequence']), reddit_maximum):
                aligned_reddit_train[i][z] = word2id['<PAD>']
    for j in range(0, len(aligned_train_dataset[i]['sentences'])):
        for z in range(0, len(aligned_train_dataset[i]['sentences'][j])):
            if aligned_train_dataset[i]['sentences'][j][z] in word2id:
                aligned_wiki_train[args.alignedSentences * i + j][z] = word2id[aligned_train_dataset[i]['sentences'][j][z]]
            else:
                aligned_wiki_train[args.alignedSentences * i + j][z] = word2id['NaN']
        for t in range(len(aligned_train_dataset[i]['sentences'][j]), max_tokens):
                aligned_wiki_train[args.alignedSentences * i + j][t] = word2id['<PAD>']

for i in range(0, len(aligned_validate_dataset)):
    for j in range(0, len(aligned_validate_dataset[i]['sequence'])):
        if aligned_validate_dataset[i]['sequence'][j] in word2id:
            aligned_reddit_validate[i][j] = word2id[aligned_validate_dataset[i]['sequence'][j]]
        else:
            aligned_reddit_validate[i][j] = word2id['NaN']
    for z in range(len(aligned_validate_dataset[i]['sequence']), reddit_maximum):
                aligned_reddit_validate[i][z] = word2id['<PAD>']
    for j in range(0, len(aligned_validate_dataset[i]['sentences'])):
        for z in range(0, len(aligned_validate_dataset[i]['sentences'][j])):
            if aligned_validate_dataset[i]['sentences'][j][z] in word2id:
                aligned_wiki_validate[args.alignedSentences * i + j][z] = word2id[aligned_validate_dataset[i]['sentences'][j][z]]
            else:
                aligned_wiki_validate[args.alignedSentences * i + j][z] = word2id['NaN']
        for t in range(len(aligned_validate_dataset[i]['sentences'][j]), max_tokens):
                aligned_wiki_validate[args.alignedSentences * i + j][t] = word2id['<PAD>']

for i in range(0, len(aligned_test_dataset)):
    for j in range(0, len(aligned_test_dataset[i]['sequence'])):
        if aligned_test_dataset[i]['sequence'][j] in word2id:
            aligned_reddit_test[i][j] = word2id[aligned_test_dataset[i]['sequence'][j]]
        else:
            aligned_reddit_test[i][j] = word2id['NaN']
    for z in range(len(aligned_test_dataset[i]['sequence']), reddit_maximum):
                aligned_reddit_test[i][z] = word2id['<PAD>']
    for j in range(0, len(aligned_test_dataset[i]['sentences'])):
        for z in range(0, len(aligned_test_dataset[i]['sentences'][j])):
            if aligned_test_dataset[i]['sentences'][j][z] in word2id:
                aligned_wiki_test[args.alignedSentences * i + j][z] = word2id[aligned_test_dataset[i]['sentences'][j][z]]
            else:
                aligned_wiki_test[args.alignedSentences * i + j][z] = word2id['NaN']
        for t in range(len(aligned_test_dataset[i]['sentences'][j]), max_tokens):
                aligned_wiki_test[args.alignedSentences * i + j][t] = word2id['<PAD>']

with h5py.File(args.wikipediaOutput, 'w') as f:
    f.create_dataset('train', data=aligned_wiki_train)
    f.create_dataset('validate', data=aligned_wiki_validate)
    f.create_dataset('test', data=aligned_wiki_test)

with h5py.File(args.redditOutput, 'w') as f:
    f.create_dataset('train', data=aligned_reddit_train)
    f.create_dataset('validate', data=aligned_reddit_validate)
    f.create_dataset('test', data=aligned_reddit_test)

dictionary = {'word2id': word2id, 'id2word': id2word}
with open(args.dictionary, 'w') as f:
    json.dump(dictionary, f, encoding='utf-8')


import cv2
import numpy as np
import torch
import torch.nn as nn
import torchvision
import torchvision.models as model
from torchsummary import summary
from collections import OrderedDict
import torch.nn.init as init
from dataset import voc_loader as loader
import torchvision.transforms as transforms

class L2Norm(nn.Module):
    def __init__(self, n_channels, scale):
        super(L2Norm, self).__init__()
        self.n_channels = n_channels
        self.gamma = scale or None
        self.eps = 1e-10
        self.weight = nn.Parameter(torch.Tensor(self.n_channels))
        self.reset_parameters()

    def reset_parameters(self):
        init.constant_(self.weight, self.gamma)

    def forward(self, x):
        norm = x.pow(2).sum(dim=1, keepdim=True).sqrt()+self.eps
        #x /= norm
        x = torch.div(x, norm)
        out = self.weight.unsqueeze(0).unsqueeze(2).unsqueeze(3).expand_as(x) * x
        return out

class SSD(nn.Module):
    def __init__(self, pretrained=True):
        super(SSD, self).__init__()

        # module list 로 둔 이유는
        self.vgg = nn.ModuleList(vgg(cfg['300'], 3))
        # self.vgg = vgg(cfg['300'], 3)
        if pretrained:
            vgg_weights = torch.load('./vgg16_reducedfc.pth')
            self.vgg.load_state_dict(vgg_weights)

        conv_8_1 = nn.Conv2d(in_channels=1024, out_channels=256, kernel_size=1)
        conv_8_2 = nn.Conv2d(in_channels=256, out_channels=512, kernel_size=3, padding=1, stride=2)
        conv_9_1 = nn.Conv2d(in_channels=512, out_channels=128, kernel_size=1)
        conv_9_2 = nn.Conv2d(in_channels=128, out_channels=256, kernel_size=3, padding=1, stride=2)
        conv_10_1 = nn.Conv2d(in_channels=256, out_channels=128, kernel_size=1)
        conv_10_2 = nn.Conv2d(in_channels=128, out_channels=256, kernel_size=3,)
        conv_11_1 = nn.Conv2d(in_channels=256, out_channels=128, kernel_size=1)
        conv_11_2 = nn.Conv2d(in_channels=128, out_channels=256, kernel_size=3)

        self.extras = nn.ModuleList([conv_8_1,  nn.ReLU(True),
                                     conv_8_2,  nn.ReLU(True),
                                     conv_9_1,  nn.ReLU(True),
                                     conv_9_2,  nn.ReLU(True),
                                     conv_10_1,  nn.ReLU(True),
                                     conv_10_2,  nn.ReLU(True),
                                     conv_11_1,  nn.ReLU(True),
                                     conv_11_2,  nn.ReLU(True)])

        self.L2Norm = L2Norm(512, 20)
        self.dbox = dbox['300']

        loc4_3 = nn.Conv2d(in_channels=512, out_channels=self.dbox[0] * 4, kernel_size=3, padding=1)
        loc7 = nn.Conv2d(in_channels=1024, out_channels=self.dbox[1] * 4, kernel_size=3, padding=1)
        loc8_2 = nn.Conv2d(in_channels=512, out_channels=self.dbox[2] * 4, kernel_size=3, padding=1)
        loc9_2 = nn.Conv2d(in_channels=256, out_channels=self.dbox[3] * 4, kernel_size=3, padding=1)
        loc10_2 = nn.Conv2d(in_channels=256, out_channels=self.dbox[4] * 4, kernel_size=3, padding=1)
        loc11_2 = nn.Conv2d(in_channels=256, out_channels=self.dbox[5] * 4, kernel_size=3, padding=1)

        cls4_3 = nn.Conv2d(in_channels=512, out_channels=self.dbox[0] * 21, kernel_size=3, padding=1)
        cls7 = nn.Conv2d(in_channels=1024, out_channels=self.dbox[1] * 21, kernel_size=3, padding=1)
        cls8_2 = nn.Conv2d(in_channels=512, out_channels=self.dbox[2] * 21, kernel_size=3, padding=1)
        cls9_2 = nn.Conv2d(in_channels=256, out_channels=self.dbox[3] * 21, kernel_size=3, padding=1)
        cls10_2 = nn.Conv2d(in_channels=256, out_channels=self.dbox[4] * 21, kernel_size=3, padding=1)
        cls11_2 = nn.Conv2d(in_channels=256, out_channels=self.dbox[5] * 21, kernel_size=3, padding=1)

        self.loc = nn.ModuleList([loc4_3,
                                  loc7,
                                  loc8_2,
                                  loc9_2,
                                  loc10_2,
                                  loc11_2])

        self.cls = nn.ModuleList([cls4_3,
                                  cls7,
                                  cls8_2,
                                  cls9_2,
                                  cls10_2,
                                  cls11_2])

    def forward(self, x):
        """
        여기서 output 은 결과적으로 loc prediction 과 cls prediction 입니다.
        :param x: input 이미지 batch data
        :return: loc, cls 입니다.
        """

        features = []  # 필요한 feature 를 담는 부분 : conv4_3 , ... , conv11_2
        loc = []
        cls = []

        for i in range(22):
            x = self.vgg[i](x)

        conv4_3 = self.L2Norm(x)
        features.append(conv4_3) # conv 4_3

        for i in range(23, len(self.vgg)):
            x = self.vgg[i](x)

        conv7 = x
        features.append(conv7)  # conv 7

        for i, ex_layer in enumerate(self.extras):
            x = ex_layer(x)
            # if i % 4 == 3:  # 4개의 한번꼴로
            #     features.append(x)
            if i == 3:
                conv8_2 = x    # conv 8_2
                features.append(conv8_2)
            if i == 7:
                conv9_2 = x    # conv 9_2
                features.append(conv9_2)
            if i == 11:
                conv10_2 = x    # conv 10_2
                features.append(conv10_2)
            if i == 15:
                conv11_2 = x    # conv 11_2
                features.append(conv11_2)

        for feature, l, c in zip(features, self.loc, self.cls):

            loc.append(l(feature).permute(0, 2, 3, 1).contiguous())
            cls.append(c(feature).permute(0, 2, 3, 1).contiguous())

        loc = torch.cat([o.view(o.size(0), -1) for o in loc], 1)  # torch.Size([B, 34928])
        cls = torch.cat([o.view(o.size(0), -1) for o in cls], 1)  # torch.Size([B, 183372])

        loc = loc.view(loc.size(0), -1, 4),  # torch.Size([B, 8732, 4])
        cls = cls.view(cls.size(0), -1, 21),  # torch.Size([B, 8732, 21])

        # issue
        # view 를 사용했는데 loc 가 갑자기 tuple 이 되버림????

        # return 이 tuple 이다.
        return loc, cls

# This function is derived from torchvision VGG make_layers()
# https://github.com/pytorch/vision/blob/master/torchvision/models/vgg.py
def vgg(cfg, input_ch):
    '''
    fc-reduced vgg 사용하기 위해서 vgg 만드는 부분!
    :param cfg: str arr : vgg 의 구성을 나타내는 string array
    :return: nn.module 들의 layer 리스트!
    '''
    layers = []
    in_channels = input_ch

    # feature extractor

    for v in cfg:
        if v == 'M':
            layers += [nn.MaxPool2d(kernel_size=2, stride=2)]
        elif v == 'C':
            layers += [nn.MaxPool2d(kernel_size=2, stride=2, ceil_mode=True)]
        else:
            layers += [nn.Conv2d(in_channels, v, kernel_size=3, padding=1)]
            layers += [nn.ReLU(inplace=True)]
            in_channels = v

    # classifier

    layers += [nn.MaxPool2d(kernel_size=3, stride=1, padding=1)]
    layers += [nn.Conv2d(512, 1024, kernel_size=3, dilation=6, padding=6)]
    layers += [nn.ReLU(True)]
    layers += [nn.Conv2d(1024, 1024, kernel_size=1)]
    layers += [nn.ReLU(True)]

    # return nn.Sequential(*layers)
    return layers

cfg = {
    '300': [64, 64, 'M', 128, 128, 'M', 256, 256, 256, 'C', 512, 512, 512, 'M',
            512, 512, 512],
    '512': [],
}

dbox = {
    '300': [4, 6, 6, 6, 4, 4],  # number of boxes per feature map location
    '512': [],
}

if __name__ == "__main__":
    transform = transforms.Compose(
        [
            transforms.Resize((300, 300)),
            transforms.ToTensor()
         ])

    # 얘는 img 에 대해서만 하는거임

    root_dir = "D:\Data\\voc\\2012"
    trainset = loader.VOC_loader(root_dir, transform=transform)

    # # img
    # # 이미지 하나씩 가져오는 부분
    # for i in range(len(trainset)):
    #     image, annotation, scale = trainset[i]
    #
    #     img = np.array(image)
    #     img = img.transpose((1, 2, 0))
    #     img *= 255
    #     img = img[:, :, ::-1].astype(np.uint8)
    #
    #     annotation = np.array(annotation)
    #     annotation[:, 0] *= scale[1]
    #     annotation[:, 2] *= scale[1]
    #     annotation[:, 1] *= scale[0]
    #     annotation[:, 3] *= scale[0]
    #
    #     for i in range(len(annotation)):
    #         img = cv2.rectangle(img, (int(annotation[i][0]), int(annotation[i][1])),
    #                             (int(annotation[i][2]), int(annotation[i][3])), (255, 255, 0), 3)
    #
    #     cv2.imshow('image', img)
    #     cv2.waitKey(0)

    trainloader = torch.utils.data.DataLoader(trainset, batch_size=32, shuffle=True, num_workers=0)

    device = torch.device("cuda" if torch.cuda.is_available() else "cpu")
    net = SSD().to(device)

    for epoch in range(10):

        running_loss = 0.0
        for i, (images, labels) in enumerate(trainloader):
            images = images.to(device)
            # labels = labels.to(device)

            out = net(images)
            print(out)
            out = 1


import requests
import telegram
from telegram.ext import CommandHandler, MessageHandler, Filters, Updater
import torch
from torchvision.datasets import ImageFolder
import torchvision.transforms as transforms
import os
import datetime
from torch.utils.data import DataLoader
import torch.nn as nn

# Define the image folder path
IMAGE_FOLDER = 'images'

# Create the image folder if it doesn't exist
if not os.path.exists(IMAGE_FOLDER):
    os.makedirs(IMAGE_FOLDER)

# Define the transformations to be applied to the images
transform = transforms.Compose([
    transforms.Resize((64, 64)),
    transforms.ToTensor(),
    transforms.Normalize((0.5, 0.5, 0.5), (0.5, 0.5, 0.5)),
])

# Create a dataset from the images in the directory
dataset = ImageFolder(root=IMAGE_FOLDER, transform=transform)

# Create a data loader that loads images from the dataset in batches
batch_size = 64
dataloader = torch.utils.data.DataLoader(dataset, batch_size=batch_size, shuffle=True)

batch_size = 32
shuffle = True

data_loader = DataLoader(dataset, batch_size=batch_size, shuffle=shuffle)

# Save the data loader to a file so that it can be used in the training script
torch.save(data_loader, 'data_loader.pth')

# Load the trained generator network
generator = torch.load('data_loader.pth')

# Replace YOUR_TOKEN with your bot's API token
bot = telegram.Bot(token='put your bot api here')

def start(update, context, my_generator):
    context.bot.send_message(chat_id=update.effective_chat.id, text="Hello! Please describe the image you want me to generate. Be as specific as possible, such as the colors, objects, shapes, etc.")
    # if user sends a description, generate an image from it
    if not update.message.text:
        context.bot.send_message(chat_id=update.effective_chat.id, text="Please describe the image you want me to generate. Be as specific as possible, such as the colors, objects, shapes, etc.")
    else:
        generate_image(update, context, my_generator)

def train(update, context):
    # Check if there is a saved image for the user
    user_image_path = os.path.join(IMAGE_FOLDER, str(update.effective_chat.id) + '.jpg')
    if not os.path.exists(user_image_path):
        context.bot.send_message(chat_id=update.effective_chat.id, text="Please send me an image to train the model.")
        return
    # Call the save_image function to save the image
    save_image(update, context)

def save_image(update, context):
    # Checl if the message contains an image
    if not update.message.photo:
        context.bot.send_message(chat_id=update.effective_chat.id, text="Please send me an image.")
        return
    # Get the file ID of the image sent by the user
    file_id = update.message.photo[-1].file_id
    # Download the photo
    file = context.bot.get_file(file_id)
    # Name the image file with the user's ID
    now = datetime.datetime.utcnow().strftime("%Y-%m-%d-%H-%M-%S-UTC")
    filename = f"{update.effective_chat.id}-{now}.jpg"
    # Save the image file
    file.download(os.path.join(IMAGE_FOLDER, filename))
    context.bot.send_message(chat_id=update.effective_chat.id, text="Image saved successfully!")

def generate_image(update, context, my_generator):
    # Get the user's input from the message text
    input_text = update.message.text

    # Convert the user's input into a latent code
    latent_code = get_latent_code(input_text, my_generator)

    # Generate an image from the latent code
    with torch.no_grad():
        image = my_generator(latent_code)

    # Convert the image tensor to a PIL Image and save it
    transform = transforms.ToPILImage()
    image = transform(image)
    image.save('generated_image.jpg')

    # Send the generated image to the user
    with open('generated_image.jpg', 'rb') as f:
        context.bot.send_photo(chat_id=update.effective_chat.id, photo=f)

def echo(update, context):
    context.bot.send_message(chat_id=update.effective_chat.id, text=update.message.text)

def get_latent_code(input_text, my_generator):
    # Define the input size, hidden size, and latent size
    input_size = 100
    hidden_size = 256
    latent_size = 100

    # Define the text encoder network
    text_encoder = nn.Sequential(
        nn.Linear(input_size, hidden_size),
        nn.ReLU(),
        nn.Linear(hidden_size, latent_size),
        nn.Tanh()
    )
    # Convert the input text to a tensor
    text_tensor = torch.Tensor([input_text])

    # Generate a latent code from the text tensor
    with torch.no_grad():
        latent_code = text_encoder(text_tensor)

    return latent_code

# command handler to get image from description
def generate_images(update, context):
    description = update.message.text.split('/generate')[1]
    r = requests.get(f'https://api.unsplash.com/photos/random?query={description}&client_id=xKiAshqqBCZJ1QfaXMhkvCLfT_qhvcZq64kVfzMzoX8')
    if r.status_code == 200:
        photo_url = r.json()['urls']['regular']
        bot.send_photo(chat_id=update.effective_chat.id, photo=photo_url)
    else:
        bot.send_message(chat_id=update.effective_chat.id, text='Sorry, could not find an image.')

# message handler to reply to non-command messages
def reply(update, context):
    bot.send_message(chat_id=update.effective_chat.id, text='Sorry, I did not understand that. Please use /generate to get an image from a description.')

def main():
    updater = Updater(token='put your bot api here', use_context=True)
    dispatcher = updater.dispatcher

    # Create a generator object
    #generator = MyGenerator()
    # Define my_generator
    my_generator = generator

    # Register the start() function with the generator argument
    start_handler = CommandHandler('start', lambda update, context: start(update, context, my_generator), pass_args=True, pass_job_queue=True, pass_chat_data=True)

    #start_handler = CommandHandler('start', start)
    generate_image_handler = MessageHandler(Filters.text & (~Filters.command), generate_image)
    train_handler = CommandHandler('train', train)
    image_handler = MessageHandler(Filters.photo & (~Filters.command), save_image)
    echo_handler = MessageHandler(Filters.text & (~Filters.command), echo)

    # add handlers to dispatcher
    dispatcher.add_handler(CommandHandler('generate', generate_images))
    dispatcher.add_handler(MessageHandler(Filters.text & (~Filters.command), reply))
    dispatcher.add_handler(start_handler)
    dispatcher.add_handler(generate_image_handler)
    dispatcher.add_handler(train_handler)
    dispatcher.add_handler(image_handler)
    dispatcher.add_handler(echo_handler)

    updater.start_polling()
    updater.idle()

if __name__ == '__main__':
    main()


#描述：requests模块post爬取 百度翻译接口
import requests
import json

post_url = 'https://fanyi.baidu.com/extendtrans'

en = input('请输入你要翻译的内容：')
post_data = {
    'query': en,
    'from': 'zh',
    'to': 'en'
}
headers = {"User-Agent":"Mozilla/5.0 (iPhone; CPU iPhone OS 9_1 like Mac OS X) AppleWebKit/601.1.46 (KHTML, like Gecko) Version/9.0 Mobile/13B143 Safari/601.1"}

r = requests.post(post_url, headers=headers, data=post_data)

dict_response = json.loads(r.content.decode())
print('要翻译的内容是',en,'翻译为', dict_response['data']['st_tag'])


import time
import os.path

from LocalFileProgram import file_output, large_file_search, parse_csv
from MongoFiles import mongo_crud, mongo_file_export, start_kill_mongod, check_for_database, search_functions

if __name__ == "__main__":
    system_choice = 0

    while system_choice is not 9:
        print("Load from local file or from the database")
        print("  1. Local File")
        print("  2. Database")
        print("  9. Exit")
        try:
            system_choice = int(input("Enter your choice: "))
        except:
            print("Please enter a valid input...\n")

        if system_choice is 1:
            bst = large_file_search.BinarySearchTree()
            csv_path = input("Enter the file name including extension: ")

            # Validate that the file is in the currenty working directory.
            if os.path.isfile(csv_path) is not True:
                print("No file found...\n")
                continue
            else:
                print("File found...")

            user_choice = 0

            while user_choice is not 9:
                print("Menu:")
                print("  1. Load Bids")
                print("  2. Display all Bids")
                print("  3. Find Bid")
                print("  4. Remove Bid")
                print("  5. Create File")
                print("  9. Exit")
                try:
                    user_choice = int(input("Enter your choice: "))
                except:
                    print("Please enter a valid input...\n")
                    continue

                if user_choice is 1:
                    bst.load_bids(csv_path)
                elif user_choice is 2:
                    node = bst.root
                    bst.display_all_bids(node)
                elif user_choice is 3:
                    try:
                        search_bid = int(input("Enter a Bid ID: "))
                    except:
                        print("Invalid input...\n")
                        continue
                    found_bid = bst.search_tree(search_bid)

                    if found_bid is not None:
                        parse_csv.print_bid(found_bid.bid)
                    else:
                        print("No bid found...")
                elif user_choice is 4:
                    try:
                        deleted_bid = int(input("Enter a Bid ID: "))
                    except:
                        print("Invalid input...\n")

                    if bst.search_tree(deleted_bid) is None:
                        print("No bid found for deletion...")
                        continue

                    bst.root = bst.delete_bid(bst.root, deleted_bid)
                    print("Bid successfully deleted...")

                elif user_choice is 5:
                    file_name = input("Enter a file name: ")
                    labels = ["AuctionID", "AuctionTitle", "Fund", "AuctionFeeTotal"]

                    file_output.create_csv(file_name, bst, labels)
                    print("File successfully created at same file location as the Main Menu...")

        elif system_choice is 2:
            start_kill_mongod.start_mongod()
            time.sleep(0.25)

            check_for_database.check_for_database('localhost', 27017, 'CityData')

            # Ensures index for AuctionID is created
            mongo_crud.create_index('localhost', 27017, 'CityData', 'bids', 'AuctionID')

            mongo_choice = 0

            while mongo_choice is not 9:
                print("Menu:")
                print("  1. Create Bid")
                print("  2. Find Bid")
                print("  3. Update Bid")
                print("  4. Remove Bid")
                print("  5. Find Bids in Range Using Auction Fee Total")
                print("  6. Export Database to CSV")
                print("  9. Exit")
                try:
                    mongo_choice = int(input("Enter your choice: "))
                except:
                    print("Please enter a valid input...\n")
                    continue

                if mongo_choice is 1:
                    mongo_crud.create_bid('localhost', 27017, 'CityData', 'bids')
                if mongo_choice is 2:
                    try:
                        search_bid = int(input("Enter a Bid ID: "))
                    except:
                        print("Invalid input...\n")
                        continue

                    found_bid = mongo_crud.find_bid('localhost', 27017, 'CityData', 'bids', search_bid)

                    # handles TypeError if found_bid returns None.
                    if found_bid is None:
                        continue

                    mongo_crud.print_results(found_bid)
                if mongo_choice is 3:
                    try:
                        search_bid = int(input("Enter a Bid ID: "))
                    except:
                        print("Invalid input...\n")
                        continue

                    found_bid = mongo_crud.find_bid('localhost', 27017, 'CityData', 'bids', search_bid)

                    # handles TypeError if found_bid returns None.
                    if found_bid is None:
                        continue

                    mongo_crud.update_bid('localhost', 27017, 'CityData', 'bids', search_bid)
                    print("Update Successful...")
                if mongo_choice is 4:
                    try:
                        search_bid = int(input("Enter a Bid ID: "))
                    except:
                        print("Invalid input...\n")
                        continue

                    found_bid = mongo_crud.find_bid('localhost', 27017, 'CityData', 'bids', search_bid)

                    # handles TypeError if found_bid returns None.
                    if found_bid is None:
                        continue

                    mongo_crud.delete_bid('localhost', 27017, 'CityData', 'bids', search_bid)

                if mongo_choice is 5:
                    search_functions.check_values()
                if mongo_choice is 6:
                    # Exports the database to a CSV file located in 'C:\data\'
                    new_file_name = input("Enter a file name fore exporting: ")
                    mongo_file_export.export_collection(new_file_name)
                    time.sleep(2)

            # Killing the MongoDB database
            print("Shutting down MongdoDB database...\n")
            time.sleep(0.25)
            start_kill_mongod.kill_mongod()
            print("")


import json
import torch
from torch import nn
from transformers import RobertaModel, RobertaTokenizer

JSON_CONTENT_TYPE = 'application/json'
PRE_TRAINED_MODEL_NAME = 'roberta-base'
CLASS_NAMES = ['negative', 'neutral', 'positive']

class SentimentClassifier(nn.Module):

    def __init__(self, n_classes):
        super(SentimentClassifier, self).__init__()
        self.roberta = RobertaModel.from_pretrained(PRE_TRAINED_MODEL_NAME)
        self.drop = nn.Dropout(p=0.3)
        self.out = nn.Linear(self.roberta.config.hidden_size, n_classes)

    def forward(self, input_ids, attention_mask):
        _, pooled_output = self.roberta(input_ids=input_ids, attention_mask=attention_mask)
        output = self.drop(pooled_output)
        return self.out(output)

# defines the model
def model_fn(model_dir):
    model_path = f'{model_dir}/model.pth'
    model = SentimentClassifier(len(CLASS_NAMES))
    model.load_state_dict(torch.load(model_path, map_location='cpu'))
    return model

# Perform prediction on the deserialized object, with the loaded model
def predict_fn(input_data, model):
    MAX_LEN = 160
    tokenizer = RobertaTokenizer.from_pretrained(PRE_TRAINED_MODEL_NAME)

    review_text = input_data['text']

    encoded_review = tokenizer.encode_plus(
      review_text,
      max_length=MAX_LEN,
      add_special_tokens=True,
      return_token_type_ids=False,
      pad_to_max_length=True,
      return_attention_mask=True,
      return_tensors='pt',
    )
    input_ids = encoded_review['input_ids']
    attention_mask = encoded_review['attention_mask']

    output = model(input_ids, attention_mask)
    _, prediction = torch.max(output, dim=1)
    return CLASS_NAMES[prediction]

def input_fn(serialized_input_data, content_type=JSON_CONTENT_TYPE):
    if content_type == JSON_CONTENT_TYPE:
        input_data = json.loads(serialized_input_data)
        return input_data
    else:
        pass

def output_fn(prediction_output, accept=JSON_CONTENT_TYPE):
    if accept == JSON_CONTENT_TYPE:
        return json.dumps(prediction_output), accept
    raise Exception('Requested unsupported ContentType in Accept: ' + accept)


'''
File with analytic versions of the transfer functions in the LHC Cavity Loop.

Taken from LHC-RF - LHC-LLRF repository on gitlab.

Author: Birk Emil Karlsen-Bæck
'''

import numpy as np

def FeedbackTF(f, g_d, tau_d, g_a, tau_a, delta_phi):
    """Evaluate the feedback transfer function for the given array of frequencies (f).

    Parameters
    ----------
     f   :   numpy.ndarray or Number
        array of frequencies at which the transfer function should be evaluated
    """

    # NOTE: changed to positive Ga, but was:  -self.gain_analog

    w = 2 * np.pi * f

    # fraction 1: \\frac{G_{D} e^{\\Delta\\varphi \\frac{\\pi}{180} i}}{1+\\omega \\tau_{D} i}
    num1 = g_d * np.exp(np.radians(delta_phi) * 1j)
    den1 = 1 + w * tau_d * 1j

    # fraction 2: \\frac{\\tau_{A} \\omega}{\\tau_{A} \\omega-i}
    num2 = tau_a * w
    den2 = tau_a * w - 1j

    resp = -g_a * (num1 / den1 + num2 / den2)

    return resp

def CavityTF(f, f_rf, delta_f, g_oo, r_over_q, q):
    """Evaluate the cavity transfer function for the given array of frequencies (f).

    Parameters
    ----------
    f   :   numpy.ndarray or Number
        array of frequencies at which the transfer function should be evaluated
    """

    w = 2 * np.pi * f  # omega
    s = 1j * (w + 2 * np.pi * f_rf)

    w_r = 2 * np.pi * (f_rf + delta_f)  # resonant frequency

    resp = g_oo * r_over_q * w_r * s / np.sqrt(q) / (s ** 2 + (w_r / q) * s + w_r ** 2)

    return resp

def H_a(f, g_a, tau_a):

    s = 1j * 2 * np.pi * f
    return g_a * tau_a * s / (1 + tau_a * s)

def H_d(f, g_a, g_d, tau_d, dphi_ad):

    s = 1j * 2 * np.pi * f
    dphi_ad = dphi_ad * np.pi / 180
    return g_a * g_d * np.exp(1j * dphi_ad) / (1 + tau_d * s)

def Z_cav(f, df, f_rf, R_over_Q, Q_L):

    s = 1j * 2 * np.pi * f
    domega = 2 * np.pi * df
    omega_rf = 2 * np.pi * f_rf

    return R_over_Q * Q_L / (1 + 2 * Q_L * (s - 1j * domega)/omega_rf)

def Z_cav2(f, df, f_rf, R_over_Q, Q_L):
    s = 1j * 2 * np.pi * (f + f_rf)
    domega = 2 * np.pi * df
    omega_rf = 2 * np.pi * f_rf
    omega_r = omega_rf + domega

    return R_over_Q * omega_r * s / Q_L / (s**2 + (omega_r/Q_L) * s + omega_r)

def H_cl(f, tau_loop, H_a, H_d, Z_cav):
    H_ad = H_a + H_d
    s = 1j * 2 * np.pi * f
    return 2 * np.exp(-tau_loop * s) * H_ad * Z_cav / (1 + 2 * np.exp(-tau_loop * s) * H_ad * Z_cav)

def H_open(f, tau_loop, H_a, H_d, Z_cav):
    H_ad = H_a + H_d
    s = 1j * 2 * np.pi * f
    return 2 * np.exp(-tau_loop * s) * H_ad * Z_cav


import argparse
from functools import partial
from typing import Optional

import numpy as np
import torch
import torchvision.datasets as TD
import torchvision.transforms as TT
from torch import Tensor, nn
from torch.utils.data import DataLoader

from modelling import get_discriminator_cls, get_generator_cls
from training import BaseTrainer, BaseTrainerConfig, compute_d_loss, compute_g_loss
from utils import add_args_from_cls, cls_from_args

def build_model(args: argparse.Namespace):
    if args.dataset == "mnist":
        y_dim = 10
        y_encoder = nn.Embedding
        img_channels = 1

    elif args.dataset == "celeba":
        y_dim = 40
        y_encoder = partial(nn.Linear, bias=False)
        img_channels = 3

    else:
        img_channels = 3

    kwargs = dict(img_size=args.img_size, img_channels=img_channels)

    if args.base_depth is not None:
        kwargs.update(base_depth=args.base_depth)

    if args.progressive_growing:
        assert args.model in ("progressive_gan",)
        kwargs.update(
            progressive_growing=args.progressive_growing,
            fade_duration=args.fade_duration,
        )

    d_cls = get_discriminator_cls(args.model)
    g_cls = get_generator_cls(args.model)

    if args.model == "sagan":
        if args.conditional:
            kwargs.update(y_dim=y_dim, y_layer_factory=y_encoder)
        dis = d_cls(**kwargs)
        gen = g_cls(**kwargs, z_dim=args.z_dim)

    elif args.model in ("dcgan", "progressive_gan", "stylegan", "stylegan2"):
        if args.conditional:
            yemb_dim = 128
            dis = get_discriminator_cls("cgan")(
                d_cls(**kwargs, img_channels=kwargs["img_channels"] + yemb_dim),
                y_encoder(y_dim, yemb_dim),
            )
            gen = get_generator_cls("cgan")(
                g_cls(**kwargs, z_dim=args.z_dim + yemb_dim),
                y_encoder(y_dim, yemb_dim),
            )
        else:
            dis = d_cls(**kwargs)
            gen = g_cls(**kwargs)

    else:
        raise ValueError(f"Unsupported model {args.model}")

    return dis, gen

def build_dataset(name: str, img_size: int):
    if name == "mnist":
        transform = TT.Compose([TT.Pad(2), TT.ToTensor(), TT.Normalize(0.5, 0.5)])
        ds = TD.MNIST("data", transform=transform)

    elif name == "celeba":
        transform = TT.Compose([TT.Resize(img_size), TT.CenterCrop(img_size), TT.ToTensor(), TT.Normalize(0.5, 0.5)])
        ds = TD.CelebA("data", split="all", transform=transform, target_transform=lambda x: x / x.sum())

    else:
        transform = TT.Compose([TT.Resize(img_size), TT.CenterCrop(img_size), TT.ToTensor(), TT.Normalize(0.5, 0.5)])
        ds = TD.ImageFolder(name, transform=transform)

    return ds

class Noise2ImgTrainer(BaseTrainer):
    def __init__(self, config, dis, gen, fixed_z: Tensor, fixed_y: Tensor):
        super().__init__(config, dis, gen)
        self.fixed_z = fixed_z.to(self.config.device)
        self.fixed_y = fixed_y.to(self.config.device)

    def _forward(self, m: nn.Module, xs: Tensor, ys: Optional[Tensor]) -> Tensor:
        return m(xs, ys) if self.config.conditional else m(xs)

    def train_step(self, x_reals, ys):
        cfg = self.config
        if cfg.channels_last:
            x_reals = x_reals.to(memory_format=torch.channels_last)

        if self.global_step % cfg.log_img_interval == 0:
            with torch.inference_mode(), self.g_ema.swap_state_dict(self.gen), self.autocast():
                x_fakes = self._forward(self.gen, self.fixed_z, self.fixed_y)
            self.log_images(x_fakes, "generated", self.global_step)

        log_dict = dict()
        log_dict["loss/d"] = self.train_d_step(x_reals, ys).item()

        if self.global_step % cfg.train_g_interval == 0:
            log_dict["loss/g"] = self.train_g_step(x_reals, ys).item()

        for m in (self.dis, self.gen):
            if hasattr(m, "step"):
                m.step()

        return log_dict

    def train_d_step(self, x_reals: Tensor, ys: Optional[Tensor]):
        bsize = x_reals.shape[0]
        cfg = self.config

        # Algorithm 1 in paper clip weights after optimizer step, but GitHub code clip before optimizer step
        # it shouldn't matter much in practice
        if cfg.method == "wgan":
            with torch.no_grad():
                for param in self.dis.parameters():
                    param.clip_(-cfg.wgan_clip, cfg.wgan_clip)

        with self.autocast():
            with torch.no_grad():
                z_noise = torch.randn(bsize, cfg.z_dim, device=x_reals.device)
                x_fakes = self._forward(self.gen, z_noise, ys)

            # if cfg.r1_penalty > 0 and self.counter % cfg.r1_penalty_interval == 0:
            #     x_reals.requires_grad_()

            d_reals = self._forward(self.dis, x_reals, ys)
            d_fakes = self._forward(self.dis, x_fakes, ys)
            loss_d = compute_d_loss(d_reals, d_fakes, cfg.method)

            if cfg.method == "wgan-gp":
                # https://pytorch.org/docs/stable/notes/amp_examples.html#gradient-penalty
                alpha = torch.rand(bsize, 1, 1, 1, device=x_reals.device)
                x_inters = x_reals.lerp(x_fakes.detach().float(), alpha).requires_grad_()
                d_inters = self._forward(self.dis, x_inters, ys).sum()

                with self.autocast(enabled=False):
                    if self.scaler is not None:
                        d_inters = self.scaler.scale(d_inters)
                        scale = self.scaler.get_scale()
                    else:
                        scale = 1

                    (d_grad,) = torch.autograd.grad(d_inters, x_inters, create_graph=True)
                    d_grad = d_grad / scale

                d_grad_norm = torch.linalg.vector_norm(d_grad, dim=(1, 2, 3))
                loss_d = loss_d + cfg.wgan_gp_lamb * (d_grad_norm - 1).square().mean()

            # for Progressive GAN only
            if cfg.drift_penalty > 0:
                loss_d = loss_d + d_reals.square().mean() * cfg.drift_penalty

        # https://arxiv.org/abs/1801.04406, for StyleGAN and StyleGAN2
        # if cfg.r1_penalty > 0 and self.counter % cfg.r1_penalty_interval == 0:
        #     (d_grad,) = torch.autograd.grad(d_reals.sum(), x_reals, create_graph=True)
        #     d_grad_norm2 = d_grad.square().sum() / bsize
        #     loss_d = loss_d + d_grad_norm2 * cfg.r1_penalty / 2

        self.step_optimizer(loss_d, self.optim_d)

        return loss_d

    def train_g_step(self, x_reals: Tensor, ys: Optional[Tensor]):
        bsize = x_reals.shape[0]
        cfg = self.config
        self.dis.requires_grad_(False)

        with self.autocast():
            z_noise = torch.randn(bsize, cfg.z_dim, device=x_reals.device)
            x_fakes = self._forward(self.gen, z_noise, ys)
            d_fakes = self._forward(self.dis, x_fakes, ys)
            loss_g = compute_g_loss(d_fakes, cfg.method)

        self.step_optimizer(loss_g, self.optim_g)
        self.dis.requires_grad_(True)
        return loss_g

def get_parser():
    parser = argparse.ArgumentParser()
    parser.add_argument("--model", default="dcgan")
    parser.add_argument("--base_depth", type=int)
    parser.add_argument("--dataset", choices=["mnist", "celeba"])
    parser.add_argument("--img_size", type=int, default=64)
    parser.add_argument("--batch_size", type=int, default=32)
    parser.add_argument("--num_workers", type=int, default=8)
    parser.add_argument("--n_steps", type=int, default=10_000)
    parser.add_argument("--n_log_imgs", type=int, default=40)
    parser.add_argument("--progressive_growing", action="store_true")
    parser.add_argument("--fade_duration", type=int)
    add_args_from_cls(parser, BaseTrainerConfig)
    return parser

def main():
    parser = get_parser()
    args = parser.parse_args()

    if args.dataset == "celeba" and args.img_size > 256:
        print("CelebA image size is 178x218. Training large image size is not optimal")

    if args.dataset == "mnist":
        print("Only allow 32x32 image for MNIST")
        args.img_size = 32

    dis, gen = build_model(args)

    fixed_z = torch.randn((args.n_log_imgs, args.z_dim))

    ds = build_dataset(args.dataset, args.img_size)
    rand_indices = np.random.choice(len(ds), args.n_log_imgs, replace=False)
    fixed_y = [ds[idx][1] for idx in rand_indices]
    fixed_y = (torch.stack if isinstance(fixed_y[0], Tensor) else torch.tensor)(fixed_y)

    config = cls_from_args(args, BaseTrainerConfig)
    trainer = Noise2ImgTrainer(config, dis, gen, fixed_z, fixed_y)

    if args.progressive_growing:
        schedule = [(4, args.fade_duration)]
        while schedule[-1][0] != args.img_size:
            schedule.append((schedule[-1][0] * 2, args.fade_duration * 2))
    else:
        schedule = [(args.img_size, args.n_steps)]

    for i, (size, n_steps) in enumerate(schedule):
        if i > 0:
            dis.grow()
            gen.grow()

        dloader = DataLoader(
            dataset=build_dataset(args.dataset, size),
            batch_size=args.batch_size,
            shuffle=True,
            num_workers=args.num_workers,
            pin_memory=True,
            persistent_workers=True,
            drop_last=True,
        )
        trainer.train(dloader, n_steps)

if __name__ == "__main__":
    main()


# Initial Java code on W3 schools from Geeks for Geeks
# public class Main {
#   public static void main(String[] args) {
#         String str= "Geeks", nstr="";
#         char ch;

#       	System.out.print("Original word: ");
#       	System.out.println("Geeks"); //Example word

#       	for (int i=0; i<str.length(); i++)
#       	{
#         	ch= str.charAt(i); //extracts each character
#         	System.out.println(i);
#         	nstr= ch+nstr; //adds each character in front of the existing string
#             System.out.println(nstr);
#       	}
#       	//System.out.println("Reversed word: "+ nstr);
#       }
# }

# Python Code
# str = str(input("Please Enter a Word: "))
# nstr = ''

# for x in str:
#     ch = str[x]
#     nstr = ch + nstr

#     x = x + 1

# print(nstr)

# Python Code
str = str(input("Please Enter a Word: "))
nstr = ''
for x in str:
    nstr = x + nstr

print(f"The Reversed Word is: '{nstr}'")


# 땅따먹기

# 문제설명: https://programmers.co.kr/learn/courses/30/lessons/12913

# 문제접근
# 1,2,3,5
# 5,6,7,8
# 4,3,2,1

# 같은 열이 아닌 값 중 제일 큰 값을 찾아서 더하면 됨
# 만약 첫 번째 행에서 (0,0) = 1 을 밟았다면
# max([1,1], [1,2], [1,3])을 사용 0번째 열을 제외한
# 나머지 열들 중 제일 큰 값을 찾으면 됨
# 그 값을 더해주면 됨

# max 함수 사용?

# DP(Dynamic Programming)?

# 문제풀이(1)
def solution(land):
    answer = 0
    dp = [[0 for _ in range(len(land[0]))] for _ in range(len(land))]

    for i in range(len(land)):
        for j in range(len(land[0])):
            dp[i][j] = max(land[i])

    print(dp)

    return answer

# 어떻게 열이 겹치지 않게 최대값을 구함?

# 각 열의 최대값을 구해서 가져옴… 그 뒤?

# 문제풀이(2)
def solution(land):
    answer = 0
    dp = [[0 for _ in range(len(land[0]))] for _ in range(len(land))]

    for i in range(len(land)):
        for j in range(len(land[0])):
            if i == 0 :
                dp[i][j] = land[i][j]
            else :
                dp[i][j] = max(dp[i][j], dp[i-1][j]+land[i][j])

    print(dp)
    answer = max(dp[-1])

    return answer

# 같은 열끼리 더해버리는 상황 발생
# 어떻게 해결할 지 찾아야 함

# for문을 하나 더 써야 하나?

# 굳이 새로운 리스트를 만들 필요가 있었나?

# 문제풀이(3) 성공
def solution(land):
    answer = 0
    dp = [[0 for _ in range(len(land[0]))] for _ in range(len(land))]

    for i in range(len(land)):
        for j in range(len(land[0])):
            if i == 0 :
                dp[i][j] = land[i][j]
                continue
            for k in range(len(land[0])) :
                if k != j :
                    dp[i][j] = max(dp[i][j], dp[i-1][k]+land[i][j])

    # print(dp)
    answer = max(dp[-1])

    return answer

# 열이 겹치지 않게 하려고 for문을 하나 더 생성
# dp리스트의 첫번째 행에 값을 삽입
# j는 지나쳐온 열의 번호
# k는 밟을 열의 번호

# 열 번호 j와 k가 같지 않을 경우
# dp[i][j] 방에 계속 비교해가며 더했을 때
# 가장 큰 값을 갱신

# 마지막 행에서 가장 큰 값을 출력

# 문제풀이(4)
def solution(land):
    answer = 0

    for i in range(1, len(land)):
        land[i][0] += max(land[i-1][1], land[i-1][2], land[i-1][3])
        land[i][1] += max(land[i-1][0], land[i-1][2], land[i-1][3])
        land[i][2] += max(land[i-1][0], land[i-1][1], land[i-1][3])
        land[i][3] += max(land[i-1][0], land[i-1][1], land[i-1][2])

    answer = max(land[-1])

    return answer

# 새로운 리스트를 만들지 않고 하니
# 코드가 간결해짐

# 하나하나 겹치지 않게 함
# 테스트는 통과하나 다음에 해결할 때
# 열과 행의 개수가 다른 테스트 케이스가
# 생길 시 오류가 발생할 확률 100%

# 다른 사람의 풀이(1)
def solution(land):

    for i in range(1, len(land)):
        for j in range(len(land[0])):
            land[i][j] = max(land[i -1][: j] + land[i - 1][j + 1:]) + land[i][j]

    return max(land[-1])

# 슬라이싱 기법을 사용하여
# 열이 겹치지 않게 한 풀이

print(solution([[1,2,3,5],[5,6,7,8],[4,3,2,1]]))    # 16


import pygame.midi
import sys
import time
import bridge

debug = not True

cm = ""

buttons = [*range(16, 23 + 1), 64]
dials = [*range(1, 8 + 1)]
dialdata = {}

named_buttons = {
    16: "STOP",
    17: "PLAY",
    18: "RECORD",
    19: "UP",
    20: "DOWN",
    21: "RIGHT",
    22: "LEFT",
    23: "SELECT",
    64: "SUSTAIN"
}

modes = ["manual", "hsv", "rgb", "hsi"]

stime = 0
position = 0
last_fill = [-1, -1, -1, -1]

def dial_handler(event):
    pos = event[2] / 127
    pos = pos if event[1] <= 4 else (pos * (1 / 127)) - (1 / 127 / 2)
    print(f"Dial {event[1]} at position {round(pos, 10)}")
    dialdata[event[1]] = pos

def send_data():
    global stime
    global last_fill
    global position
    global modes
    ptime = int(round(time.time() * 1000)) - stime
    if (cm and ptime > 10):
        fill = [-1, -1, -1, -1]
        for i in range(1, 4 + 1):
            fdata = dialdata.get(i, -1)
            if (fdata == -1):
                continue
            total = fdata + dialdata.get(i + 4, 0.)
            total = total if total <= 1 else 1
            total = total if total >= 0 else 0
            fill[i - 1] = total
        if (fill == last_fill):
            return
        last_fill = fill
        bridge.send_command(cm, "set", [modes[position], *fill])
        stime = int(round(time.time() * 1000))

def button_handler(event):
    state = "released"
    if (event[2] == 127):
        state = "pressed"
    if (event[1] in named_buttons.keys()):
        name = named_buttons[event[1]]
        print(f"{name} {state}")
        global position
        global modes
        if (name == "LEFT" and state == "released"):
            position = position - 1 if position - 1 >= 0 else len(modes) - 1
            print(f"Mode set to: {modes[position]}")
        elif (name == "RIGHT" and state == "released"):
            position = position + 1 if position + 1 < len(modes) else 0
            print(f"Mode set to: {modes[position]}")
    else:
        print(f"Button {event[1]} {state}")

def readInput(input_device):
    while True:
        if input_device.poll():
            event = input_device.read(1)[0][0]
            if (event[0] != 176):
                if (debug or event[0] not in [144,]):
                    print (event)
                continue
            if (event[1] in dials):
                dial_handler(event)
            elif (event[1] in buttons):
                button_handler(event)
            else:
                print (f"ID: {event[1]}, State: {round(event[2]/127,2)}")
        send_data()

def print_devices():
    devices = []
    for n in range(pygame.midi.get_count()):
        info = pygame.midi.get_device_info(n)
        if (info[2]):
            print (n,info[1])
            devices.append(n)
    return devices

def select_device(devices):
    while True:
        device_id = input("ID: ")
        try:
            device_id = int(device_id)
        except ValueError:
            continue
        if (device_id in devices):
            return device_id

def main():
    pygame.midi.init()
    devices = print_devices()
    device_id = select_device(devices)
    print(f"Opening device {device_id}:")
    my_input = pygame.midi.Input(device_id)
    try:
        readInput(my_input)
    except KeyboardInterrupt:
        my_input.close()
        print("Returning to device selection!")
        main()

if __name__ == '__main__':
    bc = bridge.open_listener()
    ip = bridge.await_controller(bc)
    cm = bridge.open_sender(ip)
    try:
        main()
    except KeyboardInterrupt:
        print("Exiting!")
        sys.exit()


def partition(arr, left, right):
    flag = arr[right]
    while left < right:
        while left < right and arr[left] <= flag:
            left += 1
        arr[right] = arr[left]
        while left < right and arr[right] >= flag:
            right -= 1
        arr[left] = arr[right]
    arr[left] = flag
    return left

def quickSort(arr, left, right):
    if left < right:
        flag = partition(arr, left, right)
        quickSort(arr, left, flag-1)
        quickSort(arr, flag+1, right)
    return arr

arr = [2, 4, 5, 8, 12, 9, 3, 6, 7]
result = quickSort(arr, 0, len(arr)-1)
print(result)


import json
from tqdm import tqdm
class Logger:

    def __init__(self, network, path):
        self._path = path
        self._network = network
        self._log_output = ""
        self._performance_output = ""

    def reset(self):
        self._log_output = ""

    def log_network(self, network):
        self._log_output += self._performance_output
        for layer in tqdm(network.layers):
            self.log_layer(layer.layer_id)
            for neuron in tqdm(layer.neurons):
                self.log_neuron(neuron)
                for branch in tqdm(neuron.branches_in):
                    self.log_branch(branch)

        self.write()

    def log_layer(self, layer_id):
        self._log_output +="------------------------------------------------------\n"
        self._log_output += "Couche: " + str(layer_id) + "\n"
        self._log_output +="------------------------------------------------------\n"

    def log_neuron(self, neuron):
        self._log_output +="----------------------------------\n"
        self._log_output += "Neurone id: " + neuron.neuron_id + "\n"
        self._log_output +="----------------------------------\n"
        self._log_output += "Activation (i): " + str(neuron.i) + "\n"
        self._log_output += "Sortie d'activation (a): " + str(neuron.a) + "\n"
        self._log_output += "Seuil: " + str(neuron.threshold) + "\n"
        self._log_output +="----------------------------------\n"

    def log_branch(self, branch):
        self._log_output +="----------------\n"
        self._log_output += "Branche id: " + branch.branch_id + "\n"
        self._log_output +="----------------\n"
        self._log_output += "Delta poid: " + str(branch.delta_weight) + "\n"
        self._log_output += "Poid: " + str(branch.weight) + "\n"
        self._log_output +="-----------------\n"

    def log_performance(self, mode, num_epoch, success, num_learning_data, learning_rate):

        self._performance_output +="---------------------------------------------------\n"
        self._performance_output +="Mode: " + mode + "\n"
        self._performance_output +="---------------------------------------------------\n"
        self._performance_output +="Taux de succes: (nb de succes / nb de donnee) * 100\n"
        self._performance_output +="---------------------------------------------------\n"
        self._performance_output +="Epoque: " + str(num_epoch) + "\n"
        self._performance_output +="Nb de succes: " + str(success) + "\n"
        self._performance_output +="Nb de donne: " + str(num_learning_data) + "\n"
        self._performance_output +="Taux: " + str(learning_rate) + "%\n"
        self._performance_output +="---------------------------------------------------\n"

        return self._performance_output

    def log_learning_db(self, learning_db_path, data):

        log_data_output = ""
        with open(learning_db_path, "w") as out:

            log_data_output +="----------------------------------\n"
            log_data_output += "Base de donnee d'apprentissage\n"
            log_data_output +="----------------------------------\n"

            for element in tqdm(data):
                log_data_output += json.dumps(element) + "\n"

            out.write(log_data_output)

    def write(self):
        with open(self._path, "w") as out:
            out.write(self._log_output)

    def write_performance(self):
        with open("performance-output.txt", "w") as out:
            out.write(self._performance_output)


from unittest.mock import Mock, patch

import pytest

from deep_translator.deepl import DeeplTranslator
from deep_translator.exceptions import AuthorizationException

@patch("deep_translator.deepl.requests")
def test_simple_translation(mock_requests):
    translator = DeeplTranslator(
        api_key="imagine-this-is-an-valid-api-key", source="en", target="es"
    )
    # Set the request response mock.
    mock_response = Mock()
    mock_response.status_code = 200
    mock_response.json.return_value = {"translations": [{"text": "hola"}]}
    mock_requests.get.return_value = mock_response
    translation = translator.translate("hello")
    assert translation == "hola"

@patch("deep_translator.deepl.requests.get")
def test_wrong_api_key(mock_requests):
    translator = DeeplTranslator(
        api_key="this-is-a-wrong-api-key!", source="en", target="es"
    )
    # Set the response status_code only.
    mock_requests.return_value = Mock(status_code=403)
    with pytest.raises(AuthorizationException):
        translator.translate("Hello")


from operator import itemgetter
class Solution(object):
    def findRelativeRanks(self, nums):
        """
        :type nums: List[int]
        :rtype: List[str]
        """
        withRank = list(enumerate(sorted(list(enumerate(nums)), key=itemgetter(1), reverse=True), 1))
        top3 = ["Gold Medal", "Silver Medal", "Bronze Medal"]
        for i in xrange(min(len(withRank), 3)):
            withRank[i] = (top3[i], withRank[i][1])
        return map(lambda x:str(x[0]), sorted(withRank, key=lambda x:x[1][0]))