# -*- coding: utf-8 -*-
"""
@create: 2022-07-25 10:39:19.

@author: ppolxda

@desc: ReportBro Api
"""
import json
import os
import traceback
from datetime import datetime
from enum import Enum
from io import BytesIO
from timeit import default_timer as timer
from typing import List
from typing import Optional
from typing import Union
from urllib.parse import urlencode

import filetype
import PyPDF2
import requests
from fastapi import APIRouter
from fastapi import Depends
from fastapi import HTTPException
from fastapi import Path
from fastapi import Query
from fastapi import Request
from fastapi.responses import PlainTextResponse
from fastapi.responses import StreamingResponse
from reportbro import ReportBroError
from starlette.status import HTTP_200_OK
from starlette.status import HTTP_400_BAD_REQUEST

from ..backend.backends.base import BackendBase
from ..clients import FONTS_LOADER
from ..clients import StorageMange
from ..clients import get_meth_cli
from ..clients import get_storage_mange
from ..errors import TemplageNotFoundError
from ..settings import settings
from ..utils.logger import LOGGER
from ..utils.model import ErrorResponse
from ..utils.report import ReportPdf
from ..utils.report import fill_default
from .reportbro_schema import RequestCloneTemplate
from .reportbro_schema import RequestCreateTemplate
from .reportbro_schema import RequestGenerateDataTemplate
from .reportbro_schema import RequestGenerateTemplate
from .reportbro_schema import RequestGenerateUrlTemplate
from .reportbro_schema import RequestMultiGenerateTemplate
from .reportbro_schema import RequestReviewTemplate
from .reportbro_schema import RequestUploadTemplate
from .reportbro_schema import TemplateDataResponse
from .reportbro_schema import TemplateDescData
from .reportbro_schema import TemplateDescResponse
from .reportbro_schema import TemplateDownLoadData
from .reportbro_schema import TemplateDownLoadResponse
from .reportbro_schema import TemplateListData
from .reportbro_schema import TemplateListResponse

router = APIRouter()
TAGS: List[Union[str, Enum]] = ["ReportBro Api"]
GEN_TAGS: List[Union[str, Enum]] = ["ReportBro Generate Api"]
# templates = Jinja2Templates(directory=settings.TEMPLATES_PATH)

def is_pdf(data: bytes):
    """is_pdf."""
    rtype = filetype.guess(data)
    return rtype and rtype.extension == "pdf"

@router.get(
    "/templates/list",
    tags=TAGS,
    name="Get templates List",
    response_model=TemplateListResponse,
)
async def main_index_page(
    request: Request,
    client: BackendBase = Depends(get_meth_cli),
):
    """Get templates List."""
    list_ = await client.get_templates_list()
    return TemplateListResponse(
        code=HTTP_200_OK,
        error="ok",
        data=[
            TemplateListData(
                **{
                    **i.__dict__,
                    "template_designer_page": request.url_for(
                        "Templates Designer page", tid=i.tid
                    ),
                }
            )
            for i in list_
        ],
    )

@router.get(
    "/templates/{tid}/versions",
    tags=TAGS,
    name="Get templates Versions",
    response_model=TemplateListResponse,
)
async def get_versions(
    request: Request,
    tid: str = Path(title="Template id"),
    client: BackendBase = Depends(get_meth_cli),
):
    """Get templates List."""
    list_ = await client.get_templates_version_list(tid)
    return TemplateListResponse(
        code=HTTP_200_OK,
        error="ok",
        data=[
            TemplateListData(
                **{
                    **i.__dict__,
                    "template_designer_page": request.url_for(
                        "Templates Designer page", tid=i.tid
                    ),
                }
            )
            for i in list_
        ],
    )

@router.get(
    "/templates/{tid}/desc",
    tags=TAGS,
    name="Get templates Data",
    response_model=TemplateDescResponse,
)
async def get_templates_data(
    request: Request,
    tid: str = Path(title="Template id"),
    version_id: Optional[str] = Query(
        None, title="Template version id", alias="versionId"
    ),
    client: BackendBase = Depends(get_meth_cli),
):
    """Get templates List."""
    template = await client.get_template(tid, version_id)
    if not template:
        raise TemplageNotFoundError("template not found")

    return TemplateDescResponse(
        code=HTTP_200_OK,
        error="ok",
        data=TemplateDescData(
            **{
                **template.dict(),
                "report": template.report,
                "template_designer_page": request.url_for(
                    "Templates Designer page", tid=template.tid
                ),
            }
        ),
    )

@router.put(
    "/templates",
    tags=TAGS,
    name="Create Templates",
    response_model=TemplateDataResponse,
)
async def create_templates(
    request: Request,
    req: RequestCreateTemplate,
    client: BackendBase = Depends(get_meth_cli),
):
    """Templates Manage page."""
    rrr = await client.put_template(req.template_name, req.template_type, {})
    return TemplateDataResponse(
        code=HTTP_200_OK,
        error="ok",
        data=TemplateListData(
            updated_at=datetime.now(),
            template_name=req.template_name,
            template_type=req.template_type,
            tid=rrr.tid,
            version_id=rrr.version_id,
            template_designer_page=request.url_for(
                "Templates Designer page", tid=rrr.tid
            ),
        ),
    )

@router.put(
    "/templates/{tid}",
    tags=TAGS,
    name="Create Templates, use own tid",
    response_model=TemplateDataResponse,
)
async def create_templates_tid(
    request: Request,
    req: RequestCreateTemplate,
    tid: str = Path(title="Template id"),
    client: BackendBase = Depends(get_meth_cli),
):
    """Templates Manage page."""
    rrr = await client.put_template(req.template_name, req.template_type, {}, tid=tid)
    return TemplateDataResponse(
        code=HTTP_200_OK,
        error="ok",
        data=TemplateListData(
            updated_at=datetime.now(),
            template_name=req.template_name,
            template_type=req.template_type,
            tid=rrr.tid,
            version_id=rrr.version_id,
            template_designer_page=request.url_for(
                "Templates Designer page", tid=rrr.tid
            ),
        ),
    )

@router.post(
    "/templates/{tid}",
    tags=TAGS,
    name="Save Templates",
    response_model=TemplateDataResponse,
)
async def save_templates(
    request: Request,
    req: RequestUploadTemplate,
    tid: str = Path(title="Template id"),
    client: BackendBase = Depends(get_meth_cli),
):
    """Save Templates."""
    if not req.report:
        raise HTTPException(
            status_code=HTTP_400_BAD_REQUEST,
            detail="report is empty",
        )

    obj = await client.get_template(tid)
    if not obj:
        raise TemplageNotFoundError("template not found")

    rrr = await client.put_template(
        tid=tid,
        template_name=obj.template_name,
        template_type=obj.template_type,
        report=req.report,
    )
    return TemplateDataResponse(
        code=HTTP_200_OK,
        error="ok",
        data=TemplateListData(
            updated_at=datetime.now(),
            template_name=obj.template_name,
            template_type=obj.template_type,
            tid=tid,
            version_id=rrr.version_id,
            template_designer_page=request.url_for(
                "Templates Designer page", tid=rrr.tid
            ),
        ),
    )

@router.post(
    "/templates/{tid}/clone",
    tags=TAGS,
    name="Clone Templates",
    response_model=TemplateDataResponse,
)
async def clone_templates(
    request: Request,
    req: RequestCloneTemplate,
    tid: str = Path(title="Template id"),
    client: BackendBase = Depends(get_meth_cli),
):
    """Clone Templates."""
    obj = await client.get_template(req.from_tid, req.from_version_id)
    if not obj:
        raise TemplageNotFoundError("template not found")

    if not req.from_version_id:
        req.from_version_id = obj.version_id

    if tid == req.from_tid and obj.version_id == req.from_version_id:
        raise HTTPException(
            status_code=HTTP_400_BAD_REQUEST,
            detail="tid, from_tid must not same",
        )

    obj_src = await client.get_template(tid)
    if not obj_src:
        raise TemplageNotFoundError("template not found")

    rrr = await client.put_template(
        tid=tid,
        template_name=obj_src.template_name,
        template_type=obj_src.template_type,
        report=obj.report,
    )
    return TemplateDataResponse(
        code=HTTP_200_OK,
        error="ok",
        data=TemplateListData(
            updated_at=datetime.now(),
            template_name=obj_src.template_name,
            template_type=obj_src.template_type,
            tid=tid,
            version_id=rrr.version_id,
            template_designer_page=request.url_for(
                "Templates Designer page", tid=rrr.tid
            ),
        ),
    )

@router.delete(
    "/templates/{tid}",
    tags=TAGS,
    name="Delete Templates",
    response_model=ErrorResponse,
)
async def delete_templates(
    tid: str = Path(title="Template id"),
    version_id: Optional[str] = Query(
        None, title="Template version id", alias="versionId"
    ),
    client: BackendBase = Depends(get_meth_cli),
):
    """Delete Templates."""
    await client.delete_template(tid, version_id)
    return ErrorResponse(code=HTTP_200_OK, error="ok")

# ----------------------------------------------
#        PDF REPORT Generate
# ----------------------------------------------

def gen_file_from_report(
    output_format, report_definition, data, is_test_data, disabled_fill
):
    """Review Templates Generate."""
    # all data needed for report preview is sent in the initial PUT request, it contains
    # the format (pdf or xlsx), the report itself (report_definition), the data (test data
    # defined within parameters in the Designer) and is_test_data flag (always True
    # when request is sent from Designer)
    if output_format not in ("pdf", "xlsx"):
        raise HTTPException(
            status_code=HTTP_400_BAD_REQUEST,
            detail="outputFormat parameter missing or invalid",
        )

    try:
        if not disabled_fill:
            fill_default(report_definition, data)

        report = ReportPdf(report_definition, data, FONTS_LOADER, is_test_data)
    except ReportBroError as ex:
        LOGGER.warning(
            "failed to initialize report: %s %s", str(ex), traceback.format_exc()
        )
        raise HTTPException(
            status_code=HTTP_400_BAD_REQUEST,
            detail=f"failed to initialize report[{ex}]",
        ) from ex

    if report.report.errors:
        # return list of errors in case report contains errors, e.g. duplicate parameters.
        # with this information ReportBro Designer can select object containing errors,
        # highlight erroneous fields and display error messages
        raise HTTPException(
            status_code=HTTP_400_BAD_REQUEST,
            detail=json.dumps(report.report.errors),
        )

    start = timer()
    now = datetime.now().strftime("%Y%m%d%H%M%S")
    try:
        if output_format == "pdf":
            report_file = report.generate_pdf(title=settings.PDF_TITLE)
            filename = "report-" + str(now) + ".pdf"
            return filename, report_file
        else:
            report_file = report.generate_xlsx()
            filename = "report-" + str(now) + ".xlsx"
            return filename, report_file
    except ReportBroError as ex:
        # in case an error occurs during report report generate
        # a ReportBroError exception is thrown
        # to stop processing. We return this error within a list so the error can be
        # processed by ReportBro Designer.
        raise HTTPException(
            status_code=HTTP_400_BAD_REQUEST,
            detail=f"failed to generate report[{ex}]",
        ) from ex
    finally:
        end = timer()
        LOGGER.info("pdf generated in %.3f seconds", (end - start))

