import discord
from discord.ext import commands
from dotenv.main import load_dotenv
import os
from discord.ui import View, Button
from discord.utils import get
from discord import FFmpegPCMAudio
from youtube_dl import YoutubeDL
from pytube import YouTube
import re
from yandex_music import ClientAsync
import asyncio

load_dotenv()

TOKEN = os.environ['TOKEN']
TOKEN_YANDEX = os.environ['TOKEN_YANDEX']

intents = discord.Intents.default()
intents.message_content = True
bot = commands.Bot(command_prefix='!', intents=intents)

queue = {}
track_inform = {}

@bot.command()
async def join(ctx):
    if ctx.author.voice is None:
        await ctx.send("Вы не подключены к голосовому каналу!")
        return
    channel = ctx.author.voice.channel
    await channel.connect()

async def other(ctx, url, voice_client, channel_queue):
    if voice_client.is_playing():
        channel_queue.append(url)
        queue[ctx.channel.id] = channel_queue
        # queue.append(url)
        # Получите информацию о треках для текущего канала или создайте новую
        channel_track_inform = track_inform.get(ctx.channel.id, [])
        channel_track_inform.append(url)
        track_inform[ctx.channel.id] = channel_track_inform
        message = await ctx.channel.fetch_message(ctx.channel.last_message_id)
        await message.add_reaction("👍")
    else:
        message = await ctx.channel.fetch_message(ctx.channel.last_message_id)
        await message.add_reaction("👍")
        # Получите информацию о треках для текущего канала или создайте новую
        channel_track_inform = track_inform.get(ctx.channel.id, [])
        channel_track_inform.append(url)
        track_inform[ctx.channel.id] = channel_track_inform
        await play_track(ctx, url)

async def album_yandex(ctx, url, voice_client, channel_queue):
    pattern = r'https://music\.yandex\.ru/album/(\d+)$'

    # Используем регулярное выражение для извлечения
    # идентификатора альбома из URL
    match = re.match(pattern, url)

    # Если URL соответствует шаблону, то выводим идентификатор альбома
    if match:
        message = await ctx.channel.fetch_message(ctx.channel.last_message_id)
        await message.add_reaction("🔥")
        album_id = match.group(1)
        client = ClientAsync(TOKEN_YANDEX)
        await client.init()

        album = await client.albums_with_tracks(album_id)

        del client

        track = []

        for i in album.volumes[0]:
            track.append(
                f"https://music.yandex.ru/album/{album_id}/track/{i['id']}")

        for i in track:
            if voice_client.is_playing():
                channel_queue.append(i)
                queue[ctx.channel.id] = channel_queue
                # queue.append(i)
                # Получите информацию о треках для текущего канала
                # или создайте новую
                channel_track_inform = track_inform.get(ctx.channel.id, [])
                channel_track_inform.append(i)
                track_inform[ctx.channel.id] = channel_track_inform
            else:
                # Получите информацию о треках для текущего канала
                # или создайте новую
                channel_track_inform = track_inform.get(ctx.channel.id, [])
                channel_track_inform.append(i)
                track_inform[ctx.channel.id] = channel_track_inform
                await play_track(ctx, i)
    else:
        ctx.send("Не верная ссылка на альбом.")

async def playlist_yandex(ctx, url, voice_client, channel_queue):
    pattern = r'https://music\.yandex\.ru/users/(.+)/playlists/(\d+)$'

    match = re.match(pattern, url)

    if match:
        message = await ctx.channel.fetch_message(ctx.channel.last_message_id)
        await message.add_reaction("❤")
        username = match.group(1)
        playlist_id = match.group(2)

        client = ClientAsync(TOKEN_YANDEX)
        await client.init()

        playlist = await client.users_playlists(playlist_id, username)

        tracks = []

        for i in playlist.tracks:
            track = await client.tracks(i.id)
            data = track[0].track_id.split(':')
            tracks.append(
                f"https://music.yandex.ru/album/{data[1]}/track/{data[0]}")

        del client

        for i in tracks:
            if voice_client.is_playing():
                channel_queue.append(i)
                queue[ctx.channel.id] = channel_queue
                # queue.append(i)
                # Получите информацию о треках для текущего канала
                # или создайте новую
                channel_track_inform = track_inform.get(ctx.channel.id, [])
                channel_track_inform.append(i)
                track_inform[ctx.channel.id] = channel_track_inform
            else:
                # Получите информацию о треках для текущего канала
                # или создайте новую
                channel_track_inform = track_inform.get(ctx.channel.id, [])
                channel_track_inform.append(i)
                track_inform[ctx.channel.id] = channel_track_inform
                await play_track(ctx, i)

    else:
        ctx.send("Не верная ссылка на плейлист.")

async def playlist_youtube(ctx, url, voice_client, channel_queue):
    video_urls = []

    message = await ctx.channel.fetch_message(ctx.channel.last_message_id)
    await message.add_reaction("❤🔥")

    ydl_opts = {
        'quiet': True,
        'extract_flat': True,
    }

    with YoutubeDL(ydl_opts) as ydl:
        info_dict = ydl.extract_info(url, download=False)
        if 'entries' in info_dict:
            video_info = info_dict['entries']
            for video in video_info:
                video_urls.append(
                    f'https://www.youtube.com/watch?v={video["id"]}')

    for i in video_urls:
        if voice_client.is_playing():
            channel_queue.append(i)
            queue[ctx.channel.id] = channel_queue
            # queue.append(i)
            # Получите информацию о треках для текущего канала
            # или создайте новую
            channel_track_inform = track_inform.get(ctx.channel.id, [])
            channel_track_inform.append(i)
            track_inform[ctx.channel.id] = channel_track_inform
        else:
            # Получите информацию о треках для текущего канала
            # или создайте новую
            channel_track_inform = track_inform.get(ctx.channel.id, [])
            channel_track_inform.append(i)
            track_inform[ctx.channel.id] = channel_track_inform
            await play_track(ctx, i)

@bot.command()
async def play(ctx, url):
    voice_client = ctx.guild.voice_client
    # Получите очередь для текущего канала или создайте новую
    channel_queue = queue.get(ctx.channel.id, [])
    pattern = r'https://music\.yandex\.ru/album/(\d+)$'
    pattern1 = r'https://music\.yandex\.ru/users/.+/playlists/\d+$'
    pattern2 = (
        r'(https?://)?(www\.)?(youtube\.com|youtu\.?be)'
        r'/playlist\?list=[^&]+'
    )

    if re.match(pattern, url):
        await album_yandex(ctx, url, voice_client, channel_queue)
    elif re.match(pattern1, url):
        await playlist_yandex(ctx, url, voice_client, channel_queue)
    elif re.match(pattern2, url):
        await playlist_youtube(ctx, url, voice_client, channel_queue)
    else:
        await other(ctx, url, voice_client, channel_queue)

async def play_track(ctx, url):
    YDL_OPTIONS = {'format': 'bestaudio', 'noplaylist': 'True'}
    FFMPEG_OPTIONS = {
        'before_options':
            '-reconnect 1 -reconnect_streamed 1 -reconnect_delay_max 5',
        'options': '-vn'
    }

    try:
        volume = ctx.guild.voice_client.source.volume
    except Exception:
        volume = 1.0

    voice = get(bot.voice_clients, guild=ctx.guild)

    youtube_regex = r"(youtube\.com|youtu\.be)"
    yandex_regex = r"music\.yandex\.ru"

    if not voice.is_playing():
        if re.search(youtube_regex, url):
            with YoutubeDL(YDL_OPTIONS) as ydl:
                info = ydl.extract_info(url, download=False)
            URL = info['formats'][0]['url']
            voice.play(
                discord.PCMVolumeTransformer(
                    FFmpegPCMAudio(URL, **FFMPEG_OPTIONS)
                ),
                after=lambda e: asyncio.run(play_next(ctx)))
            voice.is_playing()
            ctx.guild.voice_client.source.volume = volume
        elif re.search(yandex_regex, url):
            match = re.search(r'/album/(\d+)/track/(\d+)', url)

            if match:
                album_id, track_id = match.groups()
                formatted_string = f"{track_id}:{album_id}"

                client = ClientAsync(TOKEN_YANDEX)
                await client.init()

                track = await client.tracks(formatted_string)

                try:
                    track = await client.tracks_download_info(
                        track[0].id, get_direct_links=True)
                    URL = track[0].direct_link
                except Exception as e:
                    await ctx.send(f"Ошибка при загрузке аудио: {e}")

                del client

                voice.play(
                    discord.PCMVolumeTransformer(
                        FFmpegPCMAudio(URL, **FFMPEG_OPTIONS)
                    ),
                    after=lambda e: asyncio.run(play_next(ctx)))
                voice.is_playing()
                ctx.guild.voice_client.source.volume = volume
            else:
                await ctx.send(
                    "Не удалось найти идентификаторы альбома и трека в URL")
    else:
        await ctx.send("Уже проигрывается песня")
        return

async def play_next(ctx):
    # Получите очередь для текущего канала
    try:
        channel_queue = queue[ctx.channel.id]
        channel_track = track_inform[ctx.channel.id]
        if len(channel_queue) > 0:
            next_track = channel_queue.pop(0)
            channel_track.pop(0)
            # Обновите очередь в словаре после удаления трека
            queue[ctx.channel.id] = channel_queue
            track_inform[ctx.channel.id] = channel_track
            await play_track(ctx, next_track)
        else:
            channel_track.pop(0)
            track_inform[ctx.channel.id] = channel_track
    except Exception:
        pass

async def info(ctx):

    youtube_regex = r"(youtube\.com|youtu\.be)"
    yandex_regex = r"music\.yandex\.ru"

    # Получите информацию о треках для текущего канала
    channel_track_inform = track_inform.get(ctx.channel.id, [])
    information = []
    if channel_track_inform != []:
        for x, url in enumerate(channel_track_inform):
            if re.search(youtube_regex, url):
                yt = YouTube(url)
                information.append(f'#{x+1}: {yt.title} - {yt.author}')
            elif re.search(yandex_regex, url):
                match = re.search(r'/album/(\d+)/track/(\d+)', url)

                if match:
                    album_id, track_id = match.groups()
                    formatted_string = f"{track_id}:{album_id}"

                    client = ClientAsync(TOKEN_YANDEX)
                    await client.init()

                    track = await client.tracks(formatted_string)

                    artists = []

                    for i in track[0].artists:
                        artists.append(i.name)
                    artist = ', '.join(artists)

                    del client
                    information.append(
                        f'#{x+1}: {track[0].title} - {artist}')
    else:
        information.append("Not track in list")

    return information

