from typing import Callable, TypeVar, Generic, List, Any, NamedTuple, Protocol
from distribution import Distrib, support, uniform_support
import utils
from math import log, exp
from random import randint
from random import uniform as randuniform
from abc import ABC, abstractmethod

A = TypeVar('A')
B = TypeVar('B')
_C = TypeVar('_C')

class Prob(ABC):

    @abstractmethod
    def assume(self, p: bool) -> None:
        pass

    @abstractmethod
    def observe(self, d: Distrib[A], x: A) -> None:
        pass

    @abstractmethod
    def sample(self, d: Distrib[A]) -> A:
        pass

class InferenceMethod(ABC, Generic[A, B]):

    @abstractmethod
    def __init__(self, model: Callable[[Prob, A], B], data: A):
        pass

    @abstractmethod
    def infer(self, n: int = 1000) -> Distrib[B]:
        pass

    @staticmethod
    @abstractmethod
    def name() -> str:
        pass

class Reject(Exception):
    pass

class UndefinedSupport(Exception):
    pass

class CallableProtocol(Protocol[_C]):
    __call__: _C

class RejectionSampling(InferenceMethod[A, B]):

    class RejSampProb(Prob):
        def assume(self, p: bool) -> None:
            if not p:
                raise Reject

        def observe(self, d: Distrib[A], x: A) -> None:
            y = d.draw()
            self.assume(x == y)

        def sample(self, d: Distrib[A]) -> A:
            return d.draw()

    _model: CallableProtocol[Callable[[Prob, A], B]]
    _data: A

    def __init__(self, model: Callable[[Prob, A], B], data: A):
        self._model = model
        self._data = data

    @staticmethod
    def name() -> str:
        return "Rejection Sampling"

    def infer(self, n: int = 1000) -> Distrib[B]:
        prob = self.RejSampProb()
        values: List[B] = []
        while len(values) < n:
            try:
                value = self._model(prob, self._data)
            except Reject:
                continue
            values.append(value)
        return uniform_support(values)

class ImportanceSampling(InferenceMethod[A, B]):

    class ImpSampProb(Prob):
        _id: int
        _scores: List[float]

        def __init__(self, idx: int, scores: List[float]):
            self._id = idx
            self._scores = scores

        def factor(self, s: float) -> None:
            self._scores[self._id] += s

        def assume(self, p: bool) -> None:
            self.factor(0. if p else -float('inf'))

        def observe(self, d: Distrib[A], x: A) -> None:
            self.factor(d.logpdf(x))

        def sample(self, d: Distrib[A]) -> A:
            return d.draw()

    _model: CallableProtocol[Callable[[Prob, A], B]]
    _data: A

    def __init__(self, model: Callable[[Prob, A], B], data: A):
        self._model = model
        self._data = data

    @staticmethod
    def name() -> str:
        return "Importance Sampling"

    def infer(self, n: int = 1000) -> Distrib[B]:
        scores = [0.] * n
        values = [self._model(self.ImpSampProb(i, scores), self._data)
                  for i in range(n)]
        return support(values, scores)

_SampleState = NamedTuple('_SampleState', [('idx', int),
    ('choices', List[Any]), ('logits', List[float])])

class EnumerationSampling(InferenceMethod[A, B]):

    class EnumSampProb(Prob):
        _state_idx: int
        _score: float
        _path: List[_SampleState]
        _has_ended: bool

        def __init__(self) -> None:
            self._state_idx = -1
            self._score = 0
            self._path = []
            self._has_ended = False

        def init_next_path(self) -> None:
            # Reinitialisation des valeurs.
            self._state_idx = -1
            self._score = 0
            # Calcul de la prochaine trajectoire.
            n = len(self._path) - 1
            for i in range(n, -1, -1):
                idx, choices, logits = self._path[i]
                # On effectue le prochain choix
                if idx + 1 < len(choices):
                    self._path[i] = _SampleState(idx=idx + 1,
                    choices=choices, logits=logits)
                    return
                # Si on a fait tous les choix possibles, on revient en arrière.
                else:
                    self._path.pop()
            # Si la prochaine trajectoire est nulle, on a fini.
            if len(self._path) == 0:
                self._has_ended = True

        def assume(self, p: bool) -> None:
            if not p:
                raise Reject

        def observe(self, d: Distrib[A], x:A) -> None:
            y = self.sample(d)
            self.assume(x == y)

        def sample(self, d: Distrib[A]) -> A:
            self._state_idx += 1
            if self._state_idx >= len(self._path):
                # On est sûr dans ce cas que sample_idx == len(path)
                if d._support is None:
                    raise UndefinedSupport("The support is undefined or infinite. "\
                            "Exhaustive Sampling can't be used in that case.")
                support = d.get_support(shrink=True)
                assert(support is not None)
                self._path.append(_SampleState(idx=0, choices=support.values,
                logits=support.logits))

            idx, choices, logits = self._path[self._state_idx]
            self._score += logits[idx]  # Mult petits probs ou Add grands logits ?
            return choices[idx]  # type: ignore

    _model: CallableProtocol[Callable[[Prob, A], B]]
    _data: A

    def __init__(self, model: Callable[[Prob, A], B], data: A):
        self._model = model
        self._data = data

    @staticmethod
    def name() -> str:
        return "Enumeration Sampling"

    def infer(self, n:int = 0) -> Distrib[B]:
        prob = self.EnumSampProb()
        values = []
        logits = []
        #Tant qu'il reste des scénarios à examiner, on continue.
        while not prob._has_ended:
            try:
                value = self._model(prob, self._data)
                values.append(value)
                logits.append(prob._score)
            except Reject:
                pass
            prob.init_next_path()
        probs = utils.normalize(logits)
        values, probs = utils.shrink(values, probs)
        return support(values, [log(p) if p != 0 else -float('inf') for p in probs])

class MetropolisHastings(InferenceMethod[A, B]):

    class MHProb(Prob):
        _id: int
        _scores: List[float]
        _weights: List[float]
        _sampleResults: List[Any]
        _i: int
        _len: int
        _reuseI: int

        def __init__(self, idx: int, scores: List[float]):
            self._id = idx
            self._scores = scores
            self._i = 0
            self._reuseI = 0
            self._len = 0
            self._sampleResults = []
            self._weights = []

        def factor(self, s: float) -> None:
            self._scores[self._id] += s

        def assume(self, p: bool) -> None:
            self.factor(0. if p else -float('inf'))

        def observe(self, d: Distrib[A], x: A) -> None:
            self.factor(d.logpdf(x))

        def sample(self, d: Distrib[A]) -> A:
            if self._i < self._len:
                v = self._sampleResults[self._i]
                self._i += 1
            else:
                v = d.draw()
                self._sampleResults.append(v)
                self._weights.append(d.logpdf(v))
                self._i += 1
                self._len += 1
            return v  # type: ignore

        def go_back_to_step(self, i: int, new_id: int) -> None:
            self._sampleResults = self._sampleResults[:i]
            self._weights = self._weights[:i]
            self._reuseI = i
            self._i = 0
            self._len = i
            self._id = new_id

        def pick_random_step(self) -> int:
            assert(self._len >= 1)
            return randint(0, self._len - 1)

        def computeScore(self) -> float:
            s = 0.
            for i in range(self._reuseI):
                s += self._weights[i]
            # on a maintenant :
            # s : commme des log des poids des variables sur lesquelles on
            #     a appelé sample
            # self._scores[self._id] : somme des log des poids des variables
            #     observées (= score dans importance sampling)
            # self._len : le nombre de variables de sample
            return exp(s + self._scores[self._id]) / self._len

    _model: CallableProtocol[Callable[[Prob, A], B]]
    _data: A

    def __init__(self, model: Callable[[Prob, A], B], data: A):
        self._model = model
        self._data = data

    @staticmethod
    def name() -> str:
        return "Metropolis Hastings"

    def infer(self, n: int = 1000) -> Distrib[B]:
        scores = [0.] * n
        values = []
        logits = []
        prob = self.MHProb(0, scores)
        lastValue = self._model(prob, self._data)
        lastScore = prob.computeScore()
        values.append(lastValue)
        logits.append(log(lastScore) if lastScore > 0 else -float('inf'))
        for i in range(1, n):
            # on choisit aléatoirement un sample qui a été effectué par le
            # modèle
            step = prob.pick_random_step()
            # on exécute à nouveau le modèle depuis ce point
            prob.go_back_to_step(step, i)
            v = self._model(prob, self._data)
            score = prob.computeScore()
            x = randuniform(0, 1)
            if lastScore == 0 or x < min(1, score / lastScore):
                lastValue = v
                lastScore = score
            values.append(lastValue)
            logits.append(log(lastScore) if lastScore > 0 else -float('inf'))
        assert(len(values) == len(scores))
        return support(values, logits)


from requests import get

class BitrueService:
    def __init__(self):
        self.url = "https://openapi.bitrue.com/api/v1/ticker/bookTicker"

    def start(self, from_, to):
        PARAMS = {"symbol": f"{from_}{to}"}
        headers = {"Accept": "application/json", "Content-Type": "application/json"}
        resp = get(self.url, params=PARAMS, headers=headers)
        inch_data = resp.json()
        return inch_data


from pymd5 import *
import http.client, urllib.parse, sys
import math

url = sys.argv[1]

parsedUrl = urllib.parse.urlparse(url)
query = parsedUrl[4].split("&")
token = query[0][6:]

# Reform Old Hash
newQuery = query[1]
for x in query[2:]:
  newQuery = newQuery + "&"
  newQuery = newQuery + x

# Your code to modify url goes here
msglen = (len(newQuery) + 10) * 8
blocksize = math.ceil(msglen/512) * 512
h = md5(state=bytes.fromhex(token), count = blocksize )
x = "&command3=UnlockAllSafes"
h.update(x.encode())
newToken = str(h.hexdigest())

newQuery = urllib.parse.quote(bytes("token=" + newToken + "&") + bytes(newQuery, "UTF-8") + pymd5.padding(int(msglen)) + bytes(x, "UTF-8"))

parsedUrl = urllib.parse.urlparse(url)
reformedUrl = list(parsedUrl)
reformedUrl[4] = newQuery

parsedUrl = urllib.parse.urlunparse(reformedUrl)
parsedUrl = urllib.parse.urlparse(parsedUrl)

conn = http.client.HTTPConnection(parsedUrl.hostname,parsedUrl.port)
conn.request("GET", parsedUrl.path + "?" + parsedUrl.query)
print(conn.getresponse().read())


from flask import Flask, render_template, request
import sqlite3
import plotly.graph_objects as go
app = Flask(__name__)

def get_hotels():
    conn = sqlite3.connect('Final_Project.db')
    cur = conn.cursor()
    query = '''SELECT Id, HotelName, HotelCity, HotelState
    FROM Hotels
    '''
    results = cur.execute(query).fetchall()
    conn.close()
    return results

def get_results(sort_by, sort_order, hotel_id):
    conn = sqlite3.connect('Final_Project.db')
    cur = conn.cursor()
    if sort_by == 'rating':
        sort_column = 'Rating'
    elif sort_by == 'price':
        sort_column = 'AvgPrice'
    else:
        sort_column = 'Distance'

    query = f'''SELECT Name, Rating, AvgPrice, Distance, Link
    FROM Restaurants WHERE HotelId={hotel_id} ORDER BY {sort_column} {sort_order}
    '''
    results = cur.execute(query).fetchall()
    conn.close()
    return results

@app.route('/')
def index():
    results = get_hotels()
    return render_template('index.html', results=results)

@app.route('/results', methods=['POST'])
def results():
    sort_by = request.form['sort']
    sort_order = request.form['dir']
    hotel_id = request.form['hotel']
    results = get_results(sort_by, sort_order, hotel_id)
    arr = ['rating', 'price', 'distance']
    plot_results = request.form.get('plot', False)
    if (plot_results):
        x_vals = [r[0] for r in results]
        y_vals = [r[arr.index(sort_by) + 1] for r in results]
        bars_data = go.Bar(
            x=x_vals,
            y=y_vals
        )
        fig = go.Figure(data=bars_data)
        div = fig.to_html(full_html=False)
        return render_template("plot.html", plot_div=div)
    else:
        return render_template('results.html', sort=sort_by, order=sort_order, results=results)

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