async def read_file_in_s3(output_format, key, client: StorageMange):
    """Read file in s3."""
    if output_format not in ("pdf", "xlsx"):
        raise HTTPException(
            status_code=HTTP_400_BAD_REQUEST,
            detail="outputFormat parameter missing or invalid",
        )

    filename, report_file = await client.get_file(key)

    if output_format == "pdf":
        response = StreamingResponse(
            BytesIO(report_file),
            media_type="application/pdf",
            headers={"Content-Disposition": f'inline; filename="{filename}"'},
        )
    else:
        response = StreamingResponse(
            BytesIO(report_file),
            media_type="application/vnd.openxmlformats-officedocument.spreadsheetml.sheet",
            headers={"Content-Disposition": f'inline; filename="{filename}"'},
        )

    return response

@router.put(
    "/templates/review/generate",
    tags=GEN_TAGS,
    name="Generate preview file from template",
)
async def review_templates_gen(
    req: RequestReviewTemplate,
    disabled_fill: bool = Query(
        default=False, title="Disable fill empty fields for input data"
    ),
    storage: StorageMange = Depends(get_storage_mange),
):
    """Review Templates Generate."""
    filename, report_file = gen_file_from_report(
        req.output_format, req.report, req.data, req.is_test_data, disabled_fill
    )
    assert report_file
    key = await storage.put_file(filename, report_file)
    return PlainTextResponse(key)

@router.get(
    "/templates/review/generate",
    tags=GEN_TAGS,
    name="Get generate preview file",
)
async def review_templates(
    output_format: str = Query(
        "pdf", title="Output Format(pdf|xlsx)", regex=r"^(pdf|xlsx)$"
    ),
    key: str = Query(title="File Key", min_length=16),
    storage: StorageMange = Depends(get_storage_mange),
):
    """Review Templates."""
    r = await read_file_in_s3(output_format, key, storage)
    return r

# ----------------------------------------------
#        PDF REPORT Multiple Generate
# ----------------------------------------------

@router.put(
    "/templates/multi/generate",
    tags=GEN_TAGS,
    name="Generate file from multiple template(PDF Only)",
    response_model=TemplateDownLoadResponse,
)
async def generate_templates_multi_gen(
    request: Request,
    req: RequestMultiGenerateTemplate,
    disabled_fill: bool = Query(
        default=False, title="Disable fill empty fields for input data"
    ),
    client: BackendBase = Depends(get_meth_cli),
    storage: StorageMange = Depends(get_storage_mange),
):
    """Review Templates Generate."""
    if not req.templates:
        raise HTTPException(
            status_code=HTTP_400_BAD_REQUEST,
            detail="templates is empty",
        )

    filename = ""
    merge_file = PyPDF2.PdfFileMerger()
    for i in req.templates:
        if isinstance(i, RequestGenerateUrlTemplate):
            if i.pdf_url.startswith("file://"):
                with open(i.pdf_url[7:], "rb") as fss:
                    data = fss.read()
                filename, report_file = os.path.basename(i.pdf_url), data
            else:
                data = requests.get(i.pdf_url, timeout=settings.DOWNLOAD_TIMEOUT)
                filename, report_file = os.path.basename(i.pdf_url), data.content

            if not is_pdf(report_file):
                raise HTTPException(
                    status_code=HTTP_400_BAD_REQUEST,
                    detail="pdf_url is not pdf file",
                )
        elif isinstance(i, RequestGenerateDataTemplate):
            templage = await client.get_template(i.tid, i.version_id)
            if not templage:
                raise TemplageNotFoundError("template not found")

            filename, report_file = gen_file_from_report(
                req.output_format,
                templage.report,
                i.data,
                False,
                disabled_fill,
            )
        else:
            raise HTTPException(
                status_code=HTTP_400_BAD_REQUEST,
                detail="templates is invaild",
            )

        assert report_file
        merge_file.append(
            PyPDF2.PdfFileReader(stream=BytesIO(initial_bytes=report_file))
        )

    rrr = BytesIO()
    merge_file.write(rrr)
    rrr.seek(0)

    assert filename
    download_key = await storage.put_file(filename, rrr.read())
    return TemplateDownLoadResponse(
        code=HTTP_200_OK,
        error="ok",
        data=TemplateDownLoadData(
            download_key=download_key,
            download_url=request.url_for("Get generate file from multiple template")
            + "?"
            + urlencode(
                {
                    "key": download_key,
                }
            ),
        ),
    )

@router.get(
    "/templates/multi/generate",
    tags=GEN_TAGS,
    name="Get generate file from multiple template",
)
async def generate_templates_multi(
    key: str = Query(title="File Key", min_length=16),
    storage: StorageMange = Depends(get_storage_mange),
):
    """Review Templates."""
    r = await read_file_in_s3("pdf", key, storage)
    return r

# ----------------------------------------------
#        PDF REPORT Generate
# ----------------------------------------------

@router.put(
    "/templates/{tid}/generate",
    tags=GEN_TAGS,
    name="Generate file from template",
    response_model=TemplateDownLoadResponse,
)
async def generate_templates_gen(
    request: Request,
    req: RequestGenerateTemplate,
    tid: str = Path(title="Template id"),
    version_id: Optional[str] = Query(
        None, title="Template version id", alias="versionId"
    ),
    disabled_fill: bool = Query(
        default=False, title="Disable fill empty fields for input data"
    ),
    client: BackendBase = Depends(get_meth_cli),
    storage: StorageMange = Depends(get_storage_mange),
):
    """Review Templates Generate."""
    templage = await client.get_template(tid, version_id)
    if not templage:
        raise TemplageNotFoundError("template not found")

    filename, report_file = gen_file_from_report(
        req.output_format, templage.report, req.data, False, disabled_fill
    )
    assert report_file
    download_key = await storage.put_file(filename, report_file)
    return TemplateDownLoadResponse(
        code=HTTP_200_OK,
        error="ok",
        data=TemplateDownLoadData(
            download_key=download_key,
            download_url=request.url_for("Get generate file", tid=tid)
            + "?"
            + urlencode(
                {
                    "key": download_key,
                }
            ),
        ),
    )

@router.get(
    "/templates/{tid}/generate",
    tags=GEN_TAGS,
    name="Get generate file",
)
async def generate_templates(
    output_format: str = Query(
        "pdf", title="Output Format(pdf|xlsx)", regex=r"^(pdf|xlsx)$"
    ),
    key: str = Query(title="File Key", min_length=16),
    storage: StorageMange = Depends(get_storage_mange),
):
    """Review Templates."""
    r = await read_file_in_s3(output_format, key, storage)
    return r


#! /usr/bin/env python3
# Echo Server
import sys
import socket
import struct
import random

#Arguments, the IP Address and Port
serverIP = sys.argv[1]
serverPort = int(sys.argv[2])

#===================================
bulb_state="OFF"
#===================================
bulb_brightness=0
#===================================
color_length=0
#===================================
color1=0.00
color2=0.00
color3=0.00
full_color=(f"{color1} {color2} {color3}")
#===================================

#UDP socket created
serverSocket = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
#Assign server IP and port to socket
serverSocket.bind((serverIP, serverPort))

print("Server has been set up and ready to go!")
while True:

	the_destroyer_of_bulbs=random.randint(1,100)
	if the_destroyer_of_bulbs == 1:
		broken="BROKEN"
		bulb_state=broken

	data, address = serverSocket.recvfrom(1024)

	message_type,return_code,message_identifier,action,= struct.unpack(f"!hhih",data[:10])

	if action==0:
		if bulb_state == "ON" or bulb_state == "OFF":
			return_code=0
			bulb_state="OFF"
		else:
			return_code=1

		message_type=2

		response = struct.pack('!hhi',message_type,return_code,message_identifier)

		serverSocket.sendto(response, address)

	elif action==1:
		if bulb_state == "ON" or bulb_state == "OFF":
			return_code=0;
			brightness,color_length=struct.unpack(f"!fh",data[10:16])
			color=struct.unpack(f'!{color_length}s',data[16:])
			color=color[0].decode()

			bulb_brightness=brightness
			split_color=color.split(" ")
			color1=split_color[0]
			color2=split_color[1]
			color3=split_color[2].split("\ ")[0]
			full_color=(f"{color1} {color2} {color3}")
			bulb_state="ON"

		else:
			return_code=1;

		message_type=2

		response = struct.pack('!hhi',message_type,return_code,message_identifier)

		serverSocket.sendto(response, address)

	elif action==2:
		if bulb_state == "ON" or bulb_state == "OFF":
			return_code=0;

			color_length=struct.unpack("!h",data[10:12])
			color_len=color_length[0]
			color=struct.unpack(f'!{color_len}s',data[12:])
			color=color[0].decode()

			split_color=color.split(" ")
			color1=split_color[0]
			color2=split_color[1]
			color3=split_color[2].split("\ ")[0]
			full_color=(f"{color1} {color2} {color3}")
		else:
			return_code=1;

		message_type=2

		response = struct.pack('!hhi',message_type,return_code,message_identifier)

		serverSocket.sendto(response, address)

	elif action==3:
		if bulb_state == "ON" or bulb_state == "OFF":
			return_code=0;

			brightness =struct.unpack(f"!f",data[10:14])
			bulb_brightness=brightness[0]
		else:
			return_code=1;

		message_type=2

		response = struct.pack('!hhi',message_type,return_code,message_identifier)

		serverSocket.sendto(response, address)

	elif action==4:
		if bulb_state == "ON" or bulb_state == "OFF":
			return_code=0;

		else:
			return_code=1;

		answer=(f"Bulb:{bulb_state},Brightness:{bulb_brightness}%,RGB color %:{full_color}")
		answer_len=len(answer)

		message_type=2

		response = struct.pack(f'!hhih{answer_len}s',message_type, return_code, message_identifier,answer_len,
				answer.encode())

		serverSocket.sendto(response, address)


sayilar=[]
for i in range(1,6):
    print ("bir sayi girin")
    x=input()
    sayilar.append(int(x))
    i=i+1

enbuyuk=sayilar[1]
for i in sayilar:
    if i > enbuyuk:
        enbuyuk=i
    i=i+1
print ("en buyuk sayi:", enbuyuk)


import math
import random

# Sigmoid
def sigmoid_function(value: float, deriv: bool = False) -> float:
    if deriv:
        return value * (1 - value)
    return 1 / (1 + math.exp(-value))

# Initial Value
INITIAL_VALUE = 0.02

def forward_propagation(expected: int, number_propagations: int) -> float:

    # Random weight
    weight = float(2 * (random.randint(1, 100)) - 1)

    for _ in range(number_propagations):
        # Forward propagation
        layer_1 = sigmoid_function(INITIAL_VALUE * weight)
        # How much did we miss?
        layer_1_error = (expected / 100) - layer_1
        # Error delta
        layer_1_delta = layer_1_error * sigmoid_function(layer_1, True)
        # Update weight
        weight += INITIAL_VALUE * layer_1_delta

    return layer_1 * 100

if __name__ == "__main__":
    import doctest

    doctest.testmod()

    expected = int(input("Expected value: "))
    number_propagations = int(input("Number of propagations: "))
    print(forward_propagation(expected, number_propagations))


# -*- encoding:utf-8 -*-
import os

import xlrd
import yaml

from common.log import Log
from redConfig import porDir

