import streamlit as st
import SessionState
from prompts import PROMPT_LIST
from wit_index import WitIndex
import random
import time

# st.set_page_config(page_title="Image Search")

# vector_length = 128
wit_index_path = f"./models/wit_faiss.idx"
model_name = f"./models/distilbert-base-wit"
wit_dataset_path = "./models/wit_dataset.pkl"

@st.cache(suppress_st_warning=True, allow_output_mutation=True)
def get_wit_index():
    st.write("Loading the WIT index, dataset and the DistillBERT model..")
    wit_index = WitIndex(wit_index_path, model_name, wit_dataset_path, gpu=False)
    return wit_index

# st.cache is disabled temporarily because the inference could take forever using newer streamlit version.
# @st.cache(suppress_st_warning=True)
def process(text: str, top_k: int = 10):
    # st.write("Cache miss: process")
    distance, index, image_info = wit_index.search(text, top_k=top_k)
    return distance, index, image_info

st.title("Image Search")

st.markdown(
    """
    This application is a demo for sentence-based image search using
    [WIT dataset](https://github.com/google-research-datasets/wit). We use DistillBert to encode the sentences
    and Facebook's Faiss to search the vector embeddings.
    """
)
session_state = SessionState.get(prompt=None, prompt_box=None, text=None)
ALL_PROMPTS = list(PROMPT_LIST.keys())+["Custom"]
prompt = st.selectbox('Prompt', ALL_PROMPTS, index=len(ALL_PROMPTS)-1)
# Update prompt
if session_state.prompt is None:
    session_state.prompt = prompt
elif session_state.prompt is not None and (prompt != session_state.prompt):
    session_state.prompt = prompt
    session_state.prompt_box = None
    session_state.text = None
else:
    session_state.prompt = prompt

# Update prompt box
if session_state.prompt == "Custom":
    session_state.prompt_box = "Enter your text here"
else:
    if session_state.prompt is not None and session_state.prompt_box is None:
        session_state.prompt_box = random.choice(PROMPT_LIST[session_state.prompt])

session_state.text = st.text_area("Enter text", session_state.prompt_box)

top_k = st.sidebar.number_input(
    "Top k",
    value=6,
    min_value=1,
    max_value=10
)

wit_index = get_wit_index()
if st.button("Run"):
    with st.spinner(text="Getting results..."):
        st.subheader("Result")
        time_start = time.time()
        distances, index, image_info = process(text=session_state.text, top_k=int(top_k))
        time_end = time.time()
        time_diff = time_end-time_start
        print(f"Search in {time_diff} seconds")
        st.markdown(f"*Search in {time_diff:.5f} seconds*")
        for i, distance in enumerate(distances):
            try:
                st.image(image_info[i][0].replace("http:", "https:"), width=400)
            except FileNotFoundError:
                st.write(f"{image_info[i][0]} can't be displayed")
            st.write(f"{image_info[i][1]}. (D: {distance:.2f})")

        # Reset state
        session_state.prompt = None
        session_state.prompt_box = None
        session_state.text = None


import datetime
from discord.ext import commands, tasks

from src.modules.frog import FrogMessage
from src.config import read_config, update_guild_settings, default_config

daily_message_time = datetime.time(hour=16, tzinfo=datetime.timezone.utc)

class DailyCommands(commands.Cog):
    def __init__(self, bot):
        self.bot = bot
        self.guild_id_list = read_config()
        self.daily_frog_fact.start()

    @tasks.loop(time=daily_message_time)
    async def daily_frog_fact(self):
        '''Function to send a random frog fact daily'''
        frog_class = FrogMessage()

        # Gets a random fact
        message = frog_class.get_frog_fact(daily=True)

        # Updates variable
        self.guild_id_list = read_config()

        for guild_id in self.guild_id_list:
            # Gets channel_id and sends daily message
            try:
                if self.guild_id_list[guild_id]["subscribe.daily"]["enabled"]:
                    channel_id = self.guild_id_list[guild_id]["subscribe.daily"]["channel.id"]
                    channel = self.bot.get_channel(int(channel_id))

                    await channel.send(f"Daily Frog Fact:\n{message}")
                    continue

            except:
                if channel_id:
                    print(f"{channel_id} was not found, skipping...")

                else:
                    print("No channel was found, skipping...")

                continue
    #

    @commands.command(name="subscribe_channel")
    @commands.has_any_role("Administrator", "Admin", "Moderator", "Mod")
    async def subscribe_to_daily(self, ctx):
        guild_id = str(ctx.guild.id)

        # Checks if guild already has a daily message channel
        # If it does, checks if channel.id matches ctx channel
        # If it doesn't, it writes over the old channel.id

        if guild_id not in str(self.guild_id_list.keys()):
            # Gets template
            guild_config = default_config()

            self.guild_id_list[guild_id] = guild_config
            self.guild_id_list[guild_id]["subscribe.daily"]["enabled"] = True

        for guild in self.guild_id_list:
            if guild == guild_id:
                # Updates subscribed channel
                self.guild_id_list[guild_id]["subscribe.daily"]["enabled"] = True
                self.guild_id_list[guild_id]["subscribe.daily"]["channel.id"] = ctx.channel.id

                update_guild_settings(self.guild_id_list)

                await ctx.send("This channel has successfully enabled daily frog facts; they will be sent daily at 12pm EST.")
                break

            else:
                continue

    @commands.command(name="unsubscribe_channel")
    @commands.has_any_role("Administrator", "Admin", "Moderator", "Mod")
    async def unsubscribe_to_daily(self, ctx):
        '''Marks server as having the daily fact disabled'''
        guild_id = str(ctx.guild.id)

        if guild_id not in self.guild_id_list.keys():
            await ctx.reply("Daily frog facts were never enabled.", mention_author=False)
        else:
            for guild in self.guild_id_list:
                if guild == guild_id:
                    self.guild_id_list[guild_id]["subscribe.daily"]["enabled"] = False
                    self.guild_id_list[guild_id]["subscribe.daily"]["channel.id"] = None
                    update_guild_settings(self.guild_id_list)

                    await ctx.send("All daily frog facts have been disabled successfully.")
                    break

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


import spacy
import time
from django.db import transaction
import bson
import django
import re
from django.utils import timezone  # Import Django's timezone module
import os
import sys

sys.path.append(os.path.join(os.path.dirname(__file__), '../openCore'))
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "openCore.settings")
django.setup()
from news.models import News, WordIndex, ImportanceScore

def process_text(input_text):
    # Convert to lowercase
    lowercase_text = input_text.lower()

    # Remover acento
    no_accent_text = lowercase_text.replace('á', 'a').replace('é', 'e').replace('í', 'i').replace('ó', 'o').replace(
        'ú', 'u')

    # Remove punctuation
    no_punctuation_text = re.sub(r'[^\w\s]', '', no_accent_text)

    # Convert ñ to n
    final_text = re.sub(r'ñ', 'n', no_punctuation_text)

    return final_text

def indexer(historical_json = None):
    #regex to convert to lowercase, remove punctuation and convert ñ to n
    print('current time: ', timezone.now())
    #carga el modelo de lenguaje español
    nlp = spacy.load("es_core_news_sm")

    #obtiene el id del último artículo indexado
    last_indexed_article_id = get_last_indexed_article_id()

    # obtiene los artículos de noticias nuevos publicados después del último artículo indexado
    new_news_articles = News.objects.filter(id__gt=last_indexed_article_id)
    print (new_news_articles.count())

    #cargado de stop words
    stop_words = spacy.lang.es.stop_words.STOP_WORDS

    #word list to save will be an empty array if no historical json is passed
    #if historical json is passed, it will hold the json data
    if historical_json is None:
        word_list_to_save = []
    else:
        word_list_to_save = historical_json

    articles_word_count = {}
    for news_article in new_news_articles:
        #tokeniza, elimina las palabras vacías y pone en minúsculas las palabras en los documentos
        content = news_article.content
        doc = nlp(content)

        #lista de palabras filtradas(sin stop words)
        words = [token.text.lower() for token in doc if token.text.lower() not in stop_words and token.is_alpha]
        words = list(set(words)) #elimina duplicados
        articles_word_count[news_article.id] = len(words)

        db_words_list = set(WordIndex.objects.values_list('word', flat=True)) #lista de palabras ya indexadas en la base de datos
        # indexado de palabras en el articulo
        for word in words:
            word_normalized = process_text(word)
            frequency = content.lower().count(word)
            #si la palabra no esta en la base de datos ni en la lista de palabras a guardar, se agrega a la lista de palabras a guardar
            if word_normalized not in db_words_list and word_normalized not in [word["word"] for word in word_list_to_save]:
                word_list_to_save.append({
                    "word": word_normalized,
                    "frequency_global": frequency,
                    "importance_scores": [
                        {
                            "article_info": {
                                "article_id": news_article.id,
                                "word_count": articles_word_count[news_article.id],
                            },
                            "frequency": frequency,
                            "tf_idf": 0.0
                        }
                    ],
                })
            elif word_normalized in [word["word"] for word in word_list_to_save]:
                #if word is already in the list, append a dict to the importance_scores list with the id_noticia and frequency
                for word_dict in word_list_to_save:
                    if word_dict["word"] == word_normalized:
                        word_dict["frequency_global"] += frequency
                        word_dict["importance_scores"].append({
                            "article_info": {
                                "article_id": news_article.id,
                                "word_count": articles_word_count[news_article.id],
                            },
                            "frequency": frequency,
                            "tf_idf": 0.0
                        })
        # Update the record of the last indexed article to the most recent one in the batch
        update_last_indexed_article(news_article)
        print("indexed article: ", news_article.id)
    return word_list_to_save
    print ('time after query: ', timezone.now())

def get_last_indexed_article_id():
    # Implement a method to fetch the ID of the last indexed article from a configuration file or database
    # Return a default value (e.g., 0) if no previous indexing has been done
    try:
        last_indexed_article = News.objects.latest('indexed_on')
        if last_indexed_article.indexed_on is None:
            return 0
        return last_indexed_article.id
    except News.DoesNotExist:
        return 0

def update_last_indexed_article(news_article):
    # Implement a method to update the 'indexed_on' field of the last indexed article
    # You can set 'indexed_on' to the current date and time using Django's timezone module
    news_article.indexed_on = timezone.now()
    news_article.save()


import cv2
import numpy as np
import math

objectWidth = 8.5
objectHeight = 11

print("Distance to object")
distance = input()
print("Distance: " + distance + " in")

#Define path
path = "OpenCV/resources/Logi.jpg"

def getRectangle(path):
    image = cv2.imread(path)
    imageHSV = cv2.cvtColor(image,cv2.COLOR_BGR2HSV)
    gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
    blurred = cv2.GaussianBlur(gray,(5,5),0)
    canny = cv2.Canny(gray,30,150)

    frameMask = cv2.inRange(imageHSV,(150,0,0),(255,150,250))

    ret,binary = cv2.threshold(frameMask,100,255,cv2.THRESH_BINARY)

    contours, hierarchy = cv2.findContours(binary,cv2.RETR_EXTERNAL,cv2.CHAIN_APPROX_SIMPLE)

    cv2.imshow("Canny", binary)
    color = (255,0,0)

    if len(contours)>1:
        bestContour = max(contours, key = cv2.contourArea)

        minRect = cv2.minAreaRect(bestContour)
        box = cv2.boxPoints(minRect)
        box = np.int0(box)
        cv2.drawContours(image, [box], 0, color)

        point1 = box[0]
        point2 = box[1]
        point3 = box[2]

        print("We got 'em")
        cv2.imshow("Image",image)

    else: print("Hmmm")

    return(point1[0],point1[1],point2[0],point2[1],point3[0],point3[1])