@bot.command()
async def interface(ctx):
    Button1 = Button(label="Vol: + 10", style=discord.ButtonStyle.blurple,
                     row=0)
    Button2 = Button(label='Vol: - 10', style=discord.ButtonStyle.blurple,
                     row=0)
    Button3 = Button(label="Vol: + 50", style=discord.ButtonStyle.blurple,
                     row=0)
    Button4 = Button(label='Vol: - 50', style=discord.ButtonStyle.blurple,
                     row=0)
    Button5 = Button(label='pause', style=discord.ButtonStyle.green,
                     emoji='⏸', row=1)
    Button7 = Button(label='next', style=discord.ButtonStyle.grey, row=1)
    Button6 = Button(label='clean', style=discord.ButtonStyle.red, row=1)

    async def volume_plus_10(interaction):
        voice_client = interaction.guild.voice_client
        if (voice_client.source.volume + 0.1) <= 2.0:
            x = voice_client.source.volume + 0.1
            voice_client.source.volume = round(x, 1)
            # await interaction.response.send_message(
            #     voice_client.source.volume * 100)

            text = await info(interaction)
            text = '\n'.join(text)
            text += f'\n\nVol: \
{int(ctx.guild.voice_client.source.volume * 100)}'

            await interaction.message.edit(
                embed=discord.Embed(
                    description=text, color=discord.Color.red()), view=view)
            await interaction.response.defer()

    async def volume_minus_10(interaction):
        voice_client = interaction.guild.voice_client
        if (voice_client.source.volume - 0.1) >= 0.0:
            x = voice_client.source.volume - 0.1
            voice_client.source.volume = round(x, 1)
            # await interaction.response.send_message(
            #     voice_client.source.volume * 100)

            text = await info(interaction)
            text = '\n'.join(text)
            text += f'\n\nVol: \
{int(ctx.guild.voice_client.source.volume * 100)}'

            await interaction.message.edit(
                embed=discord.Embed(
                    description=text, color=discord.Color.red()), view=view)
            await interaction.response.defer()

    async def volume_plus_50(interaction):
        voice_client = interaction.guild.voice_client
        if (voice_client.source.volume + 0.5) <= 2.0:
            x = voice_client.source.volume + 0.5
            voice_client.source.volume = round(x, 1)
            # await interaction.response.send_message(
            #     voice_client.source.volume * 100)

            text = await info(interaction)
            text = '\n'.join(text)
            text += f'\n\nVol: \
{int(ctx.guild.voice_client.source.volume * 100)}'

            await interaction.message.edit(
                embed=discord.Embed(
                    description=text, color=discord.Color.red()), view=view)
            await interaction.response.defer()

    async def volume_minus_50(interaction):
        voice_client = interaction.guild.voice_client
        if (voice_client.source.volume - 0.5) >= 0.0:
            x = voice_client.source.volume - 0.5
            voice_client.source.volume = round(x, 1)
            # await interaction.response.send_message(
            #     voice_client.source.volume * 100)

            text = await info(interaction)
            text = '\n'.join(text)
            text += f'\n\nVol: \
{int(ctx.guild.voice_client.source.volume * 100)}'

            await interaction.message.edit(
                embed=discord.Embed(
                    description=text, color=discord.Color.red()), view=view)
            await interaction.response.defer()

    async def pause(interaction):
        voice_client = interaction.guild.voice_client
        if interaction.message.components[1].children[0].emoji.name == '⏸':
            Button5 = Button(label='resume', style=discord.ButtonStyle.green,
                             emoji='▶', row=1)
            Button5.callback = pause

            view = View()
            view.add_item(Button3)
            view.add_item(Button1)
            view.add_item(Button2)
            view.add_item(Button4)
            view.add_item(Button5)
            view.add_item(Button7)
            view.add_item(Button6)

            await interaction.message.edit(view=view)
            if voice_client is None:
                await interaction.response.send_message(
                    "Я не подключен к голосовому каналу!")
                return
            if voice_client.is_playing():
                voice_client.pause()
                await interaction.response.defer()
        elif interaction.message.components[1].children[0].emoji.name == '▶':
            Button5 = Button(label='pause', style=discord.ButtonStyle.green,
                             emoji='⏸', row=1)
            Button5.callback = pause

            view = View()
            view.add_item(Button3)
            view.add_item(Button1)
            view.add_item(Button2)
            view.add_item(Button4)
            view.add_item(Button5)
            view.add_item(Button7)
            view.add_item(Button6)

            await interaction.message.edit(view=view)
            if voice_client is None:
                await interaction.response.send_message(
                    "Я не подключен к голосовому каналу!")
                return
            if voice_client.is_paused():
                voice_client.resume()
                await interaction.response.defer()

    async def next_track(interaction):
        voice_client = ctx.guild.voice_client
        if voice_client is not None:
            voice_client.stop()
            await interaction.response.defer()

    async def clean(interaction):
        global queue
        global track_inform
        queue = {}
        track_inform = {}
        text = await info(interaction)
        text = '\n'.join(text)
        text += f'\n\nVol: \
{int(ctx.guild.voice_client.source.volume * 100)}'

        await interaction.message.edit(
            embed=discord.Embed(
                description=text, color=discord.Color.red()), view=view)
        await interaction.response.defer()

    Button1.callback = volume_plus_10
    Button2.callback = volume_minus_10
    Button3.callback = volume_plus_50
    Button4.callback = volume_minus_50
    Button5.callback = pause
    Button7.callback = next_track
    Button6.callback = clean

    view = View()
    view.add_item(Button3)
    view.add_item(Button1)
    view.add_item(Button2)
    view.add_item(Button4)
    view.add_item(Button5)
    view.add_item(Button7)
    view.add_item(Button6)
    text = await info(ctx)
    text = '\n'.join(text)
    text += f'\n\nVol: {int(ctx.guild.voice_client.source.volume * 100)}'
    await ctx.send(embed=discord.Embed(
        description=text, color=discord.Color.red()), view=view)

'''
@bot.command()
async def test(ctx):
    # Создаем кнопку с emoji
    button = Button(style=discord.ButtonStyle.blurple, label='Нажми меня',
                    emoji='👍')

    # Создаем функцию обратного вызова для кнопки
    async def callback(interaction):
        # Заменяем emoji в сообщении
        button = Button(style=discord.ButtonStyle.blurple, label='Нажми меня',
                        emoji='✅')
        button.callback = callback
        view = View()
        view.add_item(button)
        await message.edit(view=view)
        await interaction.response.send_message('Ok')

    button.callback = callback

    # Отправляем сообщение с кнопкой
    view = View()
    view.add_item(button)
    message = await ctx.send("Привет, это тестовое сообщение", view=view)

@bot.command()
async def volume(ctx, volume: int):
    voice_client = ctx.guild.voice_client
    if voice_client is None:
        await ctx.send("Я не подключен к голосовому каналу!")
        return
    if voice_client.source is None:
        await ctx.send("Сейчас ничего не воспроизводится!")
        return

    volume = max(min(volume, 200), 0)  # ограничиваем громкость от 0 до 200
    volume = volume / 100
    voice_client.source.volume = volume
'''

@bot.command()
async def leave(ctx):
    voice_client = ctx.guild.voice_client
    if voice_client is None:
        await ctx.send("Я не подключен к голосовому каналу!")
        return
    await voice_client.disconnect()

bot.run(TOKEN)


import boto3

dynamodb = boto3.resource(
    'dynamodb',
    endpoint_url='http://localhost:18000',
    region_name='us-east-2',
    aws_access_key_id='ACCESS_ID',
    aws_secret_access_key='ACCESS_KEY'
)

table = dynamodb.Table('scores')

with table.batch_writer() as batch:
    batch.put_item(Item={"question_id": "q1",  "answer": "3", "score": 10})
    batch.put_item(Item={"question_id": "q2",  "answer": "1", "score": 20})
    batch.put_item(Item={"question_id": "q3",  "answer": "2", "score": 20})


import serial
import time
import requests

try:
    arduino=serial.Serial('COM3', 9600)
except:
    arduino = serial.Serial('/dev/ttyACM0', 9600)
time.sleep(2)
while 1:
    msg = arduino.readline()
    #print(msg.decode('utf-8'))
    string = msg.decode('utf-8')
    extract = string.split("\n")[0].strip()
    print(extract)
    data = {'rfid_id': extract}
    response = requests.put('http://127.0.0.1:5000/entry_exit', json=data)
    if response.status_code == 200:
        print(response.json())


"""Create an Evolution Profile from files in a directory."""

import datetime as dt
from pathlib import Path

import bgc_data_processing as bgc_dp

CONFIG_FOLDER = Path("config")

if __name__ == "__main__":
    config_filepath = CONFIG_FOLDER.joinpath(Path(__file__).stem)
    CONFIG = bgc_dp.parsers.ConfigParser(
        filepath=config_filepath.with_suffix(".toml"),
        dates_vars_keys=["DATE_MIN", "DATE_MAX"],
        dirs_vars_keys=["SAVING_DIR"],
        existing_directory="raise",
    )
    LOADING_DIR: Path = Path(CONFIG["LOADING_DIR"])
    VARIABLE: str = CONFIG["VARIABLE"]
    SHOW: bool = CONFIG["SHOW"]
    SAVE: bool = CONFIG["SAVE"]
    DATE_MIN: dt.datetime = CONFIG["DATE_MIN"]
    DATE_MAX: dt.datetime = CONFIG["DATE_MAX"]
    LATITUDE_MIN: int | float = CONFIG["LATITUDE_MIN"]
    LATITUDE_MAX: int | float = CONFIG["LATITUDE_MAX"]
    LONGITUDE_MIN: int | float = CONFIG["LONGITUDE_MIN"]
    LONGITUDE_MAX: int | float = CONFIG["LONGITUDE_MAX"]
    DEPTH_MIN: int | float = CONFIG["DEPTH_MIN"]
    DEPTH_MAX: int | float = CONFIG["DEPTH_MAX"]
    INTERVAL: str = CONFIG["INTERVAL"]
    CUSTOM_INTERVAL: int = CONFIG["CUSTOM_INTERVAL"]
    DEPTH_INTERVAL: int = CONFIG["DEPTH_INTERVAL"]
    PRIORITY: list[str] = CONFIG["PRIORITY"]
    EXPOCODES_TO_LOAD: list[str] = CONFIG["EXPOCODES_TO_LOAD"]
    VERBOSE: int = CONFIG["VERBOSE"]
    bgc_dp.set_verbose_level(VERBOSE)

    storer = bgc_dp.io.read_files(
        filepath=list(LOADING_DIR.glob("*.txt")),
        providers_column_label=bgc_dp.defaults.VARS["provider"].label,
        expocode_column_label=bgc_dp.defaults.VARS["expocode"].label,
        date_column_label=bgc_dp.defaults.VARS["date"].label,
        year_column_label=bgc_dp.defaults.VARS["year"].label,
        month_column_label=bgc_dp.defaults.VARS["month"].label,
        day_column_label=bgc_dp.defaults.VARS["day"].label,
        hour_column_label=bgc_dp.defaults.VARS["hour"].label,
        latitude_column_label=bgc_dp.defaults.VARS["latitude"].label,
        longitude_column_label=bgc_dp.defaults.VARS["longitude"].label,
        depth_column_label=bgc_dp.defaults.VARS["depth"].label,
        variables_reference=bgc_dp.defaults.VARS.to_list(),
        category="in_situ",
        unit_row_index=1,
        delim_whitespace=True,
    )
    storer.remove_duplicates(PRIORITY)
    variables = storer.variables
    constraints = bgc_dp.Constraints()
    constraints.add_superset_constraint(
        field_label=variables.get(variables.expocode_var_name).label,
        values_superset=EXPOCODES_TO_LOAD,
    )
    constraints.add_boundary_constraint(
        field_label=variables.get(variables.date_var_name).label,
        minimal_value=DATE_MIN,
        maximal_value=DATE_MAX,
    )
    constraints.add_boundary_constraint(
        field_label=variables.get(variables.latitude_var_name).label,
        minimal_value=LATITUDE_MIN,
        maximal_value=LATITUDE_MAX,
    )
    constraints.add_boundary_constraint(
        field_label=variables.get(variables.longitude_var_name).label,
        minimal_value=LONGITUDE_MIN,
        maximal_value=LONGITUDE_MAX,
    )
    constraints.add_boundary_constraint(
        field_label=variables.get(variables.depth_var_name).label,
        minimal_value=DEPTH_MIN,
        maximal_value=DEPTH_MAX,
    )
    profile = bgc_dp.tracers.EvolutionProfile(storer, constraints=constraints)
    profile.set_date_intervals(INTERVAL, CUSTOM_INTERVAL)
    profile.set_depth_interval(DEPTH_INTERVAL)
    if SHOW:
        profile.show(VARIABLE)
    if SAVE:
        date_min_str = DATE_MIN.strftime("%Y%m%d")
        date_max_str = DATE_MAX.strftime("%Y%m%d")
        save_name = f"profile_{VARIABLE}_{date_min_str}_{date_max_str}.png"
        profile.save(
            save_path=f"{CONFIG['SAVING_DIR']}/{save_name}",
            variable_name=VARIABLE,
        )


from flask import Flask
from flask import jsonify, make_response

app = Flask(__name__)

@app.route('/')
def hello_world():
    message = {
        'note': 'test cronjob * * * * *',
    }
    value = {

        'full_name': "Yulyano Thomas Djaya",
        'nick_name': "Lino",
        'last_education': "Gunadarma University",
        'location': "Bogor",
        'last edit': "First day: Intern"
    }
    res = {
        'msg': message,
        'value': value
    }
    return make_response(jsonify(res)), 200