class unit():
    def __init__(self):
        pass
    def operaYaml(self,filename):
        file=open(filename,"r",encoding="utf-8")
        data = yaml.load(file, Loader=yaml.FullLoader)
        file.close()
        return data
    #读取测试数据
    def readExcel(self,excel_name,sheet_name):
        cls = []
        # 获取excel路径
        excelPath = os.path.join(porDir, "data", "inputData", excel_name)

        # 打开文件
        try:
            file = xlrd.open_workbook(excelPath)
            sheet = file.sheet_by_name(sheet_name)
            nrows = sheet.nrows
            for i in range(nrows):
                    cls.append(sheet.row_values(i))

            return cls
        except FileExistsError:
            Log().logger.error("文件打开失败")
         #读取导出表格数据
    #def readexcel_Dowload(self):

        #excelName='客服满意度' + '(' + i+=1 +')' + '.xlsx'


import os
from PySide6.QtWidgets import QDialog, QFileSystemModel, QAbstractItemView, QComboBox
from PySide6.QtCore import Qt, Slot, QDir, QStandardPaths, QModelIndex
from PySide6.QtGui import QKeySequence, QValidator, QAction
from spinetoolbox.helpers import ProjectDirectoryIconProvider
from spinetoolbox.widgets.notification import Notification
from spinetoolbox.widgets.custom_menus import OpenProjectDialogComboBoxContextMenu

class OpenProjectDialog(QDialog):
    """A dialog that lets user select a project to open either by choosing
    an old .proj file or by choosing a project directory."""

    def __init__(self, toolbox):
        """

        Args:
            toolbox (ToolboxUI): QMainWindow instance
        """
        from ..ui import open_project_dialog  # pylint: disable=import-outside-toplevel

        super().__init__(parent=toolbox, f=Qt.Dialog)  # Setting the parent inherits the stylesheet
        self._toolbox = toolbox
        # Set up the user interface from Designer file
        self.ui = open_project_dialog.Ui_Dialog()
        self.ui.setupUi(self)
        self.combobox_context_menu = None
        # Ensure this dialog is garbage-collected when closed
        self.setAttribute(Qt.WA_DeleteOnClose)
        self.setWindowFlag(Qt.WindowType.WindowContextHelpButtonHint, False)
        # QActions for keyboard shortcuts
        self.go_root_action = QAction(self)
        self.go_home_action = QAction(self)
        self.go_documents_action = QAction(self)
        self.go_desktop_action = QAction(self)
        self.set_keyboard_shortcuts()
        self.selected_path = ""
        self.cb_ss = self.ui.comboBox_current_path.styleSheet()
        self.file_model = CustomQFileSystemModel()
        self.file_model.setFilter(QDir.AllDirs | QDir.NoDotAndDotDot)
        self.icon_provider = ProjectDirectoryIconProvider()
        self.file_model.setIconProvider(self.icon_provider)
        self.file_model.setRootPath(QDir.rootPath())
        self.ui.treeView_file_system.setModel(self.file_model)
        self.file_model.sort(0, Qt.AscendingOrder)
        # Enable validator (experimental, not very useful here)
        # Validator prevents typing Invalid strings to combobox. (not in use)
        # When text in combobox is Intermediate, the validator prevents emitting
        # currentIndexChanged signal when enter is pressed.
        # Pressing enter still triggers the done() slot of the QDialog.
        self.validator = DirValidator()
        self.ui.comboBox_current_path.setValidator(self.validator)
        self.ui.comboBox_current_path.setInsertPolicy(QComboBox.InsertPolicy.NoInsert)
        # Read recent project directories and populate combobox
        recents = self._toolbox.qsettings().value("appSettings/recentProjectStorages", defaultValue=None)
        if recents:
            recents_lst = str(recents).split("\n")
            self.ui.comboBox_current_path.insertItems(0, recents_lst)
            # Set start index to most recent project storage or to root if it does not exist
            p = self.ui.comboBox_current_path.itemText(0)
            if os.path.isdir(p):
                start_index = self.file_model.index(p)
            else:
                start_index = self.file_model.index(QDir.homePath())
        else:
            start_index = self.file_model.index(QDir.homePath())
            self.ui.comboBox_current_path.setCurrentIndex(-1)
        self.file_model.directoryLoaded.connect(self.expand_and_resize)
        # Start browsing to start index immediately when dialog is shown
        self.start_path = self.file_model.filePath(start_index)
        self.starting_up = True
        self.ui.treeView_file_system.setCurrentIndex(start_index)
        self.connect_signals()

    def set_keyboard_shortcuts(self):
        """Creates keyboard shortcuts for the 'Root', 'Home', etc. buttons."""
        self.go_root_action.setShortcut(QKeySequence(Qt.Key_F1))
        self.addAction(self.go_root_action)
        self.go_home_action.setShortcut(QKeySequence(Qt.Key_F2))
        self.addAction(self.go_home_action)
        self.go_documents_action.setShortcut(QKeySequence(Qt.Key_F3))
        self.addAction(self.go_documents_action)
        self.go_desktop_action.setShortcut(QKeySequence(Qt.Key_F4))
        self.addAction(self.go_desktop_action)

    def connect_signals(self):
        """Connects signals to slots."""
        self.ui.toolButton_root.clicked.connect(self.go_root)
        self.ui.toolButton_home.clicked.connect(self.go_home)
        self.ui.toolButton_documents.clicked.connect(self.go_documents)
        self.ui.toolButton_desktop.clicked.connect(self.go_desktop)
        self.ui.comboBox_current_path.editTextChanged.connect(self.combobox_text_edited)
        self.ui.comboBox_current_path.currentIndexChanged.connect(self.current_index_changed)
        self.ui.comboBox_current_path.customContextMenuRequested.connect(self.show_context_menu)
        self.validator.changed.connect(self.validator_state_changed)
        self.ui.treeView_file_system.clicked.connect(self.set_selected_path)
        self.ui.treeView_file_system.doubleClicked.connect(self.open_project)
        self.ui.treeView_file_system.selectionModel().currentChanged.connect(self.current_changed)
        self.go_root_action.triggered.connect(self.go_root)
        self.go_home_action.triggered.connect(self.go_home)
        self.go_documents_action.triggered.connect(self.go_documents)
        self.go_desktop_action.triggered.connect(self.go_desktop)

    @Slot(str)
    def expand_and_resize(self, p):
        """Expands, resizes, and scrolls the tree view to the current directory
        when the file model has finished loading the path. Slot for the file
        model's directoryLoaded signal. The directoryLoaded signal is emitted only
        if the directory has not been cached already. Note, that this is
        only used when the open project dialog is opened

        Args:
             p (str): Directory that has been loaded
        """
        if self.starting_up:
            current_index = self.ui.treeView_file_system.currentIndex()
            self.ui.treeView_file_system.scrollTo(current_index, hint=QAbstractItemView.PositionAtTop)
            self.ui.treeView_file_system.expand(current_index)
            if p == self.start_path:
                self.ui.treeView_file_system.resizeColumnToContents(0)
                self.set_selected_path(current_index)
                self.starting_up = False

    @Slot()
    def validator_state_changed(self):
        """Changes the combobox border color according to the current state of the validator."""
        state = self.ui.comboBox_current_path.validator().state
        if state == QValidator.State.Acceptable:
            self.ui.comboBox_current_path.setStyleSheet(self.cb_ss)
        elif state == QValidator.State.Intermediate:
            ss = "QComboBox {border: 1px solid #ff704d}"
            self.ui.comboBox_current_path.setStyleSheet(ss)
        else:  # Invalid. This is never returned (on purpose).
            ss = "QComboBox {border: 1px solid #ff3300}"
            self.ui.comboBox_current_path.setStyleSheet(ss)

    @Slot(int)
    def current_index_changed(self, i):
        """Combobox selection changed. This slot is processed when a new item
        is selected from the drop-down list. This is not processed when new
        item txt is QValidotor.Intermediate.

        Args:
            i (int): Selected row in combobox
        """
        p = self.ui.comboBox_current_path.itemText(i)
        if not os.path.isdir(p):
            self.remove_directory_from_recents(p, self._toolbox.qsettings())
            return
        fm_index = self.file_model.index(p)
        self.ui.treeView_file_system.collapseAll()
        self.ui.treeView_file_system.setCurrentIndex(fm_index)
        self.ui.treeView_file_system.expand(fm_index)
        self.ui.treeView_file_system.scrollTo(fm_index, hint=QAbstractItemView.PositionAtTop)

    @Slot("QModelIndex", "QModelIndex", name="current_changed")
    def current_changed(self, current, previous):
        """Processed when the current item in file system tree view has been
        changed with keyboard or mouse. Updates the text in combobox.

        Args:
            current (QModelIndex): Currently selected index
            previous (QModelIndex): Previously selected index
        """
        self.set_selected_path(current)

    @Slot("QModelIndex", name="set_selected_path")
    def set_selected_path(self, index):
        """Sets the text in the combobox as the selected path in the file system tree view.

        Args:
            index (QModelIndex): The index which was mouse clicked.
        """
        if not index.isValid():
            return
        selected_path = os.path.abspath(self.file_model.filePath(index))
        self.ui.comboBox_current_path.setCurrentText(selected_path)  # Emits editTextChanged signal
        self.selected_path = selected_path

    @Slot(str)
    def combobox_text_edited(self, text):
        """Updates selected path when combobox text is edited.
        Note: pressing enter in combobox does not trigger this.
        """
        self.selected_path = text

    def selection(self):
        """Returns the selected path from dialog."""
        return os.path.abspath(self.selected_path)

    @Slot(bool, name="go_root")
    def go_root(self, checked=False):
        """Slot for the 'Root' button. Scrolls the treeview to show and select the user's root directory.

        Note: We need to expand and scroll the tree view here after setCurrentIndex
        just in case the directory has been loaded already.
        """
        self.ui.comboBox_current_path.setCurrentIndex(-1)
        root_index = self.file_model.index(QDir.rootPath())
        self.ui.treeView_file_system.collapseAll()
        self.ui.treeView_file_system.setCurrentIndex(root_index)
        self.ui.treeView_file_system.expand(root_index)
        self.ui.treeView_file_system.scrollTo(root_index, hint=QAbstractItemView.PositionAtTop)

    @Slot(bool, name="go_home")
    def go_home(self, checked=False):
        """Slot for the 'Home' button. Scrolls the treeview to show and select the user's home directory."""
        self.ui.comboBox_current_path.setCurrentIndex(-1)
        home_index = self.file_model.index(QDir.homePath())
        self.ui.treeView_file_system.collapseAll()
        self.ui.treeView_file_system.setCurrentIndex(home_index)
        self.ui.treeView_file_system.expand(home_index)
        self.ui.treeView_file_system.scrollTo(home_index, hint=QAbstractItemView.PositionAtTop)

    @Slot(bool, name="go_documents")
    def go_documents(self, checked=False):
        """Slot for the 'Documents' button. Scrolls the treeview to show and select the user's documents directory."""
        docs = QStandardPaths.writableLocation(QStandardPaths.DocumentsLocation)
        if not docs:
            return
        self.ui.comboBox_current_path.setCurrentIndex(-1)
        docs_index = self.file_model.index(docs)
        self.ui.treeView_file_system.collapseAll()
        self.ui.treeView_file_system.setCurrentIndex(docs_index)
        self.ui.treeView_file_system.expand(docs_index)
        self.ui.treeView_file_system.scrollTo(docs_index, hint=QAbstractItemView.PositionAtTop)

    @Slot(bool, name="go_desktop")
    def go_desktop(self, checked=False):
        """Slot for the 'Desktop' button. Scrolls the treeview to show and select the user's desktop directory."""
        desktop = QStandardPaths.writableLocation(QStandardPaths.DesktopLocation)  # Return a list
        if not desktop:
            return
        self.ui.comboBox_current_path.setCurrentIndex(-1)
        desktop_index = self.file_model.index(desktop)
        self.ui.treeView_file_system.collapseAll()
        self.ui.treeView_file_system.setCurrentIndex(desktop_index)
        self.ui.treeView_file_system.expand(desktop_index)
        self.ui.treeView_file_system.scrollTo(desktop_index, hint=QAbstractItemView.PositionAtTop)

    @Slot("QModelIndex")
    def open_project(self, index):
        """Opens project if index contains a valid Spine Toolbox project.
        Slot for the mouse doubleClicked signal. Prevents showing the
        'Not a valid spine toolbox project' notification if user just wants
        to collapse a directory.

        Args:
            index (QModelIndex): File model index which was double clicked
        """
        if not index.isValid():
            return
        possible_project_json_file = os.path.join(self.selection(), ".spinetoolbox", "project.json")
        if not os.path.isfile(possible_project_json_file):
            return
        self.done(QDialog.DialogCode.Accepted)

    def done(self, r):
        """Checks that selected path exists and is a valid
        Spine Toolbox directory when ok button is clicked or
        when enter is pressed without the combobox being in focus.

        Args:
            r (int) Return code
        """
        if r == QDialog.DialogCode.Accepted:
            if not os.path.isdir(self.selection()):
                notification = Notification(self, "Path does not exist")
                notification.show()
                return
            project_json_fp = os.path.abspath(os.path.join(self.selection(), ".spinetoolbox", "project.json"))
            if not os.path.isfile(project_json_fp):
                notification = Notification(self, "Not a valid Spine Toolbox project")
                notification.show()
                return
            # self.selection() now contains a valid Spine Toolbox project directory.
            # Add the parent directory of selected directory to qsettings
            self.update_recents(
                os.path.abspath(os.path.join(self.selection(), os.path.pardir)), self._toolbox.qsettings()
            )
        super().done(r)

    @staticmethod
    def update_recents(entry, qsettings):
        """Adds a new entry to QSettings variable that remembers the five most recent project storages.

        Args:
            entry (str): Abs. path to a directory that most likely contains other Spine Toolbox Projects as well.
                First entry is also used as the initial path for File->New Project dialog.
            qsettings (QSettings): Toolbox qsettings object
        """
        recents = qsettings.value("appSettings/recentProjectStorages", defaultValue=None)
        if not recents:
            updated_recents = entry
        else:
            recents = str(recents)
            recents_list = recents.split("\n")
            # Add path only if it's not in the list already
            if entry not in recents_list:
                recents_list.insert(0, entry)
                if len(recents_list) > 5:
                    recents_list.pop()
            else:
                # If entry was on the list, move it as the first item
                recents_list.insert(0, recents_list.pop(recents_list.index(entry)))
            updated_recents = "\n".join(recents_list)
        # Save updated recent paths
        qsettings.setValue("appSettings/recentProjectStorages", updated_recents)
        qsettings.sync()  # Commit change immediately

    @staticmethod
    def remove_directory_from_recents(p, qsettings):
        """Removes directory from the recent project storages.

        Args:
            p (str): Full path to a project directory
            qsettings (QSettings): Toolbox qsettings object
        """
        recents = qsettings.value("appSettings/recentProjectStorages", defaultValue=None)
        if not recents:
            return
        recents = str(recents)
        recents_list = recents.split("\n")
        if p in recents_list:
            recents_list.pop(recents_list.index(p))
        updated_recents = "\n".join(recents_list)
        # Save updated recent paths
        qsettings.setValue("appSettings/recentProjectStorages", updated_recents)
        qsettings.sync()  # Commit change immediately

    @Slot("QPoint")
    def show_context_menu(self, pos):
        """Shows the context menu for the QCombobox with a 'Clear history' entry.

        Args:
            pos (QPoint): Mouse position
        """
        # ind = self.ui.comboBox_current_path.indexAt(pos)
        global_pos = self.ui.comboBox_current_path.mapToGlobal(pos)
        # if not ind.isValid():
        self.combobox_context_menu = OpenProjectDialogComboBoxContextMenu(self, global_pos)
        action = self.combobox_context_menu.get_action()
        if action == "Clear history":
            self.ui.comboBox_current_path.clear()
            self._toolbox.qsettings().setValue("appSettings/recentProjectStorages", "")
            self.go_root()
        else:  # No option selected
            pass
        self.combobox_context_menu.deleteLater()
        self.combobox_context_menu = None

    def closeEvent(self, event=None):
        """Handles dialog closing.

        Args:
            event (QCloseEvent): Close event
        """
        if event:
            event.accept()

