#!/bin/env python
#
# This script tests the reading code by reading several regions
# using the python module and comparing to the result of reading
# the files directly with h5py.
#

import numpy as np
import h5py
import glob
import read_eagle
import hashlib

def hash_data(data):

    m = hashlib.md5()
    for name in sorted(data.keys()):
        m.update(data[name])
    return m.hexdigest()

def in_region_periodic(pos, region, boxsize):

    # Find centre of the region
    centre = np.asarray([0.5*(region[i*2+0]+region[i*2+1]) for i in range(3)])

    # Wrap positions to copy nearest centre of region
    pos_wrapped = ((pos.astype(np.float64)-centre+0.5*boxsize) % boxsize)+centre-0.5*boxsize

    # Check which points are in the region
    in_region = ((pos_wrapped[:,0] >= region[0]) & (pos_wrapped[:,0] <= region[1]) &
                 (pos_wrapped[:,1] >= region[2]) & (pos_wrapped[:,1] <= region[3]) &
                 (pos_wrapped[:,2] >= region[4]) & (pos_wrapped[:,2] <= region[5]))

    return in_region

def eagle_snapshot_name(basedir, snapnum, filenum):
    """
    Return the name of an EAGLE snapshot file
    """
    filespec = {"basedir" : basedir,
                "snapnum" : snapnum,
                "filenum" : filenum}
    fname = "{basedir}/snapshot_{snapnum:03d}_z???p???/snap_{snapnum:03d}_z???p???.{filenum:d}.hdf5"
    fname = fname.format(**filespec)
    fname = glob.glob(fname)
    if len(fname) != 1:
        raise IOError("Unable to locate EAGLE snapshot file!")
    return fname[0]

def read_region_direct(basedir, snapnum, region, itype, datasets):
    """
    Read in the specified data from an Eagle snapshot

    basedir: directory with the simulation data
    snapnum: which snapshot to read
    region:  coordinate range (xmin,xmax,ymin,ymax,zmin,zmax)
    itype:   particle type (integer, 0-5)
    datasets: HDF5 dataset names for the quantities to read

    This version reads the hdf5 file directly.
    """

    pos  = []
    data = {dataset:[] for dataset in datasets}
    ifile  = 0
    nfiles = 1
    while ifile < nfiles:

        with h5py.File(eagle_snapshot_name(basedir, snapnum, ifile),"r") as infile:

            # Get number of files from first file
            if ifile == 0:
                nfiles = infile["Header"].attrs["NumFilesPerSnapshot"]
                boxsize = infile["Header"].attrs["BoxSize"]

            # Read in the data from this file
            group = infile["PartType%d" % itype]
            pos.append(group["Coordinates"][...])
            for name in datasets:
                data[name].append(group[name][...])

            # Discard elements not in the required region
            in_region = in_region_periodic(pos[-1], region, boxsize)
            pos[-1] = pos[-1][in_region,...]
            for name in datasets:
                data[name][-1] = data[name][-1][in_region,...]

            # Next file
            ifile += 1

    # Combine arrays from individual files
    for name in datasets:
        data[name] = np.concatenate(data[name], axis=0)

    return data

def read_region_index(basedir, snapnum, region, itype, datasets):
    """
    Read in the specified data from an Eagle snapshot

    basedir: directory with the simulation data
    snapnum: which snapshot to read
    region:  coordinate range (xmin,xmax,ymin,ymax,zmin,zmax)
    itype:   particle type (integer, 0-5)
    datasets: HDF5 dataset names for the quantities to read

    This version uses the read_eagle module.
    """

    # Open the file and select the region
    snap = read_eagle.EagleSnapshot(eagle_snapshot_name(basedir, snapnum, 0))
    snap.select_region(region[0], region[1], region[2], region[3], region[4], region[5])

    # Read the particles
    data = {}
    pos = snap.read_dataset(itype, "Coordinates")
    for name in datasets:
        data[name] = snap.read_dataset(itype, name)

    # Filter out any extra particles
    in_region = in_region_periodic(pos, region, snap.boxsize)
    pos = pos[in_region,...]
    for name in datasets:
        data[name] = data[name][in_region,...]

    return data

if __name__ == "__main__":

    # Test the code on a few regions
    basedir  = "/cosma7/data/Eagle/DataRelease/L0025N0376/PE/REFERENCE/data/"
    datasets = ("Coordinates","ParticleIDs","Velocity")
    itype    = 1
    snapnum  = 28
    regions  = (
        ( 16.5, 17.5, 10.3, 11.4, -3.2, 0.5),
        ( 1,    4.,   1.,   4.,    1.,  4.),
        (-2.1,  2.1,  7.3,  9.8,   1.0, 5.6),
        (-2.,  -1.,  -5.,   1.,    8.5, 9.5),
        )

    for i,region in enumerate(regions):
        print("Region {i:d}".format(i=i))
        data1 = read_region_direct(basedir, snapnum, region, itype, datasets)
        data2 = read_region_index(basedir, snapnum, region, itype, datasets)
        # Output hash of data for easier comparison between python versions
        print("  Hash of data from direct read = "+hash_data(data1))
        print("  Hash of data from read_eagle  = "+hash_data(data2))
        for name in datasets:
            if np.all(data1[name]==data2[name]):
                print("  Region {i:d} dataset {name:s} is ok".format(i=i,name=name))
            else:
                raise Exception("Region {i:d}, dataset {name:s}: MISMATCH!".format(i=i, name=name))


import machine
import onewire
import ds18x20
import uasyncio
import utils

class Sensory:
    async def pomiar_temperatury(self, log_to_hist=False):

        termo_pin = int(utils.get_config('thermometer_pin', -1))
        termo_res = int(utils.get_config('thermometer_res', 9))
        termo_cnt = int(utils.get_config('thermometer_repeat', 5))

        temperature = 0
        if termo_pin == -1:
            return 0

        cnt = 0
        dat = machine.Pin(termo_pin)
        ds = ds18x20.DS18X20(onewire.OneWire(dat))
        roms = ds.scan()
        config = b'\x00\x00\x1f'

        for rom in roms:
            # bajty 2 3 i 4 konfiguracji
            # 2 i 3 - dane uzytkownika
            # 4 - rozdzielczosc
            if termo_res == 9:
                config = b'\x00\x00\x1f'
            if termo_res == 10:
                config = b'\x00\x00\x3f'
            if termo_res == 11:
                config = b'\x00\x00\x5f'
            if termo_res == 12:
                config = b'\x00\x00\x7f'
            try:
                ds.write_scratch(rom, config)
            except Exception as err:
                utils.log_exception(err)
            cnt += 1
        if cnt > 0:
            tc = 0
            for x in range(termo_cnt):
                try:
                    ds.convert_temp()
                    await uasyncio.sleep_ms(int(750 / (2 ** (12 - termo_res))))
                    for rom in roms:
                        t = ds.read_temp(rom)
                        temperature += t
                        tc += 1
                except Exception as err:
                    utils.log_exception(err)

            temperature = temperature / (tc * 1.0)
            if log_to_hist:
                await utils.save_to_hist(temperature, 'termometr.hist')
        return temperature


import numpy as np
import matplotlib.pyplot as plt
import json
from flask import Flask, request, jsonify

def estimate_coef(x, y):
    # number of observations/points
    x = np.array(x)
    y = np.array(y)
    n = np.size(x)

    # mean of x and y vector
    m_x = np.mean(x)
    m_y = np.mean(y)
    # calculating cross-deviation and deviation about x
    SS_xy = np.sum(y*x - n*m_y*m_x)
    SS_xx = np.sum(x*x - n*m_x*m_x)

    # calculating regression coefficients
    b_1 = SS_xy / SS_xx
    b_0 = m_y - b_1*m_x

    return(b_0, b_1)

def plot_regression_line(x, y, b):
    # predicted response vector
    x= np.array(x)
    y_pred = b[0] + b[1]*x
    z = np.array(y_pred).tolist()

    #print(y_pred)
    # putting labels
    #print(x)
    return json.dumps(z)

app = Flask(__name__)

@app.route('/', methods = ['POST'])
def main():
    # observations
    value1 = request.json['value1']
    value2 = request.json['value2']
    value3 = request.json['value3']
    value4 = request.json['value4']
    value5= request.json['value5']
    value6= request.json['value6']
    value7= request.json['value7']
    value8= request.json['value8']
    value9= request.json['value9']
    value10= request.json['value10']
    x = [value1, value2, value3, value4, value5, value6, value7, value8, value9,value10]
    y = [1, 3, 2, 5, 7, 8, 8, 9, 10, 12]
    #return "fuck"
    # estimating coefficients
    b = estimate_coef(x, y)
    print("Estimated coefficients:\nb_0 = {}  \
          \nb_1 = {}".format(b[0], b[1]))

    # plotting regression line
    s = plot_regression_line(x, y, b)
    #e = json.dumps(s)

    return jsonify({"answer-y":s,"answer-x":x})

if __name__ == "__main__":
    app.run(debug=True)


#imporiting librarie
from mod1bb.datas import preproceesingdata,show_scores,rmsle
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
from  sklearn.ensemble import RandomForestRegressor
#Data importing
df=preproceesingdata(r"C:\coding_stuff\project2\bluebook-for-bulldozers\Train\Train.csv")
#splitting
x=df.drop(["SalePrice"],axis=1)
x=x.drop(["SalePricemissing"],axis=1)
y=df["SalePrice"]
#####val#############
j=preproceesingdata("C:\\coding_stuff\\project2\\bluebook-for-bulldozers\\Valid.csv")
val_sol=pd.read_csv(r"C:\coding_stuff\project2\bluebook-for-bulldozers\ValidSolution.csv")
val_sol.drop(["Usage"],inplace=True,axis=1)
z=pd.merge(val_sol,j,"inner")
x_val=z.drop(["SalePrice"],axis=1)
y_val=z["SalePrice"]
#############################################
from  sklearn.model_selection import  RandomizedSearchCV
randf={"n_estimators":np.arange(10,200,10),
       "max_depth": np.arange(2,10,2),
       "min_samples_split": np.arange(2,20,2),
"min_samples_leaf": np.arange(1, 20, 2),
       "max_features":["auto","sqrt", "log2"],
       "max_samples":[10000],
       "n_jobs":[-1]}
ranscv=RandomizedSearchCV(RandomForestRegressor(),
                          param_distributions=randf,
                          n_iter=100,
                          cv=5,n_jobs=-1,
                          verbose=1)
ranscv.fit(x,y)
print(ranscv.best_params_)
print(ranscv.best_score_)
sc=show_scores(ranscv,x,x_val,y_val,y)
print(sc)

import pickle
filename=r"C:\coding_stuff\project2\trained_bul.pkl"
pickle.dump(ranscv, open(filename, 'wb'))


import base64
import io
import json
import requests
import argparse
import sys
import os
import numpy as np

def container_predict(image_files, image_keys, port_number=8501):
    """Sends a prediction request to TFServing docker container REST API.

    Args:
        image_files: Path to a local image for the prediction request.
        image_keys: Your chosen string key to identify the given image.
        port_number: The port number on your device to accept REST API calls.
    Returns:
        The response of the prediction request.
    """

    instances = { 'instances': [] }

    for i, path in enumerate(image_files):
        key = str(image_keys[i])

        with io.open(path, 'rb') as image_file:
            encoded_image = base64.b64encode(image_file.read()).decode('utf-8')

        instances['instances'].append({
            'image_bytes': {'b64': str(encoded_image)},
            'key': key,
        })

    url = 'http://localhost:{}/v1/models/default:predict'.format(port_number)

    return requests.post(url, data=json.dumps(instances)).json()

def show_top(file, top_labels, top_scores):
    print(os.path.basename(file))
    for i, score in enumerate(top_scores):
        print('{:.4f}, {}'.format(score, top_labels[i]))

def get_top(prediction, top):
    scores = np.array(prediction['scores'])
    labels = np.array(prediction['labels'])

    top_indexes = scores.argsort()[::-1][0:top]
    top_scores = scores[top_indexes]
    top_labels = labels[top_indexes]

    return top_labels, top_scores

def is_ext(path, ext):
    _, str = os.path.splitext(os.path.basename(path))
    return str == ext