@app.route('/hello/<name>')
def hello_name(name):
    return 'Hello %s!' % name

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


#!/usr/bin/env python
import csv
import argparse
import subprocess as sp
import os
import os.path
import sys
import re
from collections import namedtuple
from textwrap import dedent
from numbers import Number

from itertools import product

import numpy as np
import pandas as pd
from numpy import array
from scipy.optimize import curve_fit

helpText="""\
Convert mapDamage output into parameters of a function which returs
the per-base probability that it is subjected to a certain base exchange.
The parameters 'factor', 'geom_prob' and 'intercept' are estimated,
which relate to the following function:

    P_from(i, end, to) = factor x geom(i, geom_prob) + intercept

P is the probability that the base on position i, as counted 1-based from
the read end 'end' (end = 3' or 5') is subjected to the base exchange
'from' -> 'to' (where 'from' and 'to' may be A,T,G or C). 'geom' is the
geometric distribution density function with support {1,2,3...} and
probability parameter 'geom_prob'.

The input is the 'misincorporation.txt' file which is produced by the
mapDamage program (Jonsson et al. Bioinformatics 2013 and Ginolhac et
al. Bioinformatics 2011). Least-squares fitting is used to determine
the parameters of the aforementioned function.

The parameters are printed in a text table for each combination of
read end, mutation origin and target base.
"""

# Are we using Python3?
PYTHON3 = sys.version_info >= (3,0)

DIST_FIT_R_SCRIPT = os.path.dirname(
                    os.path.realpath(
                        sys.argv[0])  ) \
                    + "/../fit_geom"

GeomPars = namedtuple("GeomPar",
            ['factor', 'geom_prob', 'intercept' ])

mapDamageHeaders = ['strand', 'from', 'to']

def main():
    aparser=create_argument_parser()
    args=aparser.parse_args()

    # List of files to process
    mdfiles=args.mdfiles

    M = readMisincorporationTxt(mdfiles)
    M.drop(['Chr','Std'],axis=1,inplace=True)
    M = M.groupby(['End','Pos'])
    A = M.aggregate(np.sum)
    A = A.ix[A.Total != 0,:]

    # Calculate per-base substitution rates
    for f,t in product('ATCG','ATCG'):
        if f == t: continue
        A[f+'>'+t] = A[f+'>'+t] / A[f]

    A = A.iloc[A.index.get_level_values('Pos') <= args.n_bp,]

    results = processMapDamageFile(A)

    # Make sure that only one intercept value is reported for each
    # base exchange. There may be two, derived from 3' and 5' read
    # ends, respectively. Assign the mean to one of the output lines
    # for that base exchange and set the value in the other output
    # line to NA.
    nIntercepts = results.groupby(['from','to']).size()
    for f,t in nIntercepts.index.tolist():
        if nIntercepts.loc[f,t] > 1:
            #import pdb;pdb.set_trace()
            i = np.flatnonzero((results['from'] == f) & (results['to'] == t))
            m = np.mean(results.loc[i,'intercept'])
            results.loc[i,'intercept']    = np.nan
            results.loc[i[0],'intercept'] = m

    # Print output
    float_format="%.{}g".format(args.print_digits)
    print(results.to_csv(sep="\t",index=False,na_rep="NA",float_format=float_format), end="")

    # Create Plot folder
    plot_filename = args.fit_plots

    if plot_filename != None:
        plotFitResult(A, results, plot_filename)

def processMapDamageFile(A,readMetadataFrom="filename"
                       , plotFilename=None):
    """ Open a file, read base exchange and strand direction,
    read probability values, fit a function and print the parameters."""

    nRows = 2*4*3 # 2 strand ends, 4*3 base combinations
    pars = pd.DataFrame( index = np.arange(0, nRows)
                       , columns=[*mapDamageHeaders, *GeomPars._fields]
                       )
    # Convert the parameter columns to numeric dtype to facilitate
    # pretty printing of floats
    pars.factor = pd.to_numeric(pars.factor)
    pars.geom_prob = pd.to_numeric(pars.geom_prob)
    pars.intercept = pd.to_numeric(pars.intercept)

    iRow = 0

    for e in ['3p','5p']:
        A2 = A.xs(e,level='End')
        for (f,t) in product('ACGT','ACGT'):

            A2 = A.xs(e,level='End')
            if f == t: continue
            par = fitScalableGeom(np.array(A2.index), A2[f+'>'+t])
            pars.loc[iRow] = [e,f,t,*par]
            iRow = iRow + 1

    return pars

def readMisincorporationTxt(filename):
    """Convert the 'misincorporation.txt' file, as output by
    mapDamage, to a numpy array"""
    sep = "\t"
    with open(filename,'r') as fd:
        while True:
            line = fd.readline()
            if not line.startswith('#'): break
        header = line.split(sep)

        d = {k:'int' for k in header}
        for k in ['Chr','End','Std']: d[k] = 'str'
        M = pd.read_table(fd,names=header
                         , delimiter=sep
                         , dtype=d
                         )
    return M

def plotFitResult(probabilities, fit_parameters,filename, imgFormat='png'):
    """Plot the fit versus the data (mutation probabilities per base
    type and base position.

    Parameters:
        probabilities:
            Data frame containing the mutation probabilities per base
            position and base exchange

            index columns: End (5' or 3' read end),
                           Pos (bp distance from respective end)
            columns:       A>C, A>T, A>G, C>A, C>G, ...
                           which denote the respective base substitutions
        fit_parameters:
            Data frame containing parameters of geometric
            distributions modelling the base substitution probability
            per base substitution type and position

            columns: strand (3p or 5p)
                     from   (substitution origin base)
                     to     (substitution target base)
                     factor, geom_prob, intercept
                            (parameters of the
                             geometric distribution which models the
                             respective substitution probability)
        filename:
            String which contains the file name of the plot to be
            created.
        imgFormat (png [default] | pdf | show):
            png:  Output a PNG file.
            pdf:  Output a PDF file.
            show: Show the plot on screen.
    """

    try:
        import matplotlib
        if imgFormat == 'png':
            matplotlib.use('Agg')
        elif imgFormat == 'pdf':
            matplotlib.use('PDF')
        elif imgFormat == 'show':
            pass
        else:
            raise ValueError("imgFormat must be png or pdf")

        import matplotlib.pyplot as plt

    except ImportError:
        raise ImportError("The python package matplotlib is not "+
            "installed but is required for plotting")

    nEnds = 2  # 3' and 5' end of DNA short read
    bases = 'ATCG'

    ylim = max(max(probabilities[a+">"+b]) for (a,b) in product(bases,bases) if a!=b)

    fig, ax = plt.subplots(len(bases),len(bases)*nEnds,sharex=False, sharey=True)
    fig.subplots_adjust(left=0.13, bottom=0.13, right=0.9, top=0.85,
            wspace=0.2, hspace=0.1)
    fig.set_size_inches(8,5)

    fit_parameters.set_index(['from','to','strand'],inplace=True)

    for (iF,f),(iT,t) in product(enumerate(bases),enumerate(bases)):

        for iEnd, (sign,e) in enumerate(zip([1,-1],['5p','3p'])):
            cAx = ax[iT, iF*2+iEnd] # cAx is used outside the for loop!
            cPos = cAx.get_position()
            cWidth = cPos.width

            # No plots on diagonal
            if f == t:
                fig.delaxes(cAx)
                continue

            cPos.x0 = cPos.x0 + 0.05*cPos.width*sign
            cPos.x1 = cPos.x0 + cWidth

            cAx.set_position(cPos)

            p = probabilities.xs([e],level=['End'])[f+'>'+t]
            x = np.array(p.index.get_level_values('Pos'))

            pars = fit_parameters.loc[f,t,e].to_dict()

            # If no intercept is specified for this end, take the
            # intercept parameter from the other end.
            if np.isnan(pars['intercept']):
                otherend = next(iter(set(['5p','3p']) - set([e])))
                pars['intercept'] = fit_parameters.loc[(f,t,otherend),'intercept']

            y_fun = scalableGeom( first_success  = x
                                , p_success      = pars["geom_prob"]
                                , factor         = pars["factor"]
                                , added_constant = pars["intercept"]
                                )

            cAx.plot(sign*x, p, 'ok', ms=2)
            cAx.plot(sign*x, y_fun, "b-")
            cAx.set_ylim([0, ylim])
            for tck in cAx.get_xticklabels(): tck.set_rotation(45)

            # Only show x tick labels for the plots at the bottom end
            # of the figure
            if (iT,iF) not in [(3,0), (3,1), (3,2), (2,3)]:
                cAx.set_xticklabels([])

    xmin = min(a.get_position().xmin for a in ax.flat)
    ymin = min(a.get_position().ymin for a in ax.flat)
    xmax = max(a.get_position().xmax for a in ax.flat)
    ymax = max(a.get_position().ymax for a in ax.flat)

    # Print the bases at the outer plot margins
    for i,b in enumerate(bases):
        # A,T,C,G label offsets and spreads
        ttop, ftop = 0.21, 0.2    # top labels ("from")
        trgt, frgt = 0.24, 0.195  # right labels ("to")
        # Mutation from:
        figText(fig, b , i*ftop+ttop, 0.9   , va='bottom')
        # Mutation to:
        figText(fig, b , 0.92 , 1-(i*frgt+trgt) , ha='left')

    # Print the other outer plot margin annotations
    figText(fig, "from", 0.5, 0.95)
    figText(fig, "to"  , 0.97,0.5, rotation=90)
    figText(fig, "mutation probability"  , 0.03,0.5, rotation=90)
    figText(fig, "Base pairs"  , 0.5,0.01, va='bottom')

    # Print the markers for 5' and 3' end
    ax[1,0].annotate( "5' end", xy=(0,1), xytext=(0,20)
                    , xycoords=('axes fraction', 'axes fraction')
                    , arrowprops = dict(arrowstyle='-'
                          , connectionstyle="angle,angleA=45,angleB=90"
                    )
                    , textcoords = 'offset points')
    ax[1,1].annotate( "3' end", xy=(1,1), xytext=(-30,20)
                    , xycoords=('axes fraction', 'axes fraction')
                    , arrowprops = dict(arrowstyle='-'
                          , connectionstyle="angle,angleA=-45,angleB=90"
                    )
                    , textcoords = 'offset points')

    if imgFormat == 'show':
        plt.show()
    elif imgFormat == 'png':
        plt.savefig(filename, format='png', dpi=300)
    elif imgFormat == 'pdf':
        plt.savefig(filename, format='pdf')

def figText(fig, text, x, y
           , coord='figure fraction',ha='center',va='center'
           , **kwargs):
    cAx = fig.axes[0]
    cAx.annotate(text
                , xy=(x, y)
                , xycoords='figure fraction'
                , size=14
                , ha=ha, va=va
                , **kwargs)

def geom(xs, p):
    """Geometric probability mass function. x=number of desired
    Bernoulli trials, p=Success probability of a single Bernoulli
    trial. Returns: Probability that the x's trial is the first
    success"""
    if any(xs<1) or p<0 or p>1: raise ValueError('function not defined')
    return ((1-p)**(xs-1)) * p

def scalableGeom(first_success,p_success,factor=1,added_constant=0):
    """Geometric probability mass function which can be scaled by
    a factor and moved up and down the dependent variables axis by
    adding a constant."""
    return factor * geom(first_success,p_success) + added_constant

def fitScalableGeom(pos,probabilities):
    pars, cov = curve_fit(scalableGeom, pos, probabilities,
            p0 = array([1e-1,0,0]),
            bounds=(array([1e-1,0,0]),array([1,np.inf,np.inf])))

    # pars holds values in the same order as in the signature of
    # fitScalableGeom
    return GeomPars(geom_prob=pars[0], factor=pars[1],
            intercept=pars[2])