class CustomQFileSystemModel(QFileSystemModel):
    """Custom file system model."""

    def columnCount(self, parent=QModelIndex()):
        """Returns one."""
        return 1

class DirValidator(QValidator):
    def __init__(self, parent=None):
        super().__init__(parent)
        self.state = None

    def validate(self, txt, pos):
        """Returns Invalid if input is invalid according to this
        validator's rules, Intermediate if it is likely that a
        little more editing will make the input acceptable and
        Acceptable if the input is valid.

        Args:
            txt (str): Text to validate
            pos (int): Cursor position

        Returns:
            QValidator.State: Invalid, Intermediate, or Acceptable
        """
        previous_state = self.state
        if not txt:
            self.state = QValidator.State.Intermediate
            if not previous_state == self.state:
                self.changed.emit()
            return self.state
        if os.path.isdir(txt):
            self.state = QValidator.State.Acceptable
            if not previous_state == self.state:
                self.changed.emit()
            return self.state
        self.state = QValidator.State.Intermediate
        if not previous_state == self.state:
            self.changed.emit()
        return self.state


from od_sensor import ODSensor
import utime
from temp_control import T_control
t_control = T_control(14,32,12,34) #LED2 is pin 26
od1 = ODSensor(25,39) #OD2 is pin 36
count = 100

t0 = utime.time()

import utime
while True:
    t_control.pump.pwm.freq(0)
    utime.sleep(1)

    a=[]
    for i in range(count):
        a.append(od1.measure(150))
    avr = sum(a)/count
    print("Average: " + str(avr))

    light = open("light.txt","a")
    light.write(str(avr)+" ")
    light.close()

    temp = open("temp.txt","a")
    temp.write(str(t_control.thermometer.read())+" ")
    temp.close()

    time = open("temp.txt","a")
    time.write(str(utime.time()-t0)+" ")
    time.close()

    t_control.call()
    utime.sleep(57)


import discord
from discord.ext.commands import Cog
from discord.commands import message_command

from datetime import datetime
from apscheduler.triggers.cron import CronTrigger

from ..db import db

guild = None

class stats(Cog):
    def __init__(self,bot) -> None:
        super().__init__()
        self.bot = bot

    @Cog.listener()
    async def on_message(self,message):
        if not message.author.bot:
            if message.guild:
                year = str(datetime.now().strftime("%Y"))
                stats_add_sent_message(message.author)
                if message.mentions: #mentioned someone
                    for user in message.mentions:
                        if not user.bot:
                            stats_add_mention(message.author,user)
                if 'quoi' in message.content.lower():
                    stats_add_feur(message.author)

    @message_command(name="Dit au revoir !",guild_ids=[665676159421251587])
    async def aurevoir(self,ctx,message):
        year = str(datetime.now().strftime("%Y"))
        fanette = self.bot.get_user(249970729418752000)
        db.execute("""INSERT INTO guild_stats(guildid,year,no_goodbye_fanette) VALUES(%s,%s,%s) ON CONFLICT(guildid,year) DO UPDATE SET no_goodbye_fanette = guild_stats.no_goodbye_fanette + 1;""",str(ctx.guild.id),year,1)
        await ctx.respond(f'{fanette.mention} n\'a pas dis au revoir ? Très bien, nous allons lui niquer sa mère.')

def setup(bot):
    bot.add_cog(stats(bot))

def stats_add_feur(user):      #Nombre de fois ou le bot a repondu 'feur'
    year = str(datetime.now().strftime("%Y"))
    db.execute("""UPDATE users_stats SET feur = users_stats.feur + 1 WHERE userid=%s and year=%s""",str(user.id),year)

def stats_add_mention(user,mention):    #Nombre de mentions individuelles
    year = str(datetime.now().strftime("%Y"))
    db.execute("""INSERT INTO users_mentions(userid,mentioned_user,year,number_of_mentions)
                VALUES(%s,%s,%s,%s)
                ON CONFLICT(userid,mentioned_user,year)
                DO UPDATE SET number_of_mentions = users_mentions.number_of_mentions + 1;""",str(user.id),str(mention.id),year,1)

def stats_add_sent_message(user):  #Nombre de messages envoyés
    year = str(datetime.now().strftime("%Y"))
    db.execute("""INSERT INTO users_stats(userid,year,message_sent)
                VALUES(%s,%s,%s)
                ON CONFLICT(userid,year)
                DO UPDATE SET message_sent = users_stats.message_sent + 1;""",str(user.id),year,1)

def stats_add_music_played(user):   #Nombre de musiques jouées
    year = str(datetime.now().strftime("%Y"))
    db.execute("""UPDATE users_stats SET music_played = users_stats.music_played + 1 WHERE userid=%s AND year=%s""",str(user.id),year)

def stats_add_aurevoir():   #Nombre de fois ou fanette dit pas au revoir
    year = str(datetime.now().strftime("%Y"))
    pass

def start_timespent_recording(sched,_guild):
    global guild
    guild = _guild
    sched.add_job(stats_add_time_spent_voicechat, CronTrigger(second=55))

async def stats_add_time_spent_voicechat():
    global guild
    year = str(datetime.now().strftime("%Y"))
    for member in guild.members:
        if not member.bot:
            if member.voice is not None and member.voice.channel is not None:
                db.execute("""INSERT INTO users_stats(userid,year,voice_channel_time)
                                VALUES(%s,%s,%s)
                                ON CONFLICT(userid,year)
                                DO UPDATE SET voice_channel_time = users_stats.voice_channel_time + 1;""",str(member.id),year,1)


from django.shortcuts import render, get_object_or_404,redirect
from django.contrib import messages
from .forms import VehiculoForm, ConductorForm
from vehiculo.models import Vehiculo, Conductor, Alquiler
from django.contrib.auth.decorators import login_required
@login_required
def vehiculo_nuevo(request):
    if request.method=="POST":
        formulario=VehiculoForm(request.POST)
        m=request.POST.getlist('conductores')
        p=Conductor.objects.all()
        for m in m :
            ncon = Conductor.objects.get(pk=m)
        if formulario.is_valid():
           vehiculo = Vehiculo.objects.create(modelo=formulario.cleaned_data['modelo'])
           for conductor_id in request.POST.getlist('conductores'):
               vhi = Alquiler(conductor_id=conductor_id, vehiculo_id = vehiculo.id)
               vhi.save()
        return redirect('vehiculo_detalle', pk=vehiculo.pk)
    else:
        formulario = VehiculoForm()
    return render(request, 'vehiculo_editar.html', {'formulario': formulario})