def getPixelsToDistance(objectWidth,objectHeight,x1,x2,y1,y2,x3,y3,distance,image):

    #Pixels to inches
    wPix = math.sqrt(math.pow(x2-x1,2) + math.pow(y2-y1,2))
    hPix = math.sqrt(math.pow(x3-x2,2) + math.pow(y3-y2,2))
    multiplierW = image.shape[1] / wPix
    multiplierH = image.shape[0] / hPix
    inchesW = multiplierW * objectWidth
    inchesH = multiplierH * objectHeight
    horFOV = math.degrees( math.atan2( ( .5*inchesW ), int(distance) ) ) * 2
    verFOV = math.degrees( math.atan2( ( .5*inchesH ), int(distance) ) ) * 2

    return horFOV,verFOV

image = cv2.imread(path)

x1,x2,y1,y2,x3,y3 = getRectangle(path)

horizontalFOV,verticalFOV = getPixelsToDistance(objectWidth,objectHeight,x1,x2,y1,y2,x3,y3,distance,image)
print(horizontalFOV)
print(verticalFOV)

cv2.waitKey(0)


import sys
''' 11729번 하노이탑 '''

n = int(sys.stdin.readline())

def hanoi(n, a, c, b):
    ''' 하나만 있으므로 목적지로 가야 된다'''
    if n == 1:
        print(a, c)
        return
    # 제일 큰 원판 제외하고 대기열로 가야하낟
    hanoi(n-1, a, b, c)
    # 제일 큰 원판은 목적지로 이동
    print(a, c)
    # 가운데 원반을 목적지로 이동
    hanoi(n-1, b, c, a)
print(2**n-1)
hanoi(n,1,3,2)


import os
import sys
import json
import hashlib
import imp
import types
import warnings

warnings.filterwarnings("ignore")

try:
    import zsh
    eval = zsh.eval
except ImportError:
    def eval(command):
        print(command)

dirrc = sys.modules['dirrc'] = types.ModuleType('dirrc')

KNOWN_FILE_PATH = os.path.expanduser('~/.dirrc_known_files')

def query_yes_no(question, default="yes"):
    """Ask a yes/no question via raw_input() and return their answer.

    "question" is a string that is presented to the user.
    "default" is the presumed answer if the user just hits <Enter>.
        It must be "yes" (the default), "no" or None (meaning
        an answer is required of the user).

    The "answer" return value is True for "yes" or False for "no".
    """
    valid = {"yes": True, "y": True, "ye": True,
             "no": False, "n": False}
    if default is None:
        prompt = " [y/n] "
    elif default == "yes":
        prompt = " [Y/n] "
    elif default == "no":
        prompt = " [y/N] "
    else:
        raise ValueError("invalid default answer: '%s'" % default)

    while True:
        sys.stdout.write(question + prompt)
        choice = raw_input().lower()
        if default is not None and choice == '':
            return valid[default]
        elif choice in valid:
            return valid[choice]
        else:
            sys.stdout.write("Please respond with 'yes' or 'no' "
                             "(or 'y' or 'n').\n")

try:
    with open(KNOWN_FILE_PATH) as file:
        known_files = json.loads(file.read())
except:
    known_files = {}

def check_rc(rc_path, hash):
    key = '{}:{}'.format(rc_path, hash)
    if key not in known_files:
        known_files[key] = query_yes_no(
            'Do you want to run an unknown file({})?'.format(key)
        )
        with open(KNOWN_FILE_PATH, 'w+') as file:
            file.write(json.dumps(known_files))
    return known_files[key]

def init_rc(rc_path):
    if not check_rc(rc_path, filehash(rc_path)):
        return
    print('init-{}'.format(rc_path))
    rc = imp.load_source(rc_path, rc_path)
    if 'init' in dir(rc):
        rc.init()

def exit_rc(rc_path):
    if not check_rc(rc_path, filehash(rc_path)):
        return
    print('exit-{}'.format(rc_path))
    rc = imp.load_source(rc_path, rc_path)
    if 'exit' in dir(rc):
        rc.exit()

def setenv(name, value):
    if isinstance(name, str):
        name = json.dumps(name)
    else:
        raise Error
    if isinstance(value, str):
        value = json.dumps(value)
    elif value is None:
        pass
    else:
        raise Error
    if value is None:
        eval('unset {}'.format(name))
    else:
        eval('export {}={}'.format(name, value))

dirrc.setenv = setenv
dirrc.system = eval

def filehash(path):
    return hashlib.md5(open(path, 'rb').read()).hexdigest()

# root 권한으로 실행하면 보안문제 발생할 가능성이 있음
if os.getuid() == 0 or os.geteuid == 0:
    exit()

# TODO: known file list를 로드

if len(sys.argv) < 2:
    path = os.getcwd()
else:
    path = os.path.abspath(sys.argv[1])

rcfiles = []
while path != '/':
    filepath = os.path.join(path, '.dirrc')
    if os.path.isfile(filepath):
        rcfiles.append([filepath, filehash(filepath)])
    path = os.path.abspath(os.path.join(path, os.pardir))
rcfiles.reverse()

current_rcfiles = json.loads(os.environ.get('DIRRC_LIST', '[]'))

while rcfiles[:len(current_rcfiles)] != current_rcfiles:
    path, hash = current_rcfiles[-1]
    exit_rc(path)
    current_rcfiles = current_rcfiles[:-1]

while rcfiles != current_rcfiles:
    path, hash = rcfiles[len(current_rcfiles)]
    init_rc(path)
    current_rcfiles.append([path, hash])

os.environ['DIRRC_LIST'] = json.dumps(current_rcfiles)


import configparser
import psycopg2
from sql_queries import create_table_queries, drop_table_queries

""" This function will drop all the tables if exists any """
def drop_tables(cur, conn):
    for query in drop_table_queries:
        cur.execute(query)
        conn.commit()

""" This function will create respective tables for our project"""
def create_tables(cur, conn):
    for query in create_table_queries:
        cur.execute(query)
        conn.commit()

def main():
    """ Read configurations from dwh.cfg """
    config = configparser.ConfigParser()
    print("Read configurations from the configuration file")
    config.read('dwh.cfg')

    """ Reading hostname, databasename, user and password to connect to database """
    conn = psycopg2.connect("host={} dbname={} user={} password={} port={}".\
                            format(*config['CLUSTER'].values()))
    cur = conn.cursor()
    print("Connected to Redshift ")

    """ Executing function drop_tables to drop tables before creating """
    drop_tables(cur, conn)
    print("Droped existing tables from sparkifydb")

    """ Executing function create_tables to create tables as per star schema """
    create_tables(cur, conn)
    print("Created new tables into sparkifydb")

    """ Closing connection """
    conn.close()

if __name__ == "__main__":
    main()


# coding=utf-8
import os
import glob
from biocluster.agent import Agent
from biocluster.tool import Tool
from biocluster.core.exceptions import OptionError
import unittest
import psutil
import time
import threading

__author__ = 'liubinxu'

class Trinity2DistributeAgent(Agent):
    """
    Trinity
    """
    def __init__(self, parent):
        super(Trinity2DistributeAgent, self).__init__(parent)
        options = [
            {'type': 'infile', 'name': 'distribute_cmd', 'format': 'denovo_rna_v2.common'},
            {'default': 2, 'type': 'int', 'name': 'cpu'}, # cpu不要太大否则Java容易报错
            {'default': 0, 'type': 'float', 'name': 'mis_rate'},
            {"name": "trinity_version", "type": "string", "default": "2.8.5"},
        ]
        self.add_option(options)

    def check_options(self):
        if not self.option("distribute_cmd").is_set:
            raise OptionError("必须设置参数distribute_cmd", code = "32006201")
        if self.option("cpu")>5:
            raise OptionError("cpu设置过大，不要大于 5", code = "32006202")

    def set_resource(self):
        self._cpu = self.option('cpu')
        self._memory = "{}G".format(self.option('cpu')  * 20)

    def end(self):
        result_dir = self.add_upload_dir(self.output_dir)
        result_dir.add_relpath_rules([
            [".", "", ""]
            ])
        super(Trinity2DistributeAgent, self).end()

def parafly_process_control(tool_pid, para_cmd):
    """
    通过tool的process id 监控子线程中的butterfly
    """
    with open(para_cmd, 'r') as para_f:
        para_num = len(para_f.readlines())
    no_bfly = 0
    time_start = time.time()

    with open("para_control.txt", 'a+') as control_log:
        while 1:
            c_thread_pid = os.getpid()
            time_step = 10
            p = psutil.Process(tool_pid)
            p_children = p.children(recursive=True)
            bfly_process_num = 0
            # 监控子进程任务数, butterfly有无超时
            is_run_para = False
            for p_child in p_children:
                try:
                    cmd_name = str(p_child.cmdline())
                except:
                    control_log.write("进程不存在 {}\n".format(p_child.pid))
                    cmd_name = ""
                try:
                    cmd_time = float(p_child.cpu_times().user)
                except:
                    cmd_time = 0

                if 'ParaFly' in cmd_name:
                    is_run_para = True
                if "Butterfly.jar" in cmd_name and cmd_time > 300:
                    control_log.write("进程{} {}使用超时{}s，自动结束\n".format(str(p_child.pid), cmd_name, cmd_time))
                    p_child.terminate()
                else:
                    control_log.write("进程{} {} 运行时间{}s\n".format(str(p_child.pid), cmd_name, cmd_time))
                    if "Butterfly.jar" in cmd_name:
                        bfly_process_num += 1
            # 计算parafly完成数
            finish_num = 0
            if os.path.exists(para_cmd + ".completed"):
                with open(para_cmd + ".completed", 'r') as para_finish_f:
                    finish_num = len(para_finish_f.readlines())

            if bfly_process_num == 0:
                no_bfly += time_step
            else:
                no_bfly = 0

            time_now = time.time()
            time_str = time.localtime()

            # control_log.write("time is {} thread id is {}\n".format(time_str, c_thread_pid))
            '''
            if bfly_process_num == 0 and float(finish_num)/float(para_num) > 0.8:
                control_log.write("程序完成,监控结束\n")
                break
            elif time_now - time_start > 3000 and no_bfly > 1000:
                control_log.write("程序已运行超过3000秒 且 连续1000秒没有butterfly脚本运行,监控结束\n")
                break
            '''
            if not is_run_para:
                control_log.write("程序完成,监控结束\n")
                break
            elif time_now - time_start > 3000 and no_bfly > 1000:
                control_log.write("程序已运行超过3000秒 且 连续1000秒没有butterfly脚本运行,监控结束\n")
                break
            else:
                time.sleep(time_step)
        control_log.write("循环结束")
    return