# This function cannot be used due to a possible bug in mapDamage?
# The first line of mapDamage files doesn't reflect the direction
# of the read properly. 3' to 5' reads should (in my opinion) have
# a first line of 'pos 3pG>A' (if A is mutated to G) but has
# 'pos 5pG>A'. 5' to 3' reads have also a first line of
# 'pos 5pC>T' (if C is mutated to T). Therefore, direction is not
# inferrable from the first line. ~~~Moritz Lell, 8-May-2015
def parseFirstLine(line):
    """ Gets information about strand direction and which base to
    exchange for which base out of the first line of a mapDamage
    output. This function suffers from a bug due to mapDamage
    incorrectly reporting the read direction as always being 5'>3'."""
    p = re.compile("^pos[\t ]([35])p([ATGC])>([ATGC])")
    m = p.match(line)
    if m == None:
        raise ValueError(
        ("The line {} is not a proper mapDamage header! "+
         "An Example for a proper format: 'pos 5pG>A'").format(line))

    return(MapDamageHeader( strand   = m.group(1)
                          , fromBase = m.group(2)
                          , toBase   = m.group(3)))

def parseFileName(filename):
    """Parses a filename of the form [3|5]p[ATGC]to[ATGC]_freq.txt
    to infer read direction and exchanged bases. This method is a
    workaround for a possible bug in mapDamage that doesn't report the
    read direction correctly in the header line of its output"""
    #Only use basename, strip all directories in the path
    basename = os.path.basename(filename)
    # Expected filename format
    p = re.compile(".*([35])p([ATGC])to([ATCG])_freq\.txt$")
    m = p.match(basename)
    # Filename is not of expected format
    if m == None:
        raise ValueError(
        ("The file name {} is not in proper format! "+
         "An Example for a proper format:"+
         "'5pGtoA_freq.txt'").format(basename))

    return(MapDamageHeader( strand    = m.group(1)
                          , fromBase  = m.group(2)
                          , toBase    = m.group(3)))

def create_argument_parser():
    aparser=argparse.ArgumentParser(description=helpText
                       , formatter_class=argparse.RawTextHelpFormatter)
    aparser.add_argument("mdfiles"
        , metavar="misincorporation.txt", help=
    """`misincorporation.txt` output file of mapDamage""")

    aparser.add_argument("--fit-plots", default=None
        , metavar="FILENAME", help=dedent(
    """If this switch is given, data vs. fitted plots are created.
    The file name of the plot is expected as an argument"""))

    aparser.add_argument("--n-bp", default=20, type=int
            , metavar="N", help=dedent("""\
    The number of base pairs from the respective read end (3' or
    5') to use for fitting. Too high values might lead to higher noise
    in the mutation probabilities due to few reads bein so long, too
    low values limit the amount of data points available for fitting.
    If in doubt, create plots using `--fit-plots` and check whether the
    mutation probabilities look sensible."""))

    aparser.add_argument('--print-digits', default=4, type=int
        , metavar="N", help=dedent("""\
    The number of digits after the decimal dot to print."""))

    aparser.add_argument('--min-gp', default=0.1, type=float
        , metavar="N" , help=dedent("""\
    [default: 0.1] The minimum value which may be estimated for
    'geom_prob'. This is to avoid high values of 'factor' if no
    elevated mutation probability near the read ends is visible.

    A position-independent mutation rate shall be modelled by the
    estimating the 'intercept' parameter with this script. However, if
    the parameter 'geom_prob' becomes small, position-independent
    mutation rate can also be modelled by the 'factor' parameter.   If
    the provided mapDamage data indicates no elevated damage near the
    read end, prohibiting very small values for geom_prob will force
    the 'factor' parameter to be estimated very small, so that the
    mutation rate of the data is solely estimated by the 'intercept'
    value.

    Increase this value if the result estimates 'intercept' lower than
    the mutation baseline visible in the plot, together with a
    non-negligible value for 'factor' and a small 'geom_prob'.
    Decrease this value if the fitted mutation probability (blue line in plot)
    decreases too steep compared to its data (black dots) and
    geom_prob is estimated near the value set here."""))

    return aparser

if __name__=="__main__": main()

# vim: tw=70


import os
import random
import argparse
from string import punctuation

from tqdm import tqdm

import sentencepiece
import torchaudio
import textgrids

import numpy as np
import torch as th

from WACO.prepare_data.data_utils import load_df_from_tsv, save_df_to_tsv

parser = argparse.ArgumentParser()
parser.add_argument('--data-root', type=str)
parser.add_argument('--lang', type=str)
args = parser.parse_args()

root = args.root
lang = args.lang

spm = sentencepiece.SentencePieceProcessor()
spm.Load(os.path.join(root, 'spm_unigram10000_st.model'))
train_df = load_df_from_tsv(os.path.join(root, 'train_st.tsv'))

save_dir = os.path.join(root, 'en-{}'.format(lang), 'data', 'train', 'align')
os.makedirs(save_dir, exist_ok=True)

sentences = train_df['src_text'].tolist()

def covered(s, punctuation):
    for c in s:
        if c not in punctuation:
            return False
    return True

space = '▁'
tokenized_sentences = []
segmentss = []
punctuation = punctuation + '—’'
for sent in tqdm(train_df['src_text'].tolist()):
    tokens = spm.EncodeAsPieces(sent)
    segments = []
    last = -1
    for idx, token in enumerate(tokens):
        if token.startswith(space) or covered(token, punctuation):
            if last != -1 and last <= idx - 1:
                segments.append((last, idx - 1))
            last = idx + (token == space or covered(token, punctuation) or \
                (token.startswith(space) and len(token) > 1 and covered(token[1:], punctuation)))

    if last < len(tokens):
        segments.append((last, len(tokens) - 1))

    tokenized_sentence = []
    for seg in segments:
        token = ''.join(tokens[seg[0] : seg[1] + 1]).replace(space, '')
        if token.replace(',', '').isnumeric():
            token = token.replace(',', '')
        tokenized_sentence.append(token)

    tokenized_sentences.append(tokenized_sentence)
    segmentss.append(segments)

filtered_grids = []
n_outlier = 0
for i, id in enumerate(tqdm(train_df['id'])):
    grid_path = os.path.join(save_dir, 'textgrids/{}.TextGrid'.format(id))
    if os.path.exists(grid_path):
        grid = textgrids.TextGrid(grid_path)
        filtered_grid = [tok for tok in grid['words'] if tok.text != '']

        if len(filtered_grid) != len(tokenized_sentences[i]):
            print(i, [w.text for w in filtered_grid], tokenized_sentences[i], sep='\n')
            n_outlier += 1
            continue

        interval = np.array([(word.xmin, word.xmax) for word in filtered_grid])
        audio_path = os.path.join(save_dir, '{}.wav'.format(id))
        info = torchaudio.info(audio_path)
        duration = info.num_frames / info.sample_rate
        interval = interval / duration

        th.save([segmentss[i], interval], os.path.join(save_dir, '{}.pt'.format(id)))


import os

import numpy as np
import tensorflow as tf
import torch

from lolip.variables import get_file_name

def set_random_seed(auto_var):
    random_seed = auto_var.get_var("random_seed")

    torch.manual_seed(random_seed)
    tf.random.set_seed(random_seed)
    np.random.seed(random_seed)

    random_state = np.random.RandomState(auto_var.get_var("random_seed"))
    auto_var.set_intermidiate_variable("random_state", random_state)

    return random_state

def load_model(auto_var, trnX, trny, tstX, tsty, n_channels, model_dir="./models", device=None):
    model = auto_var.get_var("model", trnX=trnX, trny=trny, n_channels=n_channels, device=device)
    if tstX is not None and tsty is not None:
        model.tst_ds = (tstX, tsty)
    model_path = get_file_name(auto_var).split("-")
    model_path[0] = 'pgd'
    model_path = '-'.join(model_path)
    if os.path.exists(os.path.join(model_dir, model_path + '-ep%04d.pt') % model.epochs):
        model_path = os.path.join(model_dir, model_path + '-ep%04d.pt') % model.epochs
    else:
        model_path = os.path.join(model_dir, model_path + '.pt')

    model.load(model_path)
    model.model.cuda()
    return model_path, model


from urllib.request import urlopen, Request
import base64
from randmac import RandMac

def change_mac():
    new_mac = str(RandMac("00-00-00-00-00-00")).upper()[1:-1]
    req_str = f'http://192.168.1.1/userRpm/MacCloneCfgRpm.htm?mac1={new_mac}&wan=1&Save=%D0%A1%D0%BE%D1%85%D1%80%D0%B0%D0%BD%D0%B8%D1%82%D1%8C'
    req = Request(req_str)
    req.add_header('Authorization', ('Basic %s' % base64.b64encode('olexandr:routersettings'.encode('ascii')).decode('ascii')))
    req.add_header('Referer', 'http://192.168.1.1')
    urlopen(req)

def reboot():
    req = Request('http://192.168.1.1/userRpm/SysRebootRpm.htm?Reboot=Reboot')
    req.add_header('Authorization', ('Basic %s' % base64.b64encode('olexandr:routersettings'.encode('ascii')).decode('ascii')))
    req.add_header('Referer', 'http://192.168.1.1')
    urlopen(req)

def main():
    change_mac()
    reboot()

if __name__ == "__main__":
    main()


import pytest
from selenium import webdriver
from selenium.webdriver.support.wait import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.common.by import By
import re

@pytest.fixture
def driver(request):
    wd = webdriver.Chrome()
    request.addfinalizer(wd.quit)
    return wd

def test_geo_zones_order(driver):
    driver.implicitly_wait(10)
    driver.get('http://localhost/litecart/admin/?app=geo_zones&doc=geo_zones')
    driver.find_element_by_name("username").send_keys("admin")
    driver.find_element_by_name("password").send_keys("admin")
    driver.find_element_by_css_selector('button[name="login"]').click()

    # ждем появления кнопок после всех стран. Для гарантии, что все страны загрузились
    WebDriverWait(driver,10).until(EC.presence_of_element_located((By.CSS_SELECTOR, "table.table tfoot")))

    # находим все строки таблицы
    rows = driver.find_elements_by_css_selector("table.table tbody tr")

    # иницализируем список ссылок за пределами цикла for
    countries_links = []

    for row in rows:
        country_link = row.find_element_by_css_selector("a:not([title=Edit])")
        countries_links.append(country_link.get_attribute("href"))

    # печатать будем с новой строки
    print()

    # для каждой страны
    for country_link in countries_links:
        # Печатаем ссылку
        print (country_link)
        driver.get(country_link)  # загружаем страницу с зонами каждой такой страны по сохраненным ранее ссылкам
        # ждем появления кнопки "Add zone" после списка зон. Для гарантии, что все зоны загрузились
        WebDriverWait(driver,10).until(EC.presence_of_element_located((By.CSS_SELECTOR, "a.add")))

        zones = driver.find_elements_by_css_selector("table.table tbody tr td:nth-child(3)")  # 3-я колонка в таблице
        for i in range(0, len(zones)-1):
            zone_name = zones[i].get_attribute("textContent")
            next_zone_name = zones[i+1].get_attribute("textContent")
            print (zone_name)  # Печатаем название зоны
            if zone_name > next_zone_name:
                raise Exception("Зоны стоят не по порядку")
            if zone_name == next_zone_name:
                raise Exception("Две одинаковых зоны подряд")
        # Печатаем название последней зоны
        zone_name = zones[len(zones)-1].get_attribute("textContent")
        print (zone_name)


#!/usr/bin/python3
'''
@File : wheelpaintwidget.py

@Time : 2020/6/8

@Author : Boholder

@Function : Paint given emotion's position on emotion wheel picture,
            then display it in a widget.
'''

import sys

from PyQt5 import QtGui
from PyQt5.QtCore import pyqtSignal
from PyQt5.QtGui import QPixmap, QPainter
from PyQt5.QtWidgets import (QApplication, QWidget)

import jellygolem.jg_emotion.emotionwheelprocess as emotionproc

_RESOURCE_PATH = '../resource/'
_WHEEL_PIC_PATH = _RESOURCE_PATH + 'emotion-wheel.png'
_HEART_PIC_PATH = _RESOURCE_PATH + 'heart.png'