@login_required
def conductor_nuevo(request):
  if request.method == "POST":
     formulario = ConductorForm(request.POST)
     if formulario.is_valid():
        conductor = Conductor.objects.create(nombre=formulario.cleaned_data['nombre'],fecha_nacimiento=formulario.cleaned_data['fecha_nacimiento'])
     return redirect('detalle_conductor',pk=conductor.id)
  else:
      formulario = ConductorForm()
  return render(request, 'conductor_nuevo.html', {'formulario': formulario})
@login_required
def editar_conductor(request, pk):
    conductor = get_object_or_404(conductor, pk=pk)
    if request.method == "POST":
        formulario = conductorForm(request.POST, instance=conductor)
        if formulario.is_valid():
            conductor = formulario.save(commit=False)
            conductor.save()
            return redirect('conductor', pk=conductor.id)
    else:
       formulario = conductorForm(instance=conductor)
    return render(request, 'conductor_nuevo.html', {'formulario': formulario})
@login_required
def editar_conductor(request, pk):
    conduc = get_object_or_404(Conductor, pk=pk)
    if request.method == "POST":
        formulario = ConductorForm(request.POST, instance=conduc)
        if formulario.is_valid():
            conduc = formulario.save(commit=False)
            conduc.save()
            return redirect('detalle_conductor', pk=conduc.id)
    else:
       formulario = ConductorForm(instance=conduc)
    return render(request, 'conductor_editar.html', {'formulario': formulario})

#..............................
def listar_vehiculos(request):
    vh=Vehiculo.objects.all()
    return render(request,'listar_vehiculos.html',{'vh':vh})

def listar_conductores(request):
    con=Conductor.objects.all()
    return render(request,'listar_conductores.html',{'con':con})

def vehiculo_detalle(request,pk):
        p=get_object_or_404(Vehiculo, pk=pk)
        datos=[]
        vt=Alquiler.objects.filter(vehiculo_id=pk)
        for vt in vt :
            nve = Conductor.objects.get(pk=vt.conductor_id)
            datos.append (nve)
        return render(request,'vehiculo_detalle.html', {'p':p,'datos':datos})

def detalle_conductor(request,pk):
    p=get_object_or_404(Conductor, pk=pk)
    return render(request,'detalle_conductor.html', {'p':p})

def eliminar_vehiculo(request, pk):
    v = get_object_or_404(Vehiculo, pk=pk)
    v.delete()
    return redirect('/')
# Create your views here.


"""
A dynamic array is similar to an array, but with the difference that its size can be dynamically modified at runtime.
Don’t need to specify how much large an array beforehand.
The elements of an array occupy a contiguous block of memory, and once created, its size cannot be changed.
A dynamic array can, once the array is filled, allocate a bigger chunk of memory,
copy the contents from the original array to this new space, and continue to fill the available slots.

"""
import  ctypes

class DyanamicArray(object):
	"""
	Dyanamic array class simillar to to Python list
	"""
	def __init__(self):
		self.n = 0 # Count actual elements, defaults is set to 0
		self.capacity = 1 # default capacity
		self.A = self.make_array(self.capacity)

	def __len__(self):
		"""
		Returns number of element in the array
		"""
		return self.n

	def __getitem__(self, k):
		"""
		Returns element at index k
		"""
		if 0 <= k <= self.n:
			return self.A[k]
		else:
			raise IndexError("Array out of Bounds!")

	def append(self, item):
		"""
		Add element to the end of the array
		"""
		if self.n == self.capacity:
			# if the capacity is not enough, Just fucking double it
			self._resize(2 * self.capacity)

		# setting the new item to last position of the array
		self.A[self.n] = item
		self.n += 1

	def _resize(self, new_capacity):
		"""
		doubles the capacity of the array
		"""
		B = self.make_array(new_capacity) # first make a array double the size of existing

		# next copy all the value from previous array to new one
		for k in range(self.n):
			B[k] = self.A[k]

		self.A = B # replace the old array with new one
		self.capacity = new_capacity # updates the capacity with new capacity

	def make_array(self, capacity):
		"""
		creates and return a new array with provided capacity.
		"""
		return (capacity * ctypes.py_object) ()

arr = DyanamicArray()
arr.append(1)
arr.append(2)
arr.append(3)

print(arr[1])


import cv2
import numpy as np

from .schema import BoundingBox

def draw_one_box(image: np.ndarray, box: BoundingBox) -> None:
    """
    Draw one bounding box for single object with caption contained class name and confidence. Mutates input image.

    Parameters:
        image: Image to draw;
        box: Bounding box.

    Returns:
        None.
    """
    image_height, image_width, _ = image.shape
    scaled_left_x, scaled_left_y, scaled_width, scaled_height = box.coordinates
    top_left_x = int(scaled_left_x * image_width)
    top_left_y = int(scaled_left_y * image_height)
    bottom_right_x = int(scaled_width * image_width + top_left_x)
    bottom_right_y = int(scaled_height * image_height + top_left_y)

    # Draw object box.
    cv2.rectangle(image, (top_left_x, top_left_y), (bottom_right_x, bottom_right_y), box.color, thickness=5)

    caption = f'{box.class_name}: {box.confidence:.2f}'
    (width, height), baseline = cv2.getTextSize(caption, 0, fontScale=1.7, thickness=2)

    # Draw caption box and fill it with box color.
    cv2.rectangle(image, (top_left_x, top_left_y), (top_left_x + width, top_left_y - height - 10), box.color, -1)

    # Draw caption.
    cv2.putText(image, caption, (top_left_x, top_left_y - 5), 0, 1.7, [0, 0, 0], thickness=2, lineType=cv2.LINE_AA)


import openpyxl
import requests
import shutil
import time
filename = "scraped/sovereign_pr.xlsx"

book = openpyxl.load_workbook(filename)
sheet = book.active

i = 2
while i < sheet.max_row:
    id = sheet[f"B{i}"].value
    url = sheet[f"D{i}"].value
    response = requests.get(url, stream=True)
    if response.status_code == 200:
        response.raw.decode_content = True
        with open(f"images/sovereign_pr/{id}.jpg", "wb") as file:
            shutil.copyfileobj(response.raw, file)
            print(f"Image {id} has successfuly downloaded")
            i += 1
            time.sleep(1)
    else:
        print("Couldn't connect to url.")
        i += 1
        time.sleep(2)

book.close()


import re

def process(x, highest):
    y = re.match( r'(.*?) (.*)', x.group(2))
    if y.group(1) == 'inc':
        registers[x.group(1)] += int(y.group(2))
    else:
        registers[x.group(1)] -= int(y.group(2))
    return max(registers[x.group(1)], highest)

with open('input.txt') as f:
    content = f.readlines()
content = [x.strip() for x in content]

registers = {}
highest = 0
for i in content:
    x = re.match( r'(.*?) (.*?) if (.*)', i)
    registers[x.group(1)] = 0

for i in content:
    x = re.match( r'(.*?) (.*?) if (.*)', i)
    y = re.match( r'(.*?) (.*?) (.*)', x.group(3))
    if y.group(2) == '==':
        if registers[y.group(1)] == int(y.group(3)):
            highest = process(x, highest)
    elif y.group(2) == '>':
        if registers[y.group(1)] > int(y.group(3)):
            highest = process(x, highest)
    elif y.group(2) == '>=':
        if registers[y.group(1)] >= int(y.group(3)):
            highest = process(x, highest)
    elif y.group(2) == '<':
        if registers[y.group(1)] < int(y.group(3)):
            highest = process(x, highest)
    elif y.group(2) == '<=':
        if registers[y.group(1)] <= int(y.group(3)):
            highest = process(x, highest)
    elif y.group(2) == '!=':
        if registers[y.group(1)] != int(y.group(3)):
            highest = process(x, highest)

print(max([registers[i] for i in registers]))
print(highest)


#!/usr/bin/env python3

# Python 3.9.7

# 13_numpy_broadcasting.py

# Broadcasting: NumPy operations between arrays of same or different size.

# Dependency
import numpy as np

# CASE 1: Not matching row length:
identity_matrix = np.identity(3)
coefficient = 2

result = identity_matrix * coefficient
print(result)

# CASE 2: Matching rows length:
identity_matrix = np.identity(3)
print(identity_matrix)

single_row_matrix = [0, 0, 1]

result = identity_matrix + single_row_matrix
print(result)

# CASE 3: If the shapes are incompatible, an exception is raised.
matrix_a = np.array([4, 9, 2, 4])
matrix_b = np.array([6, 1, 7])

result = matrix_a[:, np.newaxis] + matrix_b # correct notation for desired output.
print(result)

try: # Raises a ValueError.
    result = matrix_a + matrix_b
except ValueError as err:
    print(err) # operands could not be broadcast together with shapes (4,) (3,)


# 0-indexed
class SegTree:
    def __init__(self, vals, seg_f, ide_ele):
        n = len(vals)
        self.seg_f = seg_f
        self.ide_ele = ide_ele
        self.leaf_n = 1 << (n-1).bit_length()
        self.tree = [ide_ele]*(2*self.leaf_n-1)
        for i in range(n):  # init leaf
            self.tree[i+self.leaf_n-1] = vals[i]
        for i in range(self.leaf_n-2, -1, -1):  # bottom-up
            self.tree[i] = self.seg_f(self.tree[2*i+1], self.tree[2*i+2])

    def update(self, i, x):
        i += (self.leaf_n-1)
        self.tree[i] = x
        while i > 0:
            i = (i-1)//2
            self.tree[i] = self.seg_f(self.tree[2*i+1], self.tree[2*i+2])

    # [l,r)
    def query(self, l, r):
        v_l = self.ide_ele
        v_r = self.ide_ele
        l += (self.leaf_n-1)
        r += (self.leaf_n-1)
        while l < r:
            if l&1 == 0:
                v_l = self.seg_f(v_l, self.tree[l])
            if r&1 == 0:
                v_r = self.seg_f(v_r, self.tree[r-1])
                r -= 1
            l >>= 1
            r >>= 1
        return self.seg_f(v_l ,v_r)

'''
memo:
GCD... INFをide_eleに設定して、片方がINFの場合はもう片方を返す
def gcd2(a,b):
    if a >= INF: return b
    elif b >= INF: return a
    else return gcd(a,b)

vl = [1,4,6,8,9]

def add(a,b): return a+b
st = SegTree(vl,add,0)
st = SegTree(vl,(lambda a,b: a+b),0)
st = SegTree(vl,min,10**10)

print(st.query(2,4))
st.update(4,-4)
print(st.query(2,5))
st.update(0,-10)
print(st.query(0,5))
'''

def main():
    n,k = map(int, input().split())
    seg = SegTree([0]*300001, max, 0)
    for _ in range(n):
        a = int(input())
        l = max(a-k,0)
        r = min(a+k,300000)
        c_max = seg.query(l,r+1)
        seg.update(a,c_max+1)

    ans = seg.query(0,300001)
    print(ans)

if __name__ == "__main__":
    main()


import cvlib as cv
from cvlib.object_detection import draw_bbox
import cv2
import json
import time
import os

class Stopwatch:
    def __init__(self):
        self.creationTime = time.time()

    def elapsedTime(self):
        return time.time() - self.creationTime

    def setZero(self):
        self.creationTime = time.time()

class Pole:
    def __init__(self):
        self.g = 0
        self.time = Stopwatch()

def ForStart(carsNorth, carsWest):
    if (carsNorth > carsWest):
        poleNorth.g = 1
        poleNorth.time.setZero()
        return [(1, 0), (0, 1)]

    poleWest.g = 1
    poleWest.time.setZero()
    return [(0, 1), (1, 0)]