import argparse
import pathlib
import sys

import numpy
import scipy.sparse as sp
import scipy.ndimage as nd

def parse_args(args):
    ap = argparse.ArgumentParser(
        description='Computes the euclidean distance transform for the sparse boundary matrix in the given shape. The boundary matrix contains all voxels on the surface boundaries.')
    ap.add_argument(dest='in_file', help='Path to 2D sparse matrix data file with shape (Samples, Values)',
                    metavar='InFile')
    ap.add_argument('-s', dest='shape', nargs='+', type=int, help='Volume Space Dimensions', metavar='Dimension')
    ap.add_argument('-f', dest='features', type=int, help='The number of features at the beginning of each record',
                    default=0, metavar='Features')
    ap.add_argument('-o', dest='out_file',
                    help='Output file location. Output format is a .npz compressed file with arr_0 as the array name.',
                    default=None, metavar='OutFile')
    ns = ap.parse_args(args)

    ns.in_file = pathlib.Path(ns.in_file)
    if ns.out_file is None:
        ns.out_file = ns.in_file.withstem(ns.in_file.stem + '_edt')
    else:
        ns.out_file = ns.in_file.joinpath(ns.out_file)
        if ns.out_file.suffix != '.npz':
            ns.out_file.joinpath(ns.in_file.stem + '_edt.npz')

    return ns

def compute_edt(mtx, shape):
    edt_output = numpy.zeros(mtx.shape, dtype=numpy.float64)
    for sample_index in range(mtx.shape[0]):
        edt_output[sample_index] = numpy.ravel(
            nd.distance_transform_edt(numpy.reshape(numpy.logical_not(mtx[sample_index].toarray()), shape)))
    return edt_output

if __name__ == '__main__':
    params = parse_args(sys.argv[1:])
    if params.shape is None:
        raise ValueError('Shape undefined.')
    print('Loading data ...', end='')
    mtx = sp.load_npz(params.in_file)[:, params.features:]
    print(' done.\nComputing euclidean distances ...', end='')
    edt = compute_edt(mtx, params.shape)
    print(' done.\nSaving results ...', end='')
    numpy.savez_compressed(params.out_file, edt)
    print(' done.')


import numpy as np
import graphviz
import random
from copy import deepcopy
from typing import Callable, List, Tuple, Optional
import matplotlib.pyplot as plt
import ast
import json as std_json

'''
==== Formal definition ====
P.S. n is number of total vertices.
     v is vertex.

------------------------------------------------------
  Name           Type              Shape      Notes
-----------------------------------------------
  strategies     List[float]       n(1D)      each v's strategy
  edges          ndarray(float)    nxn(2D)    1=connect, 0=disconnect; MUST be bi-directed if it's undirected.
  weights        List[float]       n(1D)      each v's special value. You can ignore this. You can use it as weight,
                                              or even use it to represent other meaning.
'''

class Graph:
    def __init__(self, strategies: Optional[List[float]], edges: Optional[np.ndarray], weights: Optional[List[float]]):
        """
        :param strategies: List with length n. (n is the number of vertices)
        :param edges: n by n ndarray.
        """
        self.strategies: Optional[List[float]] = strategies
        self.edges: Optional[np.ndarray] = edges
        self.weights: Optional[List[float]] = weights

    def __repr__(self):
        """Show the graph as a string."""
        representation = "\nVertexNo\tEdges\tStrategies\tWeights\n"
        for i in range(len(self.edges) + 1):
            if i > 0:
                for j in range(len(self.edges) + 1):
                    if j == 0:
                        representation += f"{i:03} -> [ "
                    else:
                        representation += str(self.edges[i - 1][j - 1]) + " "
                representation += f"]\ts{self.strategies[i - 1]}\tw{self.weights[i - 1]}\n"
        return representation

    def n_vertices(self) -> int:
        """Total number of vertices."""
        return int(len(self.edges))

    def plot_graph(self, filename='plotted_graph',
                   show=False,
                   picked_vertex: Optional[int] = None,
                   have_better_choice: Optional[List[int]] = None):
        """
        :param filename:
        :param show: whether plt show the graph
        :param have_better_choice: highlight those vertices which has other strategy to improve its payoff in this round
                                   (shown as a octagon)
        :param picked_vertex: highlight  the vertex picked
                              (may indicate its the one change its strategy to improve its payoff)
                              (shown as a tripleoctagon)
        """
        d = graphviz.Digraph(filename=filename)
        d.format = 'png'
        d.attr(rankdir='LR', concentrate='True')
        # Vertex index from 1        # Vertices
        d.attr('node', shape='circle')
        for vertex in range(self.n_vertices()):
            color = 'lightblue2' if self.strategies[vertex] != 0. else 'black'
            style = 'filled' if self.strategies[vertex] != 0. else ''
            shape = 'octagon' if (have_better_choice is not None and vertex in have_better_choice) else 'circle'
            shape = 'tripleoctagon' if (picked_vertex is not None and vertex == picked_vertex) else shape
            v_name = f'{vertex}\n(w{self.weights[vertex]})'
            d.node(v_name, color=color, style=style, shape=shape)
        for i in range(self.n_vertices()):
            for j in range(self.n_vertices()):
                if self.edges[i][j] != 0.:
                    d.edge(f'{i}\n(w{self.weights[i]})', f'{j}\n(w{self.weights[j]})')
        d.render(view=False)
        if show is True:
            plt.imshow(plt.imread(f'{filename}.png'))
            plt.axis('off')
            plt.show()

    def strategy_1_weight_sum(self) -> float:
        """Sum of the weight of all vertices which pick strategy 1"""
        s_w_sum = 0.0
        for v, s in enumerate(self.strategies):
            if s != 0.0:
                s_w_sum += self.weights[v]
        return s_w_sum

    def deserialize(self, codes: str) -> None:
        """Fetch strategies, edges, and weights from a string."""
        contents = ast.literal_eval(codes)
        self.strategies = contents['strategies']
        self.edges = np.array(contents['edges'])
        self.weights = contents['weights']

    @staticmethod
    def deserialize_edges(s: str) -> np.ndarray:
        return np.array([line.split(' ') for line in s.split('\n')])

    @staticmethod
    def serialize_edges(edges: np.ndarray) -> str:
        s = ''
        for row in edges:
            for element in row:
                s += element + ' '
        return s.strip()

    @staticmethod
    def deserialize_strategies(s: str) -> List[float]:
        return list(map(float, s.split(' ')))

    @staticmethod
    def serialize_strategies(strategies: List[float]) -> str:
        return ' '.join(map(str, strategies))

    @staticmethod
    def deserialize_weights(s: str) -> List[float]:
        return list(map(float, s.split(' ')))

    @staticmethod
    def serialize_weights(weights: List[float]) -> str:
        return ' '.join(map(str, weights))

    def serialize(self) -> str:
        return std_json.dumps(
            {'edges': self.edges.tolist(), 'strategies': list(self.strategies),
             'weights': list(map(float, self.weights))})

    @staticmethod
    def create_graph_with_edges(edges: np.ndarray) -> "Graph":
        """Create a default graph only given edges. Strategies -> all zero. Weights -> all 1."""
        return Graph(strategies=Strategy.zeros(len(edges)), edges=edges, weights=VertexWeight.same(len(edges)))

class Strategy:
    @staticmethod
    def zeros(n_vertices) -> List[float]:
        return np.zeros((n_vertices,)).tolist()

    @staticmethod
    def ones(n_vertices) -> List[float]:
        return np.ones((n_vertices,)).tolist()

    @staticmethod
    def partial_ones(n_vertices, prob_one: float) -> List[float]:  # prob_one: probability of one to appear
        """Each vertex has a chance to select strategy one, otherwise zero."""
        strategies = np.zeros((n_vertices,))  # 0 is default action.
        options = [0.0, 1.0]
        distribution = [1 - prob_one, prob_one]
        for i in range(n_vertices):
            strategies[i] = random.choices(options, distribution)[0]
        return strategies.tolist()

class VertexWeight:

    @staticmethod
    def same(n_vertices) -> List[float]:
        return np.ones((n_vertices,)).tolist()

    @staticmethod
    def ones(n_vertices) -> List[float]:
        return VertexWeight.same(n_vertices)

    @staticmethod
    def random(n_vertices) -> List[float]:
        """Permutation all weights and distribute them."""
        # Other type you may try:
        # return (np.floor(np.random.random((n_vertices,)) * 5) % 5 + 1) / 50 + 0.97
        # return (np.floor(np.random.random((n_vertices,)) * 5) % 5 + 1)
        # return np.random.normal(10, 3, (n_vertices,))
        # return np.random.randint(1, n_vertices + 1, size=(n_vertices,))
        # return np.random.randint(0, n_vertices, size=(n_vertices,))
        pool = np.arange(n_vertices)
        np.random.shuffle(pool)
        return pool.tolist()