class WheelPaintWidget(QWidget):
    value_changed_signal = pyqtSignal(float)

    def __init__(self, emotion: tuple = (0, 0), *args,
                 **kwargs):
        super(WheelPaintWidget, self).__init__(*args, **kwargs)

        self.emotion = emotion
        self.wheel_pixmap = QPixmap(_WHEEL_PIC_PATH)
        self.heart_pixmap = QPixmap(_HEART_PIC_PATH)
        # if not so, when use this widget, it has no default space to show.
        self.setMinimumSize(self.wheel_pixmap.size())

    def paintEvent(self, event: QtGui.QPaintEvent):
        super(WheelPaintWidget, self).paintEvent(event)
        self.setGeometry(self.geometry().x(), self.geometry().y(), 650, 650)
        (x, y) = emotionproc.calc_paint_position(*self.emotion)
        painter = QPainter(self)
        painter.drawPixmap(self.rect(), self.wheel_pixmap)
        painter.drawPixmap(x, y, 16, 16, self.heart_pixmap)

    def repaint_wheel(self, emotion: tuple):
        self.emotion = emotion
        self.repaint()

# if __name__ == '__main__':
#     app = QApplication([])
#     ex = WheelPaintWidget()
#     ex.show()
#     sys.exit(app.exec_())


import logging
import unittest

import torch

from openspeech.criterion import Perplexity, PerplexityLossConfigs
from openspeech.lm.transformer_lm import TransformerForLanguageModel
from openspeech.tokenizers.ksponspeech.character import KsponSpeechCharacterTokenizer
from openspeech.utils import DUMMY_INPUT_LENGTHS, DUMMY_LM_INPUTS, DUMMY_TARGETS, build_dummy_configs

logger = logging.getLogger(__name__)

class TestTransformerForLanguageModel(unittest.TestCase):
    def test_forward(self):
        configs = build_dummy_configs(
            criterion_configs=PerplexityLossConfigs(),
        )
        vocab = KsponSpeechCharacterTokenizer(configs)

        model = TransformerForLanguageModel(
            num_classes=4,
            max_length=32,
            d_model=64,
            num_attention_heads=4,
            d_ff=128,
            pad_id=0,
            sos_id=1,
            eos_id=2,
            num_layers=3,
        )

        criterion = Perplexity(configs, vocab)
        optimizer = torch.optim.Adam(model.parameters(), lr=1e-04)

        for i in range(3):
            logits = model(DUMMY_LM_INPUTS, DUMMY_INPUT_LENGTHS)

            loss = criterion(logits, DUMMY_TARGETS)
            loss.backward()
            optimizer.step()
            assert type(loss.item()) == float

    def test_forward_step(self):
        configs = build_dummy_configs(
            criterion_configs=PerplexityLossConfigs(),
        )
        vocab = KsponSpeechCharacterTokenizer(configs)

        model = TransformerForLanguageModel(
            num_classes=4,
            max_length=32,
            d_model=64,
            num_attention_heads=4,
            d_ff=128,
            pad_id=0,
            sos_id=1,
            eos_id=2,
            num_layers=3,
        )

        criterion = Perplexity(configs, vocab)
        optimizer = torch.optim.Adam(model.parameters(), lr=1e-04)

        for i in range(1, 4):
            input_lengths = torch.IntTensor([i] * 3)
            logits = model.forward_step(DUMMY_LM_INPUTS[:i], input_lengths)
            loss = criterion(logits, DUMMY_TARGETS[:i])
            loss.backward()
            optimizer.step()
            assert type(loss.item()) == float

if __name__ == "__main__":
    unittest.main()


from pydoc import cli
from PyQt5 import QtCore, QtGui, QtWidgets
from PyQt5.QtWidgets import QApplication, QWidget, QTreeView, QFileSystemModel, QVBoxLayout
from PyQt5.QtCore import QModelIndex
import qrc
import sqlite3
import json