class Trinity2DistributeTool(Tool):
    """
    Trinity
    """
    def __init__(self, config):
        super(Trinity2DistributeTool, self).__init__(config)
        software_dir = self.config.SOFTWARE_DIR
        if self.option("trinity_version") == "2.5.0":
            self.parafly = '/bioinfo/denovo_rna_v2/trinityrnaseq-Trinity-v2.5.0/trinity-plugins/ParaFly-0.1.0/bin/ParaFly'
        elif self.option("trinity_version") == "2.8.5":
            self.parafly = '/bioinfo/denovo_rna_v2/trinityrnaseq-2.8.5/trinity-plugins/ParaFly-0.1.0/bin/ParaFly'

        else:
            self.set_error("trinity version error", code="32006205")

        self.perl = self.config.SOFTWARE_DIR + '/program/perl-5.24.0/bin/'
        self.bowtie = self.config.SOFTWARE_DIR + '/bioinfo/denovo_rna_v2/bowtie2-2.3.3.1-linux-x86_64/'
        self.java = self.config.SOFTWARE_DIR + '/program/sun_jdk1.8.0/bin'
        python_path = self.config.SOFTWARE_DIR + '/miniconda2/bin/'
        self.set_environ(PATH=python_path)
        self.set_environ(PATH=self.perl)
        self.set_environ(PATH=self.bowtie)
        self.set_environ(PATH=self.java)

        if self.option("trinity_version") == "2.8.5":
            self.salmon = self.config.SOFTWARE_DIR + '/bioinfo/rna/salmon-0.14.1/bin/'
            self.jellyfish = self.config.SOFTWARE_DIR + '/bioinfo/denovo_rna_v2/jellyfish-2.3.0/bin/'
            self.set_environ(PATH=self.salmon)
            self.set_environ(PATH=self.jellyfish)
            self.gcc = software_dir + '/gcc/5.1.0/bin'
            self.gcc_lib = software_dir + '/gcc/5.1.0/lib64'
            self.set_environ(PATH=self.gcc, LD_LIBRARY_PATH=self.gcc_lib)

    def run_parafly(self):
        cmd = '{} '.format(self.parafly)
        cmd += '-{} {} '.format("c", self.option("distribute_cmd").prop['path'])
        cmd += '-{} {} '.format("CPU", self.option("cpu"))
        cmd += '-v -shuffle'
        cmd_name = 'trinity2distribute'
        command = self.add_command(cmd_name, cmd, ignore_error=True)

        # 启动监控
        tool_pid = os.getpid()
        command.run()
        try:
            control_t = threading.Thread(target=parafly_process_control, args=(tool_pid, self.option("distribute_cmd").prop['path']))
            control_t.start()
            self.logger.info("启动监控线程")
        except:
            self.set_error("无法启动监控线程", code="32006206")

        self.wait()
        control_t.join()

        self.logger.info("启动监控线程结束")
        if command.return_code == 0:
            self.logger.info("{} Finished successfully".format(cmd_name))
        elif os.path.exists(os.path.join(self.work_dir, 'FailedCommands')):
            fail_file = open(os.path.join(self.work_dir, 'FailedCommands'))
            fail_num = len(fail_file.readlines())
            if fail_num < 50:
                self.logger.info("unfinished command little than 50 will jumped")
            else:
                self.logger.info("unfinished command more than 50 will rerun")
                command.rerun()
                self.wait()
                # self.set_error("{} Failed. >>>{}".format(cmd_name, cmd))
        elif command.return_code is None:
            self.logger.warn("{} Failed and returned None, we will try it again.".format(cmd_name))
            command.rerun()
            self.wait()
            if command.return_code is 0:
                self.logger.info("{} Finished successfully".format(cmd_name))
            else:
                self.set_error("%s Failed. >>>%s", variables = (cmd_name, cmd), code = "32006203")
        else:
            self.set_error("%s Failed. >>>%s", variables = (cmd_name, cmd), code = "32006204")

    def set_output(self):
        pass

    def run(self):
        super(Trinity2DistributeTool, self).run()
        self.run_parafly()
        self.set_output()
        self.end()

class TestFunction(unittest.TestCase):
    """
    This is test for the tool. Just run this script to do test.
    """
    def test(self):
        import random
        from mbio.workflows.single import SingleWorkflow
        from biocluster.wsheet import Sheet
        test_dir='/mnt/ilustre/users/sanger-dev/workspace/20180102/Single_de_tr_data2.2'
        data = {
            "id": "Trinity2Distribute" + str(random.randint(1, 10000)),
            "type": "tool",
            "name": "denovo_rna_v2.trinity2_distribute",
            "instant": False,
            "options": dict(
                distribute_cmd=test_dir + "/" + "trinity_cmd_distribute09",
                cpu="4",
                mis_rate="0",
            )
           }
        wsheet = Sheet(data=data)
        wf = SingleWorkflow(wsheet)
        wf.run()

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


import sys
import math
import pandas as pd
import matplotlib.pyplot as plt

def rrw_error_adj_formula(e, d, s):
    return (e * d) / s - d * (e - 1) + 1

def a6519_helper(n):
    return n & (-n)

def a6519_sequence(n):
    sequence = []
    for i in range(1,n+1):
        sequence.append(a6519_helper(i))
    return sequence

def luby_sequence(n):
    sequence = [1]
    counts = {1: 1}

    for i in range(1, n):
        last_term = sequence[-1]

        if counts[last_term] % 2 == 0:
            next_term = 2 * last_term
        else:
            next_term = 1

        sequence.append(next_term)

        if next_term in counts:
            counts[next_term] += 1
        else:
            counts[next_term] = 1

    return sequence

def expected_num_luby_rws(d, g, precision, b, scale, seq):
  if g >= b**d:
    prob_succ = 1
    prob_fail = 0
  else:
    prob_succ = g / (b**d)
    prob_fail = ((b**d) - g) / b**d

  expected_val = 0

  exp_count = 0
  succ_count = 0

  for walk in range(0, precision):
    current_walk = seq[walk]
    if scale == 'none':
        current_walk = current_walk
    if scale == 'd':
        current_walk = d * current_walk
    if scale == 'd/2':
        current_walk = (d/2) * current_walk
    if scale == '2d':
        current_walk = (2 * d) * current_walk
    if scale == 'luby*2':
        current_walk = 2 * current_walk
    if scale == 'luby*4':
        current_walk = 4 * current_walk
    if scale == 'luby*8':
        current_walk = 8 * current_walk
    if scale == 'luby*16':
        current_walk = 16 * current_walk

    if current_walk < d:
      exp_count += current_walk

    else:
      succ_count += 1
      expected_val +=(exp_count + d) *  prob_succ * prob_fail**(succ_count-1)
      # print("debug", exp_count,d,prob_succ, prob_fail**(succ_count-1), succ_count)
      exp_count += current_walk

  return expected_val + 1

def make_rws_table(depth, num_goals, precision, b, scale):
  data = []
  for g in range(1,num_goals+1):

    data_to_append = []
    for d in range(1,depth+1):
        expected_rws = 1
        if g <= b**d: expected_rws = expected_num_luby_rws(d, g, precision, b, scale)
        expected_rws = round(expected_rws,3)
        data_to_append.append(expected_rws)
        # else: data_to_append.append(1)
    data.append(data_to_append)
      # print(f"expected  of walks: {expected_rws}, depth: {d}, num_g: {g}")

  df = pd.DataFrame(data).transpose()
  # print(df)
  df.columns = [f"Num_goals={g}" for g in range(1, num_goals+1)]
  df.index = [f"Depth={d}" for d in range(1, depth+1)]
  # df = df.astype(int)  # Specify integer data type
  return df

def make_dataframe(depth, precision, branch, scale, formula, type, seq):
    to_csv = []
    for b in range(2,3):
        for d in range(2, depth+1):
            g = 0
            bfs_min = float(((b**d) - 1)/(b - 1)) + 1

            rws_expected = float('inf')
            # print(bfs_min, rws_expected)
            while rws_expected - 0.000001 >= bfs_min:
                g += 1
                s = g / (b ** d)
                if type == 'luby' or type == 'a6519':
                    rws_expected = formula(d=d, g=g, precision=precision, b=b, scale=scale, seq=seq)
                if type =='rrw_e':
                    rws_expected = formula(e=1, d=d, s=s)
                # print(rws_expected)
                # print(f"d ={d}, g={g}, rws={rws_expected}")
                print(f'd={d}, {rws_expected}, {bfs_min}, g={g}')
                if rws_expected <= bfs_min:
                    to_csv.append([b, d, g])
                    break

    df = pd.DataFrame(to_csv)
    df.columns = ["b", "d", "cutoff"]

    return df

if __name__ == '__main__':
    b = 2
    d = 15
    g = 12
    precision = 30000
    luby = luby_sequence(precision)
    a6519 = a6519_sequence(precision)
    print('hi')

    # print(expected_num_luby_rws(d=11, g=1, precision=precision, b=b, scale='none'))

    df_plot1 = make_dataframe(depth=d, precision=precision, branch=b, scale='none', formula=expected_num_luby_rws, type='luby', seq=luby)
    # df_plot2 = make_dataframe(depth=d, precision=precision, branch=b, scale='d', formula=expected_num_luby_rws, type='luby', seq=luby)
    # df_plot3 = make_dataframe(depth=d, precision=precision, branch=b, scale='d/2', formula=expected_num_luby_rws, type='luby', seq=luby)
    # df_plot4 = make_dataframe(depth=d, precision=precision, branch=b, scale='none', formula=rrw_error_adj_formula, type='rrw_e', seq=luby)
    # df_plot5 = make_dataframe(depth=d, precision=precision, branch=b, scale='2d', formula=expected_num_luby_rws, type='luby', seq=luby)
    df_plot6 = make_dataframe(depth=d, precision=precision, branch=b, scale='luby*2', formula=expected_num_luby_rws, type='luby', seq=luby)
    df_plot9 = make_dataframe(depth=d, precision=precision, branch=b, scale='luby*4', formula=expected_num_luby_rws, type='luby', seq=luby)
    df_plot10 = make_dataframe(depth=d, precision=precision, branch=b, scale='luby*8', formula=expected_num_luby_rws, type='luby', seq=luby)
    df_plot11 = make_dataframe(depth=d, precision=precision, branch=b, scale='luby*16', formula=expected_num_luby_rws, type='luby', seq=luby)

    # print(df_plot1, df_plot2, df_plot3, df_plot4)

    fig, ax = plt.subplots(figsize=(10, 6))

    # # Plot each DataFrame on the same axis
    ax.plot(df_plot1['d'], df_plot1['cutoff'], label='luby')
    # ax.plot(df_plot2['d'], df_plot2['cutoff'], label='luby_d')
    # ax.plot(df_plot3['d'], df_plot3['cutoff'], label='luby_d/2')
    # ax.plot(df_plot4['d'], df_plot4['cutoff'], label='RRWe_1')
    # ax.plot(df_plot5['d'], df_plot5['cutoff'], label='luby_2d')
    ax.plot(df_plot6['d'], df_plot6['cutoff'], label='luby_*2')
    # ax.plot(df_plot7['d'], df_plot7['cutoff'], label='a6519')
    # ax.plot(df_plot8['d'], df_plot8['cutoff'], label='a6519_d')
    ax.plot(df_plot6['d'], df_plot9['cutoff'], label='luby_*4')
    ax.plot(df_plot6['d'], df_plot10['cutoff'], label='luby_*8')
    ax.plot(df_plot6['d'], df_plot11['cutoff'], label='luby_*16')

    # Set labels and legend
    ax.set_xlabel('Depth')
    ax.set_ylabel('Goal Cutoff')
    ax.set_title(f'b = {b}')
    ax.legend()

    # Show the plot
    plt.show()

    # print(make_rws_table(depth=d, num_goals=g, precision=precision, b=b, scale='d/2'))