if __name__ == "__main__":
    parser = argparse.ArgumentParser(description='get predicted result from automl edge container on local')
    parser.add_argument('image_file_path', help='image file path')
    parser.add_argument('--top', type=int, default=5, help='show result of top N class')
    parser.add_argument('--synset_labels', default=None, help='file path of labels list')
    args = parser.parse_args()
    print(args)

    if not os.path.isdir(args.image_file_path):
        result = container_predict([args.image_file_path], ['test-key'])
        top_labels, top_scores = get_top(result['predictions'][0], args.top)
        show_top(args.image_file_path, top_labels, top_scores)
        sys.exit()

    files = sorted([os.path.join(args.image_file_path, file) for file in os.listdir(args.image_file_path) if is_ext(file, '.jpg')])
    indexes = list(range(len(files)))

    pred_labels = []
    result = container_predict(files, indexes)
    predictions = sorted(result['predictions'], key=lambda x:int(x['key']))

    for i, pred in enumerate(predictions):
        top_labels, top_scores = get_top(pred, args.top)
        pred_labels.append(top_labels)
        show_top(files[i], top_labels, top_scores)

    if args.synset_labels != None:
        num_images = len(pred_labels)
        with open(args.synset_labels, 'r') as f:
            content = f.read()
            true_labels = content.split('\n')
            true_labels.pop(-1)

        assert len(true_labels) == num_images, 'images and labels are mismatched'

        top1_cnt, top5_cnt = 0.0, 0.0
        for i, label in enumerate(true_labels):
          top1_cnt += label in pred_labels[i][:1]
          top5_cnt += label in pred_labels[i][:5]

        top1, top5 = 100 * top1_cnt / num_images, 100 * top5_cnt / num_images
        print('Final: top1_acc = {:4.2f}%  top5_acc = {:4.2f}%'.format(top1, top5))


from collections import deque, defaultdict
from Axioms.Utils.axiomIterator import intraAxioms, interAxioms, derived_axioms
from Axioms.IntraAxioms.Goal import Goal

# Function that, given a goal profile (goal), the axioms, and a maximum depth,
# generate corresponding the instance graph (that is, profiles and instances)
def GraphGen(goal, axioms_to_use, MAX_DEPTH):

    # Goal(profile) ---> Goal instance of the profile
    # The outcome will be specified later on, before encoding
    # the instances as SAT. The reason is that we want to try to
    # justify multiple outcomes.
    goal_instance = Goal(goal)

    # fifo queue used to explore the graph, a là BFS
    fifo = deque()
    # (profile, depth)
    fifo.append((goal, 0))

    # init instances and profiles sets
    I, P = set(), set()
    I.add(goal_instance)

    # used to memorise, for each profile, by which
    # instances it has been reached. Useful to make some heuristics
    reachedBy = defaultdict(set)
    reachedBy[goal].add(goal_instance)

    # while the queue is nonempty
    while fifo:

        # pop a profile, and its depth
        profile, depth = fifo.popleft()

        # if profile was not explored yet...
        if profile not in P:

            # ...now it is!
            P.add(profile)

            # for every intraprofile axiom (among those we wanna use),
            # get the instances for this profile. Also pass the instances that reach the profile,
            # in case some heuristic is in place.
            for axiom in intraAxioms(axioms_to_use):
                I_prime = axiom.getInstances(profile, goal, reachedBy[profile])
                I.update(I_prime)

            # same for derived axioms.
            for derived_axiom in derived_axioms(axioms_to_use):
                I_prime = derived_axiom.getInstancesAndProfiles(profile, goal, reachedBy[profile])
                I.update(I_prime)

            # if the current depth < max depth, also expand the inter-profile instances.
            # (max_depth = None ---> no bound)
            if (MAX_DEPTH is None or depth < MAX_DEPTH):
                for axiom in interAxioms(axioms_to_use):
                    P_prime = axiom.getInstancesAndProfiles(profile, goal, reachedBy[profile])

                    # add reached profiles
                    # to the queue, with a depth+1
                    for p, inst in P_prime:
                        fifo.append((p, depth+1))
                        I.add(inst)
                        reachedBy[p].add(inst)

            # profile explored: no need to remember how it was reached, now.
            del reachedBy[profile]

    return I, P


#!/usr/bin/python3

import itertools
from intcode import intcode

with open("inputs/input2.txt", "r") as file:
    content = file.readlines()

start_ic = intcode([int(c) for c in content[0].split(',')])

def run_with_params(a, b):
    ic = start_ic.clone()
    ic[1] = a
    ic[2] = b
    ic.run()
    return ic[0]

# Part A
print(run_with_params(1,12))

# Part B
for a, b in itertools.product(range(100), range(100)):
    result = run_with_params(a,b)
    if result and result==19690720:
        print(100*a+b)
        break


import numpy as np
from json import load
from time import time
from plot import *
from config import *
from aggragation import Aggregation

class Identification(Aggregation):

    def __init__(self, template_faces_dict, features, quality_scores=None, method=None):
        super().__init__(
            template_faces_dict,
            features,
            quality_scores,
            method
        )
        self.features_dim = features.shape[1]

    def calc_distances(self, templates_features):
        gallery_S1 = np.genfromtxt("protocol/ijbb_1N_gallery_S1.csv", delimiter=",", dtype=np.int, skip_header=1)[:, [0,1]]
        gallery_S2 = np.genfromtxt("protocol/ijbb_1N_gallery_S2.csv", delimiter=",", dtype=np.int, skip_header=1)[:, [0,1]]
        gallery = np.concatenate((gallery_S1, gallery_S2), axis=0)
        probe = np.genfromtxt("protocol/ijbb_1N_probe_mixed.csv", delimiter=",", dtype=np.int, skip_header=1)[:, [0,1]]

        gallery_templates = np.unique(gallery, axis=0)
        probe_templates = np.unique(probe, axis=0)

        gallery_features = np.empty((len(gallery_templates), self.features_dim))
        gallery_identities = np.empty(len(gallery_templates))

        for i, (g, g_i) in enumerate(gallery_templates):
            gallery_features[i] = templates_features[g]
            gallery_identities[i] = g_i

        mated = []
        nonmated = []

        for p, p_i in probe_templates:

            t1 = templates_features[p]

            ## find mated features
            mated_idx = np.flatnonzero(p_i == gallery_identities)
            mated_features = gallery_features[mated_idx]

            ## find nonmated features
            mask = np.ones(len(gallery_templates), np.bool)
            mask[mated_idx] = False
            nonmated_features = gallery_features[mask]

            ## calculate mated and nonmated distances
            nonmated_d = 1 - np.dot(t1, nonmated_features.T)
            mated_d = 1 - np.dot(t1, mated_features.T)

            if len(nonmated_d) > 0:
                ## find nonmated with min dist
                nonmated_d = np.min(nonmated_d)
                nonmated.append(nonmated_d)

            if len(mated_d) > 0:
                ## find rank
                distances = 1 - np.dot(t1, gallery_features.T)
                sorted_idx = np.argsort(distances)
                sorted_identities = gallery_identities[sorted_idx]
                rank = np.flatnonzero(sorted_identities == p_i)[0] + 1

                ## find mated with max dist
                mated_d = np.max(mated_d)
                mated.append([mated_d, rank])

        return np.array(nonmated), np.array(mated)

    def calc_det(self, nonmated, mated, R=30):

        ranks = mated[:, 1]
        mated = mated[:, 0]

        min_d_nonmated = np.min(nonmated)
        max_d_nonmated = np.max(nonmated) + 1e-8

        min_d_mated = np.min(mated)
        max_d_mated = np.max(mated) + 1e-8

        min_d = min_d_mated if min_d_mated < min_d_nonmated else min_d_mated
        max_d = max_d_mated if max_d_mated > max_d_nonmated else max_d_nonmated
        thresholds = np.linspace(min_d, max_d, 500)

        fpirs = []
        fnirs = []
        for th in thresholds:

            fpir = len(nonmated[nonmated <= th])
            fnir = len(mated[(mated > th) | (ranks > R)])

            fpirs.append(fpir)
            fnirs.append(fnir)

        fpirs = np.array(fpirs) / nonmated.shape[0]
        fnirs = np.array(fnirs) / mated.shape[0]
        return fpirs, fnirs

    def calc_cmc(self, templates_features):
        gallery_S1 = np.genfromtxt("protocol/ijbb_1N_gallery_S1.csv", delimiter=",", dtype=np.int, skip_header=1)[:, [0,1]]
        gallery_S2 = np.genfromtxt("protocol/ijbb_1N_gallery_S2.csv", delimiter=",", dtype=np.int, skip_header=1)[:, [0,1]]
        gallery = np.concatenate((gallery_S1, gallery_S2), axis=0)
        probe = np.genfromtxt("protocol/ijbb_1N_probe_mixed.csv", delimiter=",", dtype=np.int, skip_header=1)[:, [0,1]]

        gallery_templates = np.unique(gallery, axis=0)
        probe_templates = np.unique(probe, axis=0)

        gallery_features = np.empty((len(gallery_templates), self.features_dim))
        gallery_identities = np.empty(len(gallery_templates))
        for i, (g, g_i) in enumerate(gallery_templates):
            gallery_features[i] = templates_features[g]
            gallery_identities[i] = g_i

        found_in_rank = []

        for p, p_i in probe_templates:

            t1 = templates_features[p]

            distances = 1 - np.dot(t1, gallery_features.T)

            sorted_idx = np.argsort(distances)

            sorted_identities = gallery_identities[sorted_idx]

            rank = np.flatnonzero(sorted_identities == p_i)[0] + 1
            found_in_rank.append(rank)

        cmc = [0]
        found_in_rank = np.array(found_in_rank)
        for rank in range(1, len(found_in_rank) + 1):

            found_n = np.flatnonzero(found_in_rank == rank).shape[0]

            prev = cmc[len(cmc) - 1]
            cmc.append(prev + found_n / len(found_in_rank))

        cmc.pop(0)

        return cmc

if __name__ == "__main__":

    template_faces_dict = load(open('resources/ijbb_templates_subjects.json', 'r'))
    template_faces_dict = {int(k) : np.array(v) for k, v in template_faces_dict.items()}
    features = np.load("resources/features/features.npy")

    interp_fpir = np.linspace(1e-4, 1, 100000)
    qualities = new_aggregation

    curves = []
    show_results = True

    for quality in qualities.values():
        print(f'\n{quality["name"]}')
        # if append_calculated(quality, 'averaging', curves, f'results/averaging.npz'):
        #     continue

        # region load values from dict

        if 'file' in quality:
            quality_scores = np.load(f"resources/{quality['file']}")
            # Normalize qualities if not in [0, 1] range
            if len(np.flatnonzero(quality_scores > 1.0)) > 0:
                min_qs = np.min(quality_scores)
                max_qs = np.max(quality_scores)
                quality_scores = (quality_scores - min_qs) / (max_qs - min_qs)
        else:
            quality_scores = None

        features = np.load(f'resources/{quality["features"]}') if 'features' in quality else features

        method = quality['method'] if 'method' in quality else None

        alpha = quality['alpha'] if 'alpha' in quality else None

        quality['color'] = quality['color'] if 'color' in quality else None

        # endregion

        start = time()
        identify = Identification(
            template_faces_dict=template_faces_dict,
            features=features,
            quality_scores=quality_scores,
            method=method
        )

        templates = identify.calc_templates(alpha=alpha)
        nonmated_d, mated_d = identify.calc_distances(templates)

        ## Calculate DET curve
        fpirs, fnirs = identify.calc_det(nonmated_d, mated_d)

        interp_fnir = np.interp(interp_fpir, fpirs, fnirs)
        print(f'Execution time: {time() - start:.2f} sec')

        print(f'AUC: {np.trapz(interp_fnir, interp_fpir):.5f}')

        quality['fpir'] = interp_fpir
        quality['fnir'] = interp_fnir

        ## Calculate CMC curve
        cmc = identify.calc_cmc(templates)
        quality['cmc'] = cmc

        if show_results:
            print('TPIR@FPIR’s of:')
            fnir_at_frir = [1e-2, 1e-1]
            for f_at_f in fnir_at_frir:
                tpir = 1 - interp_fnir[np.searchsorted(interp_fpir, f_at_f)]
                print(f'––> {f_at_f:.0E}: {tpir:.3f}')

            print('CMC:')
            for i in [0, 4, 9]:
                print(f'––> Rank-{i+1}: {cmc[i]:.3f}')

        curves.append(quality)

    np.savez_compressed("results/identification_results.npz", *curves)

    plot_cmc(curves)
    plot_det(curves)


from __future__ import unicode_literals

import urllib3