class MainDashboard(object):
    def setupUi(self, MainWindow, app):
        MainWindow.setObjectName("MainWindow")
        MainWindow.resize(867, 566)
        MainWindow.setStyleSheet("background-color: rgb(85, 85, 85);")
        self.centralwidget = QtWidgets.QWidget(MainWindow)
        self.centralwidget.setObjectName("centralwidget")

        #Current Project / Title
        self.Title = QtWidgets.QFrame(self.centralwidget)
        self.Title.setGeometry(QtCore.QRect(10, 10, 842, 40))
        self.Title.setStyleSheet("background-color: rgb(0, 153, 255);\n"
                                            "border-style: solid;\n"
                                            "border-color: rgb(43, 43, 43);\n"
                                            "border-width: 4px;\n"
                                            "border-radius: 20px;")
        self.Title.setFrameShape(QtWidgets.QFrame.StyledPanel)
        self.Title.setFrameShadow(QtWidgets.QFrame.Raised)
        self.Title.setObjectName("Title")

        #Title -CurrentProject
        self.CurrentProject = QtWidgets.QLabel(self.Title)
        self.CurrentProject.setGeometry(QtCore.QRect(1, 0, 842, 40))
        font = QtGui.QFont()
        font.setPointSize(12)
        self.CurrentProject.setFont(font)
        self.CurrentProject.setAlignment(QtCore.Qt.AlignCenter)
        self.CurrentProject.setObjectName("CurrentProject")

        #Left Frame
        self.LeftFrame_todo = QtWidgets.QFrame(self.centralwidget)
        self.LeftFrame_todo.setGeometry(QtCore.QRect(10, 60, 411, 491))
        self.LeftFrame_todo.setStyleSheet("background-color: rgb(43, 43, 43);\n"
                                            "border-style: solid;\n"
                                            "border-color: rgb(43, 43, 43);\n"
                                            "border-width: 2px;\n"
                                            "border-radius: 40px;")
        self.LeftFrame_todo.setFrameShape(QtWidgets.QFrame.StyledPanel)
        self.LeftFrame_todo.setFrameShadow(QtWidgets.QFrame.Raised)
        self.LeftFrame_todo.setObjectName("LeftFrame_todo")

        #Left Frame -list
        self.listWidget = QtWidgets.QListWidget(self.LeftFrame_todo)
        self.listWidget.setGeometry(QtCore.QRect(40, 141, 331, 331))
        self.listWidget.setStyleSheet("background-color: rgb(0, 153, 255);\n"
                                        "border-style: solid;\n"
                                        "border-color: rgb(0, 153, 255);\n"
                                        "border-width: 2px;\n"
                                        "border-radius: 20px;\n")
        self.listWidget.setObjectName("listWidget")\

        #Left Frame -FrameLabel
        self.FrameLabel = QtWidgets.QFrame(self.LeftFrame_todo)
        self.FrameLabel.setGeometry(QtCore.QRect(20, 15, 371, 26))
        self.FrameLabel.setStyleSheet("background-color: rgb(0, 153, 255);\n"
                                        "border-style: solid;\n"
                                        "border-color: rgb(0, 153, 255);\n"
                                        "border-width: 2px;\n"
                                        "border-radius: 10px;")
        self.FrameLabel.setFrameShape(QtWidgets.QFrame.StyledPanel)
        self.FrameLabel.setFrameShadow(QtWidgets.QFrame.Raised)
        self.FrameLabel.setObjectName("FrameLabel")

        #Left Frame -FrameLabel -title
        self.label = QtWidgets.QLabel(self.FrameLabel)
        self.label.setGeometry(QtCore.QRect(1, 0, 371, 26))
        font = QtGui.QFont()
        font.setPointSize(12)
        self.label.setFont(font)
        self.label.setAlignment(QtCore.Qt.AlignCenter)
        self.label.setObjectName("label")

        #Left Frame -ItemLineEdit
        self.ItemLineEdit = QtWidgets.QLineEdit(self.LeftFrame_todo)
        self.ItemLineEdit.setGeometry(QtCore.QRect(40, 60, 331, 30))
        self.ItemLineEdit.setStyleSheet("background-color: rgb(0, 153, 255);\n"
                                        "border-style: solid;\n"
                                        "border-color: rgb(0, 153, 255);\n"
                                        "border-width: 2px;\n"
                                        "border-radius: 8px;")
        self.ItemLineEdit.setObjectName("ItemLineEdit")

        #Left Frame -AddButton
        self.AddItem = QtWidgets.QPushButton(self.LeftFrame_todo)
        self.AddItem.setGeometry(QtCore.QRect(40, 105, 90, 23))
        self.AddItem.setStyleSheet("background-color: rgb(0, 153, 255);\n"
                                    "border-style: solid;\n"
                                    "border-color: rgb(0, 153, 255);\n"
                                    "border-width: 2px;\n"
                                    "border-radius: 8px;")
        self.AddItem.setObjectName("AddItem")
        self.AddItem.clicked.connect(self.AddItemEvent)

        #Left Frame -DeleteButton
        self.DeleteItem = QtWidgets.QPushButton(self.LeftFrame_todo)
        self.DeleteItem.setGeometry(QtCore.QRect(161, 105, 90, 23))
        self.DeleteItem.setStyleSheet("background-color: rgb(0, 153, 255);\n"
                                        "border-style: solid;\n"
                                        "border-color: rgb(0, 153, 255);\n"
                                        "border-width: 2px;\n"
                                        "border-radius: 8px;")
        self.DeleteItem.setObjectName("DeleteItem")
        self.DeleteItem.clicked.connect(self.DeleteItemEvent)

        #Left FRame -ClearAllButton
        self.ClearAll = QtWidgets.QPushButton(self.LeftFrame_todo)
        self.ClearAll.setGeometry(QtCore.QRect(281, 105, 90, 23))
        self.ClearAll.setStyleSheet("background-color: rgb(0, 153, 255);\n"
                                    "border-style: solid;\n"
                                    "border-color: rgb(0, 153, 255);\n"
                                    "border-width: 2px;\n"
                                    "border-radius: 8px;")
        self.ClearAll.setObjectName("ClearAll")
        self.ClearAll.clicked.connect(self.ClearAllItemEvent)

        #Right Top Frame
        self.RightFrameTop_pick = QtWidgets.QFrame(self.centralwidget)
        self.RightFrameTop_pick.setGeometry(QtCore.QRect(440, 60, 411, 161))
        self.RightFrameTop_pick.setStyleSheet("background-color: rgb(43, 43, 43);\n"
                                                "border-style: solid;\n"
                                                "border-color: rgb(43, 43, 43);\n"
                                                "border-width: 2px;\n"
                                                "border-radius: 40px;")
        self.RightFrameTop_pick.setFrameShape(QtWidgets.QFrame.StyledPanel)
        self.RightFrameTop_pick.setFrameShadow(QtWidgets.QFrame.Raised)
        self.RightFrameTop_pick.setObjectName("RightFrameTop_pick")

        #Right Top Frame -comboBox
        self.comboBox = QtWidgets.QComboBox(self.RightFrameTop_pick)
        self.comboBox.setGeometry(QtCore.QRect(40, 60, 331, 30))
        self.comboBox.setStyleSheet("background-color: rgb(0, 153, 255);\n"
                                    "border-style: solid;\n"
                                    "border-color: rgb(0, 153, 255);\n"
                                    "border-width: 2px;\n"
                                    "border-radius: 8px;")
        self.comboBox.setObjectName("comboBox")

        conn = sqlite3.connect("project.db")
        c = conn.cursor()

        c.execute("SELECT * FROM project")

        items = c.fetchall()
        none = str(items)

        if none == None:
            self.comboBox.addItem("No Repos Found")

        else:
            for item in items:
                project_name = item[0]

                self.comboBox.addItem(project_name)

        #Right Top Frame -FrameLabel
        self.RightTopFrameTitle = QtWidgets.QFrame(self.RightFrameTop_pick)
        self.RightTopFrameTitle.setGeometry(QtCore.QRect(20, 15, 371, 26))
        self.RightTopFrameTitle.setStyleSheet("background-color: rgb(0, 153, 255);\n"
                                        "border-style: solid;\n"
                                        "border-color: rgb(0, 153, 255);\n"
                                        "border-width: 2px;\n"
                                        "border-radius: 10px;")
        self.RightTopFrameTitle.setFrameShape(QtWidgets.QFrame.StyledPanel)
        self.RightTopFrameTitle.setFrameShadow(QtWidgets.QFrame.Raised)
        self.RightTopFrameTitle.setObjectName("RightTopFrameTitle")

        #Right Top Frame -FrameLabel -title
        self.RightTopTitle = QtWidgets.QLabel(self.RightTopFrameTitle)
        self.RightTopTitle.setGeometry(QtCore.QRect(1, 0, 371, 26))
        font = QtGui.QFont()
        font.setPointSize(12)
        self.RightTopTitle.setFont(font)
        self.RightTopTitle.setAlignment(QtCore.Qt.AlignCenter)
        self.RightTopTitle.setObjectName("RightTopTitle")

        #Right Top Frame -ChoseProjectButton
        self.ChooseProject = QtWidgets.QPushButton(self.RightFrameTop_pick)
        self.ChooseProject.setGeometry(QtCore.QRect(145, 110, 111, 30))
        self.ChooseProject.setStyleSheet("background-color: rgb(0, 153, 255);\n"
                                        "border-style: solid;\n"
                                        "border-color: rgb(0, 153, 255);\n"
                                        "border-width: 2px;\n"
                                        "border-radius: 8px;")
        self.ChooseProject.setObjectName("ChooseProject")
        self.ChooseProject.clicked.connect(self.ChooseProjectEvent)

        #Right Bottom Frame
        self.RightFrameBottom_file = QtWidgets.QFrame(self.centralwidget)
        self.RightFrameBottom_file.setGeometry(QtCore.QRect(440, 240, 411, 311))
        self.RightFrameBottom_file.setStyleSheet("background-color: rgb(43, 43, 43);\n"
                                                "border-style: solid;\n"
                                                "border-color: rgb(43, 43, 43);\n"
                                                "border-width: 2px;\n"
                                                "border-radius: 40px;")
        self.RightFrameBottom_file.setFrameShape(QtWidgets.QFrame.StyledPanel)
        self.RightFrameBottom_file.setFrameShadow(QtWidgets.QFrame.Raised)
        self.RightFrameBottom_file.setObjectName("RightFrameBottom_file")

        #Right Bottom Frame -FrameLabel
        self.RightBottomFrameTitle = QtWidgets.QFrame(self.RightFrameBottom_file)
        self.RightBottomFrameTitle.setGeometry(QtCore.QRect(20, 15, 371, 26))
        self.RightBottomFrameTitle.setStyleSheet("background-color: rgb(0, 153, 255);\n"
                                        "border-style: solid;\n"
                                        "border-color: rgb(0, 153, 255);\n"
                                        "border-width: 2px;\n"
                                        "border-radius: 10px;")
        self.RightBottomFrameTitle.setFrameShape(QtWidgets.QFrame.StyledPanel)
        self.RightBottomFrameTitle.setFrameShadow(QtWidgets.QFrame.Raised)
        self.RightBottomFrameTitle.setObjectName("RightBottomFrameTitle")

        #Right Bottom Frame -FrameLabel -title
        self.RightBottomTitle = QtWidgets.QLabel(self.RightBottomFrameTitle)
        self.RightBottomTitle.setGeometry(QtCore.QRect(1, 0, 371, 26))
        font = QtGui.QFont()
        font.setPointSize(12)
        self.RightBottomTitle.setFont(font)
        self.RightBottomTitle.setAlignment(QtCore.Qt.AlignCenter)
        self.RightBottomTitle.setObjectName("label_5")

        #Right Bottom Frame -FileTreeView
        self.treeView = QtWidgets.QTreeView(self.RightFrameBottom_file)
        self.treeView.setGeometry(QtCore.QRect(30, 50, 351, 241))
        self.treeView.setStyleSheet("background-color: rgb(0, 153, 255);\n"
                                    #"color: rgb(0, 153, 255);\n"
                                    "alternate-background-color: rgb(0, 153, 255);\n"
                                    "border-style: solid;\n"
                                    "border-color: rgb(0, 153, 255);\n"
                                    "border-width: 2px;\n"
                                    "border-radius: 10px;")
        app.setStyleSheet("QHeaderView::section { background-color: rgb(0, 153, 255) }\n"
                          "QListWidget::item:selected {\n"
                                "background-color: rgb(0, 89, 148);\n"
                                "border-style: solid;\n"
                                "border-color: rgb(0, 153, 255);\n"
                                "border-width: 2px;\n"
                                "border-radius: 10px;\n"
                            "};\n")
        self.treeView.setObjectName("treeView")
        self.model = QFileSystemModel()
        self.treeView.setModel(self.model)
        self.treeView.setColumnWidth(0, 250)
        self.treeView.setAlternatingRowColors(True)
        self.treeView.hideColumn(1)
        self.treeView.hideColumn(2)
        self.treeView.hideColumn(3)

        currect = self.comboBox.currentText()

        conn = sqlite3.connect("project.db")
        c = conn.cursor()

        c.execute(f"SELECT * FROM project WHERE project_name='{currect}'")

        items = c.fetchall()
        none = str(items)

        if none == "[]":
            self.CurrentProject.setText(f"Error")

        else:
            for item in items:
                name = item[0]
                dir = item[1]

            self.model.setRootPath(dir)
            self.treeView.setRootIndex(self.model.index(dir))

            self.CurrentProject.setText(f"{name} Dashboard")

        #Wave
        self.Wave = QtWidgets.QGraphicsView(self.centralwidget)
        self.Wave.setGeometry(QtCore.QRect(-52, 268, 957, 317))
        self.Wave.setStyleSheet("background-image: url(:/wave/Image/Wave/wave_2.png);\n"
                                "border-style: solid;\n"
                                "border-color: rgb(43, 43, 43);\n")
        self.Wave.setObjectName("Wave")

        #Raise
        self.Wave.raise_()
        self.LeftFrame_todo.raise_()
        self.RightFrameTop_pick.raise_()
        self.RightFrameBottom_file.raise_()
        #self.Title.raise_()

        #Other
        MainWindow.setCentralWidget(self.centralwidget)
        self.menubar = QtWidgets.QMenuBar(MainWindow)
        self.menubar.setGeometry(QtCore.QRect(0, 0, 767, 22))
        self.menubar.setObjectName("menubar")
        MainWindow.setMenuBar(self.menubar)

        #Add Items to todo
        currect = self.comboBox.currentText()

        self.CurrentProject.setText(f"{currect}⠀Dashboard")

        text = self.CurrentProject.text()

        project_name = text.split("⠀Dashboard")
        project_name = project_name[0]

        conn = sqlite3.connect("todo.db")
        c = conn.cursor()

        c.execute(f"SELECT * FROM todo WHERE project_name='{project_name}'")

        items = c.fetchall()
        none = str(items)

        if none == "[]":
            pass

        else:
            for item in items:
                todo = item[1]
                self.listWidget.addItem(todo)

        self.retranslateUi(MainWindow)
        QtCore.QMetaObject.connectSlotsByName(MainWindow)

    def retranslateUi(self, MainWindow):
        currect = self.comboBox.currentText()

        _translate = QtCore.QCoreApplication.translate
        MainWindow.setWindowTitle(_translate("MainWindow", "Orgize.code"))
        self.label.setText(_translate("MainWindow", "To Do List"))
        self.AddItem.setText(_translate("MainWindow", "Add Item"))
        self.DeleteItem.setText(_translate("MainWindow", "Delete Item"))
        self.ClearAll.setText(_translate("MainWindow", "Clear All"))
        self.RightTopTitle.setText(_translate("MainWindow", "Project Chooser"))
        self.ChooseProject.setText(_translate("MainWindow", "Change Project"))
        self.RightBottomTitle.setText(_translate("MainWindow", "Current File Directory"))
        self.CurrentProject.setText(_translate("MainWindow", f"{currect}⠀Dashboard"))

    def AddItemEvent(self):
        item = self.ItemLineEdit.text()

        self.listWidget.addItem(item)

        self.ItemLineEdit.setText("")

        clicked = self.CurrentProject.text()

        project_name = clicked.split("⠀Dashboard")

        conn = sqlite3.connect("todo.db")
        c = conn.cursor()

        c.execute(f"INSERT INTO todo VALUES ('{project_name[0]}', '{item}')")

        conn.commit()
        conn.close()

    def DeleteItemEvent(self):
        clicked = self.listWidget.currentRow()
        item = self.listWidget.currentItem().text()

        self.listWidget.takeItem(clicked)

        project_name = self.CurrentProject.text()

        project_name = project_name.split("⠀Dashboard")

        conn = sqlite3.connect("todo.db")
        c = conn.cursor()

        c.execute(f"DELETE FROM todo WHERE project_name='{project_name[0]}' AND todo='{item}'")

        conn.commit()
        conn.close()

    def ClearAllItemEvent(self):
        self.listWidget.clear()

        project_name = self.CurrentProject.text()

        project_name = project_name.split("⠀Dashboard")

        conn = sqlite3.connect("todo.db")
        c = conn.cursor()

        c.execute(f"SELECT rowid, * FROM todo WHERE project_name='{project_name[0]}'")

        items = c.fetchall()
        none = str(items)

        if none == "[]":
            pass

        else:
            for item in items:
                rowid = item[0]

                c.execute(f"DELETE FROM todo WHERE rowid={rowid}")

                conn.commit()

            conn.close()

    def ChooseProjectEvent(self):
        currect = self.comboBox.currentText()

        conn = sqlite3.connect("project.db")
        c = conn.cursor()

        c.execute(f"SELECT * FROM project WHERE project_name='{currect}'")

        items = c.fetchall()
        none = str(items)

        if none == "[]":
            self.CurrentProject.setText(f"Error")

        else:
            for item in items:
                name = item[0]
                dir = item[1]

            self.model.setRootPath(dir)
            self.treeView.setRootIndex(self.model.index(dir))

            self.CurrentProject.setText(f"{name}⠀Dashboard")

            conn.close()

            self.listWidget.clear()

            try:
                name = name.split("⠀Dashboard")
                name = name[0]

            except:
                name = name

            conn = sqlite3.connect("todo.db")
            c = conn.cursor()

            c.execute(f"SELECT * FROM todo WHERE project_name='{name}'")

            items = c.fetchall()
            none = str(items)

            if none == "[]":
                pass

            else:
                for item in items:
                    todo = item[1]

                    self.listWidget.addItem(todo)

        #self.model.setRootPath(r'C:\Users\norbe\OneDrive\Desktop\Projects')
        #self.treeView.setRootIndex(self.model.index(r'C:\Users\norbe\OneDrive\Desktop\Projects'))

if __name__ == "__main__":
    import sys
    app = QtWidgets.QApplication(sys.argv)
    MainWindow = QtWidgets.QMainWindow()
    ui = MainDashboard()
    ui.setupUi(MainWindow, app)
    MainWindow.show()
    sys.exit(app.exec_())


import discord
from discord.ext import commands

pre = "!"
token = "<YOUR DISCORD BOT TOKEN>"

bot = commands.Bot(command_prefix=f"{pre}", case_intensive=True, intents=discord.Intents.all())
bot.remove_command('help')
bot.launch_time = datetime.utcnow()

@bot.event
async def on_ready():
    print(f'{bot.user.name}')
    print(f'{bot.user.id}')
    print("Online")
    print("-------------")
    await bot.load_extension("cogs.bank")

bot.run(token)


from abc import ABC, abstractmethod
from collections import defaultdict
import random
from tkinter import EW
from typing import List, Dict, DefaultDict
from gym.spaces import Space
from gym.spaces.utils import flatdim