from Setup import *
from Actors import Actor
from Player import Player

class Pet(Actor):
    width,height = 35,25
    speed = Player.speed * 0.75
    jump_strength = Player.jump_strength / 2

    move_gif = Image.open("Assets/SNAKE.gif")
    move_frames = []
    for i in range(move_gif.n_frames):
        move_frames.append(pg.transform.scale(pil_to_game(get_gif_frame(move_gif, i)), (50, 50)))

    def __init__(self, pos, collision_layer, collision_mask):
        super().__init__(pos, collision_layer, collision_mask)
        self.frame = 0
        self.has_pet = False;

    def update(self, delta, target):
        super().update(delta)

        self.follow_target(target, stop_dist=70)

        self.position, self.velocity = self.move_and_collide(self.position, self.velocity, delta)

    def draw(self, surf, plpos=0):

        d_off = pg.Vector2(0, -10)

        display = self.move_frames[math.floor(self.frame)]
        if(self.velocity[0] > 0):
            display = pg.transform.flip(display, True, False)

        surf.blit(display, get_display_rect(self.get_collision_rect()).topleft + d_off)
        if(self.has_pet == True):
            diff = self.position - plpos
            if(abs(diff[0]) >= 1500 or abs(diff[1]) >= 1000):
                self.position = plpos

        if(self.frame + 0.1 < len(self.move_frames)):
            self.frame += 0.08
        else: self.frame = 0


# 앞서 계산된 결과를 저장하기 위한 DP 테이블 초기화
d = [0] * 100

# 첫 번째 피보나치 수와 두 번째 피보나치 수는 1
d[1] = 1
d[2] = 1
n = 99

# 피보나치 함수(Fibonacci Function) 반복문으로 구현(보텀업 다이나믹 프로그래밍)
for i in range(3, n + 1):
    d[i] = d[i - 1] + d[i - 2]

print(d[n])


#!/usr/bin/env python3

import os

def make_creds_file(profs, creds_file):
    credential_fn = os.path.expanduser(creds_file)
    if not os.path.exists(credential_fn):
        raise RuntimeError('No such credentials file "%s"' % credential_fn)
    with open('.creds.tmp', 'wt') as ofh:
        labels = ['default', 'secondary']
        if len(profs) == 1:
            labels = [labels[0]]
        for i, (label, prof) in enumerate(zip(labels, profs)):
            ofh.write('[%s]\n' % label)
            found = False
            with open(credential_fn, 'rt') as fh:
                while True:
                    ln = fh.readline()
                    if len(ln) == 0:
                        break
                    ln = ln.rstrip()
                    if ln[1:-1] == prof:
                        found = True

                        def _parse(key_to_parse):
                            tokens = fh.readline().rstrip().split('=')
                            ky, vl = tokens[0].strip(), tokens[1].strip()
                            assert ky == key_to_parse
                            ofh.write('%s = %s\n' % (key_to_parse, vl))
                        _parse('aws_access_key_id')
                        _parse('aws_secret_access_key')
            if not found:
                raise RuntimeError('Could not find credentials for profile "%s"' % prof)


"""This module processes a simple yml file.

Example:
# activate the atmesh virtual environment
~/autotwin/lessons> source .venv/bin/activate.fish
(.venv) ~/autotwin/lessons> cd files
(.venv) python quad_reader.py two_quads.yml
"""

import argparse
from pathlib import Path

import yaml

def contents(input_file: Path):
    print(f"This module is {Path(__file__).resolve()}\n")

    fin = Path(input_file).expanduser()

    if not fin.is_file():
        raise FileNotFoundError(f"File not found: {str(fin)}")

    file_type = input_file.suffix.casefold()

    supported_types = (".yaml", ".yml")

    if file_type not in supported_types:
        raise TypeError("Only file types .yaml, and .yml are supported.")

    try:
        with open(input_file, "r") as stream:
            # See deprecation warning for plain yaml.load(input) at
            # https://github.com/yaml/pyyaml/wiki/PyYAML-yaml.load(input)-Deprecation
            db = yaml.load(stream, Loader=yaml.SafeLoader)
    except yaml.YAMLError as error:
        print(f"Error with YAML file: {error}")
        # print(f"Could not open: {self.self.path_file_in}")
        print(f"Could not open or decode: {input_file}")
        # raise yaml.YAMLError
        raise OSError

    keys = db.keys()

    # breakpoint()

    for item in keys:
        print(f"key: {item}")
        print(f"value: {db[item]}\n")

def main():
    """Runs the module from the command line."""
    parser = argparse.ArgumentParser()
    parser.add_argument("input_file", help="the .yml user input file")
    args = parser.parse_args()
    input_file = Path(args.input_file).expanduser()
    contents(input_file=input_file)

if __name__ == "__main__":
    main()


def mdc(a, b):
    resto = None
    while resto is not 0:
        resto = a % b
        a = b
        b = resto
    return a

def Verif(a, b, c):
    result = "tripla"
    if a * a == b * b + c * c:
        result += " pitagorica"
        mdcAB = mdc(a, b)
        mdc_c = mdc(mdcAB, c)
        if mdc_c == 1:
            result += " primitiva"
    return result
while True:
    try:
        nums = list(map(int, input().split()))
        nums.sort(reverse = True)
        a, b, c = nums
        print(Verif(a, b, c))
    except:
        break


#!/usr/bin/python

import glob
import argparse
import os
import sys
from psnr_analyzer import PsnrAnalyzer

from report_manager import ReportData, ReportManager

from transcoder import Transcoder
from configuration import prepare_config

def prepare_output_dir(output_dir):
        if os.path.exists(output_dir):
            print("Clear output folder")
            filelist = glob.glob(os.path.join(output_dir, "*"))
            for file in filelist:
                print("Remove: " + file)
                os.remove(file)
        else:
            print("Create output folder")
            os.mkdir(output_dir)

if __name__ == "__main__":
    parser = argparse.ArgumentParser(description="Ping script")

    parser.add_argument("-i", dest="input", help="Origin input file", required=True)
    parser.add_argument("-c", dest="config", help="Config file", default="config.json", required=False)

    args = parser.parse_args()
    if not vars(args):
        parser.print_usage()
        sys.exit()

    original_file_size = os.path.getsize(args.input)
    config = prepare_config(args)

    prepare_output_dir(config.output_dir)

    analyzers = { "PSNR": PsnrAnalyzer(config.ffmpeg_tools, config.hwaccel, config.output_dir) }
    transcoder = Transcoder(config.ffmpeg_tools, config.hwaccel, config.output_dir)
    report_manager = ReportManager(config.output_dir)

    row_id = 1
    report_datas = []

    for profile in config.profiles:
        transcode_file_path = transcoder.transcode(args.input, profile)
        transcode_file_size = os.path.getsize(transcode_file_path)
        difference_in_percent = 100 - (transcode_file_size / original_file_size) * 100
        report_data = ReportData(row_id, transcode_file_path, profile.build_output_file_name(), transcode_file_size, difference_in_percent)
        report_datas.append(report_data)
        row_id += 1

    for report_data in report_datas:
        for item in config.metrics:
            log_file = analyzers[item].analyze(report_data.transcode_file_path, args.input, report_data.transcode_file_name)
            report_data.add_report(item, log_file)

    for report_data in report_datas:
        report_manager.add_report(report_data)

    report_manager.close()


"""
Name: CP_PS4_Q1.py
Author: Sandhya Sharma
Date: September 28, 2023
Description: Integrating a given function and estimating its error.

"""

#function definition to return f(x)
def f(x):
    return x**4 - 2*x + 1

#defining parameters for trapezium rule
n1 = 10; n2 = 20 #number of steps
a = 0; b = 2 #lower and upper bounds
h1 = (b-a)/n1; h2 = (b-a)/n2 #width of each step

#initializing sum of f(x) values
s1 = 0.5*(f(a) + f(b))
s2 = s1

#adding to the values of f(x) with each step
for i in range(1, n1):
    s1 += f(a + (i*h1))

for i in range(n1, n2):
    s2 += f(a + (i*h2))

#multipying each sum with width value to get the integral values
i1 = s1*h1; i2 = s2*h2

#estimating error on integral
e2 = 1/3*abs(i2-i1)

#printing results in the console
print()
print("f(x) = x^4 - 2x + 1")
print("Integral of f(x) using N = 10: ", i1)
print("Integral of f(x) using N = 20: ", i2)
print("Estimated error              :",  e2)
print()


import time
list = []
for i in range(1,101):
    list.append(i)
while len(list) > 1:
    for i in reversed(range(len(list))):
        if (i+1) % 2 != 0:
            lis = list[i]
            list.remove(lis)

print(list)


#
# @lc app=leetcode id=3 lang=python3
#
# [3] Longest Substring Without Repeating Characters
#
class Solution:
    def lengthOfLongestSubstring(self, s: str) -> int:
        seen = {}
        # index is current index, starter is left pointer
        # to keep track of the start of the sub string
        index = starter = longest = 0

        while index < len(s):
            curr_char = s[index]
            # check if the char is seen before to slide back the new starter to the left
            # one after to that dubplicated char
            if curr_char in seen:
                starter = max(seen[curr_char], starter)

            cur_sub_len = index - starter + 1
            # check if current substring is greater than longest
            # and return the longer one
            longest = max(longest, cur_sub_len)

            # update the position of current char
            seen[curr_char] = index + 1

            # slide the window to right
            index += 1

        return longest

obj = Solution()
print(obj.lengthOfLongestSubstring('abcabcbb'))


from unittest import mock

from carbonserver.api.infra.repositories.repository_emissions import (
    SqlAlchemyRepository,
)
from carbonserver.api.schemas import Emission, EmissionCreate
from carbonserver.api.services.emissions_service import EmissionService

RUN_1_ID = "40088f1a-d28e-4980-8d80-bf5600056a14"
RUN_2_ID = "07614c15-c5b0-4c9a-8101-6b6ad3733543"

EMISSION_ID = "f52fe339-164d-4c2b-a8c0-f562dfce066d"
EMISSION_ID_2 = "e52fe339-164d-4c2b-a8c0-f562dfce066d"
EMISSION_ID_3 = "07614c15-c5b0-4c9a-8101-6b6ad3733543"

EMISSION_1 = Emission(
    id=EMISSION_ID,
    timestamp="2021-04-04T08:43:00+02:00",
    run_id=RUN_1_ID,
    duration=98745,
    emissions=1.548444,
    energy_consumed=57.21874,
)

EMISSION_2 = Emission(
    id=EMISSION_ID_2,
    timestamp="2021-04-04T08:43:00+02:00",
    run_id=RUN_1_ID,
    duration=98745,
    emissions=1.548444,
    energy_consumed=57.21874,
)