class UpnpSoap:
    @staticmethod
    def extractSingleTag(self, data, tag):
        startTag = "<%s" % tag
        endTag = "</%s>" % tag
        try:
            tmp = data.split(startTag)[1]
            index = tmp.find('>')
            if index != -1:
                index += 1
                return tmp[index:].split(endTag)[0].strip()
        except:
            pass
        return None

    @staticmethod
    def send(host_name, service_type, control_url, action_name, action_arguments):

        if '://' in control_url:
            urls = control_url.split('/', 3)
            if len(urls) < 4:
                control_url = '/'
            else:
                control_url = '/' + urls[3]

        request = 'POST %s HTTP/1.1\r\n' % control_url

        # Check if a port number was specified in the host name; default is port 80
        if ':' in host_name:
            host_names = host_name.split(':')
            host = host_names[0]
            try:
                port = int(host_names[1])
            except:
                print('Invalid port specified for host connection:', host_name[1])
                return False
        else:
            host = host_name
            port = 80

        argList = ''
        for arg, (val, dt) in action_arguments.items():
            argList += '<%s>%s</%s>' % (arg, val, arg)

        body = '<?xml version="1.0"?>\n' \
                   '<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" '\
                   'SOAP-ENV:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/">\n' \
                   '<SOAP-ENV:Body>\n' \
                   '<m:%s xmlns:m="%s">\n' \
                   '%s\n' \
                   '</m:%s>\n' \
                   '</SOAP-ENV:Body>\n' \
                   '</SOAP-ENV:Envelope>\n' % (action_name, service_type, argList, action_name)

        headers = {
            'Host': host_name,
            'Content-Length': len(body.encode('ascii')),
            'Content-Type': 'text/xml',
            'SOAPAction': '"%s#%s"' % (service_type, action_name)
        }

        for head, value in headers.items():
            request += '%s: %s\r\n' % (head, value)
        request += '\r\n%s' % body
        soap_envelope_end = re.compile('<\/.*:envelope>')

        try:
            sock = socket(AF_INET, SOCK_STREAM)
            sock.connect((host, port))

            sock.send(request.encode('ascii'))
            response = ''
            while True:
                data = sock.recv(8192)
                if not data:
                    break
                else:
                    response += data.decode('UTF-8')

                    if soap_envelope_end.search(response.lower()) is not None:
                        break
            sock.close()

            (header, body) = response.split('\r\n\r\n', 1)
            if not header.upper().startswith('HTTP/1.') and ' 200 ' in header.split('\r\n')[0]:
                print('SOAP request failed with error code:', header.split('\r\n')[0].split(' ', 1)[1])
                #print(UpnpSoap.extractSingleTag(body, 'errorDescription'))
                return False
            else:
                return body
        except Exception as e:
            print('UpnpSoap.send: Caught socket exception:', e)
            sock.close()
            return False
        except KeyboardInterrupt:
            sock.close()
            return False

    # Send GET request for a UPNP XML file
    @staticmethod
    def get(url):
        headers = {
            'CONTENT-TYPE': 'text/xml; charset="utf-8"',
            'USER-AGENT': 'uPNP/1.0'
        }
        try:
            timeout = urllib3.util.timeout.Timeout(connect=2.0, read=7.0)
            http = urllib3.PoolManager(timeout=timeout)
            r = http.request("GET", url, headers=headers)
            return r.status, r.data
        except Exception as e:
            print("Request for '%s' failed: %s" % (url, e))
            return False, False


import utime
from machine import Pin
import os
import uasyncio
import set_time
import door_state
import buzzer_music
import config

opened_counter = 0
door_state.is_open = 0
door_open = False
loop = uasyncio.get_event_loop()

led = Pin(2, Pin.OUT)  # on-board LED
pin = Pin(config.BUTTON_PIN, Pin.IN, Pin.PULL_UP)

if config.ENABLE_LOG:
    if 'logs' not in os.listdir():
        os.mkdir('logs')
        log = open('logs/door.log', 'w')
        log.write('action;time')
        log.close()

    async def log_door(action, time):
        log = open('logs/door.log', 'a')
        log.write(action + ';' + str("{:04d}-{:02d}-{:02d}T{:02d}:{:02d}:{:02d}".format(*time)) + '\n')
        log.close()

async def play_melody(song_name):
    if song_name == 'random':
        song_name = buzzer_music.get_random_song()
    print('Playing "{}"...'.format(song_name))
    loop.create_task(log_door('playing: {}'.format(song_name), utime.localtime()))
    await buzzer_music.play_song(song_name)

async def play_sfx(song_name):
    if song_name == 'random':
        song_name = buzzer_music.get_random_song()
    print('Playing "{}"...'.format(song_name))
    loop.create_task(log_door('playing: {}'.format(song_name), utime.localtime()))
    await buzzer_music.play_completely(song_name)

async def door_opened():
    global opened_counter
    door_state.is_open += 1
    opened_counter += 1
    do_reset = False
    if opened_counter == config.COUNTER_MAX and config.ONE_UP:
        await play_sfx('1up')
        do_reset = True
    token = opened_counter
    print('door opened')
    if config.ENABLE_LOG:
        loop.create_task(log_door('opened', utime.localtime()))
    led.off()
    await uasyncio.sleep(config.LEGIT_OPEN_TIME)
    # start 'forgot to close'-code if still open
    # if door_state.is_open > 0 and token == opened_counter:
    while door_state.is_open > 0 and token == opened_counter:
        print('Close the door!!111')
        await play_melody('random')
        await uasyncio.sleep(3)
    print('Door has been opened {} times since last reset.\n'.format(opened_counter))
    if do_reset:
        do_reset = False
        opened_counter = 0

async def door_closed():
    door_state.is_open -= 1
    print('door closed')
    await uasyncio.sleep_ms(100)
    if config.CLOSING_SOUND:
        await play_sfx('closed')
    if config.ENABLE_LOG:
        loop.create_task(log_door('closed', utime.localtime()))
    led.on()

async def check_door():
    global door_open
    global opened_counter
    global loop
    while True:
        await uasyncio.sleep_ms(100)
        if not pin.value() == door_open:
            await uasyncio.sleep_ms(100)  # debouncing
            if not pin.value() == door_open:
                door_open = pin.value()
                if door_open:
                    loop.create_task(door_opened())
                else:
                    loop.create_task(door_closed())

def main():
    global loop
    loop.create_task(set_time.keep_time_synced())
    loop.create_task(check_door())
    loop.run_forever()

if __name__ == '__main__':
    main()


from __future__ import annotations

import logging

from pathlib import Path

from novelwriter.constants import nwHeadFmt, nwLabels
from novelwriter.core.project import NWProject
from novelwriter.core.tokenizer import Tokenizer

logger = logging.getLogger(__name__)

class ToMarkdown(Tokenizer):
    """Core: Markdown Document Writer

    Extend the Tokenizer class to writer Markdown output. It supports
    both Standard Markdown and GitHub Flavour Markdown (Extended). The
    class also supports concatenating novelWriter markup files.
    """

    M_STD = 0  # Standard Markdown
    M_GH  = 1  # GitHub Markdown

    def __init__(self, project: NWProject) -> None:
        super().__init__(project)
        self._genMode = self.M_STD
        self._fullMD: list[str] = []
        return

    ##
    #  Properties
    ##

    @property
    def fullMD(self) -> list[str]:
        """Return the markdown as a list."""
        return self._fullMD

    ##
    #  Setters
    ##

    def setStandardMarkdown(self) -> None:
        self._genMode = self.M_STD
        return

    def setGitHubMarkdown(self) -> None:
        self._genMode = self.M_GH
        return

    ##
    #  Class Methods
    ##

    def getFullResultSize(self) -> int:
        """Return the size of the full Markdown result."""
        return sum([len(x) for x in self._fullMD])

    def doConvert(self) -> None:
        """Convert the list of text tokens into a HTML document saved
        to theResult.
        """
        if self._genMode == self.M_STD:
            # Standard
            mdTags = {
                self.FMT_B_B: "**",
                self.FMT_B_E: "**",
                self.FMT_I_B: "_",
                self.FMT_I_E: "_",
                self.FMT_D_B: "",
                self.FMT_D_E: "",
            }
        else:
            # GitHub
            mdTags = {
                self.FMT_B_B: "**",
                self.FMT_B_E: "**",
                self.FMT_I_B: "_",
                self.FMT_I_E: "_",
                self.FMT_D_B: "~~",
                self.FMT_D_E: "~~",
            }

        self._result = ""

        thisPar = []
        tmpResult = []

        for tType, _, tText, tFormat, tStyle in self._tokens:

            # Process Text Type
            if tType == self.T_EMPTY:
                if len(thisPar) > 0:
                    tTemp = ("  \n".join(thisPar)).rstrip(" ")
                    tmpResult.append(f"{tTemp}\n\n")
                thisPar = []

            elif tType == self.T_TITLE:
                tHead = tText.replace(nwHeadFmt.BR, "\n")
                tmpResult.append(f"# {tHead}\n\n")

            elif tType == self.T_UNNUM:
                tHead = tText.replace(nwHeadFmt.BR, "\n")
                tmpResult.append(f"## {tHead}\n\n")

            elif tType == self.T_HEAD1:
                tHead = tText.replace(nwHeadFmt.BR, "\n")
                tmpResult.append(f"# {tHead}\n\n")

            elif tType == self.T_HEAD2:
                tHead = tText.replace(nwHeadFmt.BR, "\n")
                tmpResult.append(f"## {tHead}\n\n")

            elif tType == self.T_HEAD3:
                tHead = tText.replace(nwHeadFmt.BR, "\n")
                tmpResult.append(f"### {tHead}\n\n")

            elif tType == self.T_HEAD4:
                tHead = tText.replace(nwHeadFmt.BR, "\n")
                tmpResult.append(f"#### {tHead}\n\n")

            elif tType == self.T_SEP:
                tmpResult.append("%s\n\n" % tText)

            elif tType == self.T_SKIP:
                tmpResult.append("\n\n\n")

            elif tType == self.T_TEXT:
                tTemp = tText
                for xPos, xLen, xFmt in reversed(tFormat):
                    tTemp = tTemp[:xPos] + mdTags[xFmt] + tTemp[xPos+xLen:]
                thisPar.append(tTemp.rstrip())

            elif tType == self.T_SYNOPSIS and self._doSynopsis:
                locName = self._localLookup("Synopsis")
                tmpResult.append(f"**{locName}:** {tText}\n\n")

            elif tType == self.T_COMMENT and self._doComments:
                locName = self._localLookup("Comment")
                tmpResult.append(f"**{locName}:** {tText}\n\n")

            elif tType == self.T_KEYWORD and self._doKeywords:
                tmpResult.append(self._formatKeywords(tText, tStyle))

        self._result = "".join(tmpResult)
        tmpResult = []

        self._fullMD.append(self._result)

        return

    def saveMarkdown(self, path: str | Path) -> None:
        """Save the data to a plain text file."""
        with open(path, mode="w", encoding="utf-8") as outFile:
            outFile.write("".join(self._fullMD))
        logger.info("Wrote file: %s", path)
        return

    def replaceTabs(self, nSpaces: int = 8, spaceChar: str = " ") -> None:
        """Replace tabs with spaces."""
        spaces = spaceChar*nSpaces
        self._fullMD = [p.replace("\t", spaces) for p in self._fullMD]
        if self._keepMarkdown:
            self._allMarkdown = [p.replace("\t", spaces) for p in self._allMarkdown]
        return

    ##
    #  Internal Functions
    ##

    def _formatKeywords(self, text: str, style: int) -> str:
        """Apply Markdown formatting to keywords."""
        valid, bits, _ = self._project.index.scanThis("@"+text)
        if not valid or not bits:
            return ""

        result = ""
        if bits[0] in nwLabels.KEY_NAME:
            result += f"**{nwLabels.KEY_NAME[bits[0]]}:** "
            if len(bits) > 1:
                result += ", ".join(bits[1:])

        result += "  \n" if style & self.A_Z_BTMMRG else "\n\n"

        return result

# END Class ToMarkdown


"""
Created on Mon Jun 19 01:55:05 2017

@author: Hyeonguk Park
"""
import numpy as np
from scipy.linalg import eig, inv

def fitEllipse (x, y):
     x = x [:, np.newaxis]
     y = y [:, np.newaxis]
     D = np.hstack(( x*x , x*y , y*y , x, y, np.ones_like(x)))
     S = np.dot (D.T ,D)
     C = np.zeros ([6 , 6])
     C[0, 2] = C[2, 0] = 2
     C[1, 1] = -1
     E ,V = eig( np.dot(inv(S),C ))
     n = np.argmax(np.abs(E))
     a = V[:, n]
     if a[0] < 0 : a = -a
     return a