def lights(north, west):
    if north[0].g == 0:
        toWork = west
        noWork = north
    else:
        toWork = north
        noWork = west

    if (toWork[0].time.elapsedTime() <= 10):
        return None

    elif (toWork[0].time.elapsedTime() >= 60):
        ##change Light
        toWork[0].g = 0
        noWork[0].g = 1
        noWork[0].time.setZero()

    else:
        loadFactor = toWork[1] / (toWork[1] + noWork[1])
        if (loadFactor < threshHold):
            ##change Light
            toWork[0].g = 0
            noWork[0].g = 1
            noWork[0].time.setZero()

    return [(north[0].g, (north[0].g + 1) % 2), (west[0].g, (west[0].g + 1) % 2)]

# open webcam
webcam = cv2.VideoCapture(0)

if not webcam.isOpened():
    # print("Could not open webcam")
    exit()

person = {}
person['people'] = []

# loop through frames
while webcam.isOpened():

    # read frame from webcam
    status, frame = webcam.read()

    if not status:
        # print("Could not read frame")
        exit()

    # apply object detection
    bbox, label, conf = cv.detect_common_objects(frame)
    person['people'].append(label)
    # print(bbox, label, conf)
    count = 0
    size = len(label)
    for i in range(0, size):
        if (label[i] == 'car'):
            count += 1
    # print (count)

    # draw bounding box over detected objects
    out = draw_bbox(frame, bbox, label, conf)

    # display output
    cv2.imshow("Real-time object detection", out)
    time.sleep(3)
    # press "Q" to stop
    if cv2.waitKey(1) & 0xFF == ord('q'):
        break

# release resources
webcam.release()
cv2.destroyAllWindows()

min = 10  # sec
max = 60  # sec

threshHold = 5 / 12

carsNorth = count
carsWest = 5

poleNorth = Pole()
poleWest = Pole()

lightStatus = ForStart(carsNorth, carsWest)
print(lightStatus)

while (1):
    lightStatus = lights((poleNorth, carsNorth), (poleWest, carsWest))
    print(lightStatus)
    time.sleep(5)
    carsWest = 5


from random import sample, random
answers = [0,1,2,3]
symbols = [[1,2,3,4,5,6,7],[8,1,7,9,10,6,11],[12,13,9,14,15,3,10],[16,17,18,5,14,11,19],[20,19,18,21,17,22,23],[16,8,24,25,20,26,27]]

def _keypadsTest(keypad, testBool):
    pad = keypad.generate()
    tgt = False

    print('C ', end='') if testBool else print('I ', end='')
    print(pad,end=': ')

    # Ensure no duplicate values
    if len(set(pad)) != len(pad):
        print('Given Pad Contains Duplicates')
        return False

    # Find the proper solution column
    for i in symbols:
        correct = set(pad).issubset(i)
        if correct:
            # Ensures a solution column has not already been found
            if not tgt:
                tgt = i
            else:
                print('Given Pad Matches Multiple Solutions')
                return False

    # Ensures a solution column exists
    if tgt == -1:
        print('Unsolvable Pad')
        return False

    # Find the solution
    solution = []
    for i in tgt:
        if i in pad:
            solution.append(pad.index(i))

    # Find an incorrect solution
    incorrect = solution
    while incorrect == solution:
        incorrect = sample(answers,4)

    # Test the asked for solution
    if testBool:
        print(solution,end=' -> ')
        if keypad.solve(solution) == True:
            print('Correct')
            return True
        else:
            print('Incorrect')
            return False

    # Test the incorrect solution
    else:
        print(incorrect,end=' -> ')
        if keypad.solve(incorrect) == False:
            print('Correct')
            return True
        else:
            print('Incorrect')
            return False

def keypadsTest(keypad,tests):
    correct = 0
    corCount = 0
    incorrect = 0
    incCount = 0
    for i in range(tests):
        # Choose a good or bad guess
        guess = True if random() >= 0.5 else False
        if guess:
            corCount += 1
        else:
            incCount += 1

        # Check the solution
        if _keypadsTest(keypad,guess):
            if guess:
                correct += 1
            else:
                incorrect += 1

    print('\n\n')
    print(str(incorrect) + '/' + str(incCount) + ' Incorrect Answers Solved Correctly')
    print(str(correct) + '/' + str(corCount) + ' Correct Answers Solved Correctly')
    print('\nSolution Accuracy: ' + str(round((correct+incorrect)/(incCount+corCount),4)*100) + '%')


name = 'david'
name2 = 'David'
if name != name2:
    print('they are not equal')

x = 8
y = 15
if x > 15:
    print('true')
else:
    print(False)

z = 90
y = 89
x = 78
if z < x and z < x:
    print('z is less than')
elif y > z or x > z:
    print('both expressions are true')
elif x == z or x < z:
    print('at least one expression is true')


#! /usr/bin/env python
#-*- coding: utf-8 -*-

"""
Documents
"""

def s(*args, **kwargs):
    import pylab
    fig = pylab.figure()
    bbox = fig.add_subplot(*args, **kwargs).get_position()
    subplot = (bbox.x0, bbox.y0, bbox.width, bbox.height)
    pylab.close(fig)
    return subplot

def draw_ps_raw(raw, figure=None, subplot=111, title='', grid=True,
                      font_family=None, tick_labels_size=9, show=True):
    import analyse
    import analyse.plotter
    import pylab
    import matplotlib
    import numpy

    def_font_size = matplotlib.rcParams['font.size']
    def_font_family = matplotlib.rcParams['font.family']
    matplotlib.rcParams['font.size'] = tick_labels_size
    if font_family is not None: matplotlib.rcParams['font.family'] = font_family

    if figure is None:
        figure = pylab.figure()
    else:
        show = False

    if type(subplot) is int:
        subplot = analyse.plotter.get_subplot(subplot)
    elif type(subplot) in [list, tuple]:
        if len(subplot) == 3:
            subplot = analyse.plotter.get_subplot(subplot)

    crval = raw.data['crval1'][0]
    crpix = raw.data['crpix1'][0]
    cdelt = raw.data['cdelt1'][0]
    num = len(raw.data['data'][0])
    v = crval+(numpy.arange(num)-crpix+1)*cdelt

    ax = figure.add_axes(subplot)
    #[ax.plot(v, s) for s in spectra]
    [ax.plot(v, s) for s in raw.data['DATA']]
    ax.grid(grid)
    ax.set_title(title)

    if show:
        pylab.show()

    matplotlib.rcParams['font.size'] = def_font_size
    matplotlib.rcParams['font.family'] = def_font_family
    return figure

def draw_ps_spectrum(cube, figure=None, subplot=111, title='', grid=True,
                      font_family=None, tick_labels_size=9, show=True, *args, **kwargs):
    import analyse
    import analyse.plotter
    import pylab
    import matplotlib

    def_font_size = matplotlib.rcParams['font.size']
    def_font_family = matplotlib.rcParams['font.family']
    matplotlib.rcParams['font.size'] = tick_labels_size
    if font_family is not None: matplotlib.rcParams['font.family'] = font_family

    if figure is None:
        figure = pylab.figure()
    else:
        show = False

    if type(subplot) is int:
        subplot = analyse.plotter.get_subplot(subplot)
    elif type(subplot) in [list, tuple]:
        if len(subplot) == 3:
            subplot = analyse.plotter.get_subplot(subplot)

    nz, ny, nx = cube.data.shape
    spectra = cube.data.T.reshape(nx*ny, nz)
    v = analyse.generate_axis(cube, axis=3) / 1000.

    ax = figure.add_axes(subplot)
    [ax.plot(v, s) for s in spectra]
    ax.grid(grid)
    ax.set_title(title)

    if show:
        pylab.show()

    matplotlib.rcParams['font.size'] = def_font_size
    matplotlib.rcParams['font.family'] = def_font_family
    return figure

def draw_ss_spectrum(cube, flag, figure=None, subplot=111, title='', grid=True,
                      font_family=None, tick_labels_size=9, show=True, *args, **kwargs):
    import analyse
    import analyse.plotter
    import pylab
    import numpy
    import matplotlib

    tpeak, rms = analyse_ss(cube, flag)

    def_font_size = matplotlib.rcParams['font.size']
    def_font_family = matplotlib.rcParams['font.family']
    matplotlib.rcParams['font.size'] = tick_labels_size
    if font_family is not None: matplotlib.rcParams['font.family'] = font_family

    if figure is None:
        figure = pylab.figure()
    else:
        show = False

    if type(subplot) is int:
        subplot = analyse.plotter.get_subplot(subplot)
    elif type(subplot) in [list, tuple]:
        if len(subplot) == 3:
            subplot = analyse.plotter.get_subplot(subplot)

    nz, ny, nx = cube.data.shape
    spectra = cube.data.T.reshape(nx*ny, nz)
    v = analyse.generate_axis(cube, axis=3) / 1000.

    ax = figure.add_axes(subplot)
    [ax.plot(v, s) for s in spectra]
    ax.grid(grid)
    ax.set_title(title)
    """
    if fits_params['MOLECULE']=='12CO': tmb = float(sslist['tmb12'])
    elif fits_params['MOLECULE']=='13CO': tmb = float(sslist['tmb13'])
    elif fits_params['MOLECULE']=='C18O': tmb = float(sslist['tmb18'])
    else: pass
    """
    # 判断の参考に参考にTmbが○％のところに線を引く
    """
    xs = float(sslist['v_center']) - float(sslist['v_width'])/2.
    xe = float(sslist['v_center']) + float(sslist['v_width'])/2.
    """
    ###### atodekesu #####
    xs = -41.       #
    xe = 55.        #
    tmb = 40.       #
    ###### atodekesu #####
    percents = numpy.arange(50, 101, 10)
    percent_lines = tmb * percents / 100.
    [pylab.axhline(y=_y, color='r', linestyle='--', linewidth=2, alpha=0.5) for _y in percent_lines]
    [ax.text(xs, _y, str(_p)+'%') for _y, _p in zip(percent_lines, percents)]
    ax.set_ylim(-2, tmb*1.2)
    ax.set_ylabel('Ta* [K]')
    ax.set_xlabel('km/s')
    ax.set_xlim(xs, xe)
    #ax.set_title('%s %s' % (fits_params['OBJECT'], fits_params['DATE-OBS']))
    ax.annotate('Tpeak=%.2f [K]\nTmb=%.2f [K]\neff.=%.2f\nTrms=%.2f [K]'%(tpeak, tmb, tpeak/tmb, rms), xy=(.65,.85), xycoords='axes fraction')

    """
    if str(fits_params['BACKEND'])[-1]==1: direction='H'
    elif str(fits_params['BACKEND'])[-1]==2: direction='V'
    else: pass
    """

    if show:
        pylab.show()

    matplotlib.rcParams['font.size'] = def_font_size
    matplotlib.rcParams['font.family'] = def_font_family
    return figure