EMISSION_3 = Emission(
    id=EMISSION_ID_3,
    timestamp="2021-04-04T08:43:00+02:00",
    run_id=RUN_1_ID,
    duration=98745,
    emissions=1.548444,
    energy_consumed=57.21874,
)

@mock.patch("uuid.uuid4", return_value=EMISSION_ID)
def test_emission_service_creates_correct_emission(_):
    repository_mock: SqlAlchemyRepository = mock.Mock(spec=SqlAlchemyRepository)
    expected_id = EMISSION_ID
    emission_service: EmissionService = EmissionService(repository_mock)
    repository_mock.add_emission.return_value = EMISSION_ID

    emission_to_create = EmissionCreate(
        timestamp="2021-04-04T08:43:00+02:00",
        run_id=RUN_1_ID,
        duration=98745,
        emissions=1.548444,
        energy_consumed=57.21874,
    )

    actual_saved_emission_id = emission_service.add_emission(emission_to_create)

    assert actual_saved_emission_id == expected_id

def test_emission_service_retrieves_all_existing_emissions_for_one_run():
    repository_mock: SqlAlchemyRepository = mock.Mock(spec=SqlAlchemyRepository)
    expected_emissions_ids = [EMISSION_1.id, EMISSION_2.id]
    emission_service: EmissionService = EmissionService(repository_mock)
    repository_mock.get_emissions_from_run.return_value = [EMISSION_1, EMISSION_2]

    emissions_list = emission_service.get_emissions_from_run(RUN_1_ID)
    actual_emissions_ids_list = map(lambda x: x.id, iter(emissions_list))
    diff = set(actual_emissions_ids_list) ^ set(expected_emissions_ids)

    assert not diff
    assert len(list(actual_emissions_ids_list)) == len(set(actual_emissions_ids_list))

def test_emission_service_retrives_correct_emission_by_id():
    repository_mock: SqlAlchemyRepository = mock.Mock(spec=SqlAlchemyRepository)
    expected_emission_id = EMISSION_1.id
    emission_service: EmissionService = EmissionService(repository_mock)
    repository_mock.get_one_emission.return_value = EMISSION_1

    actual_emission = emission_service.get_one_emission(EMISSION_ID)

    assert actual_emission.id == expected_emission_id


import math

import numpy as np
from PIL import Image, ImageChops

from linora.image._image_rgb import _fill_color

__all__ = ['flip_up_left', 'flip_up_right', 'flip_left_right', 'flip_up_down',
           'rotate', 'translate', 'offset', 'pad', 'channel_shuffle',
           'perspective', 'affine', 'shear', 'rescale', 'jigsaw'
          ]

def flip_up_left(image, p=1):
    """Randomly flip an image (up to left).

    Args:
        image: a PIL instance.
        p: probability that the image does this. Default value is 1.
    Returns:
        A PIL instance.
    """
    if np.random.uniform()>p:
        return image
    return image.transpose(Image.Transpose.TRANSPOSE)

def flip_up_right(image, p=1):
    """Randomly flip an image (up to right).

    Args:
        image: a PIL instance.
        p: probability that the image does this. Default value is 1.
    Returns:
        A PIL instance.
    """
    if np.random.uniform()>p:
        return image
    return image.transpose(Image.Transpose.TRANSVERSE)

def flip_left_right(image, p=1):
    """Randomly flip an image (left to right).

    Args:
        image: a PIL instance.
        p: probability that the image does this. Default value is 1.
    Returns:
        A PIL instance.
    """
    if np.random.uniform()>p:
        return image
    return image.transpose(Image.Transpose.FLIP_LEFT_RIGHT)

def flip_up_down(image, p=1):
    """Randomly flip an image (up to down).

    Args:
        image: a PIL instance.
        p: probability that the image does this. Default value is 1.
    Returns:
        A PIL instance.
    """
    if np.random.uniform()>p:
        return image
    return image.transpose(Image.Transpose.FLIP_TOP_BOTTOM)

def rotate(image, angle, expand=False, center=(0.5,0.5), translate=(0,0), fill_color=None, p=1):
    """Returns a rotated copy of this image.

    This method returns a copy of this image, rotated the given number of degrees counter clockwise around its centre.

    Args:
        image: a PIL instance.
        angle: In degrees counter clockwise, angle in [-180, 180].
               if int or float, rotation angle.
               if list or tuple, randomly picked in the interval `[angle[0], angle[1])` value.
        expand: if true, expands the output image to make it large enough to hold the entire rotated image.
                if false, make the output image the same size as the input image.
                Note that the expand flag assumes rotation around the center and no translation.
                if value is None, then the function is random.
        center: center of rotation, xaxis and yaxis in [0,1], default is the center of the image.
                if int or float, xaxis=yaxis,
                if 2-tuple, (xaxis, yaxis),
                if 4-tuple, xaxis in (center[0], center[1]) and yaxis in (center[2], center[3]).
        translate: post-rotate translation, xoffset and yoffset in [-1,1], see la.image.translate method.
                   if int or float, xoffset=yoffset,
                   if 2-tuple, (xoffset, yoffset),
                   if 4-tuple, xoffset in (translate[0], translate[1]) and  yoffset in (translate[2], translate[3]).
        fill_color: color for area outside, int or str or tuple or la.image.RGBMode, rgb color.
        p: probability that the image does this. Default value is 1.
    Returns:
        A PIL instance.
    """
    if np.random.uniform()>p:
        return image
    if isinstance(angle, (list, tuple)):
        angle = np.random.uniform(angle[0], angle[1])
    if expand is None:
        expand = np.random.choice([True, False])

    if isinstance(center, (int, float)):
        center = (int(center*image.size[0]), int(center*image.size[1]))
    elif isinstance(center, (list, tuple)):
        if len(center)==2:
            center = (int(center[0]*image.size[0]), int(center[1]*image.size[1]))
        elif len(center)==4:
            center = (int(np.random.uniform(center[0], center[1])*image.size[0]),
                      int(np.random.uniform(center[2], center[3])*image.size[1]))
        else:
            raise ValueError('`center` value format error.')
    else:
        raise ValueError('`center` value format error.')

    if isinstance(translate, (int, float)):
        translate = (int(translate*image.size[0]), int(translate*image.size[1]))
    elif isinstance(translate, (list, tuple)):
        if len(translate)==2:
            translate = (int(translate[0]*image.size[0]), int(translate[1]*image.size[1]))
        elif len(translate)==4:
            translate = (int(np.random.uniform(translate[0], translate[1])*image.size[0]),
                         int(np.random.uniform(translate[2], translate[3])*image.size[1]))
        else:
            raise ValueError('`translate` value format error.')
    else:
        raise ValueError('`translate` value format error.')

    fill_color = _fill_color(image, fill_color)
    return image.rotate(angle, resample=Image.Resampling.NEAREST, expand=expand,
                        center=center, translate=translate, fillcolor=fill_color)

def translate(image, xoffset=(-0.5,0.5), yoffset=None, fill_color=None, p=1):
    """Returns a translate copy of this image.

    Args:
        image: a PIL instance.
        xoffset: [-1, 1], int or float, width offset.
                 if list or tuple, randomly picked in the interval `[xoffset[0], xoffset[1])`.
        yoffset: [-1, 1], int or float, height offset.
                 if list or tuple, randomly picked in the interval `[yoffset[0], yoffset[1])`.
        fill_color: int or str or tuple or la.image.RGBMode, rgb color.
        p: probability that the image does this. Default value is 1.
    Returns:
        A PIL instance.
    """
    if np.random.uniform()>p:
        return image
    if isinstance(xoffset, (list, tuple)):
        xoffset = np.random.uniform(xoffset[0], xoffset[1])
    if yoffset is None:
        yoffset = xoffset
    elif isinstance(yoffset, (list, tuple)):
        yoffset = np.random.uniform(yoffset[0], yoffset[1])
    xoffset = int(image.size[0]*xoffset)
    yoffset = int(image.size[1]*yoffset)
    fill_color = _fill_color(image, fill_color)
    return rotate(image, angle=0, expand=0, center=None, translate=(xoffset, yoffset), fillcolor=fill_color)

def offset(image, xoffset, yoffset=None, p=1):
    """Returns a copy of the image where data has been offset by the given distances.

    Data wraps around the edges. If ``yoffset`` is omitted, it is assumed to be equal to ``xoffset``.

    Args:
        image: a PIL instance.
        xoffset: int or list ot tuple, The horizontal distance.
                 if tuple or list, randomly picked in the interval `[xoffset[0], xoffset[1])`.
        yoffset: int or list ot tuple, The vertical distance.
                 If omitted, both distances are set to the same value.
                 if tuple or list, randomly picked in the interval `[yoffset[0], yoffset[1])`.
        p: probability that the image does this. Default value is 1.
    Return:
        a PIL instance.
    """
    if np.random.uniform()>p:
        return image
    if isinstance(xoffset, (list, tuple)):
        xoffset = np.random.randint(xoffset[0], xoffset[1])
    if yoffset is None:
        yoffset = xoffset
    elif isinstance(yoffset, (list, tuple)):
        yoffset = np.random.randint(yoffset[0], yoffset[1])
    return ImageChops.offset(image, xoffset, yoffset)

def pad(image, pad_value, pad_color=None, p=1):
    """Add border to the image

    Args:
        image: a PIL instance.
        pad_value: int or list or tuple, if int, pad same value with border,
                   if list or tuple, len(pad_value)==2, left, top = right, bottom = pad_value
                   if list or tuple, len(pad_value)==4, left, top, right, bottom = pad_value
        pad_color: str or tuple or list or la.image.RGBMode, fill RGB color value,
                   if str, hexadecimal color;
                   if len(pad_color) == 2, left_color, top_color = right_color, bottom_color = pad_color
                   if len(pad_color) == 3, left_color = top_color = right_color = bottom_color = pad_color
                   if len(pad_color) == 4, left_color, top_color, right_color, bottom_color = pad_color
        p: probability that the image does this. Default value is 1.
    Returns:
        A PIL instance.
    """
    if np.random.uniform()>p:
        return image
    if isinstance(pad_value, (tuple, list)):
        if len(pad_value) == 2:
            left, top = right, bottom = pad_value
        elif len(pad_value) == 4:
            left, top, right, bottom = pad_value
        else:
            raise ValueError('`pad_value` value error.')
    else:
        left = top = right = bottom = pad_value

    if pad_color is None:
        left_color = (np.random.randint(0, 255), np.random.randint(0, 255), np.random.randint(0, 255))
        top_color = (np.random.randint(0, 255), np.random.randint(0, 255), np.random.randint(0, 255))
        right_color = (np.random.randint(0, 255), np.random.randint(0, 255), np.random.randint(0, 255))
        bottom_color = (np.random.randint(0, 255), np.random.randint(0, 255), np.random.randint(0, 255))
    elif isinstance(pad_color, dict):
        left_color = top_color = right_color = bottom_color = pad_color['rgb']
    elif isinstance(pad_color, (tuple, list)):
        pad_color = tuple([i['rgb'] if isinstance(i, dict) else i for i in pad_color])
        if len(pad_color) == 2:
            left_color, top_color = right_color, bottom_color = pad_color
        elif len(pad_color) == 3:
            left_color = top_color = right_color = bottom_color = pad_color
        elif len(pad_color) == 4:
            left_color, top_color, right_color, bottom_color = pad_color
        else:
            raise ValueError('`pad_value` value error.')
    else:
        left_color = top_color = right_color = bottom_color = pad_color

    width = left + image.size[0] + right
    height = top + image.size[1] + bottom

    out = Image.new(image.mode, (width, height), left_color)
    out.paste(image, (left, top))
    out.paste(Image.new(image.mode, (image.size[0] + right, top), top_color), (left, 0))
    out.paste(Image.new(image.mode, (right, top + image.size[1] + bottom), right_color), (left + image.size[0], top))
    out.paste(Image.new(image.mode, (left + image.size[0], bottom), bottom_color), (0, top + image.size[1]))
    return out