def ellipse_center(a):
     b, c, d, f, g, a = a[1]/2, a[2], a[3]/2, a[4]/2, a[5], a[0]
     num = b*b - a*c
     x0 = (c*d - b*f)/num
     y0 = (a*f - b*d)/num
     return np.array([x0, y0])

def ellipse_axis_length (a):
     b, c, d, f, g, a = a[1]/2, a[2], a[3]/2, a[4]/2, a[5], a[0]
     up = 2*( a*f*f + c*d*d + g*b*b - 2*b*d*f - a*c*g )
     down1 = ( b*b - a*c ) * (( c - a )*np.sqrt(1 + 4*b*b/((a - c)*(a - c))) - (c + a))
     down2 = ( b*b - a*c ) * (( a - c )*np.sqrt(1 + 4*b*b/((a - c)*(a - c))) - (c + a))
     res1 = np.sqrt( up/down1 )
     res2 = np.sqrt( up/down2 )
     return np.array([res1, res2])

def ellipse_angle_of_rotation(a):
     b, c, d, f, g, a = a[1]/2 , a[2], a[3]/2, a[4]/2, a[5], a[0]
     if b == 0 :
         if a < c :
             return 0
         else :
             return np.pi/2
     else :
         if a < c :
             return np.arctan(2*b/(a - c))/2
         if a > c :
             return -np.pi/2*np.sign(b) + np.arctan(2*b/(a - c))/2

#I took the code at http://nicky.vanforeest.com/misc/fitEllipse/fitEllipse.html
#and fixed errors in ellipse_angle_of_rotation().

def CT_to_Unit_Cir(coord,a):

    center = ellipse_center(a)
    phi = ellipse_angle_of_rotation(a)
    axes = ellipse_axis_length(a)
    axes.sort()
    x, y = coord
    b, a = axes

    R = np.arange(0, 2*np.pi, 0.01)
    xx = center[0] + a*np.cos(R)*np.cos(phi) - b*np.sin(R)*np.sin(phi)
    yy = center[1] + a*np.cos(R)*np.sin(phi) + b*np.sin(R)*np.cos(phi)

    from matplotlib import pyplot as plt
    plt.figure(figsize=(3,3))
    plt.scatter(x, y)
    plt.plot(xx, yy, color='red')
    plt.show()

    x = x - center[0]
    y = y - center[1]

    u= (1/axes[1])*np.cos(phi)*x + (1/axes[1])*np.sin(phi)*y
    v= (-1/axes[0])*np.sin(phi)*x + (1/axes[0])*np.cos(phi)*y

    plt.figure(figsize=(3,3))
    plt.plot (u,v)
    plt.show()

    coord_iso = u, v

    return coord_iso


"""
    naverwebtoonfeeds.app
    ~~~~~~~~~~~~~~~~~~~~~

    Functions for creating and configuring the Flask app.

"""
import os

from flask import Flask, g, redirect, request, send_from_directory

from ._compat import string_types, urlparse, urlunparse
from .config import DefaultConfig, instance_path, resolve_instance_path
from .ext import assets_env, cache, db, gzip
from .feeds import worker  # Necessary for signals
from .feeds.views import feeds
from .filters import register_filters

default_blueprints = [feeds]

def create_app(config_pyfile_or_dict=None, blueprints=None):
    """Creates a Flask app. If *blueprints* is None, the default blueprints in
    :data:`default_blueprints` will be used.

    """
    app = Flask(__name__.rsplit('.', 1)[0],
                instance_path=instance_path,
                instance_relative_config=True)
    configure_app(app, config_pyfile_or_dict)
    register_blueprints(app, blueprints or default_blueprints)
    register_extensions(app)
    register_request_handlers(app)
    configure_jinja(app)
    configure_assets(app)
    return app

def configure_app(app, config_pyfile_or_dict=None):
    """Configures the app. Configuration is applied in the following order:

    1. :class:`naverwebtoonfeeds.config.DefaultConfig`
    2. From *NWF_SETTINGS* environment variable if it is set.
    3. From *config_pyfile_or_dict*. It can be a path to the Python file or
       a dictionary.

    Note that if the path to the configuration file can be absolute or relative
    to the instance folder.

    """
    app.config.from_object(resolve_instance_path(DefaultConfig))
    if os.environ.get('NWF_SETTINGS'):
        app.config.from_envvar('NWF_SETTINGS', silent=False)
    if isinstance(config_pyfile_or_dict, string_types):
        app.config.from_pyfile(config_pyfile_or_dict)
    elif config_pyfile_or_dict is not None:
        app.config.update(config_pyfile_or_dict)

def register_blueprints(app, blueprints):
    """Registers blueprints to the app."""
    for blueprint in blueprints:
        app.register_blueprint(blueprint)

def register_extensions(app):
    """Registers extensions for the app."""
    assets_env.init_app(app)
    db.init_app(app)
    cache.init_app(app)
    if app.config.get('GZIP'):
        gzip.init_app(app)

def register_request_handlers(app):

    if app.config['REDIRECT_TO_CANONICAL_URL']:
        @app.before_request
        def redirect_to_canonical_url():
            urlparts = urlparse(request.url)
            if urlparts.netloc != app.config['SERVER_NAME']:
                urlparts_list = list(urlparts)
                urlparts_list[1] = app.config['SERVER_NAME']
                return redirect(urlunparse(urlparts_list), 301)

def configure_jinja(app):
    """Registers template filters and context processors."""
    register_filters(app)

def configure_assets(app):
    """Adds a URL rule for generated assets."""

    def send_static_file(filename):
        cache_timeout = app.get_send_file_max_age(filename)
        return send_from_directory(app.config['ASSETS_DIRECTORY'], filename,
                                   cache_timeout=cache_timeout)

    app.add_url_rule(app.config['ASSETS_URL'] + '/<path:filename>',
                     endpoint='assets',
                     view_func=send_static_file)


#######
#PREPARE
#######

#IMPORT LIBRARIES
from itertools import count
from math import comb
import os
import csv
from statistics import mean
import statistics
from collections import Counter

#DEFINING VARIABLES
voter_id_list = []
candidate_list = []
total_votes = 0
votes_count = 0
winner = ""
winner_count = 0
candidate = ""
percent_votes = []
combined_candidates = ""

#LOCATE THE DATA
election_csv = os.path.join("Resources", "election.csv")

# OPEN AND READ DATA
with open(election_csv) as csv_file:
    csvreader = csv.reader(csv_file, delimiter=',')
    csv_header = next (csv_file)

    for row in csvreader:
#SPLIT DATA INTO LISTS
# VOTER ID
        voter_id = row
        voter_id_list.append(voter_id[0])

# CANDIDATE
        candidate = row
        candidate_list.append(candidate[2])

# Calculate total votes cast
        total_votes += 1

# Gather a list of candidates who received votes
        def unique (candidate_list):
            print (*Counter(candidate_list))
            candidate_list.append
            return (candidate)

# Gather the total votes for each candidate
    votes_count = [[candidate, candidate_list.count(candidate)] for candidate in set(candidate_list)]

# Gather the percentage of votes for each candidate
    for name, count in votes_count:
        percent_votes = (count / total_votes) * 100
        combined_candidates = combined_candidates + f"{name}: {percent_votes:.3f}% ({count})\n"

#Search for the winner by sorting data
    votes_count = sorted(votes_count, key = lambda k: k[1], reverse = True)
    winner = votes_count[0][0]

    # winner = combined_candidates [0] [0]

    #unique(candidate_list)
    #print (total_votes)
    #print (votes_count)
   # print (winner)

   #######
#PRINT ANALYSIS
#######

output = (
        f"Election Results\n"
        f"----------------------------------\n"
        f"Total Votes: {total_votes}\n"
        f"----------------------------------\n"
        f"{combined_candidates}\n"
        f"----------------------------------\n"
        f"Winner:{winner}\n"
)
#print output to terminal
print(output)
print(type(combined_candidates))

text_file = open("Election.txt", "w")
n = text_file.write(output)
text_file.close()


"""
https://adventofcode.com/2022/day/2

Let's go overboard!
"""

from typing import ClassVar, Dict, Type
from dataclasses import dataclass

@dataclass
class Hand:
    """
    The hand of a given player
    """

    score: int = 0

@dataclass
class Rock(Hand):
    """
    Rock beats scissors
    """

    score = 1

@dataclass
class Paper(Hand):
    """
    Paper beats rock
    """

    score = 2

@dataclass
class Scissors(Hand):
    """
    Scissors beats paper
    """

    score = 3

class Round:
    """
    A round of our game
    """

    loosers: ClassVar[Dict[Type[Hand], Type[Hand]]] = {
        Scissors: Rock,
        Rock: Paper,
        Paper: Scissors,
    }

    winners: ClassVar[Dict[Type[Hand], Type[Hand]]] = {
        Scissors: Paper,
        Rock: Scissors,
        Paper: Rock,
    }

    def __init__(self, opponent_letter: str, player_letter: str, problem: str = "a"):
        if opponent_letter not in "ABC":
            raise ValueError("Invalid opponent letter")
        if player_letter not in "XYZ":
            raise ValueError("Invalid player letter")
        if problem not in "ab":
            raise ValueError("Invalid problem")

        self.opponent_hand = self.create_hand(opponent_letter)
        if problem == "a":
            self.player_hand = self.create_hand(player_letter)
        else:
            self.player_hand = self.create_hand_for_outcome(player_letter)

    def create_hand_for_outcome(self, letter: str) -> Hand:
        """
        Convert the letter to the next letter in the alphabet
        """
        opponent_type = type(self.opponent_hand)
        if letter == "X":
            return self.winners[opponent_type]()
        if letter == "Y":
            return opponent_type()
        if letter == "Z":
            return self.loosers[opponent_type]()
        raise ValueError("Invalid letter")

    def round_score(self) -> int:
        """
        Return the score of the round
        """
        score = 0
        round_outcome = self.beats(self.player_hand, self.opponent_hand)
        if round_outcome == 1:
            score = 6
        elif round_outcome == 0:
            score = 3

        return score + self.player_hand.score

    @classmethod
    def create_hand(cls, letter: str) -> Hand:
        """
        Create a hand from a letter
        """
        return {
            "A": Rock,
            "B": Paper,
            "C": Scissors,
            "X": Rock,
            "Y": Paper,
            "Z": Scissors,
        }[letter]()

    @classmethod
    def beats(cls, hand1: Hand, hand2: Hand) -> int:
        """
        Return 1 if hand1 beats hand2, 0 if they are equal, -1 if hand2 beats hand1
        """
        if isinstance(hand1, type(hand2)):
            return 0

        if isinstance(hand2, cls.winners[type(hand1)]):
            return 1

        return -1

def main(filename, problem: str = "a"):
    """
    Main function
    """
    score = 0
    with open(filename, encoding="ascii") as handle:
        for line in handle.readlines():
            opponent_letter, player_letter = line.split()
            game_round = Round(opponent_letter, player_letter, problem)
            score += game_round.round_score()
    print(score)

if __name__ == "__main__":
    main("input_data.txt", "b")


"""
Time In Profile Pic.....
Command: `.bloom`
Hmmmm U need to config DOWNLOAD_PFP_URL_CLOCK var in Heroku with any telegraph image link

⚠DISCLAIMER⚠
USING THIS PLUGIN CAN RESULT IN ACCOUNT BAN. WE DONT CARE ABOUT BAN, SO WE ARR USING THIS.
"""
import asyncio
import os
import random
import shutil
from datetime import datetime

from PIL import Image, ImageDraw, ImageFont
from pySmartDL import SmartDL
from telethon.tl import functions

from userbot.utils import lightning_cmd

FONT_FILE_TO_USE = "/usr/share/fonts/truetype/dejavu/DejaVuSans.ttf"