def analyse_ss(cube, flag):
    import numpy

    g = lambda x, mu, sig: 1/numpy.sqrt(2*numpy.pi*sig**2) * numpy.exp(-(x-mu)**2/(2*sig**2.))
    x = numpy.arange(len(cube.data))
    mu = len(cube.data)/2
    sig = 20/(2*numpy.sqrt(2*numpy.log(2)))
    g0 = g(x, mu, sig)  #コンボリューション用のガウシアンを生成
    g0 /= numpy.sum(g0)  #規格化

    nz, ny, nx = cube.data.shape
    spectra = cube.data.copy().T.reshape(nx*ny, nz)
    spectrum = spectra[0]
    spectrum[numpy.isnan(spectrum)] = 0
    spectrum[numpy.isinf(spectrum)] = 0
    sd = numpy.convolve(spectrum, v=g0, mode='same')  #コンボリューション
    d_sd = [sd[i+1]-sd[i] for i,d_ in list(enumerate(sd))[:-1]]  #微分
    dd_sd = [d_sd[i+1]-d_sd[i] for i,d_ in list(enumerate(d_sd))[:-1]]  #微分
    # 観測された標準天体のピーク温度のチャンネルを算出(2回微分を行ったときの極小値)
    ddmin_ind = numpy.where(dd_sd==numpy.min(dd_sd))[0][0] - 1
    # 観測された標準天体のピーク温度を算出(上で求めたチャンネルの温度と、前後2点の値との平均をとっている)
    tpeak = numpy.average(spectrum[ddmin_ind-2:ddmin_ind+3])

    # --- rmsを求める ---
    flags = flag.data.copy().T.reshape(nx*ny, nz)
    spectra[numpy.where(flags!=0)] = 0
    spectra[numpy.isnan(spectra)] = 0
    spectra[numpy.isinf(spectra)] = 0
    rms = [numpy.sqrt(numpy.sum(spectra[i,:]**2)/float(nz)) for i in range(len(spectra))][0]

    print('tpeak: %.3f rms: %.3f'%(tpeak,rms))

    return tpeak, rms

def draw_ps(raw=None, cube=None, suptitle='', show=True,
             *args, **kwargs):
    import pylab

    fig = pylab.figure(figsize=(10,8))
    fig.suptitle(suptitle)

    #plot = custom_draw_map(figure=fig, show=False)
    draw_ps_raw(raw, figure=fig, subplot=231, title='raw', *args, **kwargs)
    draw_ps_spectrum(cube, figure=fig, subplot=234, title='spectra', *args, **kwargs)

    if show:
        pylab.show()

    return fig


# -*- coding: utf-8 -*-

# webhook address https://[YOUR WEBSITE]/whook/[YOUR TOKEN]
# setWebhook address
# https://api.telegram.org/bot[YOUR TOKEN]/setWebhook?url=https://[YOUR WEBSITE]/whook/[YOUR TOKEN]/hook

# import for script core part
import requests
import json
from multiprocessing import Process
import uuid
import urllib.parse
# import for picture generate
from PIL import Image,ImageFont,ImageDraw
from io import BytesIO
# import for Tornado WebHook
import tornado.httpserver
import tornado.ioloop
import tornado.web
import tornado.gen
from tornado.options import define, options, parse_command_line
# multi-thread async
from tornado.concurrent import run_on_executor
from concurrent.futures import ThreadPoolExecutor
import config

bot_token = config.bot_token
# Tornado define
define("port", default=8022, help="run on the given port", type=int)

url = 'https://api.telegram.org/bot%s/' % bot_token
bot_url = config.bot_callback_url

def illyasviel_answerInlineQuery(update: dict, queryResult: dict):
    # print(json.dumps(queryResult))
    r = requests.post(
        url + 'answerInlineQuery',
        data = {
            'inline_query_id': update['inline_query']['id'],
            'results': json.dumps(queryResult)
        }
    )
    print(r.content)

def illyasviel_picture(update: dict) -> bool:
    if update:
        if 'inline_query' not in update:
            return False
        queryInput = update['inline_query']['query']
        if queryInput == "":
            return False
        queryInput = urllib.parse.quote_plus(queryInput)
        queryResult = []
        for mode in range(len(config.images_dict)):
            tempDict = {}
            tempDict['type'] = "photo"
            tempDict['id'] = uuid.uuid4().hex
            tempDict['photo_width'] = config.images_dict[str(mode)][0]
            tempDict['photo_height'] = config.images_dict[str(mode)][1]
            tempDict['photo_url'] = bot_url + "img?thumb=0&mode=%s&msg=%s" % (mode, queryInput)
            tempDict['thumb_url'] = bot_url + "img?thumb=1&mode=%s&msg=%s" % (mode, queryInput)
            tempDict['title'] = str(mode)
            queryResult.append(tempDict)
        illyasviel_answerInlineQuery(update, queryResult)
    return True

def illyasviel_debug(update: dict) -> bool:
    if update:
        print(update)
    return False

def illyasviel_null(update: dict) -> bool:
    if update:
        pass
    return False

# 接收来自TG的消息请求用
class MessageEventHandler(tornado.web.RequestHandler):
    executor = ThreadPoolExecutor(10)

    @tornado.gen.coroutine
    def post(self):
        # print(self.request.body.decode(encoding='UTF-8'))
        output_string = yield self.execute_job()
        self.write(output_string)
        self.finish()

    @run_on_executor
    def execute_job(self):
        return_string = "OK"
        update = json.loads(self.request.body.decode(encoding='UTF-8'))
        jobs = []
        for function_name in [illyasviel_picture, illyasviel_debug, illyasviel_null]:
            global_job = Process(target=function_name, args=(update,))
            jobs.append(global_job)
            global_job.start()
        jobs[-1].terminate()
        return return_string

class ImageEventHandler(tornado.web.RequestHandler):
    executor = ThreadPoolExecutor(10)

    @tornado.gen.coroutine
    def get(self):
        output_data = yield self.execute_job()
        self.set_header("Content-Type", "image/jpeg")
        self.write(output_data)
        self.finish()

    @run_on_executor
    def execute_job(self):
        mode = self.get_argument("mode")
        message = self.get_argument("msg")
        thumb = self.get_argument("thumb")
        # load setting
        pos = config.images_dict[mode][2]
        font_size = config.images_dict[mode][3]
        font_color = config.images_dict[mode][4]
        filename = config.image_path + config.images_dict[mode][5]
        # gen picture
        img = Image.open(filename)
        draw = ImageDraw.Draw(img)
        font = ImageFont.truetype(config.font_path, font_size)
        imgW, imgH = img.size
        textW, textH = draw.textsize(message,font=font)
        # print(textW, textH)
        draw.text(((imgW-textW)/2,pos),message,font_color,font=font)
        # thumb
        if thumb == "1":
            img.thumbnail((300,300),Image.ANTIALIAS)
        # gen file pointer
        img_io = BytesIO()
        img.save(img_io, 'JPEG', quality=100)
        img_io.seek(0)
        # return picture
        return img_io.getvalue()

if __name__ == "__main__":
    parse_command_line()
    app = tornado.web.Application(handlers=[
        (r"/hook", MessageEventHandler),
        (r"/img", ImageEventHandler)
    ])
    http_server = tornado.httpserver.HTTPServer(app)
    http_server.listen(options.port, address="127.0.0.1")
    tornado.ioloop.IOLoop.instance().start()


# -*- coding: utf-8 -*-
import hashlib
import uuid

from dirtyfields import DirtyFieldsMixin
from django.db import models
from django.utils.translation import gettext_lazy as _
from django_auxilium.models import (
    BaseModel,
    RandomImageField,
    file_field_auto_change_delete,
)
from utils.models import FilteredTranslatableMixin, SlugFromNameMixin

@file_field_auto_change_delete
class Person(DirtyFieldsMixin, FilteredTranslatableMixin, SlugFromNameMixin, BaseModel):
    id = models.UUIDField(primary_key=True, default=uuid.uuid4, editable=False)

    name = models.CharField(_("Name"), max_length=128)

    gravatar_email = models.EmailField(
        _("Email"), blank=True, help_text=_("Gravatar email for profile image")
    )
    profile_image = RandomImageField(
        _("Profile Image"),
        blank=True,
        upload_to="people/profiles_images",
        help_text=_("Uploaded profile image"),
    )

    position = models.CharField(
        _("Position"), max_length=128, blank=True, help_text=_("Position in the church")
    )
    about = models.TextField(_("About"), blank=True)

    class Meta:
        verbose_name = _("Person")
        verbose_name_plural = _("People")
        ordering = ["name"]

    @property
    def profile_image_url(self) -> str:
        if self.profile_image:
            return self.profile_image.url
        if self.gravatar_email:
            email_hash = hashlib.md5(
                self.gravatar_email.encode("utf-8").lower().strip()
            ).hexdigest()
            return f"https://www.gravatar.com/avatar/{email_hash}?s=300"

    def __str__(self):
        return self.name


if __name__=='__main__' :
    N=int(input())
    result=-1

    for i in range(N):
        sum = 0
        sum+=i
        i=str(i)
        for j in range(len(i)):
            sum+=int(i[j])

        if sum==N:
            result=int(i)
            break

    if result==-1:
        result=0
    print(result)


N, M = map(int, input().split())
result = []
def go(index, N, M):
    if index == M:
        print(*result, sep = " ", end = "\n")
    else:
        for iter in range(1, N + 1):
            result.append(iter)
            go(index + 1, N, M)
            result.pop()
go(0, N, M)


import argparse, sys, os, time, glob
import warnings; warnings.simplefilter('ignore')  #pytorch is too noisy

from src import util

def train(args):
    '''Main training entry point'''
    imagefiles, annotations = util.read_splitfiles(
        args.training_images, args.training_annotations
    )
    print('Number of files for training:  ', len(imagefiles))

    val_imagefiles, val_annotations = None,None
    if args.validation_images:
        val_imagefiles, val_annotations = util.read_splitfiles(
            args.validation_images, args.validation_annotations
        )
        print('Number of files for validation:', len(val_imagefiles))

    destination = util.output_name(args)
    print('Output directory:', destination)
    util.backup_code(destination)

    if args.modeltype == 'segmentation':
        from src import segmentation
        model = segmentation.SegmentationModel(
            backbone           = args.backbone,
            downsample_factor  = args.downsample,
        )
        kw     = {'scales':[args.downsample*0.8, args.downsample*1.5]}
    elif args.modeltype == 'INBD':
        assert os.path.exists(args.segmentationmodel)
        segmentationmodel = util.load_segmentationmodel(args.segmentationmodel)
        from src import INBD
        model = INBD.INBD_Model(
            segmentationmodel,
            backbone           = args.backbone,
            wedging_rings      = args.wd,
            angular_density    = args.angular_density,
            concat_radii       = args.radcat,
            var_ares           = args.var_ares,
            interpolate_ambiguous = args.interpolate_ambiguous,
        )
        assert args.per_epoch_it > 0
        kw     = {
            'scales'         : [model.scale*0.9, model.scale*1.2],
            'wd_lambda'      : args.wd_lambda,
            'per_epoch_it'   : args.per_epoch_it,
            'bd_augment'     : args.bd_augment,
        }
    elif args.modeltype == 'MaskRCNN':
        from src import maskrcnn
        model = maskrcnn.MaskRCNN_RingDetector(nms = args.nms, accumulating = args.mrcnn_acc)
        kw    = {
            'scales'         : [args.downsample],
        }
    elif args.modeltype == 'cartesian':
        assert os.path.exists(args.segmentationmodel)
        segmentationmodel = util.load_segmentationmodel(args.segmentationmodel)

        from src.cartesian import cartesian
        model = cartesian.CartesianModel(segmentationmodel, input_size=args.size)
        kw    = {
            'ds_kwargs' : {
                'input_size'        : args.size,
                'segmentationmodel' : segmentationmodel,
            }
        }

    #save already now and immediately reload model
    #otherwise might lead to inconsistencies if code changes during training
    model_destination     = os.path.join(destination, 'model')
    model_destination_tmp = model.save(model_destination+'.tmp.pt.zip')
    model                 = util.load_model(model_destination_tmp)
    err = model.start_training(
        imagefiles,     annotations,
        val_imagefiles, val_annotations,
        epochs              = args.epochs,
        lr                  = args.lr,
        amp                 = args.amp,
        val_freq            = args.val_freq,
        **kw
    )
    if err:
        print('Aborted')
        sys.exit(1)

    #save again with trained weights
    model_destination = model.save( model_destination )
    os.remove(model_destination_tmp)
    print('Saved to ', model_destination)