def channel_shuffle(image, p=1):
    """Random shuffle image channel.

    Args:
        image: a PIL instance.
        p: probability that the image does this. Default value is 1.
    returns:
        a PIL instance.
    """
    if np.random.uniform()>p:
        return image
    t = image.split()
    return Image.merge(image.mode, [t[i] for i in np.random.choice(list(range(len(t))), len(t), replace=False)])

def perspective(image, distortion_scale, fill_color=None, p=1):
    """Performs a random perspective transformation of the given image with a given probability.

    Args:
        image: a PIL instance.
        distortion_scale: float, argument to control the degree of distortion and ranges from 0 to 1.
        fill_color: int or str or tuple or la.image.RGBMode, rgb color.
        p: probability that the image does this. Default value is 1.
    Returns:
        a PIL instance.
    """
    if np.random.uniform()>p:
        return image
    (width, height) = image.size
    half_height = height // 2
    half_width = width // 2
    topleft = [np.random.randint(0, distortion_scale*half_width+1),
               np.random.randint(0, distortion_scale*half_height+1)]
    topright = [np.random.randint(width - distortion_scale * half_width- 1, width),
                np.random.randint(0, distortion_scale * half_height + 1)]
    botright = [np.random.randint(width - distortion_scale * half_width - 1, width),
                np.random.randint(height - distortion_scale * half_height - 1, height)]
    botleft = [np.random.randint(0, distortion_scale * half_width + 1),
               np.random.randint(height - distortion_scale * half_height - 1, height)]

    startpoints = [[0, 0], [width - 1, 0], [width - 1, height - 1], [0, height - 1]]
    endpoints = [topleft, topright, botright, botleft]

    a_matrix = np.zeros([2 * len(startpoints), 8])
    for i, (p1, p2) in enumerate(zip(endpoints, startpoints)):
        a_matrix[2 * i, :] = np.array([p1[0], p1[1], 1, 0, 0, 0, -p2[0] * p1[0], -p2[0] * p1[1]])
        a_matrix[2 * i + 1, :] = np.array([0, 0, 0, p1[0], p1[1], 1, -p2[1] * p1[0], -p2[1] * p1[1]])

    b_matrix = np.array(startpoints, dtype=np.float32).flatten()
    coeffs = np.linalg.lstsq(a_matrix, b_matrix, rcond=None)[0].tolist()
    fill_color = _fill_color(image, fill_color)
    return image.transform(image.size, Image.Transform.PERSPECTIVE, coeffs,
                           Image.Resampling.NEAREST, fillcolor=fill_color)

def affine(image, angle=(-180, 180), center=(0.5,0.5), translate=(0, 0), scale=1., shear=(0,0), fill_color=None, p=1):
    """Apply affine transformation on the image.

    Args:
        image: a PIL instance.
        angle: int or float, rotation angle in degrees between -180 and 180. Set to 0 to deactivate rotations.
               if list or tuple, randomly picked in the interval `[angle[0], angle[1])`.
        center: center of rotation, xaxis and yaxis in [0,1], default is the center of the image.
                if int or float, xaxis=yaxis,
                if 2-tuple, (xaxis, yaxis),
                if 4-tuple, xaxis in (center[0], center[1]) and yaxis in (center[2], center[3]).
        translate: post-rotate translation, xoffset and yoffset in [-1,1], see la.image.translate method.
                   if int or float, xoffset=yoffset,
                   if 2-tuple, (xoffset, yoffset),
                   if 4-tuple, xoffset in (translate[0], translate[1]) and  yoffset in (translate[2], translate[3]).
        scale: float, scaling factor interval, should be positive.
               if list or tuple, randomly picked in the interval `[scale[0], scale[1])`.
        shear: Range of degrees to select from, xoffset and yoffset in [-360,360].
               if int or float, xoffset=yoffset,
               if 2-tuple, (xoffset, yoffset),
               if 4-tuple, xoffset in (shear[0], shear[1]) and  yoffset in (shear[2], shear[3]).
        fill_color: int or str or tuple or la.image.RGBMode, rgb color.
        p: probability that the image does this. Default value is 1.
    Returns:
        a PIL instance.
    """
    if np.random.uniform()>p:
        return image
    if isinstance(angle, (list, tuple)):
        angle = np.random.uniform(angle[0], angle[1])

    if isinstance(center, (int, float)):
        cx, cy = (int(center*image.size[0]), int(center*image.size[1]))
    elif isinstance(center, (list, tuple)):
        if len(center)==2:
            cx, cy = (int(center[0]*image.size[0]), int(center[1]*image.size[1]))
        elif len(center)==4:
            cx = int(np.random.uniform(center[0], center[1])*image.size[0])
            cy = int(np.random.uniform(center[2], center[3])*image.size[1])
        else:
            raise ValueError('`center` value format error.')
    else:
        raise ValueError('`center` value format error.')

    if isinstance(translate, (int, float)):
        tx, ty = int(translate*image.size[0]), int(translate*image.size[1])
    elif isinstance(translate, (list, tuple)):
        if len(translate)==2:
            tx, ty = int(translate[0]*image.size[0]), int(translate[1]*image.size[1])
        elif len(translate)==4:
            tx = int(np.random.uniform(translate[0], translate[1])*image.size[0])
            ty = int(np.random.uniform(translate[2], translate[3])*image.size[1])
        else:
            raise ValueError('`translate` value format error.')
    else:
        raise ValueError('`translate` value format error.')

    if isinstance(scale, (list, tuple)):
        scale = np.random.uniform(scale[0], scale[1])
    if scale <= 0.0:
        raise ValueError("Argument scale should be positive")

    if isinstance(shear, (int, float)):
        shear = (shear, shear)
    elif isinstance(shear, (list, tuple)):
        if len(shear)==4:
            shear = (np.random.uniform(shear[0], shear[1]), np.random.uniform(shear[2], shear[3]))
        elif len(shear)!=2:
            raise ValueError('`translate` value format error.')
    else:
        raise ValueError('`translate` value format error.')

    rot = math.radians(angle)
    sx = math.radians(shear[0])
    sy = math.radians(shear[1])

    a = math.cos(rot - sy) / math.cos(sy)
    b = -math.cos(rot - sy) * math.tan(sx) / math.cos(sy) - math.sin(rot)
    c = math.sin(rot - sy) / math.cos(sy)
    d = -math.sin(rot - sy) * math.tan(sx) / math.cos(sy) + math.cos(rot)

    matrix = [d, -b, 0.0, -c, a, 0.0]
    matrix = [x / scale for x in matrix]
    matrix[2] += matrix[0] * (-cx - tx) + matrix[1] * (-cy - ty)
    matrix[5] += matrix[3] * (-cx - tx) + matrix[4] * (-cy - ty)
    matrix[2] += cx
    matrix[5] += cy
    fill_color = _fill_color(image, fill_color)
    return image.transform(image.size, Image.Transform.AFFINE, matrix,
                           Image.Resampling.NEAREST, fillcolor=fill_color)

def shear(image, xoffset=(-90, 90), yoffset=None, fill_color=None, p=1):
    """Apply affine shear on the image.

    Args:
        image: a PIL instance.
        xoffset: int or list ot tuple, The horizontal degrees, xoffset in [-360,360].
                 if tuple or list, randomly picked in the interval `[xoffset[0], xoffset[1])`
        yoffset: int or list ot tuple, The vertical degrees, yoffset in [-360,360].
                 If omitted, both distances are set to the same value.
                 if tuple or list, randomly picked in the interval `[yoffset[0], yoffset[1])`
        fill_color: int or str or tuple or la.image.RGBMode, rgb color.
        p: probability that the image does this. Default value is 1.
    Returns:
        a PIL instance.
    """
    if np.random.uniform()>p:
        return image
    if isinstance(xoffset, (list, tuple)):
        xoffset = np.random.uniform(xoffset[0], xoffset[1])
    if yoffset is None:
        yoffset = xoffset
    elif isinstance(yoffset, (list, tuple)):
        yoffset = np.random.uniform(yoffset[0], yoffset[1])
    fill_color = _fill_color(image, fill_color)
    return affine(image, angle=(0,0), center=(0.5,0.5), translate=(0, 0), scale=1.,
                  shear=(xoffset, yoffset), fill_color=fill_color, p=1)

def rescale(image, xscale=(0.5,1.5), yscale=(0.5,1.5), fill_color=None, p=1):
    """Apply scaling on the x or y axis to input data.

    Args:
        image: a PIL instance.
        xscale: if int or float, width expansion and contraction, xscale should be positive.
                if tuple or list, randomly picked in the interval `[xscale[0], xscale[1])`.
        yscale: if int or float, height expansion and contraction, yscale should be positive.
                if tuple or list, randomly picked in the interval `[yscale[0], yscale[1])`.
        fill_color: int or str or tuple or la.image.RGBMode, rgb color.
        p: probability that the image does this. Default value is 1.
    Return:
        a PIL instance.
    """
    if np.random.uniform()>p:
        return image
    if isinstance(xscale, (list, tuple)):
        xscale = np.random.uniform(xscale[0], xscale[1])
    if isinstance(yscale, (list, tuple)):
        yscale = np.random.uniform(yscale[0], yscale[1])
    fill_color = _fill_color(image, fill_color)
    size = [int(image.size[0]*xscale), int(image.size[1]*yscale)]
    size1 = [min(image.size[0], size[0]), min(image.size[1], size[1])]
    box1 = [int(size[0]/2-size1[0]/2), int(size[1]/2-size1[1]/2)]
    box1 = box1 + [box1[0]+size1[0], box1[1]+size1[1]]
    box2 = [int(image.size[0]/2-size1[0]/2), int(image.size[1]/2-size1[1]/2)]
    box2 = box2 + [box2[0]+size1[0], box2[1]+size1[1]]
    image2 = Image.new(image.mode, image.size, fill_color)
    image2.paste(image.resize(size).crop(box1), box2)
    return image2