@borg.on(lightning_cmd(pattern="bloom ?(.*)"))
async def autopic(event):
    await event.edit("Bloom colour profile pic have been enabled by my master")
    downloaded_file_name = "userbot/original_pic.png"
    downloader = SmartDL(
        Var.DOWNLOAD_PFP_URL_CLOCK, downloaded_file_name, progress_bar=True
    )
    downloader.start(blocking=False)
    photo = "userbot/photo_pfp.png"
    while not downloader.isFinished():
        pass

    while True:
        # RIP Danger zone Here no editing here plox
        R = random.randint(0, 256)
        B = random.randint(0, 256)
        G = random.randint(0, 256)
        FR = 256 - R
        FB = 256 - B
        FG = 256 - G
        shutil.copy(downloaded_file_name, photo)
        image = Image.open(photo)
        image.paste((R, G, B), [0, 0, image.size[0], image.size[1]])
        image.save(photo)

        current_time = datetime.now().strftime("\n Time: %H:%M:%S \n \n Date: %d/%m/%y")
        img = Image.open(photo)
        drawn_text = ImageDraw.Draw(img)
        fnt = ImageFont.truetype(FONT_FILE_TO_USE, 60)
        ofnt = ImageFont.truetype(FONT_FILE_TO_USE, 250)
        drawn_text.text((350, 350), current_time, font=fnt, fill=(FR, FG, FB))
        drawn_text.text((350, 350), font=ofnt, fill=(FR, FG, FB))
        img.save(photo)
        file = await event.client.upload_file(photo)  # pylint:disable=E0602
        try:
            await event.client(
                functions.photos.UploadProfilePhotoRequest(file)  # pylint:disable=E0602
            )
            os.remove(photo)
            await asyncio.sleep(60)
        except:
            return


import time

import os
import ray
import numpy as np
import cupy as cp
import cupy.cuda.nccl as nccl
import torch