class Edge:
    @staticmethod
    def vertex_index(n_vertices: int, idx: int) -> int:
        """Adjust idx if it is not in the bound."""
        if idx < 0:
            return n_vertices + idx
        if idx >= n_vertices:
            return idx - n_vertices
        return idx

    @staticmethod
    def ws_model(n_vertices, k_nearest, rewire_prob) -> np.ndarray:
        """
        Each vertex connects to its k_nearest neighbors.
        K here only support even numbers.
        Half of k will try rewiring to other vertices.
        Vertex numbers are from 0 to (n_vertices - 1)
        Edge Matrix:
            - Indices are vertex no.
            - 0 means unconnected; 1 means connected.
            - Init state is bi-directional.
        Wiki: https://en.wikipedia.org/wiki/Watts%E2%80%93Strogatz_model
        """
        edges = np.zeros((n_vertices, n_vertices))

        # Connect k nearest neighbors
        if k_nearest % 2 != 0:
            raise NotImplementedError('K-nearest must be even.')
        for vertex in range(n_vertices):
            for i in range(k_nearest):
                if i < k_nearest // 2:
                    target = vertex + (i - k_nearest // 2)
                else:
                    target = vertex + (i - k_nearest // 2 + 1)
                # Handle targets not in 0~n_vertices
                target = Edge.vertex_index(n_vertices, target)
                #
                edges[vertex][target] = 1.0
        # Rewire with a probability
        if k_nearest % 2 != 0:
            raise NotImplementedError('K-nearest must be even.')
        random_options = [True, False]
        random_distribution = [rewire_prob, 1. - rewire_prob]
        for vertex in range(n_vertices):
            for i in range(k_nearest // 2):
                do_rewire = random.choices(random_options, random_distribution)
                if do_rewire[0]:
                    old_target = Edge.vertex_index(n_vertices, vertex + i + 1)
                    # Erase original edge
                    edges[vertex][old_target] = 0.
                    edges[old_target][vertex] = 0.
                    # Rewire
                    available_vertices = []
                    for possible_target in range(n_vertices):
                        if possible_target != vertex and possible_target != old_target and \
                                edges[vertex][possible_target] == 0.:
                            available_vertices.append(possible_target)
                    new_target = available_vertices[np.random.randint(len(available_vertices))]
                    edges[vertex][new_target] = 1.
                    edges[new_target][vertex] = 1.
        return edges

class Utility:
    """Each utility function here must have at least 2 arguments: graph & vertex."""

    @staticmethod
    def maximal_independent_set(graph: Graph, vertex: int, alpha=2.0) -> float:
        """Unweighted MIS game.
        :param graph:
        :param vertex: the vertex to calculate utility
        :param alpha:
        """
        if graph.strategies[vertex] != 0.0:
            utility = 1.0
            for neighbor in range(graph.n_vertices()):
                if graph.edges[vertex][neighbor] != 0. and vertex != neighbor:
                    utility += -1 * alpha * graph.strategies[vertex] * graph.strategies[neighbor]
        else:
            utility = 0.
        return utility

    @staticmethod
    def weighted_maximal_independent_set_1(graph: Graph, vertex: int, alpha=2.0) -> float:
        """WMIS with priority function: w(v)/((degree(v)+1)"""
        priority = []
        for v in range(len(graph.edges)):
            degree = sum(graph.edges[v])
            priority.append(graph.weights[v] / (degree + 1))
        #
        if graph.strategies[vertex] != 0.0:
            utility = 1.0
            for neighbor in range(graph.n_vertices()):
                if graph.edges[vertex][neighbor] != 0. and vertex != neighbor and \
                        priority[vertex] <= priority[neighbor]:  # using priority
                    utility += -1 * alpha * graph.strategies[vertex] * graph.strategies[neighbor]
        else:
            utility = 0.
        return utility

    @staticmethod
    def weighted_maximal_independent_set_2(graph: Graph, vertex: int, alpha=2.0) -> float:
        """WMIS with priority function: w(v)/sum of all v's closed neighbors' w"""
        priority = []
        for v in range(len(graph.edges)):
            tmp_p = graph.weights[v]
            for other_v in range(len(graph.edges)):
                if graph.edges[v][other_v] != 0.0:
                    tmp_p += graph.weights[other_v]
            priority.append(graph.weights[v] / tmp_p)
        #
        if graph.strategies[vertex] != 0.0:
            utility = 1.0
            for neighbor in range(graph.n_vertices()):
                if graph.edges[vertex][neighbor] != 0. and vertex != neighbor and \
                        priority[vertex] <= priority[neighbor]:  # using priority
                    utility += -1 * alpha * graph.strategies[vertex] * graph.strategies[neighbor]
        else:
            utility = 0.
        return utility

class Game:
    """
    In this game, players only have 2 actions:
            1. Turn off (0)
            2. Turn on (1)
    """

    def __init__(self, graph: Graph, utility_func: Callable):
        self.graph = graph
        self.utility_func = utility_func

    @staticmethod
    def check_nash_equilibrium(graph: Graph, utility_func: Callable, alpha=None) -> List[int]:
        """Check what vertices can improve its utility function by changing its original strategy.
        :param graph:
        :param utility_func:
        :param alpha:
        return the idx of those vertices which can improve its utitlity.
        """
        better_choice_vertices = []
        for vertex in range(graph.n_vertices()):
            temp = graph.strategies[vertex]
            if alpha is None:
                cur_utility = utility_func(graph=graph, vertex=vertex)
                graph.strategies[vertex] = 1. if temp == 0. else 0.
                new_utility = utility_func(graph=graph, vertex=vertex)
            else:
                cur_utility = utility_func(graph=graph, vertex=vertex, alpha=alpha)
                graph.strategies[vertex] = 1. if temp == 0. else 0.
                new_utility = utility_func(graph=graph, vertex=vertex, alpha=alpha)
            #
            graph.strategies[vertex] = temp
            #
            if new_utility > cur_utility:
                better_choice_vertices.append(vertex)
        return better_choice_vertices

    @staticmethod
    def run_a_time(graph, utility_func, alpha=None) -> Tuple[bool, List, Graph, Optional[int]]:  # True means terminated
        better_choice_vertices = Game.check_nash_equilibrium(graph=graph, utility_func=utility_func, alpha=alpha)
        if len(better_choice_vertices) == 0:
            return True, better_choice_vertices, graph, None  # Reach NE
        # Randomly pick one to change its action to improve its utility
        selected_index = np.random.randint(len(better_choice_vertices))
        selected_vertex = better_choice_vertices[selected_index]
        # Switch from 0/1 to 1/0
        graph.strategies[selected_vertex] = 0. if graph.strategies[selected_vertex] == 1. else 1.
        return False, better_choice_vertices, graph, selected_vertex

    def run(self, show_each_move=False, alpha=None) -> Tuple[Graph, int]:
        graph = deepcopy(self.graph)
        move_cnt = 0
        while True:
            if show_each_move:
                graph.plot_graph(show=True)
            if self.run_a_time(graph=graph, utility_func=self.utility_func, alpha=alpha)[0]:
                break
            move_cnt += 1
        return graph, move_cnt

    @staticmethod
    def check_real_independent_set(graph: Graph):
        # Method: test each vertex
        #         Turn a vertex with strategy 0 to 1, and see if it doesn't connect any vertices with strategy 1.
        #         If so, the new graph is an independent set so the original graph is not a "maximal" independent set.
        n_vertices = len(graph.edges)
        for v in range(n_vertices):
            if graph.strategies[v] != 0.:
                continue
            no_neighbor_with_s1 = True
            # See if a strategy-0 vertex's all neighbors are with strategy-0.
            for other_v in range(n_vertices):
                if other_v == v:
                    continue
                if graph.edges[v][other_v] == 1. and graph.strategies[other_v] == 1.:
                    no_neighbor_with_s1 = False
                    break
            if no_neighbor_with_s1 is True:
                return False  # TODO: check again
        return True

# times = 100
# avg_moves = []
# avg_cardinality = []
# all_p = np.arange(10.) / 10.
# for rewire_p in all_p:
#     total_moves = 0
#     total_cardinality = 0
#     for _ in range(times):
#         init_edges = Edge.ws_model(n_vertices=30, k_nearest=4, rewire_prob=rewire_p)
#         init_strategies = Strategy.partial_ones(n_vertices=len(init_edges), prob_one=0.5)
#         init_weights = VertexWeight.random(n_vertices=len(init_edges))
#         g = Graph(strategies=init_strategies, edges=init_edges, weights=init_weights)
#         m = Game(graph=g, utility_func=Utility.maximal_independent_set)
#         result_graph, moves = m.run(show_each_move=False)
#         total_moves += moves
#         total_cardinality += sum(result_graph.strategies)
#         g.plot_graph(show=True)
#         exit(1)
#     avg_moves.append(total_moves / times)
#     avg_cardinality.append(total_cardinality / times)
# plt.plot(all_p, avg_moves, label='avg_moves')
# plt.plot(all_p, avg_cardinality, label='avg_cardinality')
# plt.legend()
# plt.show()

# TODO: verify that the game state is a valid solution


from django import forms
from .models import Tag, Post
from django.core.exceptions import ValidationError

class TagForm(forms.ModelForm):
    # наследование от ModelForm позволяет связать модель и форму через класс Meta, определив: модель, поля и стили

    class Meta:
        model = Tag
        fields = ['title', 'slug']

        widgets = {
            'title': forms.TextInput(attrs={'class': 'form-control'}),
            'slug': forms.TextInput(attrs={'class': 'form-control'})
        }

    def clean_slug(self):
        # вообще для получения чего-то из словаря есть специальный метод,
        # но так как мы уже дошли до clean_SLUG, то так писать - нормально
        new_slug = self.cleaned_data['slug'].lower()

        if new_slug == 'create':
            raise ValidationError('Slug may not be "Create"')
        if Tag.objects.filter(slug__iexact=new_slug).count():
            raise ValidationError('Slug must be unique. We have "{}" slug already'.format(new_slug))
        return new_slug

class PostForm(forms.ModelForm):
    class Meta:
        model = Post
        fields = ['title', 'slug', 'body', 'tags']

        widgets = {
            'title': forms.TextInput(attrs={'class': 'form-control'}),
            'slug': forms.TextInput(attrs={'class': 'form-control'}),
            'body': forms.Textarea(attrs={'class': 'form-control'}),
            'tags': forms.SelectMultiple(attrs={'class': 'form-control'})
        }

        def clean_slug(self):
            # вообще для получения чего-то из словаря есть специальный метод,
            # но так как мы уже дошли до clean_SLUG, то так писать - нормально
            new_slug = self.cleaned_data['slug'].lower()

            if new_slug == 'create':
                raise ValidationError('Slug may not be "Create"')
            return new_slug


import pygame
import sys
from game import DaBabyKart
from road import Road
from leaderboard import Leaderboard

class Start():

    def __init__(self):
        pygame.init()
        self.screen = pygame.display.set_mode((0, 0), pygame.FULLSCREEN)
        self.screen_rect = self.screen.get_rect()
        self.image = pygame.image.load('images/dbkart.png')
        self.image_rect = self.image.get_rect()
        self.button_1 = pygame.Rect(self.screen_rect.width / 2 - 100, self.screen_rect.height / 2 - 70, 200, 100) #Ethan helped with buttons
        self.button_2 = pygame.Rect(self.screen_rect.width / 2 - 100, self.screen_rect.height / 2 + 70, 200, 100)
        self.font1 = pygame.font.SysFont('chalkduster.ttf', 75)
        self.play = self.font1.render('Play', True, (255, 255, 255))
        self.quit = self.font1.render('Quit', True, (255,255,255))
        self.dbkart = DaBabyKart()
        self.leaderboard = Leaderboard()
        self.road = Road(self)
        self.click = False

    def run_start(self):
        while True:
            pygame.mixer.music.load('sounds/bop.mp3')
            pygame.mixer.music.play(-1) # plays infinitely
            self.check_events()
            self.display_start()

    def display_start(self):
            self.screen.fill((33, 191, 143))
            for x in range(0, self.screen_rect.width, 64):
                self.screen.blit(self.road.image, (x, self.screen_rect.height / 2 - 180))
            self.screen.blit(self.image, (self.screen_rect.width / 2 - 512 , self.screen_rect.height / 2 - 460))
            pygame.draw.rect(self.screen, (0, 0, 0), self.button_1)
            pygame.draw.rect(self.screen, (0, 0, 0), self.button_2)
            self.screen.blit(self.play, (self.screen_rect.width / 2 - 55, self.screen_rect.height / 2 - 45))
            self.screen.blit(self.quit, (self.screen_rect.width / 2 - 60, self.screen_rect.height / 2 + 100))
            if self.button_1.collidepoint(pygame.mouse.get_pos()): #Josh saved me
                pygame.draw.rect(self.screen, (255, 255, 255), self.button_1)
                if self.click:
                    self.dbkart.run_game()
            if self.button_2.collidepoint(pygame.mouse.get_pos()): #Josh saved me
                pygame.draw.rect(self.screen, (255, 255, 255), self.button_2)
                if self.click:
                    sys.exit()

            pygame.display.flip()

    def check_events(self):
        for event in pygame.event.get():
            if event.type == pygame.MOUSEBUTTONDOWN:
                if event.button == 1:
                    self.click = True
            if event.type == pygame.KEYDOWN:
                if event.key == pygame.K_ESCAPE:
                    sys.exit()

db = Start()
db.run_start()


from ejson import serializers
from mock import Mock, call, patch
from datetime import datetime

from eventlib import exceptions, conf, core, tasks

def test_parse_event_name():
    core.parse_event_name('app.Event').should.be.equal(
        ('app.events', 'Event'))

    core.parse_event_name.when.called_with('stuff').should.throw(
        exceptions.InvalidEventNameError,
        'The name "stuff" is invalid. Make sure you are using the '
        '"app.KlassName" format')

    core.parse_event_name.when.called_with('other.stuff.blah').should.throw(
        exceptions.InvalidEventNameError,
        'The name "other.stuff.blah" is invalid. Make sure you are using the '
        '"app.KlassName" format')

@patch('eventlib.core.import_module')
def test_find_event(import_module):
    fake_module = Mock()
    fake_module.Event = 'my-lol-module'

    import_module.return_value = fake_module
    core.find_event('app.Event').should.be.equals('my-lol-module')

    import_module.reset_mock()
    import_module.side_effect = ImportError
    core.find_event.when.called_with('app.Event2').should.throw(
        exceptions.EventNotFoundError,
        'Event "app.Event2" not found. Make sure you have a class '
        'called "Event2" inside the "app.events" module.')

def test_filter_data_values():
    core.filter_data_values({'a': 'b', 'c': 'd'}).should.be.equals(
        {'a': 'b', 'c': 'd'}
    )
    core.filter_data_values({'a': 'b', 'request': None}).should.be.equals(
        {'a': 'b'}
    )

@patch('eventlib.core.datetime')
@patch('eventlib.core.get_ip')
def test_get_default_values_with_request(get_ip, datetime):
    get_ip.return_value = '150.164.211.1'
    datetime.now.return_value = 'tea time!'
    data = {'foo': 'bar', 'request': Mock()}
    core.get_default_values(data).should.be.equals({
        '__datetime__': 'tea time!',
        '__ip_address__': '150.164.211.1',
    })

@patch('eventlib.tasks.process')
def test_celery_process_wrapper(process):
    tasks.process_task('name', 'data')
    process.assert_called_once_with('name', 'data')

@patch('eventlib.conf.settings')
def test_django_integration(settings):
    # Given I mock django conf
    settings.LOCAL_GEOLOCATION_IP = 'CHUCK NORRIS'

    # When I try to access a variable using the getsetting method, then
    # it should contain the mocked values
    conf.getsetting('LOCAL_GEOLOCATION_IP').should.equal('CHUCK NORRIS')

@patch('eventlib.conf.settings')
@patch('eventlib.core.import_module')
def test_importing_events(import_module, settings):
    settings.INSTALLED_APPS = ['foobar', 'test_app']

    core.import_event_modules()
    calls = [call('foobar.events'), call('test_app.events')]
    import_module.assert_has_calls(calls)

    settings.INSTALLED_APPS = ['tester']
    import_module.side_effect = ImportError('P0wned!!!')
    core.import_event_modules()


import torch
import torch.utils.data
from typing import Dict, Iterable, Optional
from collections import defaultdict
from src.configs.training_configs import training_datasets
from src.utils.ProgressBar import ProgressBar
from src.utils.WandbLogger import WandbLogger
from src.utils.types import Sample, TrainingParams
from src.utils.Checkpoint import Checkpoint
from src.utils.constants import PLACEMENT

def train_model(
    model: torch.nn.Module,
    name: str,
    config: TrainingParams,
    device: torch.device,
    fine: bool
) -> None:
    model.to(device)
    optimizer = config['optimizer']
    criterion = config['criterion']

    dataset = training_datasets(config['dataset_config'], fine)

    training_data, validation_data = torch.utils.data.random_split(
        dataset, [0.8, 0.2])

    train_data_loader = torch.utils.data.DataLoader(
        training_data,
        batch_size=config['batch_size'],
        shuffle=True,
        drop_last=False,
    )

    validation_data_loader = torch.utils.data.DataLoader(
        validation_data,
        batch_size=config['batch_size'],
        shuffle=True,
        drop_last=False,
    )

    logger = ProgressBar(len(train_data_loader), config['batch_size'])
    wandb_logger = WandbLogger(config['name'], config)
    checkpoint = Checkpoint(model, f"checkpoint/{name}-{PLACEMENT}.pt")

    scheduler = torch.optim.lr_scheduler.CosineAnnealingLR(
        optimizer,  config['epochs'])

    for epoch in range(1, config['epochs'] + 1):
        print(f"Epoch {epoch}/{config['epochs']}")

        train_one_epoch(
            model,
            train_data_loader,
            criterion,
            optimizer,
            device,
            logger,
            wandb_logger
        )

        score = evaluate(
            model,
            validation_data_loader,
            device,
            criterion,
            wandb_logger,
        )

        scheduler.step()

        checkpoint(score)
        if checkpoint.is_overfitting():
            break

def train_one_epoch(
    model: torch.nn.Module,
    data_loader: Iterable[Sample],
    criterion: torch.nn.Module,
    optimizer: torch.optim.Optimizer,
    device: torch.device,
    logger: Optional[ProgressBar] = None,
    wandb_logger: Optional[WandbLogger] = None,
) -> None:
    model.train(True)
    optimizer.zero_grad()

    for step, (samples, targets) in enumerate(data_loader, start=1):
        samples = samples.to(device, non_blocking=True).requires_grad_(True)
        targets = targets.to(device, non_blocking=True)

        output = model(samples)
        loss = criterion(output, targets)

        loss_value = loss.item()
        loss.backward()

        optimizer.step()
        optimizer.zero_grad()

        if logger is not None:
            logger(step, loss=loss_value)
        if wandb_logger is not None:
            wandb_logger(loss=loss_value)

@torch.no_grad()
def evaluate(
    model: torch.nn.Module,
    data_loader:torch.utils.data.DataLoader,
    device: torch.device,
    criterion: torch.nn.Module,
    wandb_logger: Optional[WandbLogger] = None,
    **kwargs: torch.nn.Module,
) -> float:
    model.eval()
    loss = 0.0
    metrics: Dict[str, float] = defaultdict(float)

    for samples, targets in data_loader:
        samples = samples.to(device, non_blocking=True)
        targets = targets.to(device, non_blocking=True)

        output = model(samples)
        loss += criterion(output, targets).item() / len(data_loader)

        for key, metric in kwargs.items():
            metrics[key] += metric(output, targets).item() / len(data_loader)

    metrics['val_loss'] = loss
    print(' - '.join(': '.join(map(str, x)) for x in metrics.items()))

    if wandb_logger is not None:
        wandb_logger(**metrics)

    return loss


# !/usr/bin/python3
# Filename: light.py
import os
from pathlib import Path
import random
import sys
#sys.path.insert('..')
currentdir = os.path.dirname(os.path.realpath(__file__))
parentdir = os.path.dirname(currentdir)
sys.path.append(parentdir)

from utils import utils

# configure for gnome themes
#homedir = os.path.expanduser('~')
h = Path.home()
#env_spec_dir = os.path.join(h, "KDynamic", "theme", open(d_env, 'r').readline().strip())

# pic paths
pic_base = os.path.join(h, "KDynamic", "pics")
plight = os.path.join(pic_base, 'light')
plight_dark = os.path.join(pic_base, 'light_dark')
pnight = os.path.join(pic_base, 'night')
#env_file = open(d + "/d_env.txt").readline().strip().upper()
#env_spec_dir = os.path.join(d, 'theme', env_file)
#t_json = open(os.path.join(env_spec_dir, 'themes.json'),)

def tc(env, data, wm):#, icon):
    utils.theme_change(env, data, wm)

    # icon util needs fix
    #utils.icon_change(env, icon)
    #print('tc')

## variables
def wc(env, ts):
    pd = ""
    if ts == 'light':
        pd = plight
    elif ts == 'light_dark':
        pd = plight_dark
    elif ts == 'night':
        pd = pnight

    print("image path: ",os.path.join(pd, random.choice([p for p in os.listdir(pd)])))
    utils.wallp_change(env, os.path.join(pd, random.choice([p for p in os.listdir(pd)])))
    #print('wc')

def themer(env, theme, wm, ts):#, icon):

    # theme change
    tc(env, theme, wm)#, icon)

    # change pic
    wc(env, ts)

"""
if __name__ == '__main__':
    light_theme(input('env: '), input('theme: '))
"""
# end file


from django.http import HttpResponse
from django.shortcuts import render

def home(request):
    return render(request, 'home.html')

def reverse(request):
    user_text = request.GET['usertext']
    reversed_test = user_text[::-1]
    s = user_text.split()
    l = len(s)
    return render(request, 'reverse.html', {'usertext':user_text, 'reversedtext':reversed_test, 'count_words':l})


import random
import datetime

number = random.randint(1, 100)
print("instruction:\n"
      "very hot +-5\n"
      "hot +-10\n"
      "cold +- 25"
      "very cold +-100")
count = int(input('put your attempts:'))
v = 0
print("Let's go!\n"
      "Put your number:")

with open('text.txt1', 'a') as a:
    sec = datetime.datetime.now()
    while v != count:
        try:
            guess = int(input(''))
        except ValueError:
            print("Put only numbers")
            continue

        if guess <= number + 5 and guess >= number - 5:
            count -= 1
            v += 1
            if guess < number:
                print("it's very hot, bigger")
            elif guess > number:
                print("it's very hot, lower")
        elif guess <= number + 10 and guess >= number - 10:
            count -= 1
            v += 1
            if guess < number:
                print("it's hot, bigger")
            elif guess > number:
                print("it's hot, lower")
        elif guess <= number + 25 and guess >= number - 25:
            count -= 1
            v += 1
            if guess < number:
                print("it's cold, bigger")
            elif guess > number:
                print("it's cold, lower")
        elif guess < (number + 25) and guess > 0 or guess > (number + 25) and guess <= 100:
            count -= 1
            v += 1
            if guess < number:
                print("it's very cold, bigger")
            elif guess > number:
                print("it's very cold, lower")
        else:
            print('Print namber into range')
        if guess == 0:
            print("Exit programm\n\n\n"
                "Made by Islamchik04")
            break
        if guess == number:
            sec1 = datetime.datetime.now() - sec
            print(f"You win!\n"
                  f"{v} attempts from {count} :)")
            a.write(f"You started in: {sec.strftime('%X')} \n")
            a.write(f"You finished in: {datetime.datetime.now().strftime('%X')} \n")
            a.write(f"You found number for {v} attempts\n")
            a.write(f"Time {sec1.seconds}\n")
            a.write(f"If you don't find number you lose because you had only {count} attempts")
            break
        if count == 0:
            print(f'End game;(\n'
                    f"Your number was {number}\n"
                  f"In future will be better:)")
            break
        print(f"You have only {count}")


from config import config
from processed_images.processed_images import LockingProcessedImages, ProcessedImage
from hdr_finder_app import HDRProcessedImages

from graphene import ObjectType, String, Schema, DateTime, List, Int, Field, Float, JSONString

from flask import Flask
from flask_graphql import GraphQLView
from flask_cors import CORS

import logging
import sys

photos = LockingProcessedImages(db_dir=config['photo_database']['database_dir'])
photos.load()

class Photo(ObjectType):
    filetype = String()
    filename = String(required=True)
    thumbnail = String()
    datetaken = DateTime()
    latitude = Float()
    longitude = Float()
    exifdata = JSONString()

class HDRGroup(ObjectType):
  group = List(String)

class Query(ObjectType):
    photolist = List(String, startdatetime=DateTime(required=True), enddatetime=DateTime(required=True))
    photo = Field(Photo, filename=String(required=True))
    hdrgroups = List(HDRGroup)

    @staticmethod
    def resolve_photolist(root, info, startdatetime, enddatetime):
        return photos.get_file_list_date_range(startdatetime, enddatetime)

    @staticmethod
    def resolve_photo(root, info, filename):
        p = photos.retrieve(filename)

        return Photo(filetype=p.filetype,
                     filename=p.filename,
                     thumbnail=p.thumbnail,
                     datetaken=p.date_taken,
                     latitude=p.latitude,
                     longitude=p.longitude,
                     exifdata=p.exif_data)

    @staticmethod
    def resolve_hdrgroups(root, info):
        return [HDRGroup(group=[
            '/work/stash/Photos/M3/2017/03/04/CR2/IMG_4719.CR2',
            '/work/stash/Photos/M3/2017/03/04/CR2/IMG_4720.CR2',
            '/work/stash/Photos/M3/2017/03/04/CR2/IMG_4721.CR2'
        ])]

# GraphQL schema created:
schema = Schema(query=Query)

# Flask init
app = Flask(__name__)
CORS(app)

app.add_url_rule('/graphql', view_func=GraphQLView.as_view(
    'graphql',
    schema=schema,
    graphiql=True
))

# Serve this out via flask to be picked up in React:
@app.route('/queries')
def queries():
  return """
query getPhotolist {
  photolist(startdatetime: "2020-03-01T00:00:00", enddatetime: "2020-03-02T00:00:00")
}

query getPhoto($filename: String!) {
  photo(filename: $filename) {
    filetype
    filename
    datetaken
    latitude
    longitude
    thumbnail
    exifdata
  }
}

query gethdrgroups {
  hdrgroups {
    group
  }
}
"""

if __name__ == '__main__':
    app.run(host='0.0.0.0')


from discord.ext import commands

from bot import BaseBot
from core.utils import read_config

config = read_config()

class CogsOps(commands.Cog):
    def __init__(self, bot: BaseBot):
        self.bot = bot

    @commands.group(description="Cog related commands", invoke_without_command=True)
    @commands.has_role(config["perms"]["cog_ops_access_role"])
    async def cog(self, ctx: commands.Context):
        loaded_cogs = []
        unloaded_cogs = []
        for ext in self.bot.config["default"]["core_cogs"]:
            try:
                await self.bot.load_extension(f"core.{ext}")
            except commands.ExtensionAlreadyLoaded:
                loaded_cogs.append(ext)
            except commands.ExtensionNotFound:
                unloaded_cogs.append(ext)
        for ext in self.bot.config["cogs"]["custom"]:
            try:
                await self.bot.load_extension(f"cogs.custom.{ext}")
            except commands.ExtensionAlreadyLoaded:
                loaded_cogs.append(ext)
            except commands.ExtensionNotFound:
                unloaded_cogs.append(ext)
        for ext in self.bot.config["cogs"]["list"]:
            try:
                await self.bot.load_extension(f"cogs.{ext}")
            except commands.ExtensionAlreadyLoaded:
                loaded_cogs.append(ext)
            except commands.ExtensionNotFound:
                unloaded_cogs.append(ext)
        await ctx.send(
            f"```\nLoaded cogs: {', '.join(loaded_cogs)}\nUnloaded cogs: {','.join(unloaded_cogs)}```"
        )

    @cog.command()
    async def rel(self, ctx: commands.Context, ext):
        self.bot.log(
            f"Cog [{ext}] reload initiated by @{ctx.author.name}#{ctx.author.discriminator} [{ctx.author.id}]"
        )
        if ext in self.bot.config["default"]["core_cogs"]:
            msg = await ctx.send("`Reloading core cog: {}` 🛠".format(ext))
            try:
                await self.bot.reload_extension("core.{}".format(ext))
                await msg.edit(content="`Reloaded core cog: {}` 🆗".format(ext))
            except Exception as e:
                await msg.edit(content="`Failed to reload core cog: {}` 🔴".format(ext))
                raise e

        else:
            msg = await ctx.send("`Trying to reload cog: {}` 🛠".format(ext))
            try:
                await self.bot.reload_extension("cogs.{}".format(ext))
                await msg.edit(content="`Reloaded cog: {}` 🆗".format(ext))
            except Exception as e:
                await msg.edit(content="`Failed to reload cog: {}` 🔴".format(ext))
                raise e

async def setup(bot):
    await bot.add_cog(CogsOps(bot))


"""
给定一个二叉树，找出其最小深度。

最小深度是从根节点到最近叶子节点的最短路径上的节点数量。

说明：叶子节点是指没有子节点的节点。

示例 1：

输入：root = [3,9,20,null,null,15,7]
输出：2
示例 2：

输入：root = [2,null,3,null,4,null,5,null,6]
输出：5

来源：力扣（LeetCode）
链接：https://leetcode-cn.com/problems/minimum-depth-of-binary-tree
著作权归领扣网络所有。商业转载请联系官方授权，非商业转载请注明出处。
"""
# Definition for a binary tree node.
class TreeNode:
    def __init__(self, val=0, left=None, right=None):
        self.val = val
        self.left = left
        self.right = right
from collections import deque

class Solution:
    def minDepth(self, root: TreeNode) -> int:
        #bfs也可以解决最短路径问题
        if not root:
            return 0
        ans=0
        q=deque()
        q.append(root)
        while q:
            size=len(q)
            ans+=1 #进入了下一层
            for i in range(size):
                tmp=q.popleft()
                if not tmp.left and not tmp.right:
                    return ans # 遇到叶子节点就直接返回层数
                if tmp.left:
                    q.append(tmp.left)
                if tmp.right:
                    q.append(tmp.right)
        return ans

分类/树的BFS（层次遍历）/111.二叉树的最小深度.py

111.二叉树的最小深度.py


#-*- coding = utf-8 -*-
# @Time    : 2021/3/21 12:42
# @Author  : circle
# @File    : wordcloud.py
# @Software: PyCharm
import jieba
from matplotlib import pyplot as plt
from wordcloud import WordCloud
from PIL import Image
import numpy as np
import sqlite3

conn = sqlite3.connect('../movie.db')
cur = conn.cursor()
sql = 'select instroduction from movie250'
content = cur.execute(sql)
print('打开数据库')
text = ''
for item in content:
    text = text + item[0]
cur.close()
conn.close()
#分词
cut = jieba.cut(text)
temp = ' '.join(cut)
print('cut value', temp)
img = Image.open('tree.jpg')
#将图片转化为数组
img_array = np.array(img)
#设置
wc = WordCloud(
    background_color='white',
    mask=img_array,
    font_path='msyh.ttc',
).generate_from_text(temp)
#绘制图片
fig = plt.figure(1)
plt.imshow(wc)
plt.axis('off')
# plt.show() 显示图片
plt.savefig('wordcloud.jpg')


import os

from django.http import HttpResponse, HttpResponseRedirect, HttpResponseBadRequest, QueryDict
from django.shortcuts import get_object_or_404, redirect, render
from django.template import Context, RequestContext, loader
from django.contrib.auth.decorators import login_required
from django import forms
from django.http import HttpResponseRedirect
from django.contrib import messages

from astrometry.net.models import *
from astrometry.net import settings
from astrometry.net.log import *
from astrometry.net.tmpfile import *
from astrometry.net.util import get_page, get_session_form, store_session_form
from astrometry.net.util import NoBulletsRadioSelect

from astrometry.util.run_command import run_command

from astrometry.net.views.comment import *

def album(req, album_id=None):
    album = get_object_or_404(Album, pk=album_id)

    comment_form = get_session_form(req.session, PartialCommentForm)

    page_number = req.GET.get('page',1)
    page = get_page(album.user_images.public_only(req.user),4*3,page_number)
    context = {
        'album': album,
        'comment_form': comment_form,
        'image_page': page,
        'request': req,
    }

    if album.is_public() or (album.user == req.user and req.user.is_authenticated):
        template = 'album/view.html'
    #elif SharedHideable.objects.filter(shared_with=req.user.id, hideable=album).count():
    #    template = 'album/view.html'
    else:
        messages.error(req, "Sorry, you don't have permission to view this content.")
        template = 'album/permission_denied.html'
    return render(req, template, context)

class AlbumForm(forms.ModelForm):
    class Meta:
        model = Album
        exclude = ('user', 'owner', 'user_images', 'tags', 'created_at', 'comment_receiver')
        widgets = {
            'description': forms.Textarea(attrs={'cols':60,'rows':3}),
            'publicly_visible': NoBulletsRadioSelect(),
        }

    def clean(self):
        cleaned_data = self.cleaned_data
        title = cleaned_data.get('title')
        if title:
            # make sure the user doesn't have another album with the same title
            query = Album.objects.filter(user=self.instance.user, title=title)
            query = query.exclude(pk=self.instance.id)
            if query.count() != 0:
                self._errors['title'] = self.error_class(['You already have an album with this title.'])
                del cleaned_data['title']

        return cleaned_data

@login_required
def edit(req, album_id=None):
    album = get_object_or_404(Album, pk=album_id)
    if album.user != req.user:
        messages.error(req, "Sorry, you don't have permission to view this content.")
        return render(req, 'album/permission_denied.html')

    if req.method == 'POST':
        form = AlbumForm(req.POST, instance=album)
        if form.is_valid():
            form.save()
            messages.success(req, 'Album details successfully updated.')
            return redirect(album)
        else:
            messages.error(req, 'Please fix the following errors:')
    else:
        form = AlbumForm(instance=album)

    context = {
        'album_form': form,
        'album': album,
    }
    return render(req, 'album/edit.html', context)

@login_required
def new(req):
    if req.method == 'POST':
        album = Album(user=req.user)
        form = AlbumForm(req.POST, instance=album)
        if form.is_valid():
            form.save(commit=False)
            album.comment_receiver=CommentReceiver.objects.create()
            album.save()
            messages.success(req, "Album '%s' successfully created." % album.title)
            return redirect(album)
        else:
            store_session_form(req.session, AlbumForm, req.POST)
            messages.error(req, 'Please fix the following errors:')
            return redirect(req.POST.get('from','/'))
    else:
        pass

@login_required
def delete(req, album_id):
    album = get_object_or_404(Album, pk=album_id)
    redirect_url = req.GET.get('next','/')
    if album.user == req.user:
        album.delete()
        messages.success(req, "Album '%s' successfully deleted." % album.title)
        return HttpResponseRedirect(redirect_url)
    else:
        # render a "you don't have permission" view
        pass


__author__ = "Saumik"
__date__ = "11/03/2023"
__source__ = "https://3dmatch.cs.princeton.edu/"

# This script is used for extracting and registering point clouds using the
# datasets provided by the 3DMatch project (https://3dmatch.cs.princeton.edu/).
# It includes functionalities to download a .mat file from Google Drive,
# extract point clouds, and run a registration pipeline.

import sys
import os
import gdown
from RegistrationPipeline import RegistrationPipeline
from PointCloudExtractor import PointCloudExtractor

def main():
    if len(sys.argv) != 3:
        print("Usage: python main.py <action> <number of point clouds>")
        sys.exit(1)

    action = sys.argv[1]
    num = int(sys.argv[2])

    # Google Drive URL for the .mat file
    url = 'https://drive.google.com/uc?id=1ba9Styp7qjCpJlrZnvCCHtgYV1Mv255E'
    # Local directory to save the downloaded .mat file
    data_dir = 'data'
    # Ensure the data directory exists
    os.makedirs(data_dir, exist_ok=True)
    # Local file path to save the downloaded .mat file
    mat_file_path = os.path.join(data_dir, 'validation-set.mat')

    # Download the .mat file from Google Drive if it does not exist
    if not os.path.exists(mat_file_path):
        print("Downloading .mat file...")
        gdown.download(url, mat_file_path, quiet=False)
    else:
        print(".mat file already exists. Skipping download.")

    if action == "extract":
        extractor = PointCloudExtractor(mat_file_path)
        extractor.extract_point_clouds(limit=num)
    elif action == "register":
        pipeline = RegistrationPipeline(mat_file_path)
        pipeline.run(limit=num)
        pipeline.save_to_hdf5()
    else:
        print("Invalid action. Use 'extract' or 'register'.")

if __name__ == "__main__":
    main()


'''

-Medium-
*DFS*

There is an undirected tree with n nodes labeled from 0 to n - 1 and n - 1 edges.

You are given a 2D integer array edges of length n - 1 where edges[i] = [ai, bi] indicates that there is an edge between nodes ai and bi in the tree. You are also given an integer array restricted which represents restricted nodes.

Return the maximum number of nodes you can reach from node 0 without visiting a restricted node.

Note that node 0 will not be a restricted node.

Example 1:

Input: n = 7, edges = [[0,1],[1,2],[3,1],[4,0],[0,5],[5,6]], restricted = [4,5]
Output: 4
Explanation: The diagram above shows the tree.
We have that [0,1,2,3] are the only nodes that can be reached from node 0 without visiting a restricted node.
Example 2:

Input: n = 7, edges = [[0,1],[0,2],[0,5],[0,4],[3,2],[6,5]], restricted = [4,2,1]
Output: 3
Explanation: The diagram above shows the tree.
We have that [0,5,6] are the only nodes that can be reached from node 0 without visiting a restricted node.

Constraints:

2 <= n <= 105
edges.length == n - 1
edges[i].length == 2
0 <= ai, bi < n
ai != bi
edges represents a valid tree.
1 <= restricted.length < n
1 <= restricted[i] < n
All the values of restricted are unique.

'''

from typing import List
from collections import defaultdict

class Solution:
    def reachableNodes(self, n: int, edges: List[List[int]], restricted: List[int]) -> int:
        graph = defaultdict(list)
        R = set(restricted)
        for u, v in edges:
            graph[u].append(v)
            graph[v].append(u)
        cnt = 0
        vis = [False]*n
        def dfs(u):
            nonlocal cnt
            cnt += 1
            vis[u] = True
            for v in graph[u]:
                if v not in R and not vis[v]:
                    dfs(v)
        dfs(0)
        return cnt

    def reachableNodes2(self, n: int, edges: List[List[int]], restricted: List[int]) -> int:
        graph = defaultdict(list)
        vis = set(restricted)
        for u, v in edges:
            graph[u].append(v)
            graph[v].append(u)
        def dfs(u):
            vis.add(u)
            for v in graph[u]:
                if v not in vis:
                    dfs(v)
        dfs(0)
        return len(vis) - len(restricted)

if __name__ == "__main__":
    print(Solution().reachableNodes(n = 7, edges = [[0,1],[1,2],[3,1],[4,0],[0,5],[5,6]], restricted = [4,5]))
    print(Solution().reachableNodes(n = 7, edges = [[0,1],[0,2],[0,5],[0,4],[3,2],[6,5]], restricted = [4,2,1]))


from itertools import count
import sys
import numpy as np
import cvxopt as co
import pickle
import time
import os

from sklearn.svm import SVC
import matplotlib.pyplot as plt
from cvxopt import matrix as cvxopt_matrix
from cvxopt import solvers as cvxopt_solvers

def extractData(dataDict):
    # number of features
    n=32*32*3
    # treating label 1 as -1 and label 2 as +1
    posClassSize=0
    negClassSize=0

    for j in range(0,dataDict["data"].shape[0]):
        if dataDict["labels"][j]==1:
            negClassSize+=1
        if dataDict["labels"][j]==2:
            posClassSize+=1

    xValue=np.empty([posClassSize+negClassSize,n])
    yValue=np.empty([posClassSize+negClassSize])

    currInd=0

    for j in range(0,dataDict["data"].shape[0]):
        if dataDict["labels"][j]==1:
            # swapped=np.swapaxes(dataDict["data"][j],0,2)
            flattened=dataDict["data"][j].reshape([3072])
            # flattened=swapped.flatten()
            xValue[currInd]=flattened
            yValue[currInd]=-1
            currInd+=1
        if dataDict["labels"][j]==2:
            # swapped=np.swapaxes(dataDict["data"][j],0,2)
            flattened=dataDict["data"][j].reshape([3072])
            # flattened=swapped.flatten()
            xValue[currInd]=flattened
            yValue[currInd]=1
            currInd+=1

    xValue=xValue/255
    return xValue,yValue

def train(trainingDict,C=1,gamma=0.001):
    xValue,yValue=extractData(trainingDict)
    # xValue=xValue[0:10,0:5]
    m,n=xValue.shape
    yValue=yValue.reshape(-1,1)

    # Gaussian Kernel
    # Calculating the H matrix
    H=(-2)*np.matmul(xValue,xValue.T)
    H+=np.sum(np.square(xValue),axis=1).reshape(xValue.shape[0],1)
    H=H.T
    H+=np.sum(np.square(xValue),axis=1).reshape(xValue.shape[0],1)
    H=H.T
    H=np.exp((-gamma)*H)
    H=np.multiply(np.matmul(yValue,yValue.T),H)

    #Converting into cvxopt format
    P=cvxopt_matrix(H)
    q=cvxopt_matrix(-np.ones((m, 1)))
    G=cvxopt_matrix(np.vstack((np.eye(m)*-1,np.eye(m))))
    h=cvxopt_matrix(np.hstack((np.zeros(m), np.ones(m) * C)))
    A=cvxopt_matrix(yValue.reshape(1, -1))
    b=cvxopt_matrix(np.zeros(1))

    #Run solver
    sol=cvxopt_solvers.qp(P,q,G,h,A,b,options={"show_progress":False})
    # sol=cvxopt_solvers.qp(P,q,G,h,A,b)

    alphas=np.array(sol['x'])
    # sol=cvxopt_solvers.qp(P,q,G,h,A,b)

    return alphas,xValue,yValue

def test(alphas,b,xTrainData,yTrainData,testDict,gamma=0.001):

    # Initializing results as predicition being right or wrong
    results=np.zeros([2],dtype=np.float64)
    # alphas=np.array(allPara['x'])

    # Extracting Data
    xValue,yValue=extractData(testDict)

    # Calculating the prediction
    yPred=(-2)*np.matmul(xTrainData,xValue.T)
    yPred=yPred.T
    yPred+=np.sum(np.square(xValue),axis=1).reshape(xValue.shape[0],1)
    yPred=yPred.T
    yPred+=np.sum(np.square(xTrainData),axis=1).reshape(xTrainData.shape[0],1)
    yPred=np.exp((-gamma)*yPred)
    yPred=np.multiply(yPred,alphas.reshape(xTrainData.shape[0],1))
    yPred=np.multiply(yPred,yTrainData.reshape(xTrainData.shape[0],1))
    yPred=np.sum(yPred,axis=0)

    # Adding the intercept term
    yPred+=b

    for i in range(0,yValue.shape[0]):
        if yPred[i]*yValue[i]>0:
            results[0]+=1
        else:
            results[1]+=1

    results=results/np.sum(results)
    results=results*100

    return results

def main():

    trainingDir=sys.argv[1]
    testDir=sys.argv[2]

    trainingData=pickle.load(open(trainingDir+"/train_data.pickle","rb"))
    testData=pickle.load(open(testDir+"/test_data.pickle","rb"))

    print("Model training started")
    trainStart=time.time()
    alphas,xTrainData,yTrainData=train(trainingData)
    trainEnd=time.time()
    print("Model training completed")
    print("\nTraining Time: ",trainEnd-trainStart,"sec")
    # retrieving alphas --> Langrangian Parameters
    # alphas=np.array(allPara['x'])

    indexSorted=np.argsort(alphas.reshape(-1,))[-5:]
    for ind in indexSorted:
        # print("ind: ",ind)
        img=xTrainData[ind].reshape([32,32,3])
        plt.imshow(img)
        plt.savefig(f"sv{ind}.png")
        plt.close()

    inf=float('inf')
    negSupport,posSupport=-inf,inf
    gamma=0.001

    # Finding intercept term - b
    yPred=(-2)*np.matmul(xTrainData,xTrainData.T)
    yPred=yPred.T
    yPred+=np.sum(np.square(xTrainData),axis=1).reshape(xTrainData.shape[0],1)
    yPred=yPred.T
    yPred+=np.sum(np.square(xTrainData),axis=1).reshape(xTrainData.shape[0],1)
    yPred=np.exp((-gamma)*yPred)
    yPred=np.multiply(yPred,alphas.reshape(xTrainData.shape[0],1))
    yPred=np.multiply(yPred,yTrainData.reshape(xTrainData.shape[0],1))
    yPred=np.sum(yPred,axis=0)

    for i in range(0,xTrainData.shape[0]):
        if yTrainData[i]>0:
            posSupport=min(posSupport,yPred[i])
        else:
            negSupport=max(negSupport,yPred[i])

    b =-(negSupport+posSupport)/2

    # retrieving support vectors
    countSupportVectors=np.zeros([2],dtype=np.float64)
    for i in range(0,alphas.shape[0]):
        if alphas[i][0]>1e-5:
            if yTrainData[i]<0:
                countSupportVectors[0]+=1
            else:
                countSupportVectors[1]+=1

     # printing on console
    print("\nNo. of support vectors in Class 1 are ",countSupportVectors[0])
    print("No. of support vectors in Class 2 are ",countSupportVectors[1])
    print("Support Vector percentage in training examples is ",np.sum((countSupportVectors)/xTrainData.shape[0])*100,"%")

    testTestStart=time.time()
    results=test(alphas,b,xTrainData,yTrainData,testData)
    testTestEnd=time.time()
    print("\nTesting Time over testing data set: ",testTestEnd-testTestStart,"sec")
    # print(results)

    print("\nThe accuracy over test data in case of gaussian kernel is: ",results[0],"%\n")

main()


# Description: Fetches METAR data from Aviation Weather Center API and posts it to PocketBase API

# Import libraries
import requests
import csv
import json
from datetime import datetime

# Define constants
API_URL = "https://www.aviationweather.gov/adds/dataserver_current/httpparam" # Aviation Weather Center API URL
POCKETBASE_API_URL = "https://custom.domain/api/collections/collection_name/records" # PocketBase API URL

# Define variables
data_type = "metars"
airport_code = "XXXX" # Airport code
hours_before_now = "24" # Number of hours before now to fetch data for
output_format = "csv"

# Define function to get current time
def execution_time():
    return datetime.utcnow().strftime("%Y-%m-%d %H:%M:%S")

# Define function to fetch CSV data
def fetch_csv_data(api_url, parameters):
    print(execution_time() + " - Making request to Aviation Weather Center...")
    # Make the API request
    response = requests.get(api_url, params=parameters)
    # Check for successful request
    if response.status_code == 200:
        # Decode the CSV content
        content = response.content.decode("utf-8")
        # Parse the CSV data and return it
        csv_data = list(csv.reader(content.splitlines(), delimiter=","))
        return csv_data
    else:
        print(execution_time() + " - Request to Aviation Weather Center failed! with status code: " + str(response.status_code))

# Set up the API request parameters
parameters = {
    "dataSource": data_type,
    "requestType": "retrieve",
    "format": output_format,
    "stationString": airport_code,
    "hoursBeforeNow": hours_before_now,
}

# Print execution time
print(execution_time() + " - Executing script...")

# Call the function to fetch the CSV data
csv_data = fetch_csv_data(API_URL, parameters)

# Check if there are results in the CSV data
if len(csv_data) <= 6:
    print(execution_time() + " - No results found in CSV data received from Aviation Weather Center")
else:
    print(execution_time() + " - CSV data received from Aviation Weather Center successfully!")
    # Parse the remaining rows of the CSV data and convert to JSON
    print(execution_time() + " - Parsing CSV data and converting it to JSON...")
    for row in csv_data[6:]: # Skip the first 6 rows
        # Get the headers from the first row of the CSV data
        headers = csv_data[5]
        # Create a dictionary with the desired keys and values
        data = {
            "raw_text": row[headers.index("raw_text")],
            "station_id": airport_code,
            "observation_time": datetime.strptime(row[headers.index("observation_time")], "%Y-%m-%dT%H:%M:%SZ").strftime("%Y-%m-%d %H:%M:%S.000Z"),
            "temp_c": float(row[headers.index("temp_c")]),
            "dewpoint_c": float(row[headers.index("dewpoint_c")]) if row[headers.index("dewpoint_c")] else 99, # Set to 99 if dewpoint_c is empty
            "wind_dir_degrees": int(row[headers.index("wind_dir_degrees")]) if row[headers.index("wind_dir_degrees")] else 0,
            "wind_speed_kt": int(row[headers.index("wind_speed_kt")]) if row[headers.index("wind_speed_kt")] else 0,
            "altim_in_hg": float(row[headers.index("altim_in_hg")]),
            "corrected": bool(row[headers.index("corrected")]),
            "precip_in": float(row[headers.index("precip_in")]) if row[headers.index("precip_in")] else 0,
            "metar_type": row[headers.index("metar_type")],
        }

        # Set up the headers for the POST request
        headers = {'Content-Type': 'application/json'}

        # Make the POST request to PocketBase API
        print(execution_time() + " - Sending data to PocketBase with date and time: " + data["observation_time"])
        response = requests.post(POCKETBASE_API_URL, data=json.dumps(data), headers=headers)

        # Check for successful request
        if response.status_code == 200:
            print(execution_time() + " - Data sent to PocketBase successfully!")
        else:
            print(execution_time() + " - Request to PocketBase failed! with status code: " + str(response.status_code))


import requests
from bs4 import BeautifulSoup
import sqlite3

conn = sqlite3.connect('assign.db')
c = conn.cursor()

def create_table():
    c.execute('CREATE TABLE IF NOT EXISTS moviedetails (title TEXT , released_date TEXT ,duration TEXT , description TEXT , rating TEXT , url TEXT)')

def data_entry(i):
    c.execute("INSERT INTO moviedetails (title, released_date, duration, description, rating, url) VALUES (?,?,?,?,?,?)",
              (title[i],date[i],duration[i],description[i],rating[i],movies[i]))
    conn.commit()

URL = "https://www.imdb.com/chart/top?ref_=nv_mv_250"
r = requests.get(URL)

soup = BeautifulSoup(r.content, 'html5lib')

movies=[]
rating = []
description = []
duration = []
title = []
date = []

table = soup.findAll('td', attrs = {'class':'titleColumn'})

for row in table:
    movie = {}
    movie['url']=row.a['href']
    movies.append(movie)

print(movies)

for i in range(0,250):
        movies[i] = str(movies[i])
        movies[i]=(movies[i][9:-2])
        movies[i]= 'https://www.imdb.com' + movies[i]

for i in range(0,250):
    r = requests.get(movies[i])
    soup = BeautifulSoup(r.content, 'html5lib')
    table = soup.findAll('div', attrs = {'class':'ratingValue'})
    for row in table:
        rating.append(row.strong.text)

    table = soup.findAll('div', attrs = {'class':'widget_inline_blurb'})
    for row in table:
        title.append(row.a.text)

    table = soup.findAll('div', attrs = {'class':'subtext'})
    for row in table:
        duration.append(row.time.text)

    table = soup.findAll('a', attrs = {'title':'See more release dates'})
    for row in table:
        date.append(row.text)

    table = soup.findAll('div', attrs = {'class':'summary_text'})
    for row in table:
        description.append(row.text)
    print(i)
    date[i] = date[i][:-1]
    description[i]=description[i][21:-13]
    duration[i] = duration[i][25:-21]

rows = zip(title,date,duration,description,rating,movies)

create_table()
for i in range(0,250):
    data_entry(i)
c.close()
conn.close()

#with open("output.csv", "w") as f:
 #   writer = csv.writer(f)
  #  for movie in rows:
   #     writer.writerow([movie])


import xml.etree.ElementTree as et
import Levenshtein as lev
import csv

def parser_xml(curriculo):

    t = et.parse(curriculo)
    cv = t.getroot()

    return cv

def extrair_livros(cv):
    m = []
    l = []
    a = 0

    while a <= len(cv[1][2][1])-1:
        for i in cv[1][2][1][a]:
            l.append(i.attrib)
        m.append(l)
        l = []
        a += 1
    print('Foram extraidos',len(m),'livros')
    print()
    return m

def extrair_metadados(m):
    x = 0
    au = []
    pc = []
    metadados = []
    while x <= len(m)-1:
        for i in m[x]:
            try:
                tit = i['TITULO-DO-CAPITULO-DO-LIVRO']
                ano = i['ANO']
                idi = i['IDIOMA']
            except KeyError:
                try:
                    livro = i['TITULO-DO-LIVRO']
                    pg_i = i['PAGINA-INICIAL']
                    pg_f = i['PAGINA-FINAL']
                    cidade = i['CIDADE-DA-EDITORA']
                    editora = i['NOME-DA-EDITORA']
                except KeyError:
                    try:
                        au.append(i['NOME-COMPLETO-DO-AUTOR'])
                    except KeyError:
                        try:
                           pc.append(i['PALAVRA-CHAVE-1'])
                           pc.append(i['PALAVRA-CHAVE-2'])
                           pc.append(i['PALAVRA-CHAVE-3'])
                        except:
                            ignore = 0

        d = {
            'titulo' : tit,
            'ano' : ano,
            'idioma' : idi,
            'livro' : livro,
            'pag. inicial' : pg_i,
            'pag. final' : pg_f,
            'cidade' : cidade,
            'editora' : editora,
            'autores' : au,
            'assunto' : pc,
            }

        metadados.append(d)
        au = []
        pc = []

        x += 1

    return metadados

def eliminar_titulos_similares(metadados):
    repetidos = []
    for i in range(len(metadados)-1):
        for j in range(i+1, len(metadados)):
            if lev.distance(metadados[i]['titulo'], metadados[j]['titulo']) <= 5:
                repetidos.append(metadados[j])

    m = []
    print('Foram eliminados',len(repetidos),'títulos similares')
    for i in metadados:
        if i not in repetidos:
            m.append(i)

    return m

def escrever_csv(metadados):
    with open('capitulo_livros.csv', 'w', newline='', encoding='utf-8') as f:
        n = ['Autores',
             'Título',
             'Livro',
             'Idioma',
             'Cidade',
             'Editora',
             'Ano',
             'Pag. Inicial',
             'Pag. Final',
             'Assunto']
        e = csv.DictWriter(f, fieldnames=n)

        e.writeheader()
        c = 0
        while c <= len(metadados)-1:
            e.writerow({'Autores' : metadados[c]['autores'],
                        'Título' : metadados[c]['titulo'],
                        'livro' : metadados[c]['livro'],
                        'Idioma' : metadados[c]['idioma'],
                        'Cidade' : metadados[c]['cidade'],
                        'Editora' : metadados[c]['editora'],
                        'Ano' : metadados[c]['ano'],
                        'Pag. Inicial' : metadados[c]['pag. inicial'],
                        'Pag. Final' : metadados[c]['pag. final'],
                        'Assunto' : metadados[c]['assunto']})
            c += 1


from django.shortcuts import render, redirect
from django.test import tag
from .models import Categorys, Posts, blogpostComments

# Create your views here.

def blogs(request):
    cat = Categorys.objects.all()
    post = Posts.objects.all().order_by("-upload_time")[:20]
    context = {
        'cats': cat,
        'posts': post
    }
    return render(request, 'blogs.html', context)

def blogpost(request, url):
    try:
        post = Posts.objects.get(url=url)
        relatedPost = Posts.objects.all().exclude(post_id=post.post_id)[:5]
        # work to do here
        comments = blogpostComments.objects.filter(post=post)
        def spaceRemove(text):
            TEXT = text.replace(" ", "")
            return TEXT
        tags = post.tags
        splitedText = tags.split(",")
        hastags = []
        for j in splitedText:
            hastags.append(spaceRemove(j))

        final = map(lambda x: f"#{x}", hastags)
        finalTags = list(final)
        context = {
            'posts': post,
            'comment': comments,
            'relatedpost': relatedPost,
            'tags': finalTags
        }
        return render(request, 'blogpost.html', context)
    except:
        return render(request, '500.html')

def category(request, url):
    searchCat = Categorys.objects.get(url=url)
    post = Posts.objects.filter(cat=searchCat)
    cat = Categorys.objects.all()
    context = {
        'cats': cat,
        'posts': post
    }
    return render(request, 'blogs.html', context)

def comment(request):
    if request.user.is_anonymous:
        return redirect('login')
    if request.method == "POST":
        comment = request.POST.get('comment')
        user = request.user
        postno = request.POST.get('Sno')
        post = Posts.objects.get(post_id=postno)
        comment = blogpostComments(comments=comment, user=user, post=post)
        comment.save()
    return redirect(f'/blogs/{post.url}')


from numpy import *
import matplotlib.pyplot as plt
from Tkinter import *

def loadDataSet(fileName):
    dataMat = []
    fr = open(fileName)
    for line in fr.readlines():
        curLine = line.strip().split('\t')
        fltLine = list(map(float, curLine)) #转化为float类型
        dataMat.append(fltLine)
    return dataMat

def plotDataSet(fileName):
    dataMat = loadDataSet(fileName)
    print(shape(dataMat))
    dataMat = array(dataMat)
    fig = plt.figure()
    ax = fig.add_subplot(111)
    ax.scatter(dataMat[:, 0], dataMat[:, 1], s = 20, c = 'b')
    plt.title('DataSet')
    plt.xlabel('X')
    plt.ylabel('Y')
    plt.show()

'''
函数说明:根据特征切分数据集合
    Parameters:
        dataSet - 数据集合
        feature - 带切分的特征
        value - 该特征的值
    Returns:
        mat0 - 切分的数据集合0
        mat1 - 切分的数据集合1
'''
def binSplitDataSet(dataSet, feature, value):
    mat0 = dataSet[nonzero(dataSet[:, feature] > value)[0], :]
    mat1 = dataSet[nonzero(dataSet[:, feature] <= value)[0], :]
    return mat0, mat1

'''
函数说明:生成叶结点
    Parameters:
        dataSet - 数据集合
    Returns:
        目标变量的均值
'''
def regLeaf(dataSet):
    return mean(dataSet[:, -1])

'''
函数说明:误差估计函数
    Parameters:
        dataSet - 数据集合
    Returns:
        目标变量的总方差
'''
def regErr(dataSet):
    # 均方差 * 样本个数 = 总方差
    return var(dataSet[:, -1] * shape(dataSet)[0])

'''
函数说明:找到数据的最佳二元切分方式函数
    Parameters:
        dataSet - 数据集合
        leafType - 生成叶结点
        regErr - 误差估计函数
        ops - 用户定义的参数构成的元组
    Returns:
        bestIndex - 最佳切分特征
        bestValue - 最佳特征值
'''
def chooseBestSplit(dataSet, leafType = regLeaf, errType = regErr, ops = (1,4)):
    tolS = ops[0]   # tolS允许的误差下降值
    tolN = ops[1]   # tolN切分的最少样本数
    if (len(set(dataSet[:, -1].T.tolist()[0])) == 1):
        # 如果当前所有值相等,则退出。(根据set的特性)
        return None, leafType(dataSet)
    m, n =shape(dataSet)
    S = errType(dataSet)    #默认最后一个特征为最佳切分特征,计算其误差估计
    bestS = float('inf')    #最佳误差
    bestIndex = 0           #最佳特征切分的索引值
    bestValue = 0           #最佳特征值
    for featIndex in range(n - 1):  #遍历所有特征列
        for splitVal in set(dataSet[:, featIndex].T.A.tolist()[0]): #遍历所有特征值
            mat0, mat1 = binSplitDataSet(dataSet, featIndex, splitVal)  #根据特征和特征值切分数据集
            if (shape(mat0)[0] < tolN or shape(mat1)[0] < tolN):    #如果数据少于tolN,则退出
                continue
            newS = errType(mat0) + errType(mat1)     #计算误差估计
            if newS < bestS:    #如果误差估计更小,则更新特征索引值和特征值
                bestIndex = featIndex
                bestValue = splitVal
                bestS = newS
    if ((S - bestS) < tolS):    #如果误差减少不大则退出
        return None, leafType(dataSet)
    mat0, mat1 = binSplitDataSet(dataSet, bestIndex, bestValue) #根据最佳的切分特征和特征值切分数据集合
    if (shape(mat0)[0] < tolN or shape(mat1)[0] < tolN):    #如果切分出的数据集很小则退出
        return None, leafType(dataSet)
    return bestIndex, bestValue #返回最佳切分特征和特征值

'''
函数说明:树构建函数
    Parameters:
        dataSet - 数据集合
        leafType - 建立叶结点的函数
        errType - 误差计算函数
        ops - 包含树构建所有其他参数的元组
    Returns:
        retTree - 构建的回归树
'''
def createTree(dataSet, leafType = regLeaf, errType = regErr, ops = (1, 4)):
    # 选择最佳切分特征和特征值
    feat, val = chooseBestSplit(dataSet, leafType, errType, ops)
    if feat == None:    #r如果没有特征,则返回特征值
        return val
    retTree ={} #回归树
    retTree['spInd'] = feat
    retTree['spVal'] = val
    lSet, rSet = binSplitDataSet(dataSet, feat, val)    #分成左数据集和右数据集
    # 创建左子树和右子树
    retTree['left'] = createTree(lSet, leafType, errType, ops)
    retTree['right'] = createTree(rSet, leafType, errType, ops)
    return retTree

# fileName = 'ex2.txt'
# plotDataSet(fileName)

def isTree(obj):    #判断测试输入变量是否是一棵树
    import types
    return (type(obj).__name__ == 'dict')

def getMean(tree):  # 如果找到两个leaf，则对树进行塌陷处理(即返回树平均值)
    if (isTree(tree['left'])):
        tree['left'] = getMean(tree['left'])
    if (isTree(tree['right'])):
        tree['right'] = getMean(tree['right'])
    return (tree['left'] + tree['right']) / 2.0

def prune(tree, testData): # 后剪枝
    if (shape(testData)[0] == 0):   #如果测试集为空,则对树进行塌陷处理
        return getMean(tree)
    if (isTree(tree['left']) or isTree(tree['right'])): #如果有左子树或者右子树,则切分数据集
        lSet, rSet = binSplitDataSet(testData, tree['spInd'], tree['spVal'])
    if (isTree(tree['left'])):  #处理左子树(剪枝)
        tree['left'] = prune(tree['left'], lSet)
    if (isTree(tree['right'])): #处理右子树(剪枝)
        tree['right'] = prune(tree['right'], rSet)
    if not isTree(tree['left']) and not isTree(tree['right']):  #如果当前结点的左右结点为叶结点
        lSet, rSet = binSplitDataSet(testData, tree['spInd'], tree['spVal'])
        # 计算没有合并的误差
        errorNoMerge = sum((lSet[:, -1] - tree['left']) ** 2) + sum((rSet[:, -1] - tree['right']) ** 2)
        # 计算合并的均值
        treeMean = (tree['left'] + tree['right']) / 2.0
        # 计算合并的误差
        errorMerge = sum((testData[:, -1] - treeMean) ** 2)
        # 如果合并的误差小于没有合并的误差,则合并
        if errorMerge < errorNoMerge:
            return treeMean
        else:
            return tree
    else:
        return tree


from collections import UserDict
from functools import wraps
import itertools
from typing import Generator, Iterable, Mapping, Union

from fiona.transform import transform_geom  # type: ignore
import shapely  # type: ignore
import shapely.ops  # type: ignore
from shapely.geometry import mapping, shape  # type: ignore
from shapely.geometry.base import BaseGeometry, BaseMultipartGeometry  # type: ignore

from .errors import ReduceError
from . import snuggs

# Patch snuggs's func_map, extending it with Python builtins, geometry
# methods and attributes, and functions exported in the shapely module
# (such as set_precision).

class FuncMapper(UserDict, Mapping):
    """Resolves functions from names in pipeline expressions."""

    def __getitem__(self, key):
        """Get a function by its name."""
        if key in self.data:
            return self.data[key]
        elif key in __builtins__ and not key.startswith("__"):
            return __builtins__[key]
        elif key in dir(shapely):
            return lambda g, *args, **kwargs: getattr(shapely, key)(g, *args, **kwargs)
        elif key in dir(shapely.ops):
            return lambda g, *args, **kwargs: getattr(shapely.ops, key)(
                g, *args, **kwargs
            )
        else:
            return (
                lambda g, *args, **kwargs: getattr(g, key)(*args, **kwargs)
                if callable(getattr(g, key))
                else getattr(g, key)
            )

def collect(geoms: Iterable) -> object:
    """Turn a sequence of geometries into a single GeometryCollection.

    Parameters
    ----------
    geoms : Iterable
        A sequence of geometry objects.

    Returns
    -------
    Geometry

    """
    return shapely.GeometryCollection(list(geoms))

def dump(geom: Union[BaseGeometry, BaseMultipartGeometry]) -> Generator:
    """Get the individual parts of a geometry object.

    If the given geometry object has a single part, e.g., is an
    instance of LineString, Point, or Polygon, this function yields a
    single result, the geometry itself.

    Parameters
    ----------
    geom : a shapely geometry object.

    Yields
    ------
    A shapely geometry object.

    """
    if hasattr(geom, "geoms"):
        parts = geom.geoms
    else:
        parts = [geom]
    for part in parts:
        yield part

def identity(obj: object) -> object:
    """Get back the given argument.

    To help in making expression lists, where the first item must be a
    callable object.

    Parameters
    ----------
    obj : objeect

    Returns
    -------
    obj

    """
    return obj

def vertex_count(obj: object) -> int:
    """Count the vertices of a GeoJSON-like geometry object.

    Parameters
    ----------
    obj: object
        A GeoJSON-like mapping or an object that provides
        __geo_interface__.

    Returns
    -------
    int

    """
    shp = shape(obj)
    if hasattr(shp, "geoms"):
        return sum(vertex_count(part) for part in shp.geoms)
    elif hasattr(shp, "exterior"):
        return vertex_count(shp.exterior) + sum(
            vertex_count(ring) for ring in shp.interiors
        )
    else:
        return len(shp.coords)

def binary_projectable_property_wrapper(func):
    """Project func's geometry args before computing a property.

    Parameters
    ----------
    func : callable
        Signature is func(geom1, geom2, *args, **kwargs)

    Returns
    -------
    callable
        Signature is func(geom1, geom2, projected=True, *args, **kwargs)

    """

    @wraps(func)
    def wrapper(geom1, geom2, *args, projected=True, **kwargs):
        if projected:
            geom1 = shape(transform_geom("OGC:CRS84", "EPSG:6933", mapping(geom1)))
            geom2 = shape(transform_geom("OGC:CRS84", "EPSG:6933", mapping(geom2)))

        return func(geom1, geom2, *args, **kwargs)

    return wrapper

def unary_projectable_property_wrapper(func):
    """Project func's geometry arg before computing a property.

    Parameters
    ----------
    func : callable
        Signature is func(geom1, *args, **kwargs)

    Returns
    -------
    callable
        Signature is func(geom1, projected=True, *args, **kwargs)

    """

    @wraps(func)
    def wrapper(geom, *args, projected=True, **kwargs):
        if projected:
            geom = shape(transform_geom("OGC:CRS84", "EPSG:6933", mapping(geom)))

        return func(geom, *args, **kwargs)

    return wrapper

def unary_projectable_constructive_wrapper(func):
    """Project func's geometry arg before constructing a new geometry.

    Parameters
    ----------
    func : callable
        Signature is func(geom1, *args, **kwargs)

    Returns
    -------
    callable
        Signature is func(geom1, projected=True, *args, **kwargs)

    """

    @wraps(func)
    def wrapper(geom, *args, projected=True, **kwargs):
        if projected:
            geom = shape(transform_geom("OGC:CRS84", "EPSG:6933", mapping(geom)))
            product = func(geom, *args, **kwargs)
            return shape(transform_geom("EPSG:6933", "OGC:CRS84", mapping(product)))
        else:
            return func(geom, *args, **kwargs)

    return wrapper

area = unary_projectable_property_wrapper(shapely.area)
buffer = unary_projectable_constructive_wrapper(shapely.buffer)
distance = binary_projectable_property_wrapper(shapely.distance)
set_precision = unary_projectable_constructive_wrapper(shapely.set_precision)
simplify = unary_projectable_constructive_wrapper(shapely.simplify)
length = unary_projectable_property_wrapper(shapely.length)

snuggs.func_map = FuncMapper(
    area=area,
    buffer=buffer,
    collect=collect,
    distance=distance,
    dump=dump,
    identity=identity,
    length=length,
    simplify=simplify,
    set_precision=set_precision,
    vertex_count=vertex_count,
    **{
        k: getattr(itertools, k)
        for k in dir(itertools)
        if not k.startswith("_") and callable(getattr(itertools, k))
    },
)

def map_feature(
    expression: str, feature: Mapping, dump_parts: bool = False
) -> Generator:
    """Map a pipeline expression to a feature.

    Yields one or more values.

    Parameters
    ----------
    expression : str
        A snuggs expression. The outermost parentheses are optional.
    feature : dict
        A Fiona feature object.
    dump_parts : bool, optional (default: False)
        If True, the parts of the feature's geometry are turned into
        new features.

    Yields
    ------
    object

    """
    if not (expression.startswith("(") and expression.endswith(")")):
        expression = f"({expression})"

    try:
        geom = shape(feature.get("geometry", None))
        if dump_parts and hasattr(geom, "geoms"):
            parts = geom.geoms
        else:
            parts = [geom]
    except (AttributeError, KeyError):
        parts = [None]

    for part in parts:
        result = snuggs.eval(expression, g=part, f=feature)
        if isinstance(result, (str, float, int, Mapping)):
            yield result
        elif isinstance(result, (BaseGeometry, BaseMultipartGeometry)):
            yield mapping(result)
        else:
            try:
                for item in result:
                    if isinstance(item, (BaseGeometry, BaseMultipartGeometry)):
                        item = mapping(item)
                    yield item
            except TypeError:
                yield result

def reduce_features(expression: str, features: Iterable[Mapping]) -> Generator:
    """Reduce a collection of features to a single value.

    The pipeline is a string that, when evaluated by snuggs, produces
    a new value. The name of the input feature collection in the
    context of the pipeline is "c".

    Parameters
    ----------
    pipeline : str
        Geometry operation pipeline such as "(unary_union c)".
    features : iterable
        A sequence of Fiona feature objects.

    Yields
    ------
    object

    Raises
    ------
    ReduceError

    """
    if not (expression.startswith("(") and expression.endswith(")")):
        expression = f"({expression})"

    collection = (shape(feat["geometry"]) for feat in features)
    result = snuggs.eval(expression, c=collection)

    if isinstance(result, (str, float, int, Mapping)):
        yield result
    elif isinstance(result, (BaseGeometry, BaseMultipartGeometry)):
        yield mapping(result)
    else:
        raise ReduceError("Expression failed to reduce to a single value.")


import azure.functions as func
import logging
import pyodbc
import pandas as pd
from azure.storage.blob import BlobServiceClient
from sqlalchemy.engine import URL
from sqlalchemy import create_engine
import os

# environment variables:
CONN_STR_BLOB = os.getenv('CONN_STR_BLOB')
CONN_STR_DB = os.getenv('CONN_STR_DB')
# modificar:
line_where_table_start = 9
TABLE_NAME = "my_table"
CONTAINER_NAME = 'my_container'

def test_db():
    cnxn = pyodbc.connect(CONN_STR_DB)
    cursor = cnxn.cursor()
    query="select * from " + TABLE_NAME + " limit 10;"
    cursor.execute(query)
    row = cursor.fetchall()
    rows = []
    if row:
        rows.append(row)
    print(rows)
    return rows

# drop unnamed columns in the table
def drop_unnamed(df):
    df=[c for c in range(len(df.columns)) if ('Unnamed' in str(df.columns[c]))]
    return df

def main(myblob: func.InputStream):
    blob = myblob.name.split('/',1)[1]
    logging.info(f"blob: {blob}")
    blob_service_client = BlobServiceClient.from_connection_string(CONN_STR_BLOB)
    source_blob = blob_service_client.get_blob_client(container = CONTAINER_NAME, blob=blob)
    content = source_blob.download_blob().readall()
    df_data = pd.read_excel(content, header=line_where_table_start).dropna(how='all').reset_index(drop=True)
    df_data.drop(columns=drop_unnamed(df_data), inplace=True)
    connection_string = CONN_STR_DB
    connection_url = URL.create("mssql+pyodbc", query={"odbc_connect": connection_string})
    engine = create_engine(connection_url, fast_executemany=True)
    conn = engine.connect()
    df_data.to_sql(name=TABLE_NAME, con=conn, if_exists='replace', chunksize=100, index=False )
    conn.commit()
    test = test_db()
    try:
        if test:
            print("------elements in table------")
        else:
            print("------empty table------")
    except:
        print("ERROR")


from django.urls import path
from django.views.generic import RedirectView

from . import views

urlpatterns = [
    path(
        '',
        RedirectView.as_view(url='/1'),
        name='index'
    ),
    path(
        '<int:page>',
        views.ArticleListView.as_view(),
        name='article_list'
    ),
    path(
        'article/<int:article_id>',
        views.ArticleDetailView.as_view(),
        name='article_detail'
    ),
    path(
        'article/<int:article_id>/edit',
        views.manage_article_view,
        name='article_edit'
    ),
    path(
        'article/create',
        views.manage_article_view,
        name='article_create',
        kwargs={'article_id': None}
    ),
    path(
        'category_list',
        views.CategoryListView.as_view(),
        name="category_list"
    ),
    path(
        'category/<int:category_id>/<int:page>/',
        views.CategoryDetailView.as_view(),
        name='category_detail'
    )
    ]


""" setup.py is the build script for setuptools. It tells setuptools about your package
(such as the name and version) as well as which code files to include."""
import setuptools

with open("README.md", "r") as fh:
    long_description = fh.read()

setuptools.setup(
    name="pygtlink", # Replace with your own username
    version="1.0.0",
    author="Maria Tirindelli",
    author_email="maria.tirindelli@hotmail.it",
    description="A package to handle basic openigtlink message with python",
    long_description=long_description,
    long_description_content_type="text/markdown",
    url="https://github.com/mariatirindelli/PyOpenIgtlink",
    packages=setuptools.find_packages(exclude=("tests", "examples", "docs")),
    install_requires=["crcmod", "numpy"],
    classifiers=[
        "Programming Language :: Python :: 3",
        "License :: OSI Approved :: MIT License",
        "Operating System :: OS Independent",
    ],
    python_requires='>=3.6',
)