def inference(args):
    import matplotlib.cm as mplcm, PIL.Image, numpy as np, torch

    if not os.path.exists(args.images):
        print(f'File {args.images} does not exist')
        return

    if args.images.lower().endswith('.txt'):
        imagefiles = util.read_splitfile(args.images)
    elif args.images.lower().endswith('.jpg') or args.images.lower().endswith('.jpeg'):
        imagefiles = [args.images]
    else:
        print(f'[ERROR] unknown file type: {args.images}')
        return
    print(f'Running inference on {len(imagefiles)} files')

    assert os.path.exists(args.model)
    model      = util.load_model(args.model).eval().requires_grad_(False)
    if torch.cuda.is_available():
        model.cuda()

    modelbasename = args.model.split('/')[-2]
    outputdir     = os.path.join(args.output, f'{modelbasename}_{args.suffix}' )
    os.makedirs(outputdir, exist_ok=True)
    print(f'Saving outputs to: {outputdir}')

    for i,f in enumerate(imagefiles):
        print(f'[{i:4d}/{len(imagefiles)}] {os.path.basename(f)}', end='\r')
        upscale = (not args.seg)
        try:
            output  = model.process_image(f, upscale_result=upscale)
        except Exception as e:
            print(f'Could not process image {os.path.basename(f)}: {e}')
            continue

        outf     = os.path.join(outputdir, os.path.basename(f))
        if hasattr(output, 'labelmap'):
            labelmap = output.labelmap
            #save labelmap
            np.save(outf+'.labelmap.npy', labelmap)

            labelmap_rgba = mplcm.gist_ncar( labelmap / labelmap.max() )
            PIL.Image.fromarray((labelmap_rgba*255).astype('uint8')).save(outf+'.labelmap.png')

            open(outf+'.areas.csv', 'w').write(util.labelmap_to_areas_output(labelmap))

        if hasattr(output, 'boundaries'):
            from src import INBD
            open(outf+'.widths.csv', 'w').write(INBD.boundaries_to_ring_width_output(output.boundaries, scale=model.scale))
            if hasattr(output, 'labelmap'):
                H,W = output.labelmap.shape[-2:]
                open(outf+'.labelmap.svg','w').write(INBD.boundaries_to_svg(output.boundaries, (W,H), model.scale))

        if hasattr(output, 'boundary'):
            #segmentation map
            np.save(outf+'.segmentation.npy', output)

            boundaries_normed = np.tanh(output.boundary)/2+0.5
            PIL.Image.fromarray((boundaries_normed*255).astype('uint8')).save(outf+'.segmentation.png')
    print()

def evaluate(args):
    from src import evaluation
    import pickle, json
    annotations = sorted(util.read_splitfile(args.annotations), key=os.path.basename)
    results     = sorted(glob.glob( os.path.join(args.outputs, '*.npy' ) ), key=os.path.basename )
    assert len(annotations) == len(results), [len(annotations), len(results)]
    #TODO: check that the filenames are the same

    print(f'Evaluating {len(results)} results')
    metrics, metrics_raw = evaluation.evaluate_resultfiles(results, annotations)
    print(metrics)
    json.dump(metrics, open(os.path.join(args.outputs, 'metrics.json' ), 'w') )
    pickle.dump( metrics_raw, open(os.path.join(args.outputs, 'metrics.pkl' ), 'wb') )

def update(args):
    '''Update a saved INBD model with new source code'''
    assert os.path.exists(args.model)

    model = util.load_model(args.model).eval().requires_grad_(False)
    assert 'INBD' in model.__class__.__name__, NotImplementedError()

    from src import INBD, segmentation
    segmodel     = model.segmentationmodel[0]
    new_segmodel = segmentation.SegmentationModel(
        backbone           = segmodel.backbone_name,
        downsample_factor  = segmodel.scale,
    )
    new_segmodel.load_state_dict(segmodel.state_dict())

    new_model = INBD.INBD_Model(
        new_segmodel,
        backbone           = model.backbone_name,
        wedging_rings      = model.wd_det is not None,
        angular_density    = model.angular_density,
        concat_radii       = model.concat_radii,
        var_ares           = model.var_ares,
        interpolate_ambiguous = getattr(model, 'interpolate_ambiguous', True), #legacy
    )

    new_model.load_state_dict(model.state_dict())
    outputpath = args.model.replace(".pt.zip", ".update.pt.zip")
    new_model.save(outputpath)

if __name__ == '__main__':
    parser     = argparse.ArgumentParser()
    subparsers = parser.add_subparsers(title='subcommands', required=True)

    parser_train = subparsers.add_parser('train', help='Train a network')
    parser_train.add_argument('modeltype',                choices=['segmentation', 'INBD', 'MaskRCNN', 'cartesian'], help='Model type')
    parser_train.add_argument('training_images',          type=str, help='Path to a text file containing paths to training images')
    parser_train.add_argument('training_annotations',     type=str, help='Path to a text file containing paths to training annotations')
    parser_train.add_argument('--validation_images',      type=str, help='Path to a text file containing paths to validation images')
    parser_train.add_argument('--validation_annotations', type=str, help='Path to a text file containing paths to validation annotations')
    parser_train.add_argument('--segmentationmodel',      type=str, help='Path to pretrained segmentation model (INBD only)')
    parser_train.add_argument('--epochs',          type=int,   default=100, help='Number of training epochs')
    parser_train.add_argument('--downsample',      type=float, default=4,   help='Resolution downsampling factor')
    parser_train.add_argument('--size',            type=int,   default=512, help='Resolution for the cartesian model')
    parser_train.add_argument('--backbone',        type=str,   default='mobilenet3l',  help='UNet backbone')

    parser_train.add_argument('--wd',              type=int,   default=1,    help='Wedging ring detection (WRD)')  #bool
    parser_train.add_argument('--wd_lambda',       type=float, default=0.01, help='WRD loss weight')
    parser_train.add_argument('--radcat',          type=int,   default=1,    help='Concatenate radii as input for the INBD network')  #bool
    parser_train.add_argument('--angular-density', type=float, default=6.28, help='Hyperparameter alpha')
    parser_train.add_argument('--per_epoch_it',    type=int,   default=3,    help='Number of iterations per training epoch')
    parser_train.add_argument('--bd_augment',      type=int,   default=1,    help='Boundary augmentations')
    parser_train.add_argument('--var_ares',        type=int,   default=1,    help='Variable angular resolution')
    parser_train.add_argument('--interpolate_ambiguous', type=int, default=1, help='Interpolate ambiguous boundary points')

    parser_train.add_argument('--nms',        type=float, default=0.7,   help='Non-Max Suppression threshold (Mask-RCNN)')
    parser_train.add_argument('--mrcnn_acc',  type=int,   default=0,     help='Mask-RCNN: accumulate rings (filled mode)')

    parser_train.add_argument('--lr',         type=float, default=1e-3,  help='Learning rate')
    parser_train.add_argument('--amp',        type=bool,  default=True,  help='Mixed precision training')
    parser_train.add_argument('--val_freq',   type=int,   default=1,     help='Validation frequency (epochs)')

    parser_train.add_argument('--output',     type=str,   default='checkpoints/',   help='Output directory')
    parser_train.add_argument('--suffix',     type=str,   default='',               help='Suffix/description to add to output name')
    parser_train.set_defaults(func=train)

    parser_inf   = subparsers.add_parser('inference', help='Process images with a network')
    parser_inf.add_argument('model',       type=str, help='Path to pretrained model')
    parser_inf.add_argument('images',      type=str, help='Path to a text file containing paths to images')
    parser_inf.add_argument('--output',    type=str, default='inference/', help='Output directory')
    parser_inf.add_argument('--suffix',    type=str, default='',           help='Suffix/description to add to output name')
    parser_inf.add_argument('--seg',       type=bool,default=False,        help='Save only segmentation output')
    parser_inf.set_defaults(func=inference)

    parser_eval  = subparsers.add_parser('evaluate',  help='Evaluate a network')
    parser_eval.add_argument('outputs',     type=str, help='Path to a folder containing inference outputs')
    parser_eval.add_argument('annotations', type=str, help='Path to a text file containing paths to annotations')
    parser_eval.set_defaults(func=evaluate)

    parser_up = subparsers.add_parser("update", help="Update a saved model with new source code")
    parser_up.set_defaults(func=update)
    parser_up.add_argument("model", type=str, help="Path to model")

    args = parser.parse_args(sys.argv[1:] or ['--help'])
    args.func(args)

    print('Done')


import pygame
import sys
from pygame.locals import *

WHITE = (255, 255, 255)

class Square:
    def __init__(self, screen, centerPosition, color = WHITE, numberOfPieces = 0):
        self.centerPosition = centerPosition
        self.color = color
        self.numberOfPieces = numberOfPieces
        self.screen = screen
        self.font = pygame.font.SysFont(None, 100)

    def drawSquare(self):
        pygame.draw.circle(self.screen, self.color, self.centerPosition, 60)
        pygame.draw.rect(self.screen, self.color, (self.centerPosition[0] - 40, self.centerPosition[1] - 40, 80, 80))

    def drawKallah(self):
        pygame.draw.circle(self.screen, self.color, self.centerPosition, 60)
        pygame.draw.circle(self.screen, self.color, (self.centerPosition[0], self.centerPosition[1] + 250), 60)
        pygame.draw.rect(self.screen, self.color, (self.centerPosition[0] - 60, self.centerPosition[1], 120, 250))

    def displayNumberOfPieces(self):
        text = self.font.render(str(self.numberOfPieces), True, WHITE)
        textRect = text.get_rect(center = self.centerPosition)
        self.screen.blit(text, textRect)

    def displayNumberOfPiecesOnKallah(self):
        text = self.font.render(str(self.numberOfPieces), True, WHITE)
        textRect = text.get_rect(center = (self.centerPosition[0], self.centerPosition[1] + 125))
        self.screen.blit(text, textRect)

    def checkButtonClickOnSquare(self):
        mouse = pygame.mouse.get_pos()

        if self.centerPosition[0] - 40 <= mouse[0] <= self.centerPosition[0] + 40 and self.centerPosition[1] - 40 <= mouse[1] <= self.centerPosition[1] + 40:
            return True

        else:
            return False

def setPlayerPosition(screen, positionKallah, positionY, color):
    positionX = 85
    player = []

    for cont in range(6):
        player.append(Square(screen, (positionX + 145, positionY), color, 4))
        positionX += 145

    player.append(Square(screen, (positionKallah, 125), color))

    return player

def drawPlayer(player):
    for cont in range(6):
        player[cont].drawSquare()
        player[cont].displayNumberOfPieces()

    player[6].drawKallah()
    player[6].displayNumberOfPiecesOnKallah()