def jigsaw(image, size=(10,10), prob=0.1, p=1):
    """Move cells within images similar to jigsaw patterns.

    Args:
        image: a PIL instance.
        size: if int or float, xsize=ysize, numbers of jigsaw.
              if 2-tuple, (xsize, ysize),
              if 4-tuple, xsize in (size[0], size[1]) and  ysize in (size[2], size[3]).
        prob: probability of every jigsaw being changed.
        p: probability that the image does this. Default value is 1.
    Return:
        a PIL instance.
    """
    if isinstance(size, (int, float)):
        size = (size, size)
    elif isinstance(size, (list, tuple)):
        if len(size)==4:
            size = (np.random.uniform(size[0], size[1]), np.random.uniform(size[2], size[3]))
        elif len(size)!=2:
            raise ValueError('`size` value format error.')
    else:
        raise ValueError('`size` value format error.')
    size = (max(2, int(size[0])), max(2, int(size[1])))

    w = image.size[0]//size[0]
    h = image.size[1]//size[1]
    axis = [[i*w, j*h, i*w+w, j*h+h] for i in range(size[0]) for j in range(size[1])]
    image2 = image.copy()
    s = np.random.choice(range(size[0]*size[1]), max(int(size[0]*size[1]*prob), 2), replace=False)
    s_index = np.random.choice(s, len(s), replace=False)
    for i,j in zip(s, s_index):
        image2.paste(image.crop(axis[i]), axis[j])
    return image2


# import the necessary packages
from scipy.spatial import distance as dist
from imutils import face_utils
from operator import itemgetter
from numpy import nan

import numpy as np
import argparse
import imutils
import time
import dlib
import cv2
import sys,os
import importlib

from data_funcs import *

def eye_aspect_ratio(eye):
    # compute the euclidean distances between the two sets of
    # vertical eye landmarks (x, y)-coordinates
    A = dist.euclidean(eye[1], eye[5])
    B = dist.euclidean(eye[2], eye[4])

    # compute the euclidean distance between the horizontal
    # eye landmark (x, y)-coordinates
    C = dist.euclidean(eye[0], eye[3])

    # compute the eye aspect ratio
    ear = (A + B) / (2.0 * C)

    # return the eye aspect ratio
    return ear

# returns:
# rect = dlib.rectangle or None if no faces found
# detectType to say which detector the rectangle represents
#
# if detector does not find a face than detector2 will try
def detectFaces(gray,FACE_DOWNSAMPLE_RATIO):
    detectType = 1

    # rescale frame for face detection
    gray_rescale = cv2.resize(gray, (0,0),fx=1.0/FACE_DOWNSAMPLE_RATIO,fy=1.0/FACE_DOWNSAMPLE_RATIO)

    # detect faces in the grayscale frame
    rects = detector(gray_rescale, 0)

    # dets = detector3(gray_rescale,0)

    # rects = dlib.rectangles()
    # rects.extend([d.rect for d in dets])

    # note rect is a dlib rectangle
    if(len(rects) == 0):
        # if no face found, try second detector
        faces = detector2.detectMultiScale(gray_rescale,1.3,5)
        if(len(faces) == 0):
            return (None,None)

        faces = sorted(faces,reverse = True,key=lambda x: x[2] * x[3])
        # use largest face found
        face = faces[0]
        (x,y,w,h) = face
        rect = dlib.rectangle(left=(x+w).item(), bottom=(y+h).item(), right=x.item(), top=y.item())
        detectType = 2
    else:

        # use largest face found
        # use first face found
        rects = sorted(rects,reverse=True,key=lambda x: x.area())
        rect = rects[0]

    return rect, detectType

# flip frame
def horizontal_flip(src):
    return cv2.flip(src,-1)

# tool built by Steven to label the video data
# p to pause, b to label, k to go back, any other button goes forward
# video is file name
def label_video(video,starting_frame = 0,FLIP = False):
    vs = cv2.VideoCapture(vidPath + video)

    num_frames = vs.get(cv2.CAP_PROP_FRAME_COUNT)
    FPS = vs.get(cv2.CAP_PROP_FPS)

    video_label = np.zeros(int(num_frames))
    current_frame = 0
    video_frame = []

    print("num frames = " + str(num_frames))

    if(starting_frame > num_frames):
        return "Starting_frame > num_frames"

    # go to starting frame
    while current_frame != starting_frame:
        cv2.waitKey(40)
        flag,frame = vs.read()
        if flag:
            if(current_frame % int(num_frames/100) == 0):
                print("loading: " + str(current_frame))
            current_frame += 1
        else:
            print("did not grab frame")
            time.sleep(0.5)

    first = True
    while True:
        #print("current frame: " + str(current_frame))
        flag, frame = vs.read()
        if flag:
            frame = cv2.resize(frame,(1280,720))
            if(FLIP):
                frame = horizontal_flip(frame)
            video_frame.append(frame)
            if(len(video_frame) >= 1*int(FPS)):
                video_frame.pop(0)
            cv2.putText(frame, "Frame: {}".format(current_frame), (10, 30), cv2.FONT_HERSHEY_SIMPLEX, 0.7, (0, 0, 255), 2)
            cv2.imshow("Frame", frame)
            key = cv2.waitKey(40)

            # pause
            if first or key == ord('p'):
                first = False
                frame_counter = len(video_frame) - 1
                frame_pause = video_frame[int(frame_counter)]
                while True:
                    key2 = cv2.waitKey(0)
                    # label
                    if key2 == ord('b'):
                        video_label[current_frame - (len(video_frame) - frame_counter)] = 1
                        cv2.putText(frame_pause, "Paused", (10, 60), cv2.FONT_HERSHEY_SIMPLEX, 0.7, (0, 0, 255), 2)
                        cv2.putText(frame_pause, "Labeled: {}".format(current_frame - (len(video_frame) - frame_counter-1)), (10, 90), cv2.FONT_HERSHEY_SIMPLEX, 0.7, (0, 0, 255), 2)
                        cv2.imshow("Frame", frame_pause)
                    # go back one frame
                    elif key2 == ord('k'):
                        if frame_counter > 0:
                            frame_counter -= 1
                        frame_pause = video_frame[int(frame_counter)]
                        cv2.putText(frame_pause, "Paused", (10, 60), cv2.FONT_HERSHEY_SIMPLEX, 0.7, (0, 0, 255), 2)
                        cv2.imshow("Frame", frame_pause)
                    elif key2 == ord('p'):
                        break
                    else:
                        # any other goes forward a frame
                        if frame_counter < len(video_frame) - 1:
                            frame_counter += 1
                        frame_pause = video_frame[int(frame_counter)]
                        cv2.putText(frame_pause, "Paused", (10, 60), cv2.FONT_HERSHEY_SIMPLEX, 0.7, (0, 0, 255), 2)
                        cv2.imshow("Frame", frame_pause)
            elif key == ord('q'):
                break

            current_frame += 1
        else:
            # vs.set(cv2.CAP_PROP_POS_FRAMES, current_frame-1)
            print("frame is not ready")
            key = cv2.waitKey(40)
            if(key == ord('q')):
                break
            # It is better to wait for a while for the next frame to be ready
            continue

        if current_frame == num_frames or current_frame == num_frames - 1:
            # If the number of captured frames is equal to the total number of frames,
            # we stop
            key2 = cv2.waitKey(0)
            if(key == ord('q')):
                break

    cv2.destroyAllWindows()
    vs.release()
    return video_label

# Generates a csv string of the ears of each frame (nothing if no face detected)
def gen_ears(filename, SHOW_FRAME = True, FLIP = False):
    print("Generating EARS for " + vidPath + filename)

    # How much to downsample face for detection
    FACE_DOWNSAMPLE_RATIO = 4

    # output matrix
    out = []

    # grab the indexes of the facial landmarks for the left and
    # right eye, respectively
    (lStart, lEnd) = face_utils.FACIAL_LANDMARKS_IDXS["left_eye"]
    (rStart, rEnd) = face_utils.FACIAL_LANDMARKS_IDXS["right_eye"]

    # start the video stream thread
    vs = cv2.VideoCapture(vidPath + filename)

    time.sleep(5.0)
    FRAME_NUM = 0
    print("Applying classifer to " + vidPath + filename)

    print("Video properties:")
    FPS = vs.get(cv2.CAP_PROP_FPS)
    FC = vs.get(cv2.CAP_PROP_FRAME_COUNT)
    F = vs.get(cv2.CAP_PROP_FORMAT)
    W = vs.get(cv2.CAP_PROP_FRAME_WIDTH)
    H = vs.get(cv2.CAP_PROP_FRAME_HEIGHT)
    print("\tFPS = " + str(FPS))
    print("\tFrame count = " + str(FC))
    print("\tFormat = " + str(F))
    print("\t(width,height) = (" + str(W) + "," + str(H) + ")")

    # "dropped" frames
    NOT_GRABBED = 0

    # loop over frames from the video stream
    # stop when we haven't grabbed END_VIDEO_LIMIT frames
    while FRAME_NUM < FC:

        # Try to grab frame
        (grabbed,frame) = vs.read()

        if(grabbed):
            FRAME_NUM += 1
            NOT_GRABBED = 0
        else:
            print("not grabbed = " + str(NOT_GRABBED))
            NOT_GRABBED += 1
            continue

        if(FLIP):
            frame = horizontal_flip(frame)

        # output timestamp and frame
        #timestamp = 1000.0 * float(FRAME_NUM)/FPS
        timestamp = FRAME_NUM

        # Apply transformations (one of them being grayscale)
        gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)

        rect, detectType = detectFaces(gray, FACE_DOWNSAMPLE_RATIO)

        if(rect is not None):
            # Resize obtained rectangle for full resolution image
            rect_resize = dlib.rectangle(
                left=rect.left() * FACE_DOWNSAMPLE_RATIO,
                top=rect.top() * FACE_DOWNSAMPLE_RATIO,
                right=rect.right() * FACE_DOWNSAMPLE_RATIO,
                bottom=rect.bottom() * FACE_DOWNSAMPLE_RATIO
            )

            shape = predictor(gray,rect_resize)
            shape = face_utils.shape_to_np(shape)
            # extract the left and right eye coordinates, then use the
            # coordinates to compute the eye aspect ratio for both eyes
            leftEye = shape[lStart:lEnd]
            rightEye = shape[rStart:rEnd]

            leftEAR = eye_aspect_ratio(leftEye)
            rightEAR = eye_aspect_ratio(rightEye)

            # average the eye aspect ratio together for both eyes
            ear = (leftEAR + rightEAR) / 2.0

            # compute the convex hull for the left and right eye, then
            # visualize each of the eyes
            leftEyeHull = cv2.convexHull(leftEye)
            rightEyeHull = cv2.convexHull(rightEye)

            cv2.rectangle(frame,(rect_resize.left(),rect_resize.top()),(rect_resize.right(),rect_resize.bottom()),cv2.COLOR_BGR2HSV,10)
            cv2.drawContours(frame, [leftEyeHull], -1, (0, 255, 0), 2)
            cv2.drawContours(frame, [rightEyeHull], -1, (0, 255, 0), 2)

        if(SHOW_FRAME):
            display_frame = cv2.resize(frame,(1280,720))
            # draw the total number of blinks on the frame along with
            # the computed eye aspect ratio for the frame
            # Reset counter if we did not find any faces
            if(rect is None):
                cv2.putText(display_frame, "EAR: N\\A", (300, 30),
                    cv2.FONT_HERSHEY_SIMPLEX, 0.7, (0, 0, 255), 2)
                cv2.putText(display_frame, "NO FACE DETECTED", (300, 60),
                    cv2.FONT_HERSHEY_SIMPLEX, 0.7, (0, 0, 255), 2)
            else:
                cv2.putText(display_frame, "EAR: {:.2f}".format(ear), (300, 30),
                    cv2.FONT_HERSHEY_SIMPLEX, 0.7, (0, 0, 255), 2)

            cv2.putText(display_frame, "Frame: {}".format(FRAME_NUM), (10, 60),
                cv2.FONT_HERSHEY_SIMPLEX, 0.7, (0, 0, 255), 2)

            # show the frame
            cv2.imshow("Frame", display_frame)

        # output different csv things if face was detected
        if(rect is not None):
            out.append([int(timestamp),ear])
        else:
            out.append([int(timestamp),nan])

        if cv2.waitKey(1) & 0xFF == ord('q'):
            cv2.destroyAllWindows()
            return out
            break

    # do a bit of cleanup
    cv2.destroyAllWindows()

    return np.asarray(out)

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