class Agent(ABC):
    """Base class for Q-Learning agent

    """

    def __init__(
        self,
        action_space: Space,
        obs_space: Space,
        gamma: float,
        epsilon: float,
        **kwargs
    ):
        """Constructor of base agent for Q-Learning

        Initializes basic variables of the Q-Learning agent
        namely the epsilon, learning rate and discount rate.

        :param action_space (int): action space of the environment
        :param obs_space (int): observation space of the environment
        :param gamma (float): discount factor (gamma)
        :param epsilon (float): epsilon for epsilon-greedy action selection

        :attr n_acts (int): number of actions
        :attr q_table (DefaultDict): table for Q-values mapping (OBS, ACT) pairs of observations
            and actions to respective Q-values
        """

        self.action_space = action_space
        self.obs_space = obs_space
        self.n_acts = flatdim(action_space)

        self.epsilon: float = epsilon
        self.gamma: float = gamma

        self.q_table: DefaultDict = defaultdict(lambda: 0)

    def act(self, obs: int) -> int:
        import numpy as np
        """Implement the epsilon-greedy action selection here

        :param obs (int): received observation representing the current environmental state
        :return (int): index of selected action
        """

        q_vector = np.zeros(self.action_space.n)

        for (i, j), value in self.q_table.items():
            if i == obs:
                q_vector[j] += value

        if random.uniform(0,1) < self.epsilon:
            action = self.action_space.sample()
        else:
            action=np.argmax(q_vector)

        return action

    @abstractmethod
    def schedule_hyperparameters(self, timestep: int, max_timestep: int):
        """Updates the hyperparameters

        This function is called before every episode and allows you to schedule your
        hyperparameters.

        :param timestep (int): current timestep at the beginning of the episode
        :param max_timestep (int): maximum timesteps that the training loop will run for
        """
        ...

    @abstractmethod
    def learn(self):
        ...