# @ray.remote(num_gpus=1, resources={'machine': 1})
@ray.remote(num_gpus=1)
class BenchmarkWorker:
    def __init__(self,
                 world_size,
                 world_rank,
                 object_size):
        self.world_size = world_size
        self.world_rank = world_rank
        self.object_size = object_size

        self.comm = None
        self.uid = None

        self.send = None
        self.recv = None

    def gen_unique_id(self):
        if self.world_rank != 0:
            raise ValueError('should not reach here...')
        uid = nccl.get_unique_id()
        self.uid = uid
        return uid

    def setup(self, uid):
        # cp.cuda.Stream.null.synchronize()
        self.comm = nccl.NcclCommunicator(
            self.world_size, uid, self.world_rank)

    def put_object(self, tensor_type='cupy'):
        cp.cuda.Stream.null.synchronize()
        if tensor_type == 'cupy':
            self.send = cp.ones((round(self.object_size / 4),), dtype=cp.float32)
            self.recv = cp.zeros((round(self.object_size / 4),), dtype=cp.float32)
        elif tensor_type == 'pytorch':
            self.send = torch.cuda.FloatTensor(self.object_size // 4).fill_(1.0)
            self.recv = torch.cuda.FloatTensor(self.object_size // 4).fill_(0.0)
        else:
            raise ValueError('unrecognized tensor backend')
        print(self.world_rank, self.send)
        cp.cuda.Stream.null.synchronize()
        return True

    def allreduce(self):
        if isinstance(self.send, cp.core.core.ndarray):
            send_ptr = self.send.data.ptr
        elif isinstance(self.send, torch.Tensor):
            send_ptr = self.send.data_ptr()
        else:
            raise ValueError('unrecognized tensor backend')

        if isinstance(self.recv, cp.core.core.ndarray):
            recv_ptr = self.recv.data.ptr
        elif isinstance(self.recv, torch.Tensor):
            recv_ptr = self.recv.data_ptr()
        else:
            raise ValueError('unrecognized tensor backend')

        start = time.time()
        self.comm.allReduce(send_ptr,
                            recv_ptr,
                            round(self.object_size / 4),
                            cp.cuda.nccl.NCCL_FLOAT32,
                            0,
                            cp.cuda.Stream.null.ptr)

        cp.cuda.Stream.null.synchronize()
        duration = time.time() - start
        print(self.world_rank, self.recv)
        return duration

    def destroy(self):
        self.comm.destroy()
        return True

class BenchmarkWorkerPool:
    def __init__(self,
                 world_size,
                 object_size):
        self.actors = []
        leading_actor = BenchmarkWorker.remote(world_size, 0, object_size)
        uid = ray.get(leading_actor.gen_unique_id.remote())
        self.actors.append(leading_actor)

        for world_rank in range(1, world_size):
            actor = BenchmarkWorker.remote(world_size, world_rank, object_size)
            self.actors.append(actor)
        ray.wait([actor.setup.remote(uid) for actor in self.actors])

    def put_objects(self):
        rets = []
        for i, w in enumerate(self.actors):
            if i % 2 == 0:
                rets.append(w.put_object.remote(tensor_type='cupy'))
            else:
                rets.append(w.put_object.remote(tensor_type='pytorch'))
        ray.wait(rets, num_returns=len(rets), timeout=None)
        return True

    def release_actors(self):
        ray.wait([w.destroy.remote() for w in self.actors])
        ray.wait([w.__ray_terminate__.remote() for w in self.actors])
        for w in self.actors:
            ray.kill(w)

    def __getitem__(self, item):
        return self.actors[item]

    def __len__(self):
        return len(self.actors)

def cupy_pytorch_allreduce(world_size, object_size):
    workers = BenchmarkWorkerPool(world_size, object_size)
    workers.put_objects()
    durations = ray.get([w.allreduce.remote() for w in workers])
    workers.release_actors()
    return max(durations)

if __name__ == "__main__":
    ray.init(address='auto')

    ## Hao: This prototype proves that we can use cupy.nccl to reduce pytorch and cupy tensors together
    ## Hence interoperatorability between cupy and torch.cuda.Tensor, or numpy and torch.Tensor
    world_size = 4
    object_size = 2 ** 10
    duration = cupy_pytorch_allreduce(world_size, object_size)
    print(duration)
    ray.shutdown()


import os, sys
from os.path import join, isdir, abspath, dirname
from collections import defaultdict
import shutil
import numpy as np
import json
import csv
from addict import Dict
import torch
import torch.nn as nn
import torch.nn.functional as F
import torch.distributed as dist
from torch.nn.parallel import DistributedDataParallel as DDP
from torch.utils.data import DataLoader, DistributedSampler
from torch.optim import SGD, Adam, AdamW
from torch.optim.lr_scheduler import ExponentialLR, CyclicLR
from torch.distributed import init_process_group, destroy_process_group
import torch.multiprocessing as mp
import timm
from model import nnUnet
from dataset import TotalSegmentatorData
from metrics import DiceWin, DiceMax
from utils import OneHot, TimeFuncDecorator

class NullScheduler:

    def __init__(self, lr):
        self.lr = lr

    def get_last_lr(self):
        return [self.lr]

class Train:

    def __init__(self, cfgs):
        assert torch.cuda.is_available()
        self.no_gpus = torch.cuda.device_count()

        self.paths = cfgs.paths
        self.model_cfgs = cfgs.model_params
        self.optimizer_cfgs = cfgs.optimizer_params
        self.scheduler_cfgs = cfgs.scheduler_params
        self.train_data_cfgs = cfgs.train_dataset_params
        self.eval_data_cfgs = cfgs.validation_dataset_params
        self.train_cfgs = cfgs.run_params
        self.prev_model = self.paths.model_load_src

        self.ckpts_path = abspath(self.paths.model_ckpts_dest)
        self.model_best_path = abspath(self.paths.model_best_dest)
        self.train_report_path = abspath(self.paths.train_report_path)
        self.eval_report_path = abspath(self.paths.eval_report_path)
        self.data_path = abspath(self.paths.data_dest)
        self.train_data_path = join(self.data_path, "train")
        self.val_data_path = join(self.data_path, "val")

        self.mode = self.train_cfgs.mode
        self.train = self.train_cfgs.train
        self.epochs = self.train_cfgs.epochs
        self.batch_size = self.train_cfgs.batch_size
        self.val_size = self.train_cfgs.validation_size
        self.track_freq = self.train_cfgs.tracking_frequency
        self.block_size = self.track_freq * self.batch_size
        self.model_name = self.train_cfgs.model
        self.met_name = self.train_cfgs.metric
        self.sel_optim = self.train_cfgs.optimizer
        self.sel_scheduler = self.train_cfgs.scheduler
        self.label_weights = self.train_cfgs.label_weights
        self.lw = self.train_cfgs.loss_weights
        self.lw_decay = self.train_cfgs.loss_weights_decay
        self.num_classes = self.train_cfgs.num_classes
        self.se = self.train_cfgs.starting_epoch

        self.model_dict = defaultdict(self._NoModelError, {
            "nnunet": nnUnet,
        })
        self.optim_dict = defaultdict(AdamW, {
            "adam": Adam,
            "adamw": AdamW,
            "sgd": SGD,
        })
        self.scheduler_dict = defaultdict(None, {
            "exponential": ExponentialLR,
            "cyclic": CyclicLR,
        })

        # self.labels = self.data_cfgs.labels
        # assert len(self.labels) == len(self.label_weights)
        # assert len(self.labels) == self.model_cfgs.num_classes
        assert len(self.lw) == 2
        assert len(self.lw_decay) == 2

        self.e = 1e-6

    def _NoModelError(self):
        raise Exception("Not a valid model")

    def _CheckMakeDirs(self, filepath):
        if not isdir(dirname(filepath)): os.makedirs(dirname(filepath))

    def _RemoveDir(self, dirpath):
        try:
            shutil.rmtree(dirpath)
        except OSError:
            pass

    def _SaveBestModel(self, state, value):
        self._CheckMakeDirs(self.model_best_path)
        torch.save(state, self.model_best_path)
        print(f"New best model with {self.met_name} = {value} saved to {self.model_best_path}.")

    def _SaveCkptsModel(self, state, value):
        self._CheckMakeDirs(self.ckpts_path)
        torch.save(state, self.ckpts_path)
        print(f"Checkpoint with {self.met_name} = {value} saved to {self.ckpts_path}.")

    def _ConfusionMatrix(self, p, gt):
        tp = np.sum((p == 1) & (gt == 1)).astype(int)
        fp = np.sum(p).astype(int) - tp
        tn = np.sum((p == 0) & (gt == 0)).astype(int)
        fn = np.sum(gt).astype(int) - tp
        return tp, fp, tn ,fn

    def _SetupDDP(self, rank, world_size):
        """
        Args:
            rank: Unique identifier of each process
            world_size: Total number of processes
        """
        os.environ["MASTER_ADDR"] = "localhost"
        os.environ["MASTER_PORT"] = "12355"
        init_process_group(backend="nccl", rank=rank, world_size=world_size)
        return

    def _ShutdownDDP(self):
        destroy_process_group()
        return

    def _SetupLogs(self, gpu_id):
        if self.mode != "DDP":
            self._RemoveDir(self.train_report_path)
            self._RemoveDir(self.eval_report_path)
            os.makedirs(self.train_report_path)
            os.makedirs(self.eval_report_path)
        elif gpu_id == 0:
            self._RemoveDir(self.train_report_path)
            self._RemoveDir(self.eval_report_path)
            os.makedirs(self.train_report_path)
            os.makedirs(self.eval_report_path)
        train_log = open(join(self.train_report_path, f"rank{gpu_id}.csv"), "a")
        eval_log = open(join(self.eval_report_path, f"rank{gpu_id}.csv"), "a")
        train_writer = csv.writer(train_log)
        eval_writer = csv.writer(eval_log)
        train_writer.writerow(["epoch", "block", "learning_rate",
                               "loss", "cross_entropy_scores", "dice_scores"])
        eval_writer.writerow(["epoch", "samples", "bboxes",
                              "cross_entropy_scores", "dice_scores"])
        return train_log, eval_log, train_writer, eval_writer

    def _SetupData(self, device):
        self.train_data = TotalSegmentatorData(device, self.train_data_path, self.train_data_cfgs)
        self.val_data = TotalSegmentatorData(device, self.val_data_path, self.eval_data_cfgs)
        if self.mode == "DDP":
            self.train_sampler = DistributedSampler(self.train_data, shuffle=True)
            self.val_sampler = DistributedSampler(self.val_data, shuffle=True)
            self.trainloader = DataLoader(self.train_data, self.batch_size, sampler=self.train_sampler)
            self.validloader = DataLoader(self.val_data, self.val_size, sampler=self.val_sampler)
            self.total_val_size = len(self.val_sampler)
        else:
            self.trainloader = DataLoader(self.train_data, self.batch_size, shuffle=True)
            self.validloader = DataLoader(self.val_data, self.val_size, shuffle=True)
            self.total_val_size = len(self.validloader)

    def _SetupModelAndOptim(self, gpu_id, device):
        model = self.model_dict[self.model_name](**self.model_cfgs).to(device)
        if self.prev_model != None:
            self.prev_model = torch.load(self.prev_model, map_location=device)
            model_state = self.prev_model["model"]
            optimizer_state = self.prev_model["optimizer"]
            model.load_state_dict(model_state)
            print(f"gpu_id: {gpu_id} - model loaded.")
        else:
            model_state = None
            optimizer_state = None
        if self.mode == "DDP":
            self.model = DDP(model, device_ids=[gpu_id])
        else:
            self.model = model
        self.optimizer = self.optim_dict[self.sel_optim](self.model.parameters(),
                                                         **self.optimizer_cfgs)
        if optimizer_state != None:
            self.optimizer.load_state_dict(optimizer_state)
        del model_state
        del optimizer_state
        del self.prev_model
        torch.cuda.empty_cache()
        return

    def _SetupScheduler(self):
        if self.sel_scheduler == None:
            self.scheduler = NullScheduler(self.optimizer_cfgs.lr)
        else:
            self.scheduler = self.scheduler_dict[self.sel_scheduler](self.optimizer,
                                                                      **self.scheduler_cfgs)
        if self.sel_scheduler == "cyclic":
            for _ in range(self.scheduler_cfgs.step_size_up):
                self.scheduler.step()

    def _TrainLoop(self, gpu_id, train_log, eval_log, train_writer, eval_writer):
        device = torch.device("cuda", gpu_id)
        best_score = 0.
        sco = 0.
        block = 1
        dice_scores = []
        ce_scores = []
        losses = []
        for epoch in range(1, self.epochs + 1):
            if self.mode == "DDP":
                self.train_sampler.set_epoch(epoch)
                self.val_sampler.set_epoch(epoch)

            # Training loop
            if self.train:
                self.model.train()
                for batch, (pat_id, bbox, inp, gt) in enumerate(self.trainloader):
                    last_lr = self.scheduler.get_last_lr()[0]
                    self.optimizer.zero_grad()
                    inp = inp.to(device)
                    gt = gt.to(dtype=torch.int64, device=device)
                    p = self.model(inp)
                    # remove overlap class
                    mask=~torch.eq(gt, 105)
                    gt[gt == 105] = 0
                    gt_oh = OneHot(gt, self.num_classes - 1)
                    ce = F.cross_entropy(p, gt.squeeze(1), reduction="none")
                    dice = DiceMax(F.softmax(p, 1), gt_oh, mask)
                    loss = self.lw[0]*self.lw_decay[0]**(epoch+self.se-1)*ce.mean() + self.lw[1]*self.lw_decay[1]**(epoch+self.se-1)*dice.mean()
                    loss.backward()
                    dice_scores.append(1. - dice.detach().cpu().tolist())
                    ce_scores.append(ce.detach().cpu().tolist())
                    losses.append(loss.detach().cpu().item())
                    self.optimizer.step()
                    if self.sel_scheduler == "cyclic":
                        self.scheduler.step()
                    if (batch + 1) % self.track_freq == 0:
                        block_loss = np.asarray(losses).flatten().mean()
                        block_dice = np.asarray(dice_scores).flatten().mean()
                        block_ce = np.asarray(ce_scores).mean()
                        train_writer.writerow([epoch, block, last_lr, block_loss,
                                               block_ce, block_dice])
                        if self.mode != "DDP":
                            print((f"epoch {epoch}/{self.epochs} | block: {block}, block_size: {self.block_size} | "
                                   f"loss: {block_loss:.5f}, cross_entropy: {block_ce}, block_dice: {block_dice:.3f}, "
                                   f"{self.met_name}: {sco:.3f}, best: {best_score:.3f}"))
                        elif gpu_id == 0:
                            print((f"epoch {epoch}/{self.epochs} | block: {block}, block_size: {self.block_size} | "
                                   f"loss: {block_loss:.5f}, cross_entropy: {block_ce}, block_dice: {block_dice:.3f}, "
                                   f"{self.met_name}: {sco:.3f}, best: {best_score:.3f}"))
                        dice_scores = []
                        ce_scores = []
                        losses = []
                        block += 1

            # Validation loop;  every epoch
            if (self.sel_scheduler != "cyclic") and (self.sel_scheduler != None):
                self.scheduler.step()
            samples = []
            bboxes = []
            dice_scores = []
            ce_scores = []
            self.model.eval()
            with torch.no_grad():
                for vbatch, (vpat_id, vbbox, vi, vt) in enumerate(self.validloader):
                    samples.append(vpat_id.detach().item())
                    bboxes.append(vbbox.detach().tolist())
                    vi = vi.to(device)
                    vt = vt.to(dtype=torch.int64, device=device)
                    pv = self.model(vi)
                    mask=~torch.eq(vt, 105)
                    vt[vt == 105] = 0
                    vt_oh = OneHot(vt, self.num_classes - 1)
                    ce = F.cross_entropy(pv, gt.squeeze(1))
                    dice = DiceMax(F.softmax(pv, 1), vt_oh, mask)
                    vt[vt == self.num_classes - 1] = 0
                    dice_scores.append(1. - dice.detach().tolist())
                    ce_scores.append(ce.detach().tolist())
            eval_writer.writerow([epoch, samples, bboxes, ce_scores, dice_scores])
            if self.mode != "DDP":
                sco = np.asarray(dice_scores).flatten().mean()
                state = {
                    "model": self.model.state_dict(),
                    "optimizer": self.optimizer.state_dict()
                }
                self._SaveCkptsModel(state, sco)
                if sco > best_score:
                    best_score = sco
                    self._SaveBestModel(state, best_score)
            elif gpu_id == 0:
                sco = np.asarray(dice_scores).flatten().mean()
                state = {
                    "model": self.model.module.state_dict(),
                    "optimizer": self.optimizer.state_dict()
                }
                self._SaveCkptsModel(state, sco)
                if sco > best_score:
                    best_score = sco
                    self._SaveBestModel(state, best_score)
            samples = []
            bboxes = []
            dice_scores = []
            ce_scores = []
        train_log.close()
        eval_log.close()

    def _TrainModel(self, gpu_id):
        if self.mode == "DDP":
            self._SetupDDP(gpu_id, self.no_gpus)
        train_log, eval_log, train_writer, eval_writer = self._SetupLogs(gpu_id)
        device = torch.device("cuda", gpu_id)
        torch.cuda.set_device(device)
        self._SetupData(device)
        self._SetupModelAndOptim(gpu_id, device)
        self._SetupScheduler()
        self._TrainLoop(gpu_id, train_log, eval_log, train_writer, eval_writer)
        if self.mode == "DDP":
            self._ShutdownDDP()
        return

    @TimeFuncDecorator(True)
    def Run(self, gpu_id=0):
        if self.mode == "DDP":
            mp.spawn(self._TrainModel, nprocs=self.no_gpus)
        else:
            self._TrainModel(gpu_id)

    @TimeFuncDecorator(True)
    def LoopDataset(self):
        temp_data = TotalSegmentatorData(torch.device("cpu"), self.train_data_path, self.train_data_cfgs)
        temp_loader = DataLoader(temp_data, batch_size=self.batch_size, shuffle=False)
        for name, loc, inp, gt in temp_loader:
            print(f"pat: {name} | im: {inp.shape}, {inp.dtype} | gt: {gt.shape}, {gt.dtype}")
        return

if __name__ == "__main__":
    pass


from django.urls import path
#from .views import OnboardedOrderBillingListView
from .views import DeliveryOfficerCreateAPIView, DeliveryOfficerListAPIView, DeliveryOfficerOrdersListAPIView, DeliveryOfficerProfileView

urlpatterns = [
	path('create-officer/', DeliveryOfficerCreateAPIView.as_view(), name='create-do'),
	path('all-officers/', DeliveryOfficerListAPIView.as_view(), name='list-do'),
	path('<int:pk>/officer-orders/', DeliveryOfficerOrdersListAPIView.as_view(), name='do-orders'),
	path('officer/<int:pk>/', DeliveryOfficerProfileView.as_view(), name='delivery-officer-retrieve'),
]


from uuid import uuid4 as _uuid4

from fastapi import APIRouter as _APIRouter
from fastapi import BackgroundTasks as _BackgroundTasks
from fastapi import HTTPException as _HTTPException
from pydantic import BaseModel as _BaseModel
from pydantic import Field as _Field

from nedrexapi.common import _MUST_COLL, _MUST_COLL_LOCK
from nedrexapi.networks import normalise_seeds_and_determine_type
from nedrexapi.tasks import queue_and_wait_for_job

router = _APIRouter()

class MustRequest(_BaseModel):
    seeds: list[str] = _Field(None, title="Seeds for MuST", description="Seeds for MuST")
    network: str = _Field(
        None,
        title="NeDRex-based PPI/GGI network to use",
        description="NeDRex-based PPI/GGI network to use. Default: `DEFAULT`",
    )
    hubpenalty: float = _Field(None, title="Hub penalty", description="Specific hub penalty between 0.0 and 1.0")
    multiple: bool = _Field(
        None, title="Multiple", description="Boolean flag to indicate whether multiple results should be returned."
    )
    trees: int = _Field(None, title="Trees", description="The number of trees to be returned.")
    maxit: int = _Field(None, title="Max iterations", description="Adjusts the maximum number of iterations to run.")

    class Config:
        extra = "forbid"

_DEFAULT_MUST_REQUEST = MustRequest()

@router.post("/submit", summary="MuST Submit")
async def must_submit(background_tasks: _BackgroundTasks, mr: MustRequest = _DEFAULT_MUST_REQUEST):
    """
    Submits a job to run MuST using a NEDRexDB-based gene-gene or protein-protein network.
    The required parameters are:
      - `seeds` - a parameter used to identify seed gene(s) or protein(s) for MuST
      - `multiple` - a parameter indicating whether you want multiple results from MuST
      - `maxit` - a parameter used to adjust the maximum number of iterations for MuST
      - `trees` - a parameter used to indicate the number of trees to be returned
    """
    if not mr.seeds:
        raise _HTTPException(status_code=400, detail="No seeds submitted")
    if mr.hubpenalty is None:
        raise _HTTPException(status_code=400, detail="Hub penalty not specified")
    if mr.multiple is None:
        raise _HTTPException(status_code=400, detail="Multiple is not specified")
    if mr.trees is None:
        raise _HTTPException(status_code=400, detail="Trees is not specified")
    if mr.maxit is None:
        raise _HTTPException(status_code=400, detail="Max iterations is not specified")

    new_seeds, seed_type = normalise_seeds_and_determine_type(mr.seeds)
    mr.seeds = new_seeds

    if not 0.0 <= mr.hubpenalty <= 1.0:
        raise _HTTPException(status_code=422, detail=f"Hub penalty given ({mr.hubpenalty}) is not between 0.0 and 1.0")
    if not mr.trees > 0:
        raise _HTTPException(status_code=422, detail="Trees must be greater than zero")
    if not mr.maxit > 0:
        raise _HTTPException(status_code=422, detail="Max iterations must be greater than zero")

    query = {
        "seeds": sorted(mr.seeds),
        "seed_type": seed_type,
        "network": "DEFAULT" if mr.network is None else mr.network,
        "hub_penalty": mr.hubpenalty,
        "multiple": mr.multiple,
        "trees": mr.trees,
        "maxit": mr.maxit,
    }

    with _MUST_COLL_LOCK:
        result = _MUST_COLL.find_one(query)

        if result:
            uid = result["uid"]
        else:
            uid = f"{_uuid4()}"
            query["uid"] = uid
            query["status"] = "submitted"
            _MUST_COLL.insert_one(query)
            background_tasks.add_task(queue_and_wait_for_job, "must", uid)

    return uid

@router.get("/status", summary="MuST Status")
def must_status(uid: str):
    """
    Returns the details of the MuST job with the given `uid`, including the original query parameters and the status
    of the job (`submitted`, `running`, `failed`, or `completed`).
    If the job fails, then these details will contain the error message.
    """
    query = {"uid": uid}
    result = _MUST_COLL.find_one(query)
    if not result:
        raise _HTTPException(status_code=404, detail=f"No MuST job with UID {uid!r}")
    result.pop("_id")
    return result


from __future__ import print_function
from __future__ import division
import pickle
import numpy as np
import torch
from torch.autograd import Variable
import torch.nn as nn
import torch.nn.functional as F
import torchvision
import torchvision.transforms as transforms
import torch.optim as optim
from joblib import Parallel, delayed
import multiprocessing as mp
from tqdm import tqdm

classes_c2f_map = [['beaver', 'dolphin', 'otter', 'seal', 'whale'],
                   ['aquarium_fish', 'flatfish', 'ray', 'shark', 'trout'],
                   ['orchid', 'poppy', 'rose', 'sunflower', 'tulip'],
                   ['bottle', 'bowl', 'can', 'cup', 'plate'],
                   ['apple', 'mushroom', 'orange', 'pear', 'sweet_pepper'],
                   ['clock', 'keyboard', 'lamp', 'telephone', 'television'],
                   ['bed', 'chair', 'couch', 'table', 'wardrobe'],
                   ['bee', 'beetle', 'butterfly', 'caterpillar', 'cockroach'],
                   ['bear', 'leopard', 'lion', 'tiger', 'wolf'],
                   ['bridge', 'castle', 'house', 'road', 'skyscraper'],
                   ['cloud', 'forest', 'mountain', 'plain', 'sea'],
                   ['camel', 'cattle', 'chimpanzee', 'elephant', 'kangaroo'],
                   ['fox', 'porcupine', 'possum', 'raccoon', 'skunk'],
                   ['crab', 'lobster', 'snail', 'spider', 'worm'],
                   ['baby', 'boy', 'girl', 'man', 'woman'],
                   ['crocodile', 'dinosaur', 'lizard', 'snake', 'turtle'],
                   ['hamster', 'mouse', 'rabbit', 'shrew', 'squirrel'],
                   ['maple_tree', 'oak_tree', 'palm_tree', 'pine_tree', 'willow_tree'],
                   ['bicycle', 'bus', 'motorcycle', 'pickup_truck', 'train'],
                   ['lawn_mower', 'rocket', 'streetcar', 'tank', 'tractor']]
mmap = None

class Net(nn.Module):
    def __init__(self):
        super(Net, self).__init__()
        # auxiliary
        self.dropout_conv = nn.Dropout(p=0.15)
        self.dropout_fc = nn.Dropout(p=0.25)
        # block 1
        self.conv_b1_1 = nn.Conv2d(3, 32, 3, padding=1)
        self.conv_b1_bn1 = nn.BatchNorm2d(32)
        self.conv_b1_2 = nn.Conv2d(32, 32, 3, padding=1)
        self.conv_b1_bn2 = nn.BatchNorm2d(32)
        self.conv_b1_3 = nn.Conv2d(32, 32, 3, padding=1)
        self.conv_b1_bn3 = nn.BatchNorm2d(32)
        self.pool_b1 = nn.MaxPool2d(2, 2)
        # block 2
        self.conv_b2_1 = nn.Conv2d(32, 64, 3, padding=1)
        self.conv_b2_bn1 = nn.BatchNorm2d(64)
        self.conv_b2_2 = nn.Conv2d(64, 64, 3, padding=1)
        self.conv_b2_bn2 = nn.BatchNorm2d(64)
        self.conv_b2_3 = nn.Conv2d(64, 64, 3, padding=1)
        self.conv_b2_bn3 = nn.BatchNorm2d(64)
        self.pool_b2 = nn.MaxPool2d(2, 2)
        # block 3
        self.conv_b3_1 = nn.Conv2d(64, 128, 3, padding=1)
        self.conv_b3_bn1 = nn.BatchNorm2d(128)
        self.conv_b3_2 = nn.Conv2d(128, 128, 3, padding=1)
        self.conv_b3_bn2 = nn.BatchNorm2d(128)
        self.conv_b3_3 = nn.Conv2d(128, 128, 3, padding=1)
        self.conv_b3_bn3 = nn.BatchNorm2d(128)
        self.pool_b3 = nn.MaxPool2d(2, 2)
        # block 4
        self.conv_b4_1 = nn.Conv2d(128, 256, 3, padding=1)
        self.conv_b4_bn1 = nn.BatchNorm2d(256)
        self.conv_b4_2 = nn.Conv2d(256, 256, 3, padding=1)
        self.conv_b4_bn2 = nn.BatchNorm2d(256)
        self.conv_b4_3 = nn.Conv2d(256, 256, 3, padding=1)
        self.conv_b4_bn3 = nn.BatchNorm2d(256)
        self.pool_b4 = nn.MaxPool2d(2, 2)
        # block 5
        self.conv_b5_1 = nn.Conv2d(256, 512, 3, padding=1)
        self.conv_b5_bn1 = nn.BatchNorm2d(512)
        self.conv_b5_2 = nn.Conv2d(512, 512, 3, padding=1)
        self.conv_b5_bn2 = nn.BatchNorm2d(512)
        self.conv_b5_3 = nn.Conv2d(512, 512, 3, padding=1)
        self.conv_b5_bn3 = nn.BatchNorm2d(512)
        self.pool_b5 = nn.MaxPool2d(2, 2)

        # coarse branch 1 -> generalized classes
        self.br1_fc1 = nn.Linear(512, 4096)
        self.br1_bn1 = nn.BatchNorm1d(4096)
        self.br1_fc2 = nn.Linear(4096, 4096)
        self.br1_bn2 = nn.BatchNorm1d(4096)
        self.br1_fc3 = nn.Linear(4096, 20)
        self.br1_sm = nn.Softmax(dim=1)
        # branch 2 -> Fine layers
        self.br2_fc1 = nn.Linear(512, 4096)
        self.br2_bn1 = nn.BatchNorm1d(4096)
        self.br2_fc2 = nn.Linear(4096, 4096)
        self.br2_bn2 = nn.BatchNorm1d(4096)
        self.br2_fc3 = nn.Linear(4096, 100)
        self.br2_sm = nn.Softmax(dim=1)

    def forward(self, x):
        # block 1 forward prop
        x = F.leaky_relu(self.conv_b1_bn1(self.conv_b1_1(x)))
        x = self.dropout_conv(x)
        x = F.leaky_relu(self.conv_b1_bn2(self.conv_b1_2(x)))
        x = self.dropout_conv(x)
        x = F.leaky_relu(self.conv_b1_bn3(self.conv_b1_3(x)))
        x = self.dropout_conv(x)
        x = self.pool_b1(x)
        # block 2 forward prop
        x = F.leaky_relu(self.conv_b2_bn1(self.conv_b2_1(x)))
        x = self.dropout_conv(x)
        x = F.leaky_relu(self.conv_b2_bn2(self.conv_b2_2(x)))
        x = self.dropout_conv(x)
        x = F.leaky_relu(self.conv_b2_bn3(self.conv_b2_3(x)))
        x = self.dropout_conv(x)
        x = self.pool_b2(x)
        # block 3 forward prop
        x = F.leaky_relu(self.conv_b3_bn1(self.conv_b3_1(x)))
        x = self.dropout_conv(x)
        x = F.leaky_relu(self.conv_b3_bn2(self.conv_b3_2(x)))
        x = self.dropout_conv(x)
        x = F.leaky_relu(self.conv_b3_bn3(self.conv_b3_3(x)))
        x = self.dropout_conv(x)
        x = self.pool_b3(x)
        # block 3 forward prop
        x = F.leaky_relu(self.conv_b4_bn1(self.conv_b4_1(x)))
        x = self.dropout_conv(x)
        x = F.leaky_relu(self.conv_b4_bn2(self.conv_b4_2(x)))
        x = self.dropout_conv(x)
        x = F.leaky_relu(self.conv_b4_bn3(self.conv_b4_3(x)))
        x = self.dropout_conv(x)
        x = self.pool_b4(x)
        # block 3 forward prop
        x = F.leaky_relu(self.conv_b5_bn1(self.conv_b5_1(x)))
        x = self.dropout_conv(x)
        x = F.leaky_relu(self.conv_b5_bn2(self.conv_b5_2(x)))
        x = self.dropout_conv(x)
        x = F.leaky_relu(self.conv_b5_bn3(self.conv_b5_3(x)))
        x = self.dropout_conv(x)
        x = self.pool_b5(x)
        # offshoot branch 1
        br1_x = x.view(-1, self.num_flat_features(x))
        br1_x = self.br1_fc1(br1_x)
        br1_x = self.br1_bn1(br1_x)
        br1_x = F.leaky_relu(br1_x)
        br1_x = self.dropout_fc(br1_x)
        br1_x = self.br1_fc2(br1_x)
        br1_x = self.br1_bn2(br1_x)
        br1_x = F.leaky_relu(br1_x)
        br1_x = self.dropout_fc(br1_x)
        br1_x = self.br1_fc3(br1_x)
        br1_out = self.br1_sm(br1_x)
        # offshoot branch 2
        br2_x = x.view(-1, self.num_flat_features(x))
        br2_x = self.br2_fc1(br2_x)
        br2_x = self.br2_bn1(br2_x)
        br2_x = F.leaky_relu(br2_x)
        br2_x = self.dropout_fc(br2_x)
        br2_x = self.br2_fc2(br2_x)
        br2_x = self.br2_bn2(br2_x)
        br2_x = F.leaky_relu(br2_x)
        br2_x = self.dropout_fc(br2_x)
        br2_x = self.br2_fc3(br2_x)
        br2_out = self.br2_sm(br2_x)
        return(br1_out, br2_out)

    def num_flat_features(self, x):
        size = x.size()[1:]  # all dimensions except the batch dimension
        num_features = 1
        for s in size:
            num_features *= s
        return num_features

def map_subclasses(array):
    for i in range(0, len(array)):
        array[i] = mmap[array[i]]
    return(array)

def eval_net(dataloader):
    correct_coarse = 0
    correct_fine = 0
    total = 0
    total_loss_coarse = 0
    total_loss_fine = 0
    net.eval()
    criterion1 = nn.CrossEntropyLoss(reduction='mean')
    criterion2 = nn.CrossEntropyLoss(reduction='mean')
    for data in dataloader:
        images, labels = data
        coarse_labels = np.copy(labels.numpy())
        coarse_labels = map_subclasses(coarse_labels)
        coarse_labels = torch.from_numpy(coarse_labels)
        images = Variable(images).cuda()
        labels = Variable(labels).cuda()
        coarse_labels = Variable(coarse_labels).cuda()
        coarse_out, fine_out = net(images)
        _, predicted_coarse = torch.max(coarse_out.data, 1)
        _, predicted_fine = torch.max(fine_out.data, 1)
        total += labels.size(0)
        correct_coarse += (predicted_coarse == coarse_labels.data).sum()
        correct_fine += (predicted_fine == labels.data).sum()
        fine_loss = criterion1(fine_out, labels)
        coarse_loss = criterion2(coarse_out, coarse_labels)
        total_loss_fine += fine_loss.item()
        total_loss_coarse += coarse_loss.item()
    net.train()
    return (total_loss_coarse / total, correct_coarse.float() / total,
            total_loss_fine / total, correct_fine.float() / total)

def objective(model, input, coarse_label, fine_labels):
    coarse_out, fine_out = model(input)
    # return torch.max(fine_out[0, fine_labels])
    return 2 * torch.max(fine_out[0, fine_labels]) - coarse_out[0, coarse_label]

def objective_gradient(objective, model, input, coarse_label, fine_labels):
    x = input.detach().clone()
    x.requires_grad = True
    output = objective(model, x, coarse_label, fine_labels)
    output.backward()
    grad = x.grad.clone()
    return grad

def projection(input):
    input = input
    input[input > 1] = 1
    input[input < -1] = -1
    return input

def attack(model, input, coarse_label, fine_labels, epsilon):
    curr = input.clone()
    curr.requires_grad = True

    for iter in range(30):

        grad = objective_gradient(objective, model, curr,
                                  coarse_label, fine_labels)
        grad = epsilon * grad / torch.norm(grad, p="fro")
        next = curr - grad

        curr.data = next.clone()

    return projection(curr.detach())

def job(i, model, images, labels):
    image = images[i, :, :, :].unsqueeze(0)
    label = labels[i]
    coarse_label = map_subclasses(np.array(label, ndmin=2))
    fine_labels = np.flatnonzero(mmap == coarse_label)
    coarse_label = torch.from_numpy(coarse_label)
    fine_labels = torch.from_numpy(fine_labels)

    output_image = attack(net, image, coarse_label, fine_labels, 1)

    return (output_image, coarse_label)

if __name__ == "__main__":
    BATCH_SIZE = 32  # mini_batch size

    transform = transforms.Compose(
        [transforms.ToTensor(),
         transforms.Normalize((0.5, 0.5, 0.5), (0.5, 0.5, 0.5))])
    train_transform = transforms.Compose(
        [transforms.ToTensor(),
         transforms.Normalize((0.5, 0.5, 0.5), (0.5, 0.5, 0.5))])

    trainset = torchvision.datasets.CIFAR100(root='./data', train=True,
                                             download=True, transform=train_transform)
    trainloader = torch.utils.data.DataLoader(trainset, batch_size=BATCH_SIZE,
                                              shuffle=True, num_workers=2)

    testset = torchvision.datasets.CIFAR100(root='./data', train=False,
                                            download=True, transform=transform)
    testloader = torch.utils.data.DataLoader(testset, batch_size=BATCH_SIZE,
                                             shuffle=False, num_workers=2)

    classes = pickle.load(open('./data/cifar-100-python/meta', 'rb'))
    fine = classes['fine_label_names']
    coarse = classes['coarse_label_names']
    a = []
    for name in fine:
        i = 0
        for sublist in classes_c2f_map:
            if name in sublist:
                a.append(i)
            i = i + 1
    mmap = np.array(a)
    net = Net().cpu()
    optimizer = optim.SGD(net.parameters(), lr=0.005, momentum=0.85)
    pretrained = torch.load('block5_branch.pth', map_location=torch.device('cpu'))
    net.load_state_dict(pretrained['state_dict'])
    net.eval()

    output_labels = np.empty((0, 1))
    output_images = np.empty((0, 3, 32, 32))

    # set up multiprocessing
    num_cores = mp.cpu_count()

    ctr = 0
    for data in trainloader:
        images, labels = data
        n_items = len(labels)
        idxs = tqdm(range(n_items))
        results = (Parallel(n_jobs=num_cores)(delayed(job)(i, net, images, labels) for i in idxs))

        for i in range(n_items):
            output_images = np.append(output_images, results[i][0].numpy(), axis=0)
            output_labels = np.append(output_labels, results[i][1].numpy(), axis=0)

        np.save("attacked_images.npy", output_images)
        np.save("attacked_image_labels.npy", output_labels)


import numpy as np
import matplotlib.pyplot as plt

x=np.linspace(0,4*np.pi)
y=np.cos(x)
plt.plot(x,y)
plt.title("gráfica del cos")
plt.xlabel("x")
plt.ylabel("cos(x)")
plt.savefig("grafica.png")


# Example: Button
from gpiozero import Button
from time import sleep

#Refer to the gpio.jpg for pin layout.
btn = Button(17)

while True:
	btn.wait_for_press()
	print("Button pressed")
	break


import re
from datetime import datetime
import json
import glob
import os
import pendulum

class EmailFiles:
    @staticmethod
    def get_list_of_files(pattern):
        return glob.glob(pattern)

class ParseShadowBackupEmails:
    active_email_dictionary = {}
    web_page_file = 'sp.html'
    master_email_dictionary = {}
    change_count = 0
    backup_code_1120 = []
    backup_code_1121 = []
    backup_code_unknown = []
    default_threshold = 72
    row_id = 0
    date_format = '%m-%d-%Y %H:%M:%S'
    max_parse_time = 'none'
    min_parse_time = 'none'
    company_count = 0
    table_width = "100%"

    def __init__(self, directory):
        self.dictionary_file = os.getenv("HOME") + '/email_dictionary.json'
        list_of_email_files = self.check_for_shadow_email(EmailFiles.get_list_of_files(directory))
        subjects = self.get_subjects(list_of_email_files)
        split_subjects = self.split_subject(subjects)
        self.build_unique_active_dictionary(split_subjects)
        self.load_master_dictionary()
        self.compare_master_and_active_dictionaries()

    @staticmethod
    def check_for_shadow_email(list_of_files):
        list_of_shadow_emails = []
        for email in list_of_files:
            with open(email) as f:
                if 'ShadowProtectSvc' in f.read():
                    list_of_shadow_emails.append(email)
        return list_of_shadow_emails

    def get_subjects(self, list_of_email_files):
        subjects = []
        for email in list_of_email_files:
            with open(email) as f:
                file_data = f.readlines()
                subjects.append(self.get_match_and_next_line("^Subject:", file_data))
                os.remove(email)
        return subjects

    def rename_web_page(self):
        os.rename(self.web_page_file, "/var/www/html/reports/" + self.web_page_file)

    @staticmethod
    def get_match_and_next_line(pattern, file_data):
        from_date = ''
        for line_number, line in enumerate(file_data):
            if re.search("^From", line) and line_number == 1:
                from_date = "| " + line
            if re.search(pattern, line):
                subject = line.rstrip() + " " + file_data[line_number + 1].rstrip() + " " + from_date.rstrip()
                return subject

    def split_subject(self, subjects):
        split_subjects = []
        for subject in subjects:
            split_subject = subject.split('|')
            split_subjects.append(self.create_dictionary(split_subject))
        return split_subjects

    def create_dictionary(self, split_subject):
        if len(split_subject) == 7:
            subject_dictionary = {
                'server': str(split_subject[0].strip().replace('Subject: ', '')),
                'client': str(split_subject[1].strip()),
                'company': str(split_subject[2].strip()),
                'backup_code': str(self.get_backup_code(split_subject[5].strip())),
                'email_time': self.convert_utc_to_local(str(self.get_email_time(split_subject[-1].strip()))),
                'threshold': self.default_threshold
            }
            return subject_dictionary

    def convert_utc_to_local(self, email_time):
        dt = pendulum.from_format(email_time, 'MMM DD HH:mm:ss YYYY', tz='UTC')
        tz = pendulum.timezone('US/Eastern')
        in_est = tz.convert(dt)
        return in_est.strftime(self.date_format)

    def build_unique_active_dictionary(self, split_subjects):
        split_subjects = list(filter(None.__ne__, split_subjects))
        for subject in split_subjects:
            key = subject['company'] + subject['server'] + subject['client']
            if key not in self.active_email_dictionary:
                self.active_email_dictionary[key] = subject
            elif key in self.active_email_dictionary:
                datetime_object_in_dict = datetime.strptime(self.active_email_dictionary[key]['email_time'],
                                                            self.date_format)
                datetime_object = datetime.strptime(subject['email_time'], self.date_format)
                if datetime_object > datetime_object_in_dict:
                    self.active_email_dictionary[key] = subject
        self.initialize_dictionary()

    def compare_master_and_active_dictionaries(self):
        for key, email_data in self.active_email_dictionary.items():
            if key not in self.master_email_dictionary:
                self.master_email_dictionary[key] = email_data
                self.change_count += 1
            elif key in self.master_email_dictionary:
                datetime_object_in_master_dict = datetime.strptime(self.master_email_dictionary[key]['email_time'],
                                                                   self.date_format)
                datetime_object = datetime.strptime(email_data['email_time'], self.date_format)
                if datetime_object > datetime_object_in_master_dict:
                    if self.master_email_dictionary[key]['threshold'] != email_data['threshold']:
                        email_data['threshold'] = self.master_email_dictionary[key]['threshold']
                    self.master_email_dictionary[key] = email_data
                    self.change_count += 1
        if self.change_count > 0:
            print("Something Change Updating Dictionary on disk")
            self.save_json(self.master_email_dictionary, self.dictionary_file)

    def generate_html_table(self):
        self.sort_master_dictionary_for_web_page()
        table = ''
        table += self.build_html_table_header()
        table += self.build_html_table_data('unknown', self.backup_code_unknown)
        table += self.build_html_table_data('critical', self.backup_code_1121)
        table += self.build_html_table_data('ok', self.backup_code_1120)
        table += self.build_html_table_footer()
        with open(self.web_page_file, "w") as text_file:
            text_file.write(table)

    def build_dashboard(self):
        current_time = pendulum.now('US/Eastern')
        table = ''
        table += "
\n"
        table += "
\n"
        table += " OK 	\n"
        table += " UNKNOWN 	\n"
        table += " CRITICAL 	\n"
        table += " Clients 	\n"
        table += " Companies 	\n"
        table += " First Email 	\n"
        table += " Last Email 	\n"
        table += " Page Generated 	\n"
        table += "
\n"
        table += "
\n"
        table += " " + str(len(self.backup_code_1120)) + "	\n"
        table += " " + str(len(self.backup_code_unknown)) + "	\n"
        table += " " + str(len(self.backup_code_1121)) + "	\n"
        table += " " + str(
            len(self.backup_code_1121) + len(self.backup_code_1120) + len(self.backup_code_unknown)) + "	\n"
        table += " " + str(self.company_count) + "	\n"
        table += " " + self.min_parse_time.strftime(self.date_format) + "	\n"
        table += " " + self.max_parse_time.strftime(self.date_format) + "	\n"
        table += " " + current_time.strftime(self.date_format) + "	\n"
        table += "

\n"
        return table

    def build_html_table_data(self, status, list_of_code):
        table_data = ''
        for data in list_of_code:
            self.row_id += 1
            table_data += self.build_table_row_data(self.row_id, status, data)
        return table_data

    @staticmethod
    def get_row_color(status):
        colors = {'unknown': 'orange', 'ok': 'white', 'critical': 'E64A34'}
        return colors[status]

    def build_table_row_data(self, row_id, status, row):
        table_row = ''
        table_row += "
"
        table_row += "" + str(row_id) + "	"
        table_row += "" + status.upper() + "	"
        table_row += "" + row['company'] + "	"
        table_row += "" + row['server'] + "	"
        table_row += "" + row['client'] + "	"
        table_row += "" + row['email_time'] + "	"
        table_row += "" + row['backup_code'] + "	"
        table_row += "" + str(row['threshold']) + " Hours	"
        table_row += "
\n"
        return table_row

    def build_html_table_header(self):
        header = ['id', 'status', 'company', 'server', 'client', 'last email', 'backup_code', 'threshold']
        table_head = ''
        table_head += "\n"
        table_head += "\n"
        table_head += "<title> Shadow Protect Backup Status </title>\n"
        table_head += "\n"
        table_head += self.build_dashboard()
        table_head += "
\n"
        table_head += "
"
        for column in header:
            table_head += '' + column.upper() + '	'
        table_head += "
\n"
        return table_head

    @staticmethod
    def build_html_table_footer():
        footer = ''
        footer += "
"
        footer += ""
        return footer

    def sort_master_dictionary_for_web_page(self):
        company_list = []
        for key, data in sorted(self.master_email_dictionary.items()):
            company_list.append(data['company'])
            self.get_parse_time(data['email_time'])
            now = pendulum.now('US/Eastern')
            threshold_time = now.subtract(hours=data['threshold'])
            alert_time_formatted = threshold_time.strftime(self.date_format)
            alert_time = datetime.strptime(alert_time_formatted, self.date_format)
            email_time = datetime.strptime(data['email_time'], self.date_format)
            if email_time < alert_time:
                self.backup_code_unknown.append(data)
            elif data['backup_code'] == "1120":
                self.backup_code_1120.append(data)
            elif data['backup_code'] == "1121":
                self.backup_code_1121.append(data)
        self.company_count = len(set(company_list))

    def get_parse_time(self, parse_time):
        if self.max_parse_time == 'none':
            self.max_parse_time = datetime.strptime(parse_time, self.date_format)
        elif datetime.strptime(parse_time, self.date_format) > self.max_parse_time:
            self.max_parse_time = datetime.strptime(parse_time, self.date_format)
        if self.min_parse_time == 'none':
            self.min_parse_time = datetime.strptime(parse_time, self.date_format)
        elif datetime.strptime(parse_time, self.date_format) < self.min_parse_time:
            self.min_parse_time = datetime.strptime(parse_time, self.date_format)

    def load_master_dictionary(self):
        if os.path.isfile(self.dictionary_file):
            self.master_email_dictionary = self.load_json(self.dictionary_file)

    def initialize_dictionary(self):
        if not os.path.isfile(self.dictionary_file):
            print("Initialized Dictionary on Disk")
            try:
                self.save_json(self.active_email_dictionary, self.dictionary_file)
            except (FileNotFoundError, FileExistsError, IOError) as err:
                print(err)

    @staticmethod
    def save_json(data, file_name):
        try:
            with open(file_name, 'w') as fp:
                json.dump(data, fp)
        except (FileNotFoundError, FileExistsError, IOError) as err:
            print(err)

    @staticmethod
    def load_json(file_name):
        try:
            with open(file_name, 'r') as fp:
                return json.load(fp)
        except (FileExistsError, IOError) as err:
            print(err)

    @staticmethod
    def get_backup_code(raw_code):
        backup_code = raw_code.split()
        return backup_code[1].strip("'")

    @staticmethod
    def get_email_time(raw_email_time):
        email_time_list = raw_email_time.split()
        email_time = email_time_list[-4] + ' ' + email_time_list[-3] + ' ' + email_time_list[-2] + ' ' + \
                     email_time_list[-1]
        return email_time