WRITE_TO_CSV = True

print("[INFO] loading facial classifiers...")
# dlibs HOG based classifier
detector = dlib.get_frontal_face_detector()
# openCVs HAAR cascade classifier
detector2 = cv2.CascadeClassifier(detector2Path)
# dlibs CNN based classifier
# currently too slow even with rescaling
detector3 = dlib.cnn_face_detection_model_v1(detector3Path)
# dlibs facial landmark detector (68 points)
predictor = dlib.shape_predictor(shapePredPath)

# get files
files = []
for filename in os.listdir(vidPath):
    print(filename)
    if(filename.endswith(".MP4") or filename.endswith(".mp4")):
        files.append(filename)

# =============================================================================
# # gen ears
# file = files[0]
# out = gen_ears(file)
# out = np.asarray(out)
# print("saving ears")
# vidName, ext = os.path.splitext(os.path.basename(file))
# np.savetxt(csvPath + vidName + "_ears.csv", out, delimiter=",")
# =============================================================================

# # gen ears
# for file in files:
    # vidName, ext = os.path.splitext(os.path.basename(file))
    # out = gen_ears(file,SHOW_FRAME = True)
    # if(WRITE_TO_CSV):
        # print("Writing " + str(vidName) + "_ears.csv")
        # #np.savetxt(csvPath + vidName + "_ears.csv", out, delimiter=",")

    # print("-----")

# Label video
file = files[0]
out = label_video(file,starting_frame=70000)
print(out.shape)
vidName, ext = os.path.splitext(os.path.basename(file))
print("saving label file")
np.savetxt(csvPath + vidName + "_labels.csv", out, delimiter=",")

# Label video
# # for file in files:
    # # vidName, ext = os.path.splitext(os.path.basename(filename))
    # # print("labeling " + vidPath + filename)
    # # video_label = label_video(file)
    # # if(WRITE_TO_CSV):
        # # np.savetxt(csvPath + vidName + "_labels.csv", video_label, delimiter=",")

print("Done!")


class Solution:
    def maxAreaOfIsland(self, grid: List[List[int]]) -> int:
        maxArea = 0
        visited = set()
        ROWS, COLS = len(grid), len(grid[0])
        def dfs(r,c):

            if min(r,c) < 0 or r >= ROWS or c >= COLS or (r,c) in visited or grid[r][c] == 0:
                return 0
            visited.add((r,c))

            return (1 + dfs(r+1,c)+
                        dfs(r-1,c)+
                        dfs(r,c+1)+
                        dfs(r,c-1))

        for i in range(len(grid)):
            for j in range(len(grid[0])):
                if grid[i][j] == 1:
                    area = dfs(i,j)
                    maxArea = max(area,maxArea)
        return maxArea


import sys

def computeLPS(word, lps):
    suffix = 0
    prefix = 1
    while prefix < len(word):
        if word[prefix] == word[suffix]:
            suffix += 1
            lps[prefix] = suffix
            prefix += 1
        else:
            if suffix != 0:
                suffix = lps[suffix - 1]
            else:
                lps[prefix] = 0
                prefix += 1

def KMP(word, test):
    l_word = len(word)
    l_test = len(test)

    computeLPS(test, lps)

    w_index = 0
    t_index = 0

    while w_index < l_word:
        if test[t_index] == word[w_index]:
            w_index += 1
            t_index += 1
        elif test[t_index] != word[w_index]:
            if t_index != 0:
                t_index = lps[t_index - 1]
            else:
                w_index += 1

        if t_index == l_test:
            ans.append(w_index - t_index + 1)
            t_index = lps[t_index - 1]

word = sys.stdin.readline().rstrip('\n')
test = sys.stdin.readline().rstrip('\n')

ans = []
lps = [0 for _ in range(len(test))]

KMP(word, test)

print(len(ans))
print(*ans)


# -*- coding: utf-8 -*-
"""
Created on Mon Oct 22 23:57:46 2018

@author: zhengjt
"""

import json
import urllib3

#利用urllib2获取网络数据
http = urllib3.PoolManager()
#url ="http://f.apiplus.net/ssq.json"
url ="http://caipiaojieguo.com/api/lottrey?biaoshi=ssq&format=json&rows=10"
r = http.request('GET', url)
value=json.loads(r.data)
rootlist=value.keys()
for rootkey in rootlist:
    print(rootkey)
datas=value['data']

num=len(datas)
i=0
#逐个号码解析出来

#while(i<num):
#    str_code=datas[i]['opencode']
#    blue_ball=str_code[-2:]
#    print('blue ball: ',blue_ball)
#    str_code_split=str_code[:-3].split(',')
#    j=0
#    while(j<len(str_code_split)):
#        print(datas[i]['expect'],str_code_split[j])
#        j=j+1
#    i=i+1

#检索是否中奖
targe_red_ball=['13', '03', '14', '16', '25', '28']
while(i<num):
#    from彩票结果网
    str_code=datas[i]['result']
    blue_ball=str_code[-2:]
    print('blue ball: ',blue_ball)
    red_ball_list=str_code[:-3].split(',')
#    开彩网
#    str_code=datas[i]['opencode']
#    blue_ball=str_code[-2:]
#    print('blue ball: ',blue_ball)
#    red_ball_list=str_code[:-3].split(',')
#    向字典加入内容项
    datas[i]['blue_ball']=blue_ball
    datas[i]['red_ball']=red_ball_list
#    print(datas[i]['expect']+':',red_ball_list)
    print(datas[i]['qishu']+':',red_ball_list)
    j=0
    result=[0,0,0,0,0,0]
    while(j<len(red_ball_list)):
        result[j]=red_ball_list.count(targe_red_ball[j])
        j+=1
    print('中奖结果：',result)
    i+=1

#把字典写到文件
jsObj = json.dumps(datas)

fileObject = open('double_color_ball.json', 'w')
fileObject.write(jsObj)
fileObject.close()


from __future__ import unicode_literals

import re

from .common import InfoExtractor
from ..utils import str_to_int

class NineGagIE(InfoExtractor):
    IE_NAME = '9gag'
    _VALID_URL = r'https?://(?:www\.)?9gag(?:\.com/tv|\.tv)/(?:p|embed)/(?P<id>[a-zA-Z0-9]+)(?:/(?P<display_id>[^?#/]+))?'

    _TESTS = [{
        'url': 'http://9gag.com/tv/p/Kk2X5/people-are-awesome-2013-is-absolutely-awesome',
        'info_dict': {
            'id': 'kXzwOKyGlSA',
            'ext': 'mp4',
            'description': 'This 3-minute video will make you smile and then make you feel untalented and insignificant. Anyway, you should share this awesomeness. (Thanks, Dino!)',
            'title': '\"People Are Awesome 2013\" Is Absolutely Awesome',
            'uploader_id': 'UCdEH6EjDKwtTe-sO2f0_1XA',
            'uploader': 'CompilationChannel',
            'upload_date': '20131110',
            'view_count': int,
        },
        'add_ie': ['Youtube'],
    }, {
        'url': 'http://9gag.com/tv/p/aKolP3',
        'info_dict': {
            'id': 'aKolP3',
            'ext': 'mp4',
            'title': 'This Guy Travelled 11 countries In 44 days Just To Make This Amazing Video',
            'description': "I just saw more in 1 minute than I've seen in 1 year. This guy's video is epic!!",
            'uploader_id': 'rickmereki',
            'uploader': 'Rick Mereki',
            'upload_date': '20110803',
            'view_count': int,
        },
        'add_ie': ['Vimeo'],
    }, {
        'url': 'http://9gag.com/tv/p/KklwM',
        'only_matching': True,
    }, {
        'url': 'http://9gag.tv/p/Kk2X5',
        'only_matching': True,
    }, {
        'url': 'http://9gag.com/tv/embed/a5Dmvl',
        'only_matching': True,
    }]

    _EXTERNAL_VIDEO_PROVIDER = {
        '1': {
            'url': '%s',
            'ie_key': 'Youtube',
        },
        '2': {
            'url': 'http://player.vimeo.com/video/%s',
            'ie_key': 'Vimeo',
        },
        '3': {
            'url': 'http://instagram.com/p/%s',
            'ie_key': 'Instagram',
        },
        '4': {
            'url': 'http://vine.co/v/%s',
            'ie_key': 'Vine',
        },
    }

    def _real_extract(self, url):
        mobj = re.match(self._VALID_URL, url)
        video_id = mobj.group('id')
        display_id = mobj.group('display_id') or video_id

        webpage = self._download_webpage(url, display_id)

        post_view = self._parse_json(
            self._search_regex(
                r'var\s+postView\s*=\s*new\s+app\.PostView\({\s*post:\s*({.+?})\s*,\s*posts:\s*prefetchedCurrentPost',
                webpage, 'post view'),
            display_id)

        ie_key = None
        source_url = post_view.get('sourceUrl')
        if not source_url:
            external_video_id = post_view['videoExternalId']
            external_video_provider = post_view['videoExternalProvider']
            source_url = self._EXTERNAL_VIDEO_PROVIDER[external_video_provider]['url'] % external_video_id
            ie_key = self._EXTERNAL_VIDEO_PROVIDER[external_video_provider]['ie_key']
        title = post_view['title']
        description = post_view.get('description')
        view_count = str_to_int(post_view.get('externalView'))
        thumbnail = post_view.get('thumbnail_700w') or post_view.get('ogImageUrl') or post_view.get('thumbnail_300w')

        return {
            '_type': 'url_transparent',
            'url': source_url,
            'ie_key': ie_key,
            'id': video_id,
            'display_id': display_id,
            'title': title,
            'description': description,
            'view_count': view_count,
            'thumbnail': thumbnail,
        }


file = open('27-13b.txt')
n = int(file.readline())
pris = [0] * 7

k1 = 0
k2 = 0
k7 = 0
k14 = 0
count = 0

for i in range(7):
    pris[i] = int(file.readline())

for i in range(7, n):
    old = pris[0]
    new = int(file.readline())

    if old % 14 == 0:
        k14 += 1
    elif old % 7 == 0:
        k7 += 1
    elif old % 2 == 0:
        k2 += 1
    else:
        k1 += 1

    if new % 14 == 0:
        count += k1 + k2 + k7 + k14
    elif new % 7 == 0:
        count += k2 + k14
    elif new % 2 == 0:
        count += k7 + k14
    else:
        count += k14

    pris = pris[1:] + [new]

print(count)