class QLearningAgent(Agent):
    """
    Agent using the Q-Learning algorithm

    """

    def __init__(self, alpha: float, **kwargs):
        """Constructor of QLearningAgent

        Initializes some variables of the Q-Learning agent, namely the epsilon, discount rate
        and learning rate alpha.

        :param alpha (float): learning rate alpha for Q-learning updates
        """

        super().__init__(**kwargs)
        self.alpha: float = alpha

    def learn(
        self, obs: int, action: int, reward: float, n_obs: int, done: bool
    ) -> float:
        """Updates the Q-table based on agent experience

        :param obs (int): received observation representing the current environmental state
        :param action (int): index of applied action
        :param reward (float): received reward
        :param n_obs (int): received observation representing the next environmental state
        :param done (bool): flag indicating whether a terminal state has been reached
        :return (float): updated Q-value for current observation-action pair
        """

        import numpy as np

        q_vector_n_obs = np.zeros(self.action_space.n)

        for (i, j), value in self.q_table.items():
            if i == n_obs:
                q_vector_n_obs[j] += value
        best_qn = np.max(q_vector_n_obs)

        new_q_value = self.q_table[(obs,action)]+self.alpha*(reward+self.gamma*best_qn-self.q_table[(obs,action)])
        self.q_table[(obs,action)] = new_q_value

        return self.q_table[(obs, action)]

    def schedule_hyperparameters(self, timestep: int, max_timestep: int):
        """Updates the hyperparameters

        This function is called before every episode and allows you to schedule your
        hyperparameters.

        :param timestep (int): current timestep at the beginning of the episode
        :param max_timestep (int): maximum timesteps that the training loop will run for
        """

        import numpy as np
        alpha_min = 0
        alpha_max = 1

        #Cosine annealing
        self.alpha = alpha_min + 0.5*(alpha_max-alpha_min)*(1+np.cos(timestep/max_timestep*np.pi))

        steepness = 2
        self.alpha = (2*alpha_max)/(np.exp(steepness*timestep/max_timestep)+1)

        self.epsilon = 0.05/(timestep//1000+1)

class MonteCarloAgent(Agent):
    """
    Agent using the Monte-Carlo algorithm for training

    """

    def __init__(self, **kwargs):
        """Constructor of MonteCarloAgent

        Initializes some variables of the Monte-Carlo agent, namely epsilon,
        discount rate and an empty observation-action pair dictionary.

        :attr sa_counts (Dict[(Obs, Act), int]): dictionary to count occurrences observation-action pairs
        """
        super().__init__(**kwargs)
        self.sa_counts = {}

    def learn(
        self, obses: List[int], actions: List[int], rewards: List[float]
    ) -> Dict:
        """Updates the Q-table based on agent experience

        :param obses (List(int)): list of received observations representing environmental states
            of trajectory (in the order they were encountered)
        :param actions (List[int]): list of indices of applied actions in trajectory (in the
            order they were applied)
        :param rewards (List[float]): list of received rewards during trajectory (in the order
            they were received)
        :return (Dict): A dictionary containing the updated Q-value of all the updated state-action pairs
            indexed by the state action pair.
        """
        updated_values = {}
        import numpy as np
        g = 0

        pairs=[(i,j)for i,j in zip(obses,actions)]

        for s in reversed(range(len(obses))):

            g = self.gamma*g + rewards[s]

            if (obses[s],actions[s]) not in pairs[:s]:

                if (obses[s],actions[s]) not in self.sa_counts.keys():
                    self.sa_counts[(obses[s],actions[s])]=0
                else:
                    self.sa_counts[(obses[s],actions[s])]+=1

                if (obses[s],actions[s]) in self.q_table.keys():
                    temp_v = self.q_table[(obses[s],actions[s])]
                else:
                    temp_v = 0

                new_val = (temp_v*self.sa_counts[(obses[s],actions[s])]+g)/(self.sa_counts[(obses[s],actions[s])]+1)
                updated_values[(obses[s],actions[s])] = new_val
                self.q_table[(obses[s],actions[s])] = new_val

        return updated_values

    def schedule_hyperparameters(self, timestep: int, max_timestep: int):
        """Updates the hyperparameters

        This function is called before every episode and allows you to schedule your
        hyperparameters.

        :param timestep (int): current timestep at the beginning of the episode
        :param max_timestep (int): maximum timesteps that the training loop will run for
        """
        import numpy as np
        init_eps = 0.65
        steepness = 5
        self.epsilon = (2*init_eps)/(np.exp(steepness*timestep/max_timestep)+1)


import pathlib
from django.db.models.signals import post_save
from django.dispatch import receiver
from allauth.account.signals import user_signed_up
from django.contrib.auth.models import Group
from io import BytesIO
from wagtail.users.models import UserProfile
from custom_storages import s3_media_storage
from users.models import CustomUserProfile, CustomUser
from PIL import Image

@receiver(user_signed_up)
def group_and_profiles(sender, request, user, **kwargs):
	""" add new user to "customers" group, create
	wagtail and user profile fields with a default
	language setting. """
	if user.is_anonymous:
		pass
	else:
		group = Group.objects.get(name='Customers')
		user.groups.add(group)
		wagtail_userprofile_defaults = {
			'submitted_notifications': False,
			'approved_notifications': False,
			'rejected_notifications': False,
			'preferred_language': 'en',
		}

		base_userprofile_defaults = {
			'user_id': user.id,
		}
		user.save()
		UserProfile.objects.get_or_create(user_id=user.id, defaults=wagtail_userprofile_defaults)
		CustomUserProfile.objects.get_or_create(user_id=user.id, defaults=base_userprofile_defaults)

@receiver(post_save, sender=CustomUser)
def default_groups(sender, instance, **kwargs):
	if instance.is_superuser and kwargs.get('created'):
		Group.objects.get_or_create(name='Contributors')
		Group.objects.get_or_create(name='Authors')
		Group.objects.get_or_create(name='Customers')
		user = CustomUser.objects.get(pk=instance.id)
		groups = Group.objects.all()
		user.first_name = 'Admin'
		user.last_name = 'McAdmin'
		user.is_smssubscribed = True
		user.is_mailsubscribed = True
		user.is_active = True
		for group in groups:
			group.user_set.add(user)
		user.save()

		wagtail_userprofile_defaults = {
			'submitted_notifications': True,
			'approved_notifications': True,
			'rejected_notifications': True,
			'updated_comments_notifications': True,
			'preferred_language': 'en',
		}

		base_userprofile_defaults = {
			'user_id': user.id,
		}

		UserProfile.objects.get_or_create(user_id=user.id, defaults=wagtail_userprofile_defaults)
		CustomUserProfile.objects.get_or_create(user_id=user.id, defaults=base_userprofile_defaults)
	else:
		pass

def crop_center(img, crop_width, crop_height):
	width, height = img.size
	return img.crop(((width - crop_width) // 2,
					(height - crop_height) // 2,
					(width + crop_width) // 2,
					(height + crop_height) // 2))

def crop_max_square(img):
    return crop_center(img, min(img.size), min(img.size))

@receiver(post_save, sender=UserProfile)
def resize_avatar(sender, instance, **kwargs):
	if instance.avatar:
		memfile = BytesIO()
		try:
			img = Image.open(instance.avatar.file)
		except:
			img = None

		if img:
			width, height = img.size
			newsize = 100, 100
			try:
				imgformat = img.format
			except:
				imgformat = pathlib.Path(instance.avatar.file.name).suffix.split('.')[1].upper()
			img = crop_max_square(img).resize((newsize), Image.LANCZOS)
			img.save(memfile, imgformat)
			s3_media_storage.save(instance.avatar.name, memfile)
			img.close()
			memfile.close()


import streamlit as st
import time
import numpy as np
import pandas as pd

st.set_page_config(
    page_title="База данных",
    page_icon="📈"
)

st.markdown("# Данные о растениях")

# ========== READ THE DATA ==========

# species
f = open("data/atlas_species.txt", "r")
species = [x.replace("\n", "") for x in f.readlines()]

# collected CSV
daf_path = "data/result.csv"
daf = pd.read_csv(daf_path)

# ==============================

search_query = st.text_input("Поиск по базе данных", placeholder="Поиск по базе данных")
for ix, specie in enumerate([x for x in species if search_query.lower() in x.lower()]):
    row = daf[daf['name'] == specie]
    if row.shape[0] == 0:
        continue
    row = row.iloc[0]

    # st.markdown(f"**{specie}**")
    with st.expander(f"**{specie}**"):
        st.markdown(f"**Поизрастает:** {row['area']}")
        st.markdown(f"**Почва:** {row['soil']}")
        st.markdown(f"**Время:** {row['timings']}")
        st.markdown(f"**Время:** {row['chemicals']}")
        st.markdown(f"**Время:** {row['medicine']}")


from tkinter import *
from tkinter.messagebox import showinfo
from PIL import ImageTk, Image
from tkinter.ttk import Progressbar
import glob

screen = (1280,1024)
image = []

fen = Tk()
fen.geometry('%sx%s+0+0'%screen)
fen.resizable(False,False)
fen.overrideredirect(True)
fen.bind('<Button-1>', lambda x:fen.destroy())
label = Label(text='dir',font=('Comic Sans MS', 10),compound=CENTER)
label.pack()
showinfo(message='Mouse Button 1 to exit.')

def tree(a):
   for b in a:
      if b.split('.')[-1] in ['png','jpg','gif','ico','bmp']:
         try:
            img = Image.open(b).resize(screen)
            img = ImageTk.PhotoImage(image=img)
            label.config(image=img,text=b)
         except Exception as error:
            print(error, b)
         fen.update()
      c = glob.glob(b+'/*')
      tree(c)

tree(glob.glob('c:\*'))

fen.mainloop()


import keras
from keras import backend as K
from keras.models import Sequential, Model
from keras.layers import Input, Reshape, merge
from keras.layers import Activation
from keras.layers.core import Flatten, Dense, Dropout, Lambda
from keras.regularizers import l2, activity_l2, l1, activity_l1
from keras.layers.normalization import BatchNormalization
from keras.optimizers import SGD, RMSprop, Adam
from keras.metrics import categorical_crossentropy, categorical_accuracy
from keras.layers.convolutional import *
from keras.layers.pooling import GlobalAveragePooling2D

BOUND_SIZE = 32
def get_model():
    model = Sequential([
        Lambda(norm_input, input_shape=(1,BOUND_SIZE,BOUND_SIZE)),
        Convolution2D(64,2,2, activation='relu'), #31
        BatchNormalization(axis=1),
        Convolution2D(64,2,2, activation='relu'), #30
        BatchNormalization(axis=1),
        Convolution2D(64,2,2, subsample=(2, 2), activation='relu'), #15
        BatchNormalization(axis=1),
        Convolution2D(128,2,2, activation='relu'), #14
        BatchNormalization(axis=1),
        Dropout(0.3),
        Convolution2D(128,2,2, activation='relu'), #13
        BatchNormalization(axis=1),
        Dropout(0.3),
        Convolution2D(128,2,2, subsample=(2, 2), activation='relu'), #6
        BatchNormalization(axis=1),
        Dropout(0.3),
        Convolution2D(192,2,2, activation='relu'), #5
        BatchNormalization(axis=1),
        Dropout(0.4),
        Convolution2D(192,2,2, activation='relu'), #4
        BatchNormalization(axis=1),
        Dropout(0.4),
        Convolution2D(192,2,2, subsample=(2, 2), activation='relu'), #2
        BatchNormalization(axis=1),
        Dropout(0.4),
        Convolution2D(256,2,2, activation='relu'), #1
        BatchNormalization(axis=1),
        Dropout(0.5),
        Convolution2D(256,1,1, activation='relu'), #1
        BatchNormalization(axis=1),
        Dropout(0.5),
        Convolution2D(2,1,1, activation='relu'), #1
        GlobalAveragePooling2D(),
        Activation('softmax')
        ])
    model.compile(Adam(), loss='categorical_crossentropy', metrics=['accuracy'])
    return model


import os
import glob
import json
import argparse

from invoicenet import FIELDS
from invoicenet.acp.acp import AttendCopyParse

def main():
    ap = argparse.ArgumentParser()

    ap.add_argument("--field", nargs='+', type=str, required=True, choices=FIELDS.keys(),
                    help="field to train parser for")
    ap.add_argument("--invoice", type=str, default=None,
                    help="path to directory containing prepared data")
    ap.add_argument("--data_dir", type=str, default='test_data/',
                    help="path to directory containing prepared data")
    ap.add_argument("--pred_dir", type=str, default='predictions/',
                    help="path to directory containing prepared data")

    args = ap.parse_args()

    paths = []
    fields = []
    predictions = {}

    if args.invoice:
        if not os.path.exists(args.invoice):
            print("Could not find file '{}'".format(args.invoice))
            return
        paths.append(args.invoice)
    else:
        paths = [os.path.abspath(f) for f in glob.glob(args.data_dir + "**/*.pdf", recursive=True)]

    if not os.path.exists('./models/invoicenet/'):
        print("Could not find any trained models!")
        return
    else:
        models = os.listdir('./models/invoicenet/')
        for field in args.field:
            if field in models:
                fields.append(field)
            else:
                print("Could not find a trained model for field '{}', skipping...".format(field))

    for field in fields:
        print("\nExtracting field '{}' from {} invoices...\n".format(field, len(paths)))
        model = AttendCopyParse(field=field, restore=True)
        predictions[field] = model.predict(paths=paths)

    os.makedirs(args.pred_dir, exist_ok=True)
    for idx, filename in enumerate(paths):
        filename = os.path.basename(filename)[:-3] + 'json'
        labels = {}
        if os.path.exists(os.path.join(args.pred_dir, filename)):
            with open(os.path.join(args.pred_dir, filename), 'r') as fp:
                labels = json.load(fp)
        with open(os.path.join(args.pred_dir, filename), 'w') as fp:
            print("\nFilename: {}".format(filename))
            for field in predictions.keys():
                labels[field] = predictions[field][idx]
                print("  {}: {}".format(field, labels[field]))
            fp.write(json.dumps(labels, indent=2))
            print('\n')

    print("Predictions stored in '{}'".format(args.pred_dir))

if __name__ == '__main__':
    main()


import os
import torch
import numpy as np
import pandas as pd
import random
import logging
import copy
from .metrics import Metrics

class EarlyStopping:
    """Early stops the training if validation loss doesn't improve after a given patience."""
    def __init__(self, args, delta=1e-6):
        """
        Args:
            patience (int): How long to wait after last time validation loss improved.
            delta (float): Minimum change in the monitored quantity to qualify as an improvement.
        """
        self.patience = args.wait_patience
        self.logger = logging.getLogger(args.logger_name)
        self.monitor = args.eval_monitor
        self.counter = 0
        self.best_score = 1e8 if self.monitor == 'loss' else 1e-6
        self.early_stop = False
        self.delta = delta
        self.best_model = None

    def __call__(self, score, model):

        better_flag = score <= (self.best_score - self.delta) if self.monitor == 'loss' else score >= (self.best_score + self.delta)

        if better_flag:
            self.counter = 0
            self.best_model = copy.deepcopy(model)
            self.best_score = score

        else:
            self.counter += 1
            self.logger.info(f'EarlyStopping counter: {self.counter} out of {self.patience}')

            if self.counter >= self.patience:
                self.early_stop = True

def set_torch_seed(seed):
    random.seed(seed)
    np.random.seed(seed)
    torch.manual_seed(seed)
    torch.cuda.manual_seed(seed)
    torch.cuda.manual_seed_all(seed) # if you are using multi-GPU.
    torch.backends.cudnn.deterministic = True
    torch.backends.cudnn.benchmark = False
    os.environ['PYTHONHASHSEED'] = str(seed)

def set_output_path(args):

    if not os.path.exists(args.output_path):
        os.makedirs(args.output_path)

    pred_output_path = os.path.join(args.output_path, args.logger_name)
    if not os.path.exists(pred_output_path):
        os.makedirs(pred_output_path)

    model_path = os.path.join(pred_output_path, args.model_path)
    if not os.path.exists(model_path):
        os.makedirs(model_path)

    return pred_output_path, model_path

def save_npy(npy_file, path, file_name):
    npy_path = os.path.join(path, file_name)
    np.save(npy_path, npy_file)

def load_npy(path, file_name):
    npy_path = os.path.join(path, file_name)
    npy_file = np.load(npy_path)
    return npy_file

def save_model(model, model_dir):

    save_model = model.module if hasattr(model, 'module') else model
    model_file = os.path.join(model_dir, 'pytorch_model.bin')
    model_config_file = os.path.join(model_dir, 'config.json')
    torch.save(save_model.state_dict(), model_file)
    with open(model_config_file, "w") as f:
        f.write(save_model.config.to_json_string())

def restore_model(model, model_dir):
    output_model_file = os.path.join(model_dir, 'pytorch_model.bin')
    model.load_state_dict(torch.load(output_model_file))
    return model

def save_results(args, test_results, debug_args = None):

    pred_labels_path = os.path.join(args.pred_output_path, 'y_pred.npy')
    np.save(pred_labels_path, test_results['y_pred'])

    true_labels_path = os.path.join(args.pred_output_path, 'y_true.npy')
    np.save(true_labels_path, test_results['y_true'])

    if 'features' in test_results.keys():
        features_path = os.path.join(args.pred_output_path, 'features.npy')
        np.save(features_path, test_results['features'])

    if not os.path.exists(args.results_path):
        os.makedirs(args.results_path)

    results = {}
    metrics = Metrics(args)
    for key in metrics.eval_metrics:
        results[key] = round(test_results[key] * 100, 2)

    eval_key = 'eval_' + args.eval_monitor
    results.update({eval_key: test_results['best_eval_score']})

    _vars = [args.dataset, args.method, args.text_backbone, args.seed, args.logger_name]
    _names = ['dataset',  'method', 'text_backbone', 'seed', 'logger_name']

    if debug_args is not None:
        _vars.extend([args[key] for key in debug_args.keys()])
        _names.extend(debug_args.keys())

    vars_dict = {k:v for k,v in zip(_names, _vars)}
    results = dict(results,**vars_dict)

    keys = list(results.keys())
    values = list(results.values())

    results_path = os.path.join(args.results_path, args.results_file_name)

    if not os.path.exists(results_path) or os.path.getsize(results_path) == 0:
        ori = []
        ori.append(values)
        df1 = pd.DataFrame(ori,columns = keys)
        df1.to_csv(results_path,index=False)
    else:
        df1 = pd.read_csv(results_path)
        new = pd.DataFrame(results,index=[1])
        df1 = df1.append(new,ignore_index=True)
        df1.to_csv(results_path,index=False)
    data_diagram = pd.read_csv(results_path)

    print('test_results', data_diagram)


from collections import Counter

def get_nekodic():
    nekodic = []
    dic = {}
    with open('neko.txt.mecab') as f:
        for line in f.readlines():
            line = line[:-1]
            line = line.split('\t')
            if len(line) < 2:
                break
            surface = line[0]
            res = line[1].split(',')
            dic = {
                'surface': surface,
                'base': res[6],
                'pos': res[0],
                'pos1': res[1]
            }
            nekodic.append(dic)
    return nekodic

if __name__ == "__main__":
    waganeko = get_nekodic()
    word_c = Counter()
    word_c.update([neko['surface'] for neko in waganeko])
    result_c = word_c.most_common()
    print(result_c)


from django.shortcuts import get_object_or_404,render,redirect
from django.urls import reverse
from movies.models import MovieReview, Movie
from movies.forms import GiveReviewForm, UpdateReviewForm
from accounts.models import Account
from base import views
from movies.models import MovieReview, Movie
from games.models import GameReview, Game
from series.models import EpisodeReview, Series, Episode
def index(request):
    movie_list= Movie.objects.order_by('-name')
    context = {'movie_list':movie_list}
    return render(request,'movies/movielist.html',context)

def details(request,movie_id):
    movie= get_object_or_404(Movie,pk=movie_id)
    context = {'movie':movie}
    return render(request,'movies/details.html',context)

def give_movie_review(request, movie_id):

    context = {}

    user = request.user
    movie = get_object_or_404(Movie, id=movie_id)
    if not user.is_authenticated:
        return redirect('accounts:must_authenticate')

    review = MovieReview.objects.filter(movie_id=movie_id, author=request.user)
    if len(review)==0:
        form = GiveReviewForm(request.POST or None)
        if form.is_valid():
            obj = form.save(commit=False)
            obj.movie = movie
            obj.author = user
            obj.save()
            form = GiveReviewForm()
            return redirect('movies:review_detail', obj.slug)

        context['form']=form
        return render(request, 'give_movie_review.html', context)
    else:
        return redirect('movies:review_detail', review[0].slug)

def select_movie(request):

    movies = Movie.objects.all()
    context ={'movies':movies}

    return render(request, 'select_movie.html', context)

def review_detail(request, slug):
    context = {}
    review = get_object_or_404(MovieReview, slug=slug)
    context['review']=review

    return render(request, 'movies/review_detail.html', context)

def edit_review(request, slug):

    context = {}

    user = request.user
    if not user.is_authenticated:
        return redirect('accounts:must_authenticate')

    review = get_object_or_404(MovieReview, slug=slug)
    if request.POST:
        form = UpdateReviewForm(request.POST or None, instance=review)
        if form.is_valid():
            obj = form.save(commit=False)
            obj.update()
            context['success_message'] = "Updated"
            review = obj
            return redirect('base:home')
    form = UpdateReviewForm(
            initial = {
                    "title": review.title,
                    "body": review.body,
                    "rating": review.rating,
                }
    )

    context['form'] = form
    return render(request, 'movies/edit_review.html', context)


from pptx import Presentation

prs = Presentation('../Test-Files/original.pptx')
print(len(prs.slides))
i = 0
for slide in prs.slides:
    if i % 2 == 0:
        prs.slides.pop(slide)
    print(slide)
    i+=1
prs.save('../Test-Files/new.pptx')


import speech_recognition as sr
import openpyxl

# Initialize the recognizer class
r = sr.Recognizer()

# Get the audio from the microphone
with sr.Microphone() as source:
    print("Speak: ")
    audio = r.listen(source)

# Convert the audio to text
try:
    text = r.recognize_google(audio)
    print("You said: {}".format(text))
except sr.UnknownValueError:
    print("Sorry, I didn't catch that.")

# Load the workbook and select the active sheet
workbook = openpyxl.load_workbook("data.xlsx")
sheet = workbook.active

# Get the current number of rows in the sheet
rows = sheet.max_row + 1

# Write the text to the first column of the next row
sheet.cell(row=rows, column=1).value = text

# Save the changes to the workbook
workbook.save("data.xlsx")