from typing_extensions import Self

class Node:
    def __init__(self, column: int, row: int, count: int = 1,
                 up: Self = None, down: Self = None,
                 left: Self = None, right: Self = None):
        self.column = column
        self.row = row
        self.count = count
        self.up = up or self
        self.down = down or self
        self.left = left or self
        self.right = right or self

    def iterate_up(self, inclusive: bool = False):
        itr = self
        if inclusive:
            yield itr
        while itr.up != self:
            itr = itr.up
            yield itr

    def iterate_down(self, inclusive: bool = False):
        itr = self
        if inclusive:
            yield itr
        while itr.down != self:
            itr = itr.down
            yield itr

    def iterate_left(self, inclusive: bool = False):
        itr = self
        if inclusive:
            yield itr
        while itr.left != self:
            itr = itr.left
            yield itr

    def iterate_right(self, inclusive: bool = False):
        itr = self
        if inclusive:
            yield itr
        while itr.right != self:
            itr = itr.right
            yield itr


N, coins = 5, [3, 2, 1, 1, 9]

# My solution
def my_solution():
    from itertools import combinations
    num_set = set()
    for i in range(1, len(coins) + 1):
        num_set = num_set.union(map(sum, combinations(coins, i)))

    for i, p in enumerate(sorted(list(num_set)), start=1):
        if i != p:
            result = i
            break
    return result

# Book's solution
def solution():
    target = 1  # 0까지는 만들 수 있고, 1을 만들 수 있는 지 판단
    for a in sorted(coins):
        if a > target:  # a <= target 이면 target + a - 1 까지 만들 수 있다는 뜻!
            break
        target += a
    return target

print(my_solution())
print(solution())
# 8

04 만들 수 없는 금액.py


import json
import petname
import random
from flask import Flask, request

app = Flask(__name__)

# test
@app.route('/helloworld', methods=['GET'])
def hello_world():
	return "Hello world\n"

@app.route('/countAnimals', methods=['GET'])
def get_animals_count():
	animal_data = get_data()
	return str(len(animal_data['animals'])) + '\n'

@app.route('/specificAnimals', methods=['GET'])
def get_specific():
	head = request.args.get('head')
	body = request.args.get('body')
	arms = request.args.get('arms')
	legs = request.args.get('legs')
	tails = request.args.get('tails')

	result = get_specific_animals(head, body, arms, legs, tails)

	return json.dumps(result['animals'], indent = 2)

@app.route('/animals', methods=['GET'])
def get_animals():
	return json.dumps(get_data(), indent = 2)

@app.route('/buildAnimal/random', methods=['GET'])
def create_animal():
	animal = {}
	animal['animals'] = []
	head = {
		0: 'snake',
		1: 'bull',
		2: 'lion',
		3: 'raven',
		4: 'bunny'
	}
	arms = random.randrange(2, 11, 2)
	legs = random.randrange(3, 13, 3)
	animal['animals'].append({
		'head': head[random.randint(0, 4)],
		'body': petname.name() + "-" + petname.name(),
		'arms': arms,
		'legs': legs,
		'tails': arms + legs
	})

	return json.dumps(animal['animals'][0], indent = 2) + '\n'

@app.route('/buildAnimal', methods=['GET'])
def create_specific_animal():
	animal = {}
	animal['animals'] = []
	animal['animals'].append({
		'head': request.args.get('head'),
		'body': request.args.get('body'),
		'arms': int(request.args.get('arms')),
		'legs': int(request.args.get('legs')),
		'tails': int(request.args.get('tails'))
	})

	return json.dumps(animal['animals'][0], indent = 2) + '\n'

def get_data():
	with open("animals.json", 'r') as json_file:
		userdata = json.load(json_file)
	return userdata

def get_specific_animals(head, body, arms, legs, tails):
	animal_data = get_data()
	result = {}
	result['animals'] = []

	if head is not None:
		for i in range(len(animal_data['animals'])):
			if str(animal_data['animals'][i]['head']) == str(head):
				result['animals'].append(animal_data['animals'][i])

	if body is not None:
		for i in reversed(range(len(result['animals']))):
			if str(result['animals'][i]['body']) != str(body):
				del result['animals'][i]

	if arms is not None:
		for i in reversed(range(len(result['animals']))):
			if str(result['animals'][i]['arms']) != str(arms):
				del result['animals'][i]

	if legs is not None:
		for i in reversed(range(len(result['animals']))):
			if str(result['animals'][i]['legs']) != str(legs):
				del result['animals'][i]

	if tails is not None:
		for i in reversed(range(len(result['animals']))):
			if str(result['animals'][i]['tails']) != str(tails):
				del result['animals'][i]

	return result

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


"""
You are given a string where you have to find its first word.
When solving a task pay attention to the following points:
-There can be dots and commas in a string
-A string can start with a letter or, for example, a dot or space.
-A word can contain an apostrophe and it's a part of a word.
-The whole text can be represented with one word and that's it.
Input: A string
Output: A string
Example:
first_word("Hello world") == "Hello"
first_word("greetings, friends") == "greetings"
"""

#replace strip split사용하기

my_text = "greetings, friends"

def first_word(my_text):
    my_text = my_text.replace(",", " ")
    my_text = my_text.replace(".", " ")
    my_text = my_text.strip() #양옆 공백을 지워준다 - 근데 두개이상 스페이스 일때 하나로 지워주는 기능이지 하나만 공백 있을때는 안지운다
    my_text = my_text.split()  #공백기준으로 나눈다

    return my_text[0]

answer = first_word(my_text)
print(answer)


from celery import Celery
from src.config import *

# A display message when the app starts
print("[INFO] Keep Calm n Enjoy the drill...")

# Function to create celery
def make_celery(app_name=__name__):
    return Celery(
        app_name,
        broker=BROKER_URL,
        backend=BACKEND_URL
    )

celery = make_celery()


from random import randint

def quickSort(arr) :
  if (len(arr) < 2) : return arr
  pivot = randint(0, len(arr))
  less = [val for idx, val in enumerate(arr) if val <= arr[pivot] and idx != pivot]
  greater = [val for idx, val in enumerate(arr) if val > arr[pivot] and idx != pivot]
  return quickSort(less) + [arr[pivot]] + quickSort(greater)

arr = [56, 21, 45, 2, 14, 86, 33, 12, 8]
print(arr)
print(quickSort(arr))


from genericpath import exists
from os import makedirs
from os.path import exists
from PIL import Image, ImageDraw
from math import ceil
from functools import reduce
import constants as const
import utils

def main():
  file_names = utils.get_filenames(const.FOLDER_PATH, const.DB)
  if len(file_names) == 0:
    print('Нет ниодного изображения. Выход...')
    return
  pillow_images = utils.get_images(file_names, const.FOLDER_PATH)
  images = utils.resize_images(pillow_images, const.IMAGE_WIDTH, const.BLOCK_HEIGHT, const.IMAGE_RESOLUTION)
  ll = len(images)
  total_amount = reduce(lambda s, img: s + img.amount, images, 0)
  print(f' Всего изображений: {ll}\n Количество строк: {const.VERTICAL_AMOUNT}\n Количество столбцев: {const.HORIZONTAL_AMOUNT}')
  total_weight = input('- Введите вес подарка: ')
  total_price = input('- Введите цену подарка: ')
  layout_name = input('- Введите название сгенерированной картинки: ') or 'test'
  if not exists('result'):
    makedirs('result')

  layout_number = 1
  layouts_amount = ceil(ll / (const.HORIZONTAL_AMOUNT * const.VERTICAL_AMOUNT))
  pasted_counter = 0
  is_ended = False
  try:
    bg = Image.open(const.LAYOUT_BACKGROUND).resize((const.LAYOUT_WIDTH, const.LAYOUT_HEIGHT))
  except:
    print(f' Не удалось загрузить фон {const.LAYOUT_BACKGROUND}')

  while not is_ended:
    x_offset = const.LAYOUT_PADDING_HORIZONTAL + const.BLOCK_MARGIN
    y_offset = const.LAYOUT_PADDING_TOP + const.BLOCK_MARGIN
    layout = Image.new('RGB', [const.LAYOUT_WIDTH, const.LAYOUT_HEIGHT], (255, 255, 255))
    layout.paste(bg, (0, 0))
    # Layout number / layouts amount
    drawer_font = const.TEXT['NUMB']
    drawer_text = f'{layout_number} / {layouts_amount}'
    drawer_text_width = drawer_font.getsize(drawer_text)[0]
    drawer_size = (150, 60)
    drawer_position = (ceil(const.LAYOUT_WIDTH * 0.923), ceil(const.LAYOUT_HEIGHT * 0.95))
    layout.paste(utils.text_drawer(drawer_text, drawer_size, drawer_font, ((drawer_size[0] - drawer_text_width) // 2, 0)), drawer_position)
    # Price
    drawer_fill = (255, 25, 31)
    drawer_size = (400, 80)
    drawer_font = const.TEXT['INFO']
    drawer_text = total_price
    drawer_text_size = drawer_font.getsize(drawer_text)
    drawer_text_pos = ((drawer_size[0] - drawer_text_size[0]) // 2, (drawer_size[1] - drawer_text_size[1]) // 2)
    drawer_position = (ceil(const.LAYOUT_WIDTH * 0.8), ceil(const.LAYOUT_HEIGHT * 0.07))
    layout.paste(utils.text_drawer(drawer_text, drawer_size, drawer_font, drawer_text_pos, drawer_fill), drawer_position)
    # Weight
    drawer_text = total_weight
    drawer_text_size = drawer_font.getsize(drawer_text)
    drawer_text_pos = ((drawer_size[0] - drawer_text_size[0]) // 2, (drawer_size[1] - drawer_text_size[1]) // 2)
    drawer_position = (ceil(const.LAYOUT_WIDTH * 0.6357), ceil(const.LAYOUT_HEIGHT * 0.07))
    layout.paste(utils.text_drawer(drawer_text, drawer_size, drawer_font, drawer_text_pos, drawer_fill), drawer_position)
    # Amount
    drawer_text = f'{total_amount} штук'
    drawer_text_size = drawer_font.getsize(drawer_text)
    drawer_text_pos = ((drawer_size[0] - drawer_text_size[0]) // 2, (drawer_size[1] - drawer_text_size[1]) // 2)
    drawer_position = (ceil(const.LAYOUT_WIDTH * 0.4775), ceil(const.LAYOUT_HEIGHT * 0.07))
    layout.paste(utils.text_drawer(drawer_text, drawer_size, drawer_font, drawer_text_pos, drawer_fill), drawer_position)

    row = col = 0
    while not is_ended and col < const.HORIZONTAL_AMOUNT:
      while not is_ended and row < const.VERTICAL_AMOUNT:
        img = images[pasted_counter]
        x_offset_centred = x_offset + (const.IMAGE_WIDTH - img.size[0]) // 2
        y_offset_centred = y_offset + (const.BLOCK_HEIGHT - img.size[1]) // 2
        txt = utils.db_name(img.key, const.DB)
        sire = txt['sire']
        name = txt['name'].replace('гр)', 'г)').replace(' г)', 'г)')
        desc = txt.get('description', None)
        weight = txt.get('weight', None)
        if weight is not None and weight not in name:
          name += f' ({weight}г)'

        try:
          layout.paste(img, (x_offset_centred, y_offset_centred), mask=img.split()[3])
        except:
          layout.paste(img, (x_offset_centred, y_offset_centred))
        img.close()

        text = Image.new('RGBA', [const.TEXT_WIDTH, const.BLOCK_HEIGHT], (255, 255, 255))
        drawer = ImageDraw.Draw(text)

        text_x = text_y = 0
        drawer.text((text_x, text_y), sire, font=const.TEXT['SIRE'], fill=(120, 120, 120))

        text_x = const.TEXT['SIRE'].getsize(sire)[0] + 10
        drawer.text((text_x, text_y), f'{img.amount} шт', font=const.TEXT['ENUM'], fill=(18,183,45))

        text_x = 0
        text_y += const.TEXT['ENUM'].getsize(sire)[1] + const.TEXT_MARGIN
        name, shift = utils.to_multiline(name, const.TEXT['NAME'], const.TEXT_WIDTH, const.NAME_LINES)
        drawer.multiline_text((text_x, text_y), name, font=const.TEXT['NAME'], fill=(3, 3, 3))

        if desc is not None:
          text_y += shift + const.TEXT_MARGIN
          desc, shift = utils.to_multiline(desc, const.TEXT['DESC'], const.TEXT_WIDTH)
          drawer.multiline_text((text_x, text_y), desc, font=const.TEXT['DESC'], fill=(3, 3, 3))
          text_height = text_y + shift

        text_x = x_offset + const.IMAGE_WIDTH + const.IMAGE_TEXT_MARGIN
        text_y = y_offset + (const.BLOCK_HEIGHT - text_height) // 2
        layout.paste(text, (text_x, text_y))
        text.close()

        y_offset += const.BLOCK_HEIGHT + const.BLOCK_MARGIN
        pasted_counter += 1
        row += 1

        if pasted_counter >= ll:
          is_ended = True

      x_offset += const.BLOCK_WIDTH + const.BLOCK_MARGIN
      y_offset = const.LAYOUT_PADDING_TOP + const.BLOCK_MARGIN
      col += 1
      row = 0

    layout.convert('RGB').save(f"result/{layout_name}-{layout_number}.jpg")
    layout.close()
    print(f" Файл '{layout_name}-{layout_number}.jpg' сохранен в папке 'result'")
    layout_number += 1
  bg.close()

if __name__ == '__main__':
  main()
  input("\n Программа закончила работу\n Нажмите 'Enter' чтобы закрыть программу")


# First compare lengths of the first and second and define if operation was removing, inserting, or editing(or no change).
# Then use appropriate function to determine if it was only one operation
# Only one function? Yes, You can make three functions but you will look closely they are pretty much same. Little bit of here and there
# You can combine all the three functions into a single function

def one_way(first, second):
    # If length of first and second differs more than one, then just return False
    if abs(len(first) - len(second)) <= 1:
        return operation_check(first, second)
    return False

def operation_check(first, second):
    # Two pointers for first and second
    p = 0
    q = 0
    # One operation which will be removed whenever we encounter the first operation
    operation = 1

    while p < len(first) and q < len(second):
        # If we dont have any operation and still p and q are not equal, that means first and second differs more than one
        if operation <= 0 and first[p] != second[q]:
            return False
            # First time encounter the "result of operation", minus one from operation and then check for which operation is performed
        elif first[p] != second[q]:
            operation -= 1
            # Which operation was performed? length is greater? Insertion
            if len(first) > len(second):
                q -= 1
            # length is smaller? Deletion
            elif len(first) < len(second):
                q += 1
            # No change of q pointer for edit operation
        q += 1
        p += 1
    return True

print(one_way("pale", "ple"))
print(one_way("pales", "pale"))
print(one_way("pale", "bale"))
print(one_way("pale", "bake"))
print(one_way("hake", "hakse"))

1. Arrays and Strings/1.5 One Away/1. Three Functions.py


import collections

data = collections.deque(list(open("./input.csv").read()))
dirs = {">": +1, "<": -1}

stack = {(x+0j) for x in range(1,8)}

# Note that the 4th rock is the first element in the list due to modulo operator
rocks = [{(3+0j), (4+0j), (5+0j), (6+0j)},
    {(4+0j), (3+1j), (4+1j), (5+1j), (4+2j)},
    {(3+0j), (4+0j), (5+0j), (5+1j), (5+2j)},
    {(3+0j), (3+1j), (3+2j), (3+3j)},
    {(3+0j), (3+1j), (4+0j), (4+1j)}]

part2 = True
m = 5 * len(data) # Modulous

if part2 == False:
    n = len(data)
    rock_i = 0
    dir_i = 0
    max_height = 0j
    while rock_i != 2022: # New rock
        rock_i += 1
        rock = {pos+max_height+4j for pos in rocks[(rock_i % 5)-1 if rock_i % 5 != 0 else 4]}
        while True: # New direction of jet
            dir_i += 1
            dir = data[(dir_i % n)-1 if dir_i % n != 0 else n-1]

            # Jet push
            rock_moved = {pos+dirs[dir] for pos in rock}
            if (0 not in [int(pos.real) for pos in rock_moved]) and (8 not in [int(pos.real) for pos in rock_moved]) and not (rock_moved & stack):
                rock = rock_moved

            # Gravity drop
            rock_moved = {pos-1j for pos in rock}
            if rock_moved & stack:
                stack |= rock
                max_height = complex(0, max(pos.imag for pos in stack))
                break
            rock = rock_moved

    print(max_height)
else:
    n = len(data)
    rock_i = 0
    dir_i = 0
    max_height = 0j
    seen = []
    while True: # New rock
        rock_i += 1
        rock = {pos+max_height+4j for pos in rocks[(rock_i % 5)-1 if rock_i % 5 != 0 else 4]}
        while True: # New direction of jet
            dir_i += 1
            dir = data[(dir_i % n)-1 if dir_i % n != 0 else n-1]

            # Jet push
            rock_moved = {pos+dirs[dir] for pos in rock}
            if (0 not in [int(pos.real) for pos in rock_moved]) and (8 not in [int(pos.real) for pos in rock_moved]) and not (rock_moved & stack):
                rock = rock_moved

            # Gravity drop
            rock_moved = {pos-1j for pos in rock}
            if rock_moved & stack:
                stack |= rock
                max_height = complex(0, max(pos.imag for pos in stack))
                break
            rock = rock_moved

        top_stack = frozenset({pos-(max_height-50) for pos in stack if pos.imag > max_height.imag-50})
        new = (top_stack, (rock_i % 5)-1 if rock_i % 5 != 0 else 4, (dir_i % n)-1 if dir_i % n != 0 else n-1)

        if new not in seen:
            seen.append(new)
        else:
            repeat = len(seen)-seen.index(new) # Cycle repeating length. (Every 35 rocks)
            start = seen.index(new) + 1 # The i-th rock where the pattern first appears
            print((start, repeat, max_height))
            break
    # TEST INPUT: For top stack of depth 50 - Cycle starts at 47th rock (height 76), repeats every 35 rocks which adds (129-76)=53 height. (1000000000000-47)%35 = 3. 3 extra rocks add 2 height (max_height(47+3)-max_height(47))
    print(((1000000000000-47)//35)*53 + 76 + (78-76))

    # ACTUAL INPUT: For top stack of depth 50 - Cycle starts at 102th rock (height 154), repeats every 1745 rocks which adds (2892-154)=2738 height. (1000000000000-102)%1745 = 908. 908 extra rocks add 2 heights (max_height(102+908)-max_height(102))
    print(((1000000000000-102)//1745)*2738 + 154 + (1567-154))


"""
Import section (to put in)
"""

cash = []

def restartgame():
    """
    Function to start from the beginning
    """
    restart = input('Would you like to play again? Y/N')
    if restart.capitalize() == 'Y':
        print('Great!')
        main()
    else:
        print('You have choosen no. see you soon...')
        restartgame()

def introduction():

    """
    Function to get the users name and to explain the rules
    """
    name = input('What is your name: ')
    print('\n')
    print(f'Hello {name} and welcome to the Cash Building Quiz! \n')
    print('The rules are simply... you have 10 questions ')
    print('The questions get harder for each one you answer correctly ')
    print('You gain a massive 100 euro to your pot for each question you answer right')
    print('You have the option to leave the game with your cash that you earned ')
    print('Or do you dare to answer the next question answer wrong and you lose all your cash. \n')
    play = input('Do you wish to play the Cash Building Game? type Y or N :')
    if play.capitalize() == 'Y':
        return
    elif play.capitalize() == 'N':
        print(f'You have choose not to play. Come back when your ready {name}')
        main()
    else:
        print(f'Invalid choice {name} The game will now restart')
        main()

def start_game():

    """
    question one
    """
    print('Question Number One for 100euro....\n')
    print('Q1. What is the Capital of Ireland: \nA. Galway \nB. Dublin \nC. Kilkenny \nD. Cork')
    answer = input('What do you think the answer is :')
    if answer.capitalize() == 'B' or answer.capitalize() == 'Dublin':
        cash =+ 100
        print(f'Well Done You have won {cash} euro!!')
        decision = input(f'Would you like to answer another question or take the {cash} euro. \nA. Another Question \nB. Keep The Cash :')
        if decision.capitalize() == 'A' or answer.capitalize() == 'Another question':
                return cash
        else:
             print (f'You have decided to keep the {cash} euro. \nThank you for playing the game!')
             restartgame()
    else:
        print('Your wrong! The Answer was B. Dublin. Thanks for playing!')
        restartgame()

def question_two():
    """
    Question two function
    """

    print('Question Number two for 200euro....\n')
    print('Q2. Who Created the Xbox: \nA. Apple \nB. Sony \nC. Nintendo \nD. Microsoft')
    answer = input ('What do you think the answer is :')
    if answer.capitalize() == 'D' or answer.lower() == str.lower('microsoft'):
        cash =+ 100
        print(f'Well Done You have won {cash} euro!!')
        decision = input(f'Would you like to answer another question or take the {cash} euro. \nA. Another Question \nB. Keep The Cash :')
        if decision.capitalize() == 'A' or answer.lower() == str.lower('another question'):
                return cash
        else:
            print (f'You have decided to keep the {cash} euro. \nThank you for playing the game!')
            restartgame()
    else:
        print('Your wrong! The Answer was D. Microsoft. Thanks for playing!')
        restartgame()

def question_three():
    """
    question three function
    """

    print('Question Number three for 300euro....\n')
    print('Q3. Where is the Car manufacturers Audi From:\nA. Germany \nB. China\nC. U.S.A \nD. England')
    answer = input ('What do you think the answer is :')
    if answer.capitalize() == 'A' or answer.capitalize() == 'Germany':
        cash =+ 100
        print(f'Well Done You have won {cash} euro!!')
        decision = input(f'Would you like to answer another question or take the {cash} euro. \nA. Another Question \nB. Keep The Cash :')
        if decision.capitalize() == 'A' or answer.capitalize() == 'Another question':
                return cash
        else:
            print (f'You have decided to keep the {cash} euro. \nThank you for playing the game!')
            restartgame()
    else:
        print('Your wrong! The Answer was A. Germany. Thanks for playing!')
        restartgame()

def question_four():
    """
    question four function
    """
    print('Question Number four for 400euro....\n')
    print('Q4.Which of these is a Song from Harry Style:\nA. UpTown Girl\nB. Californication\nC. Adore You \nD. Londons Burning')
    answer = input('What do you think the answer is :')
    if answer.capitalize() == 'B' or answer.capitalize() == 'Californication':
        cash =+ 100
        print(f'Well Done You have won {cash} euro!!')
        decision = input(f'Would you like to answer another question or take the {cash} euro. \nA. Another Question \nB. Keep The Cash :')
        if decision.capitalize() == 'A' or answer.capitalize() == 'Another question':
                return cash
        else:
            print(f'You have decided to keep the {cash} euro. \nThank you for playing the game!')
            restartgame()
    else:
        print('Your wrong! The Answer was B Californication . \nThanks for playing!')
        restartgame()

def question_five():
    """
    question five function
    """
    print('Half way there with 500euro....\n')
    print('Q5. Which of these EU countries does not use the euro as its currency?\nA. Poland\nB. Denmark \nC. Sweden\nD. All of the above  ')
    answer = input ('What do you think the answer is :')
    if answer.capitalize() == 'D' or answer.capitalize() == 'All of the above':
        cash =+ 100
        print(f'Well Done You have won {cash} euro!!')
        decision = input(f'Would you like to answer another question or take the {cash} euro. \nA. Another Question \nB. Keep The Cash :')
        if decision.capitalize() == 'A' or answer.capitalize() == 'Another question':
                return cash
        else:
            print(f'You have decided to keep the {cash} euro. \nThank you for playing the game!')
            restartgame()
    else:
        print('Your wrong! The Answer was D. All of the above. Thanks for playing!')
        restartgame()

def question_six():
    """
    question six function
    """
    print('Question number six for 600euro....\n')
    print('Q6.What color dresses do Chinese women traditionally wear on their wedding day?\nA. Blue \nB. Gold\nC. White \nD. Red ')
    answer = input ('What do you think the answer is :')
    if answer.capitalize() == 'D' or answer.capitalize() == 'Red':
        cash =+ 100
        print(f'Well Done You have won {cash} euro!!')
        decision = input(f'Would you like to answer another question or take the {cash} euro. \nA. Another Question \nB. Keep The Cash :')
        if decision.capitalize() == 'A' or answer.capitalize() == 'Another question':
                return cash
        else:
            print(f'You have decided to keep the {cash} euro. \nThank you for playing the game!')
            restartgame()
    else:
        print('Your wrong! The Answer was D. Red. Thanks for playing!')
        restartgame()

def question_seven():
    """
    question seven function
    """
    print('Question number seven for 700euro....\n')
    print('Q7.How many molecules of oxygen does ozone have?\nA. 1\nB. 2\nC. 3 \nD. 4 ')
    answer = input ('What do you think the answer is :')
    if answer.capitalize() == 'C' or answer.capitalize() == 'Three' or answer == '3':
        cash =+ 100
        print(f'Well Done You have won {cash} euro!!')
        decision = input(f'Would you like to answer another question or take the {cash} euro. \nA. Another Question \nB. Keep The Cash :')
        if decision.capitalize() == 'A' or answer.capitalize() == 'Another question':
                return cash
        else:
            print(f'You have decided to keep the {cash} euro. \nThank you for playing the game!')
            restartgame()
    else:
        print('Your wrong! The Answer was C. Three. Thanks for playing!')
        restartgame()

def question_eight():
    """
    Question eight function
    """
    print('Question number eight for 800euro....\n')
    print('Q8. Where did the croissant originate?\nA. France\nB. Austria \nC. Turkey \nD. Tokyo')
    answer = input ('What do you think the answer is :')
    if answer.capitalize() == 'B' or answer.capitalize() == 'Austria':
        cash =+ 100
        print(f'Well Done You have won {cash} euro!!')
        decision = input(f'Would you like to answer another question or take the {cash} euro. \nA. Another Question \nB. Keep The Cash :')
        if decision.capitalize() == 'A' or answer.capitalize() == 'Another question':
                return cash
        else:
            print(f'You have decided to keep the {cash} euro. \nThank you for playing the game!')
            restartgame()
    else:
        print('Your wrong! The Answer was B. Austria Thanks for playing!')
        restartgame()

def question_nine():
    """
    Question nine function
    """
    print('Question number nine for 900euro....\n')
    print('Q9. Q9. Pupusas are from what country?\nA. Mexico\nB. El Salvador \nC. Brazil \nD. Poland ')
    answer = input ('What do you think the answer is :')
    if answer.capitalize() == 'B' or answer.capitalize() == 'El Salador':
        cash =+ 100
        print(f'Well Done You have won {cash} euro!!')
        decision = input(f'Would you like to answer the FINAL question or take the {cash} euro. \nA. Another Question \nB. Keep The Cash :')
        if decision.capitalize() == 'A' or answer.capitalize() == 'Another question':
                return cash
        else:
            print(f'You have decided to keep the {cash} euro. \nThank you for playing the game!')
            restartgame()
    else:
        print('Your wrong! The Answer was B. El Salvador Thanks for playing!')
        restartgame()

def question_ten():
    """
    Question ten function
    """
    print('Last question for a massive 1000euro....\n')
    print('Q10. Which of these US presidents appeared on the television series "Laugh-In?"\nA: Lyndon Johnson \nB: Richard Nixon \nC: Jimmy Carter \nD: Gerald Ford')
    answer = input ('What do you think the answer is :')
    if answer.capitalize() == 'B' or answer.capitalize() == 'Richard Nixon':
        cash =+ 100
        print(f'Congratulations you have won {cash} euro and have completed the game. I hope you had fun!!')
    else:
        print('Oh no you lost all the cash! The Answer was B. Richard Nixon. Thanks for playing!')
        restartgame()

def main():
    """
    Main function to run the game
    """
    cash = 0
    introduction()
    start_game()
    question_two()
    question_three()
    question_four()
    question_five()
    question_six()
    question_seven()
    question_eight()
    question_nine()
    question_ten()

main()


from venv import logger

import pygame

class self:
    pass

class GameEvent:
    pass

class World:
    pass

for event in self.events:
    if event.is_key_down(pygame.K_LEFT, pygame.K_a):
        self.move_left(True)
    elif event.is_key_down(pygame.K_RIGHT, pygame.K_d):
        self.move_right(True)
    elif event.is_key_down(pygame.K_UP, pygame.K_SPACE, pygame.K_w):
        self.jump()
    elif event.is_key_up(pygame.K_LEFT, pygame.K_a):
        self.move_left(False)
    elif event.is_key_up(pygame.K_RIGHT, pygame.K_d):
        self.move_right(False)
    elif event.is_key_down(pygame.K_f):
        self._handle_throw()

def jump(self):
    if self.is_landed:
        self.is_landed = False
        self.dy = -self.jump_vertical_speed

self._handle_get_hit()

def handle_get_hit(self)->None:
    for shadow in self.world.get_entities(EntityType.SHADOW):
        if self.collide(shadow):
            self._take_damage(1)

def take_damage(self, damage: int) -> None:
    if now() - self.last_hit_t > PlayerConfig.INVULNERABLE_DURATION_MS:
        self.last_hit_t = now()
        self.hp -= damage

def _pick_item_near_by(self):
    """
    If Player collides with a collectable entity, remove that entity from World,
    while adding that entity to the self.inventory list.
    """
    for entity in self.world.get_collectable_tiles():
        if self.collide(entity):
            self.world.remove_entity(entity.id)
            self.inventory.append(entity)
            logger.info(f"Player picked up 1 {entity.entity_type}")

def _update_inventory_entity(self):
    """
    This Player entity directly manages a PlayerInventory entity.
    """
    if not self.inventory_entity_id:
        self.inventory_entity_id = self.world.add_entity(EntityType.PLAYER_INVENTORY)
    self.world.get_entity(self.inventory_entity_id).set_inventory(self.inventory)

def _maybe_jump_with_trampoline(self):
    for trampoline in self.world.get_trampolines():
        if self.collide(trampoline) and self.rect.bottom > trampoline.rect.top:
            trampoline.set_action(ActionType.JUMP)
            self.jump_with_trampoline()
        else:
            trampoline.set_action(ActionType.IDLE)

def update(self, events: Sequence[GameEvent], world: World) -> None:
    super().update(events, world)
    self._update_npc_near_by()
    self._pick_item_near_by()
    self._handle_events()
    self._update_screen_offset()
    # highlight this call only
    self._maybe_jump_with_trampoline()
    # Manage the dependent entities.
    self._update_inventory_entity()
    ball = self.world.get_entity(ball_id)

def render(self, screen: pygame.Surface, *args, **kwargs):
    super().render(screen, *args, **kwargs)

    for i in range(0, PlayerConfig.MAX_HP):
        if i < self.hp:
            screen.blit(
                pygame.image.load(PlayerHpConfig.FULL_HEART_PATH),
                (PlayerHpConfig.X + i * PlayerHpConfig.X_STEP, PlayerHpConfig.Y),
            )
        else:
            screen.blit(
            pygame.image.load(PlayerHpConfig.EMPTY_HEART_PATH),
            (PlayerHpConfig.X + i * PlayerHpConfig.X_STEP, PlayerHpConfig.Y),
            )


"""
FILE: router_api_v2.py
DESCRIPTION: all routes for API v2
AUTHOR: Nuttaphat Arunoprayoch
DATE: 04-April-2020
"""
from functools import wraps
from datetime import datetime
from typing import Dict, Any
from fastapi import HTTPException, BackgroundTasks
from starlette.requests import Request

from . import v2
from models.covid_model_api_v2 import CovidAPIv2

# Reload model (APIv2)
def reload_model_api_v2(func):
    """ Reload a model APIv2 for each quest """
    @wraps(func)
    def wrapper(*args, **kwargs):
        global covid_api_v2
        covid_api_v2 = CovidAPIv2()
        return func(*args, **kwargs)
    return wrapper

# Logging
def write_log(requested_path: str, client_ip: str) -> None:
    file_name = datetime.now().strftime('%d-%b-%Y')
    with open('logs/{}.txt'.format(file_name), mode='a+') as log_file:
        date_time_message = datetime.now().strftime('%d-%b-%Y, %H:%M:%S | ')
        message = date_time_message + requested_path + ' | ' + client_ip + '\n'
        log_file.write(message)
    return None

@v2.get('/current')
@reload_model_api_v2
def get_current(request: Request, background_tasks: BackgroundTasks) -> Dict[str, Any]:
    try:
        background_tasks.add_task(write_log, requested_path=str(request.url), client_ip=str(request.client))
        data = covid_api_v2.get_current()

    except Exception as e:
        raise HTTPException(status_code=400, detail=e)

    return data

@v2.get('/total')
@reload_model_api_v2
def get_total(request: Request, background_tasks: BackgroundTasks) -> Dict[str, Any]:
    try:
        background_tasks.add_task(write_log, requested_path=str(request.url), client_ip=str(request.client))
        data = covid_api_v2.get_total()

    except Exception as e:
        raise HTTPException(status_code=400, detail=e)

    return data

@v2.get('/confirmed')
@reload_model_api_v2
def get_confirmed(request: Request, background_tasks: BackgroundTasks) -> Dict[str, int]:
    try:
        background_tasks.add_task(write_log, requested_path=str(request.url), client_ip=str(request.client))
        data = covid_api_v2.get_confirmed()

    except Exception as e:
        raise HTTPException(status_code=400, detail=e)

    return data

@v2.get('/deaths')
@reload_model_api_v2
def get_deaths(request: Request, background_tasks: BackgroundTasks) -> Dict[str, int]:
    try:
        background_tasks.add_task(write_log, requested_path=str(request.url), client_ip=str(request.client))
        data = covid_api_v2.get_deaths()

    except Exception as e:
        raise HTTPException(status_code=400, detail=e)

    return data

@v2.get('/recovered')
@reload_model_api_v2
def get_recovered(request: Request, background_tasks: BackgroundTasks) -> Dict[str, int]:
    try:
        background_tasks.add_task(write_log, requested_path=str(request.url), client_ip=str(request.client))
        data = covid_api_v2.get_recovered()

    except Exception as e:
        raise HTTPException(status_code=400, detail=e)

    return data

@v2.get('/active')
@reload_model_api_v2
def get_active(request: Request, background_tasks: BackgroundTasks) -> Dict[str, int]:
    try:
        background_tasks.add_task(write_log, requested_path=str(request.url), client_ip=str(request.client))
        data = covid_api_v2.get_active()

    except Exception as e:
        raise HTTPException(status_code=400, detail=e)

    return data

@v2.get('/country/{country_name}')
@reload_model_api_v2
def get_country(country_name: str, request: Request, background_tasks: BackgroundTasks) -> Dict[str, Any]:
    """ Search by name or ISO (alpha2) """
    try:
        background_tasks.add_task(write_log, requested_path=str(request.url), client_ip=str(request.client))
        raw_data = covid_api_v2.get_country(country_name.lower())

    except Exception as e:
        raise HTTPException(status_code=404, detail="Item not found")

    return raw_data

@v2.get('/timeseries/{case}')
@reload_model_api_v2
def get_time_series(case: str, request: Request, background_tasks: BackgroundTasks) -> Dict[str, Any]:
    """ Get the time series based on a given case: global, confirmed, deaths, *recovered
        * recovered will be deprecated by the source data soon
    """
    background_tasks.add_task(write_log, requested_path=str(request.url), client_ip=str(request.client))

    if case.lower() not in ['global', 'confirmed', 'deaths', 'recovered']:
            raise HTTPException(status_code=404, detail="Item not found")

    data = covid_api_v2.get_time_series(case.lower())

    return data

@v2.get('/timeseries/US/{case}')
@reload_model_api_v2
def get_US_time_series(case: str, request: Request, background_tasks: BackgroundTasks) -> Dict[str, Any]:
    """ Get the USA time series based on a given case: confirmed, deaths """
    background_tasks.add_task(write_log, requested_path=str(request.url), client_ip=str(request.client))

    if case.lower() not in ['confirmed', 'deaths']:
            raise HTTPException(status_code=404, detail="Item not found")

    data = covid_api_v2.get_US_time_series(case.lower())

    return data


import math

#power
# print(3**2)

#print(math.sqrt(81))

"""
def isPP(n):
    #your code here
    #num = int(n/2)
    #print(num)
    for i in range(2,11):
        for j in range(1,10):
            if i**j == n:
                return[i,j]

    return None

num = isPP(32)
print(num)

"""

#geeksforgeeks
# Python3 program to count number
# of numbers from 1 to n are of
# type x^y where x>0 and y>1

# Function that keeps all the odd
# power numbers upto n
def powerNumbers(n):

	# v is going to store all
	# unique power numbers
	v = set();
	v.add(1);

	# Traverse through all base
	# numbers and compute all
	# their powers smaller than
	# or equal to n.
	for i in range(2, n+1):
		if(i * i <= n):
			j = i * i;
			v.add(j);
			while (j * i <= n):
				v.add(j * i);
				j = j * i;

	return len(v);

print (powerNumbers(2373046875));
# This code is contributed by
# Manish Shaw (manishshaw1)


from os import linesep
import googletrans

translator = googletrans.Translator()

read_file_path = r'9.영어로된 문서를 한글로 자동 번역\english.txt'

with open(read_file_path, 'r') as f:
    readLines = f.readlines()

for lines in readLines:
    result1 = translator.translate(lines, dest='ko', src='auto')
    print(result1.text)

9.영어로된 문서를 한글로 자동 번역/main9-3.py


import argparse
from argparse import ArgumentParser
from featuretrack.trackers.algorithms import lucas_kanade, siftbf, kalman

def add_gft_sift_detectors_subparsers(parser: ArgumentParser):
  subparsers = parser.add_subparsers(help='Feature extraction algorithm')

  gft_parser = subparsers.add_parser(
    'gft', help='Extract feature points according to the Good Features To Track algorithm',
    description='',
    epilog=''
  )
  gft_parser.set_defaults(features='gft')
  gft_parser.add_argument('-p', '--points', default=100, type=int,
                          help='Maximum number of corners to extract [default: 100]')
  gft_parser.add_argument('-q', '--quality', default=0.2, type=float,
                          help='Minimum accepted quality ratio with respect to the highest quality corner [default: 0.2]')
  gft_parser.add_argument('-d', '--distance', default=10, type=int,
                          help='Minimum euclidian distance between corners [default: 10]')
  gft_parser.add_argument('-s', '--size', default=3, type=int,
                          help='Block size around pixels for computing features [default: 3]')

  sift_parser = subparsers.add_parser(
    'sift', help='Extract feature points according to the Scale-Invariant Feature Transform algorithm',
    description='',
    epilog=''
  )
  sift_parser.set_defaults(features='sift')
  sift_parser.add_argument('-p', '--points', default=100, type=int, help='Number of keypoints to extract [default: 100]')

def add_lucas_kanade_subparser(subparsers):
  lk_parser = subparsers.add_parser(
    'lk', help='Lucas-Kanade tracking algorithm',
    description='Lucas-Kanade tracking, working with feature points extracted by the specified algorithm',
    epilog='')
  lk_parser.set_defaults(func=lucas_kanade)
  lk_parser.add_argument('-i', '--interval', default=60, type=int,
                         help='Interval of frames in which feature points are tracked before being recomputed [default: 60]')
  add_gft_sift_detectors_subparsers(lk_parser)
  return lk_parser

def add_siftbf_subparser(subparsers):
  siftbf_parser = subparsers.add_parser(
    'siftbf', help='Brute force tracking based on L2-distance between SIFT point descriptors',
    description='Feature points are periodically computed by the Scale-Invariant Feature Transform algorithm and at each frame they are tracked by matching them with the most similar new points based on L2-distance between original and new SIFT descriptors',
    epilog=''
  )
  siftbf_parser.set_defaults(func=siftbf)
  siftbf_parser.set_defaults(features='sift')
  siftbf_parser.add_argument('-p', '--points', default=100, type=int, help='Number of keypoints to extract [default: 100]')
  siftbf_parser.add_argument('-i', '--interval', default=60, type=int,
                           help='Interval of frames in which feature points are tracked before being recomputed [default: 60]')
  siftbf_parser.add_argument('-t', '--thresh', default=90, type=int,
                           help='Matching quality threshold (distance) [default: 90]')
  siftbf_parser.add_argument('--hidematch', default=False, action='store_true',
                           help='If specified hides reference and current frames with the explicit matching')
  return siftbf_parser

def add_kalman_subparser(subparsers):
  kalman_parser = subparsers.add_parser(
    'kalman', help='Kalman Filter tracking algorithm',
    description='Kalman Filter tracking, working with feature points extracted by the specified algorithm',
    epilog='')
  kalman_parser.set_defaults(func=kalman)
  kalman_parser.add_argument('-i', '--interval', default=60, type=int,
                             help='Interval of frames in which feature points are tracked before being recomputed [default: 60]')
  kalman_parser.add_argument('-c', '--correct', default=1, type=int,
                             help='Number of frames after which ground truth information is used to update the prediction of the Kalman Filter [default: 1]')
  kalman_parser.add_argument('-a', '--avgacc', default=False, action='store_true',
                             help='If specified, use the average accelerations of the previous feature points when recomputing the feature points, otherwise set the accelerations of the new feature points to zero')
  add_gft_sift_detectors_subparsers(kalman_parser)
  return kalman_parser

def prepare_parser():
  parser = argparse.ArgumentParser(description='Track features using different tracking algorithms combined with different feature detectors',
                                   prog='python -m featuretrack')
  parser.add_argument('-v', '--video', type=str, required=True,
                      help='Path to the video on which to perform tracking')
  parser.add_argument('-d', '--delay', default=1, type=int,
                      help='Delay (ms) in between frames (influences video preview framerate) [default: 1 (minimum possible delay)]')
  parser.add_argument('-s','--scale', nargs=2, default=[1,1], type=float, metavar=('H_SCALE', 'W_SCALE'),
                      help='Scaling factors to be applyed respectively to the height and the width of the video [default: 1 1]')
  parser.add_argument('-o','--output', type=str,
                      help='Output file name: the video will be saved as \'./results/OUTPUT.avi\'')
  parser.add_argument('-f', '--framerate', default=30, type=int, help='Output video framerate [default: 30]')
  parser.add_argument('-r', '--radious', default=3, type=int,
                         help='Radious of circles used to show the location of feature points [default: 3]')
  parser.add_argument('-t', '--thickness', default=2, type=int,
                         help='Thickness of the circle borders [default: 2]')
  subparsers = parser.add_subparsers(help='Tracking algorithm')

  add_siftbf_subparser(subparsers)

  add_lucas_kanade_subparser(subparsers)

  add_kalman_subparser(subparsers)

  return parser


import pandas as pd

toSplitPath = "\\\\AURORA\\Users\\Public\\Documents\\Accounts 2020\\MasterSample.xlsx"
toSplitData = pd.read_excel(toSplitPath, sheet_name='ToSplitSample', index_col=0)

masterBDPath = "\\\\AURORA\\Users\\Public\\Documents\\Accounts 2020\\MasterBD.xlsx"
masterBDData = pd.read_excel(masterBDPath)

# toSplitData.columns.name = 'UI'
toSplitData['Amount'] = -1 * toSplitData['Amount']

x = toSplitData.copy()
y = masterBDData.copy()

modified1 = x.reset_index()
modified2 = y.reset_index()

inner_join = pd.merge(modified1,
                      modified2,
                      on = 'Unique',
                      how = 'inner')

for i in range(len(inner_join)):
    masterBDData['UID'].iloc[inner_join['index_y'].iloc[i]] = inner_join['index_x'].iloc[i]
    masterBDData['UID'].iloc[inner_join['index_y'].iloc[i] - 1] = inner_join['index_x'].iloc[i]
    toSplitData['Empty'].iloc[inner_join['index_y'].iloc[i] - 1] = "x"

masterBDData.to_excel('CompareData.xlsx', index=False)

print(toSplitData.to_string())


"""
====================================
Comparing Linear Bayesian Regressors
====================================

This example compares two different bayesian regressors:

 - a :ref:`automatic_relevance_determination`
 - a :ref:`bayesian_ridge_regression`

In the first part, we use an :ref:`ordinary_least_squares` (OLS) model as a
baseline for comparing the models' coefficients with respect to the true
coefficients. Thereafter, we show that the estimation of such models is done by
iteratively maximizing the marginal log-likelihood of the observations.

In the last section we plot predictions and uncertainties for the ARD and the
Bayesian Ridge regressions using a polynomial feature expansion to fit a
non-linear relationship between `X` and `y`.

"""

# Author: Arturo Amor <david-arturo.amor-quiroz@inria.fr>

# %%
# Models robustness to recover the ground truth weights
# =====================================================
#
# Generate synthetic dataset
# --------------------------
#
# We generate a dataset where `X` and `y` are linearly linked: 10 of the
# features of `X` will be used to generate `y`. The other features are not
# useful at predicting `y`. In addition, we generate a dataset where `n_samples
# == n_features`. Such a setting is challenging for an OLS model and leads
# potentially to arbitrary large weights. Having a prior on the weights and a
# penalty alleviates the problem. Finally, gaussian noise is added.

from sklearn.datasets import make_regression

X, y, true_weights = make_regression(
    n_samples=100,
    n_features=100,
    n_informative=10,
    noise=8,
    coef=True,
    random_state=42,
)

# %%
# Fit the regressors
# ------------------
#
# We now fit both Bayesian models and the OLS to later compare the models'
# coefficients.

import pandas as pd

from sklearn.linear_model import ARDRegression, BayesianRidge, LinearRegression

olr = LinearRegression().fit(X, y)
brr = BayesianRidge(compute_score=True, max_iter=30).fit(X, y)
ard = ARDRegression(compute_score=True, max_iter=30).fit(X, y)
df = pd.DataFrame(
    {
        "Weights of true generative process": true_weights,
        "ARDRegression": ard.coef_,
        "BayesianRidge": brr.coef_,
        "LinearRegression": olr.coef_,
    }
)

# %%
# Plot the true and estimated coefficients
# ----------------------------------------
#
# Now we compare the coefficients of each model with the weights of
# the true generative model.
import matplotlib.pyplot as plt
import seaborn as sns
from matplotlib.colors import SymLogNorm

plt.figure(figsize=(10, 6))
ax = sns.heatmap(
    df.T,
    norm=SymLogNorm(linthresh=10e-4, vmin=-80, vmax=80),
    cbar_kws={"label": "coefficients' values"},
    cmap="seismic_r",
)
plt.ylabel("linear model")
plt.xlabel("coefficients")
plt.tight_layout(rect=(0, 0, 1, 0.95))
_ = plt.title("Models' coefficients")

# %%
# Due to the added noise, none of the models recover the true weights. Indeed,
# all models always have more than 10 non-zero coefficients. Compared to the OLS
# estimator, the coefficients using a Bayesian Ridge regression are slightly
# shifted toward zero, which stabilises them. The ARD regression provides a
# sparser solution: some of the non-informative coefficients are set exactly to
# zero, while shifting others closer to zero. Some non-informative coefficients
# are still present and retain large values.

# %%
# Plot the marginal log-likelihood
# --------------------------------
import numpy as np

ard_scores = -np.array(ard.scores_)
brr_scores = -np.array(brr.scores_)
plt.plot(ard_scores, color="navy", label="ARD")
plt.plot(brr_scores, color="red", label="BayesianRidge")
plt.ylabel("Log-likelihood")
plt.xlabel("Iterations")
plt.xlim(1, 30)
plt.legend()
_ = plt.title("Models log-likelihood")

# %%
# Indeed, both models minimize the log-likelihood up to an arbitrary cutoff
# defined by the `max_iter` parameter.
#
# Bayesian regressions with polynomial feature expansion
# ======================================================
# Generate synthetic dataset
# --------------------------
# We create a target that is a non-linear function of the input feature.
# Noise following a standard uniform distribution is added.

from sklearn.pipeline import make_pipeline
from sklearn.preprocessing import PolynomialFeatures, StandardScaler

rng = np.random.RandomState(0)
n_samples = 110

# sort the data to make plotting easier later
X = np.sort(-10 * rng.rand(n_samples) + 10)
noise = rng.normal(0, 1, n_samples) * 1.35
y = np.sqrt(X) * np.sin(X) + noise
full_data = pd.DataFrame({"input_feature": X, "target": y})
X = X.reshape((-1, 1))

# extrapolation
X_plot = np.linspace(10, 10.4, 10)
y_plot = np.sqrt(X_plot) * np.sin(X_plot)
X_plot = np.concatenate((X, X_plot.reshape((-1, 1))))
y_plot = np.concatenate((y - noise, y_plot))

# %%
# Fit the regressors
# ------------------
#
# Here we try a degree 10 polynomial to potentially overfit, though the bayesian
# linear models regularize the size of the polynomial coefficients. As
# `fit_intercept=True` by default for
# :class:`~sklearn.linear_model.ARDRegression` and
# :class:`~sklearn.linear_model.BayesianRidge`, then
# :class:`~sklearn.preprocessing.PolynomialFeatures` should not introduce an
# additional bias feature. By setting `return_std=True`, the bayesian regressors
# return the standard deviation of the posterior distribution for the model
# parameters.

ard_poly = make_pipeline(
    PolynomialFeatures(degree=10, include_bias=False),
    StandardScaler(),
    ARDRegression(),
).fit(X, y)
brr_poly = make_pipeline(
    PolynomialFeatures(degree=10, include_bias=False),
    StandardScaler(),
    BayesianRidge(),
).fit(X, y)

y_ard, y_ard_std = ard_poly.predict(X_plot, return_std=True)
y_brr, y_brr_std = brr_poly.predict(X_plot, return_std=True)

# %%
# Plotting polynomial regressions with std errors of the scores
# -------------------------------------------------------------

ax = sns.scatterplot(
    data=full_data, x="input_feature", y="target", color="black", alpha=0.75
)
ax.plot(X_plot, y_plot, color="black", label="Ground Truth")
ax.plot(X_plot, y_brr, color="red", label="BayesianRidge with polynomial features")
ax.plot(X_plot, y_ard, color="navy", label="ARD with polynomial features")
ax.fill_between(
    X_plot.ravel(),
    y_ard - y_ard_std,
    y_ard + y_ard_std,
    color="navy",
    alpha=0.3,
)
ax.fill_between(
    X_plot.ravel(),
    y_brr - y_brr_std,
    y_brr + y_brr_std,
    color="red",
    alpha=0.3,
)
ax.legend()
_ = ax.set_title("Polynomial fit of a non-linear feature")

# %%
# The error bars represent one standard deviation of the predicted gaussian
# distribution of the query points. Notice that the ARD regression captures the
# ground truth the best when using the default parameters in both models, but
# further reducing the `lambda_init` hyperparameter of the Bayesian Ridge can
# reduce its bias (see example
# :ref:`sphx_glr_auto_examples_linear_model_plot_bayesian_ridge_curvefit.py`).
# Finally, due to the intrinsic limitations of a polynomial regression, both
# models fail when extrapolating.


import json
import logging
import os
import sys
from alive_progress import alive_bar

import boto3
logging.basicConfig(level=logging.INFO, handlers=[logging.StreamHandler(sys.stdout)])
log = logging.getLogger("master")

class Master:

    def __init__(self, supplier=None, reducer=None, terminate=None):
        self.supplier = supplier
        self.reducer = reducer
        self.terminate = terminate

    def start(self):
        log.info("Starting...")
        aws_region = boto3.session.Session().region_name
        sqs = boto3.client('sqs')
        aws_account_id = boto3.client('sts').get_caller_identity().get('Account')

        queue_jobs = "https://{}.queue.amazonaws.com/{}/{}".format(aws_region, aws_account_id, os.environ['Q_TASK'])
        queue_results = "https://{}.queue.amazonaws.com/{}/{}".format(aws_region, aws_account_id, os.environ['Q_RESULTS'])

        log.info("Task queue: {}".format(queue_jobs))
        log.info("Results queue: {}".format(queue_results))

        tasks_submitted = {}

        # Push the task in the queue
        log.info("Pushing tasks to SQS")
        with alive_bar() as bar:
            for task in self.supplier():
                body = json.dumps(task)
                response = sqs.send_message(
                    QueueUrl=queue_jobs,
                    DelaySeconds=1,
                    MessageBody=body
                )
                tasks_submitted[task['id']] = response['MessageId']
                # log.info("Queued {} ".format(body))
                bar()

        # Collect the results.
        accumulator = list()
        keep_polling = True
        empty_counter = 0

        print(" ")
        log.info("Waiting for the results!")

        with alive_bar(len(tasks_submitted)) as bar:
            while keep_polling:
                resp = sqs.receive_message(
                    QueueUrl=queue_results,
                    AttributeNames=['All'],
                    MaxNumberOfMessages=10,
                    VisibilityTimeout=120,
                    WaitTimeSeconds=20
                )

                message = None
                total_task = len(tasks_submitted)
                try:
                    for message in resp['Messages']:
                        body = message['Body']
                        result = json.loads(body)
                        sqs.delete_message(QueueUrl=queue_results, ReceiptHandle=message['ReceiptHandle'])
                        del tasks_submitted[result['id']]
                        self.reducer(result, accumulator, bar)
                        bar()
                        keep_polling = False if len(tasks_submitted) == 0 else True
                except KeyError:
                    empty_counter += 1
                    keep_polling = False if empty_counter > 10 or len(tasks_submitted) == 0 else True
                    # continue

        self.terminate(accumulator)


'''
Выполнить функцию, которая принимает несколько параметров, описывающих данные пользователя:
имя, фамилия, год рождения, город проживания, email, телефон.
Функция должна принимать параметры как именованные аргументы.
Осуществить вывод данных о пользователе одной строкой.
'''

def user_info(name = None,
            last_name = None,
            year_of_birth = None,
            city = None,
            email = None,
            phone_num = None):
    '''
    :param name: имя
    :param last_name: фамилия
    :param year_of_birth: год рождения
    :param city: город проживания
    :param email: адрес электронной почты
    :param phone_num: номер телефона
    :return: вывод на экран информации о пользователе
    '''
    print(f'{name} {last_name} родился в {year_of_birth} году, проживает в городе {city}. '
          f'Телефон для связи: {phone_num}. '
          f'E-mail: {email}')

user_info('Анатолий', 'Воронов', 1993, 'Москва', 'a.voron@ya.ru', 89235632)


from sourpea.primitives import *
from sourpea.util import *
import pandas as pd
import os
_dir=os.path.dirname(__file__)
### REGULAR FACTORS
kX0oWT8=Factor("{%BI_g6XF",['jyii','HZ3Qv '])
HyeFQL=Factor('cEO)VAKx',["p&PLjSRFjie%#1",Level('_{EOfzrFhKw@9R',4)])

### EXPERIMENT
design=[kX0oWT8,HyeFQL]
crossing=[kX0oWT8,HyeFQL]
### APPENDIX
block=Block(design,crossing,[])
sequence_code_1=trials_from_csv(os.path.join(_dir,"out_code_1/2_2_1_0.csv"))
nr_factors=2
nr_levels=2
test_code_1=block.test(sequence_code_1)
try:
	sequence_code_2=trials_from_csv(os.path.join(_dir,"out_code_2/2_2_1_0.csv"))
	test_code_2=block.test(sequence_code_2)
except:
	test_code_2={"pValue":0}
df=pd.read_csv(os.path.join(_dir,"result_sour_c1.csv"))
df.loc[len(df.index)] = [test_code_1["pValue"], test_code_2["pValue"], nr_factors, nr_levels]
df.to_csv(os.path.join(_dir,"result_sour_c1.csv"), index=False)


from .user_settings import get_list_from_csv
from talon import Module, Context, actions, app

mod = Module()
mod.list("file_extension", desc="A file extension, such as .py")

_file_extensions_defaults = {
    "point pie": ".py",
    "point talon": ".talon",
    "point mark down": ".md",
    "point shell": ".sh",
    "point vim": ".vim",
    "point see": ".c",
    "point see sharp": ".cs",
    "point com": ".com",
    "point net": ".net",
    "point org": ".org",
    "point us": ".us",
    "point U S": ".us",
    "point exe": ".exe",
    "point bin": ".bin",
    "point bend": ".bin",
    "point jason": ".json",
    "point jay son": ".json",
    "point J S": ".js",
    "point java script": ".js",
    "point TS": ".ts",
    "point type script": ".ts",
    "point csv": ".csv",
    "totssv": ".csv",
    "tot csv": ".csv",
    "point cassie": ".csv",
    "point text": ".txt",
}

file_extensions = get_list_from_csv(
    "file_extensions.csv",
    headers=("File extension", "Name"),
    default=_file_extensions_defaults,
)

ctx = Context()
ctx.lists["self.file_extension"] = file_extensions


import ply.yacc as yacc
import ply.lex as lex
import sys

keywords = (
    'DIM', 'LET', 'PROGRAM', 'END'
)

tokens = keywords + (
    'EQUALS', 'PLUS', 'MINUS', 'MULT', 'POWER', 'DIV', 'LPAREN', 'RPAREN',
    'LT', 'LE', 'GT', 'GE', 'NE', 'ID', 'FLOAT'
)

t_ignore = r' '

t_EQUALS = r'='
t_PLUS = r'\+'
t_MINUS = r'-'
t_MULT = r'\*'
t_POWER = r'\^'
t_DIV = r'/'
t_LPAREN = r'\('
t_RPAREN = r'\)'
t_LT = r'<'
t_LE = r'<='
t_GT = r'>'
t_GE = r'>='
t_NE = r'<>'

def t_ID(t):
    r'[a-zA-Z_][a-zA-Z0-9_]*'
    if t.value.upper() in keywords:
        t.value = t.value.upper()
        t.type = t.value
    return t

def t_FLOAT(t):
    r'\d+'
    t.value = float(t.value)
    return t

def t_error(t):
    print("ILLEGAL CHARACTER")
    t.lexer.skip(1)

lexer = lex.lex()

precedence = (
    ('left', 'PLUS', 'MINUS'),
    ('left', 'MULT', 'DIV'),
    #('right', 'UMINUS'),
)

def p_S(p):
    '''
    S : PROGRAM program END
    '''

def p_program(p):
    '''
    program : definition
    | command
    | operation
    '''

def p_dim(p):
    '''
    definition : DIM ID
    '''
    print("\tINPUT SUCCESFUL")

def p_let(p):
    '''
    command : LET ID EQUALS FLOAT
    '''
    print("\tINPUT SUCCESFUL")

def p_binaryOp(p):
    '''
    operation : ID PLUS ID
    | ID MINUS ID
    | ID MULT ID
    | ID DIV ID
    | ID POWER ID
    '''

def p_error(p):
    print("\tSYNTAX ERROR")

parser = yacc.yacc()

while True:
    try:
        s = input('')
    except EOFError:
        break
    parser.parse(s)


"""
finite difference 2D poisson equation with iterative method.

u[i,j] = 0.25*( u[i+1,j] + u[i-1,j] + u[i,j+1] + u[i,j-1] ) + 0.25*f*dx*dx
from: Computational Physics, P468 Eq(19.31)

date : 2018-05-21
author: kouui
"""
################################################################################

import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import Axes3D
import numpy as np
import numba as nb

################################################################################
@nb.jit(nb.void(nb.float64[:],nb.float64[:],nb.float64,nb.float64))
def solve2DPoisson_iter(u,f, dx2, dy2):
    """
    this function updates 2D poisson equation using Gauss-Seidel method.
    boudary condition: the 2 rows and 2 columns at boudary are all fixed.

    input:
        u   : 2darray, unknown in Poisson equation
        r   : 2darray, source term in Poisson equation
        dx2 : dx**2
        dy2 : dy**2

    output: void

    """
    for i in range(1,u.shape[0]-1):
        for j in range(1,u.shape[1]-1):
            u[i,j] = ( dy2*(u[i,j-1]+u[i,j+1]) + dx2*(u[i-1,j]+u[i+1,j]) + dx2*dy2*f[i,j] ) *0.5 / (dx2+dy2)

################################################################################

if __name__=="__main__":

    N = 101
    u = np.zeros((N,N), np.double)
    f = np.ones((N,N), np.double)
    x = np.linspace(0,1,N)
    y = np.linspace(0,1,N)
    dx2, dy2 = (x[1]-x[0])*(x[1]-x[0]), (y[1]-y[0])*(y[1]-y[0])
    errorMax = 1.

    #-- boundary
    #u[:,0] = 1.

    #-- solve
    iter = 1
    print(" iter \t errorMax")
    print("-"*20)
    while errorMax > 1.99E-6:
        if iter%100==0: print("{0:5d} \t {1:.2E} ".format(iter, errorMax))
        u_old = u.copy()
        solve2DPoisson_iter(u,f, dx2, dy2)
        errorMax = (abs(u[1:-1,1:-1] - u_old[1:-1,1:-1])).max()
        iter += 1

    #-- visualization
    X,Y = np.meshgrid(x,y)
    if True:
        fig = plt.figure(figsize=(4,4),dpi=150)
        ax = Axes3D(fig)
        #ax.plot_wireframe(X,Y,u, color="r")
        ax.plot_surface(X,Y,u, cmap="jet")
        plt.show()


import torch
import torch.nn as nn
import LoadData
from torch.utils.tensorboard import SummaryWriter
from torch.utils.data import TensorDataset, DataLoader
import argparse
from pathlib import Path
import time
import pickle
from torch.optim.optimizer import Optimizer
import matplotlib
from matplotlib import pyplot as plt
import numpy as np
import os
import yaml
from argparse import Namespace
import models
os.environ["KMP_DUPLICATE_LIB_OK"]="TRUE"

if torch.cuda.is_available():
    DEVICE = torch.device("cuda")
else:
    DEVICE = torch.device("cpu")

#Code based on the code developed for the Applied Deep Learning unit coursework

#Trainer class
class Trainer:
    """
    Initialises the model
    Args: train and test data iterables, loss criterion, optimiser, summary writer, and torch device (CUDA or CPU)
    """
    def __init__(
        self,
        model: nn.Module,
        train_loader: DataLoader,
        val_loader: DataLoader,
        truth_train: DataLoader,
        truth_test: DataLoader,
        criterion: nn.Module,
        optimizer: Optimizer,
        summary_writer: SummaryWriter,
        device: torch.device,
    ):
        self.model = model.to(device)
        self.train_loader = train_loader
        self.val_loader = val_loader
        self.truth_train = truth_train
        self.truth_test = truth_test
        self.criterion = criterion
        self.optimizer = optimizer
        self.summary_writer = summary_writer
        self.step = 0
        self.device = device
        self.minLoss = -1
        self.minLossEpoch = 0
        self.stop = False
    """
    Trains the network
    Args: learning rate, number of epochs, validation frequency, print frequency, log frequency
    """
    def train(
        self,
        lr:float,
        epochs: int,
        val_frequency: int,
        print_frequency: int = 10,
        log_frequency: int = 10,
    ):
        #trains the model for the number of epochs
        for epoch in range(epochs):
            self.model.train()
            data_load_start_time = time.time()
            #iterates through the data in batches
            # for batch, labels in self.train_loader:
            for i, (batch, labels) in enumerate(zip(self.train_loader, self.truth_train)):
                print("Epoch " + str(epoch) + " batch "+ str(i))
                #turns the data into tensors of the appropriate type
                batch = batch[0].to(self.device)
                labels = labels[0].to(self.device)
                data_load_end_time = time.time()

                #Compute the forward pass of the model
                logits = torch.squeeze(self.model.forward(batch, noskip=args.noskip, transconv=args.transconv))
                # print(logits.shape)
                # print(labels[0].shape)
                #Compute the loss using the MSE Loss
                loss = self.criterion(logits, labels)

                #Compute the backward pass
                loss.backward()

                #Step the optimizer and then zero out the gradient buffers.
                self.optimizer.step()
                self.optimizer.zero_grad()

                #Logging
                data_load_time = data_load_end_time - data_load_start_time
                step_time = time.time() - data_load_end_time
                if ((self.step + 1) % log_frequency) == 0:
                    self.log_metrics(epoch, loss, data_load_time, step_time)
                if ((self.step + 1) % print_frequency) == 0:
                    self.print_metrics(epoch, loss, data_load_time, step_time)

                self.step += 1
                data_load_start_time = time.time()

            #Adds information to the summary writter/logger
            self.summary_writer.add_scalar("epoch", epoch, self.step)

            #Calculates the validation loss if it is the right epoch to do so
            if ((epoch + 1) % val_frequency) == 0:
                self.validate(epoch)
                # self.validate() puts the model in validation mode, so we then switch back to train mode
                PATH = "state_dict_model.pt"
                torch.save(self.model, PATH)
                self.model.train()
            if self.stop:
                break

    #Prints the current step and epoch, the batch loss, time taken to load the data, and time taken to complete the step
    def print_metrics(self, epoch, loss, data_load_time, step_time):
        epoch_step = self.step % len(self.train_loader)
        print(
                f"epoch: [{epoch}], "
                f"step: [{epoch_step}/{len(self.train_loader)}], "
                f"batch loss: {loss:.5f}, "
                f"data load time: "
                f"{data_load_time:.5f}, "
                f"step time: {step_time:.5f}"
        )
    #Adds the loss, time taken loading data, and time taken completing steps to the logs
    def log_metrics(self, epoch, loss, data_load_time, step_time):
        self.summary_writer.add_scalar("epoch", epoch, self.step)
        self.summary_writer.add_scalars(
                "loss",
                {"train": float(loss.item())},
                self.step
        )
        self.summary_writer.add_scalar(
                "time/data", data_load_time, self.step
        )
        self.summary_writer.add_scalar(
                "time/data", step_time, self.step
        )

    #Run the validation data through the network
    def validate(self, epoch):
        results = {"preds": [], "labels": [], "logits":[]}
        total_loss = 0
        self.model.eval()

        # No need to track gradients for validation, we're not optimizing.
        with torch.no_grad():
            for i, (batch, labels) in enumerate(zip(self.val_loader, self.truth_test)):
                batch = batch[0].to(self.device)
                labels = labels[0].to(self.device)
                logits = torch.squeeze(self.model(batch,noskip=args.noskip, transconv=args.transconv))
                results["logits"].extend(logits)
                loss = self.criterion(logits, labels)
                total_loss += loss.item()*len(batch)
                preds = logits.cpu().numpy()
                results["preds"].extend(list(preds))
                # fig, ax = plt.subplots()
                # print("should show plot now")
                # print(preds)
                #print(type(preds[0]))
                #print(type(labels[0]))
                # for j in range(batch.shape[0]):
                #     # print(j)
                #     # print(preds[j])
                #     fig, ax = plt.subplots(1,2)
                #     ax[0].contourf(preds[j],levels=51)
                #     ax[1].contourf(labels[j].cpu(),levels=51)
                #     plt.savefig("thing"+str(j)+".png")
                #     plt.clf()
        print(total_loss)
        #Store the predictions
        np.save('predictions.npy',results['preds'])

        #Calculate and print the average loss in the validation set
        average_loss = total_loss / len(self.val_loader.dataset)
        #Keeps track of the minimum loss and sets a flag to stop the training process if the loss has not decreased in a while
        if self.minLoss <0:
            self.minLoss=average_loss
            self.minLossEpoch=epoch
        elif average_loss < self.minLoss:
            self.minLoss=average_loss
            self.minLossEpoch=epoch
        elif epoch - self.minLossEpoch > 100:
            self.stop=True
        self.summary_writer.add_scalars(
                "loss",
                {"test": average_loss},
                self.step
        )
        print(f"validation loss: {average_loss:.5f}")

#Creates a unique sub directory to log this run in
def get_summary_writer_log_dir(args: argparse.Namespace) -> str:
    tb_log_dir_prefix = f'CNN_bs={args.batch_size}_lr={args.learning_rate}_momentum={args.momentum}_samples={args.samples}_run_'
    i = 0
    while i < 1000:
        tb_log_dir = Path(args.log_dir) / (tb_log_dir_prefix + str(i))
        if not tb_log_dir.exists():
            return str(tb_log_dir)
        i += 1
    return str(tb_log_dir)

def main(args):
    assert args.samples%10==0
    print("in main")
    #load the test and training data
    dataset, ground_truth, v = LoadData.load(args.samples, balancewind=args.balancewind, fixwind=args.fixwind, variables=args.vars, timestep=args.timestep)
    np.save('groundtruth.npy', ground_truth[int(args.samples*0.8):][0])
    global variance
    variance=v
    print("got dataset")
    print(len(dataset))
    train_dataset=TensorDataset(dataset[:int(args.samples*0.8)][0])
    test_dataset = TensorDataset(dataset[int(args.samples*0.8):][0])
    truth_train = TensorDataset(ground_truth[:int(args.samples*0.8)][0])
    truth_test = TensorDataset(ground_truth[int(args.samples*0.8):][0])
    #initialise the iterables for the training and validation sets
    train_loader = torch.utils.data.DataLoader(
        train_dataset,
        shuffle=False,
        batch_size=args.batch_size,
        pin_memory=True,
    )
    test_loader = torch.utils.data.DataLoader(
        test_dataset,
        shuffle=False,
        batch_size=args.batch_size,
        pin_memory=True,
    )
    truth_train_loader = torch.utils.data.DataLoader(
        truth_train,
        shuffle=False,
        batch_size=args.batch_size,
        pin_memory=True,
    )
    truth_test_loader = torch.utils.data.DataLoader(
        truth_test,
        shuffle=False,
        batch_size=args.batch_size,
        pin_memory=True,
    )
    # Initialises the network
    model_name=args.model
    model = getattr(models,model_name)(channels=len(args.vars),norm=args.norm, noskip=args.noskip, transconv=args.transconv)

    # Defines MSE loss criterion
    criterion = torch.nn.MSELoss()

    # Defines the Stochastic Gradient Descent optimiser with the given learning rate and momentum
    learn = float(args.learning_rate)
    print(model.parameters())
    if not args.adam:
        optimizer = torch.optim.SGD(model.parameters(), lr=args.learning_rate, momentum=args.momentum)
    else:
        optimizer = torch.optim.Adam(model.parameters(), lr=args.learning_rate, betas=(args.beta1, args.beta2))
    # Initiates log writting
    log_dir = get_summary_writer_log_dir(args)
    print(f"Writing logs to {log_dir}")
    summary_writer = SummaryWriter(
            str(log_dir),
            flush_secs=5
    )
    # Initialises the trainer class
    trainer = Trainer(
        model, train_loader, test_loader, truth_train_loader, truth_test_loader, criterion, optimizer, summary_writer, DEVICE
    )
    # Trains the model
    trainer.train(
        args.learning_rate,
        args.epochs,
        args.val_frequency,
        print_frequency=args.print_frequency,
        log_frequency=args.log_frequency,
    )
    # Closes the log writter
    summary_writer.close()

if __name__ == "__main__":
    print("hi")
    with open("args.yaml") as file:
        args=Namespace(**yaml.load(file,Loader=yaml.FullLoader))
        print(args)
    main(args)


from keras.models import Model
from keras.layers import Input, Conv2D, Dense, Dropout, GlobalAveragePooling2D, MaxPooling2D

def build_siamese_model(inputShape, embeddingDim=48):
    # embeddingDim: Output dimensionality of the final fully-connected layer in the network.
    inputs = Input(inputShape)

    # define first set of CONV => RELU => POOL => DROPOUT layer
    x = Conv2D(64, (2, 2), padding="same", activation="relu")(inputs)
    x = MaxPooling2D(pool_size=2)(x)
    x = Dropout(0.3)(x)

    # Sencond layer
    x = Conv2D(64, (2, 2), padding="same", activation="relu")(x)
    x = MaxPooling2D(pool_size=2)(x)
    x = Dropout(0.3)(x)

    # prepare final output
    pooledOutput = GlobalAveragePooling2D()(x)
    outputs = Dense(embeddingDim)(pooledOutput)

    # Build Model
    model = Model(inputs, outputs)

    return model


import os
import shutil

_custom_template_dir = False
_template_dir = ""

def copy_from_template_dir(filename, working_dir=os.getcwd()):
    """
    Copy a file from the template directory to the given working directory.

    Args:
    filename -- The filename of the template to be copied.
    working_dir -- The directory where the file should be copied to.
    """
    src = os.path.join(find_template_dir(), filename)
    dest = os.path.join(working_dir, filename)

    shutil.copyfile(src, dest)

def set_template_dir(directory=None):
    """
    Override the default template directory that comes with bikey.

    Arguments:
    dir -- the custom template directory. If None the default template
        directory will be used.
    """
    if directory is None:
        # fall back to bikey's default template dir
        _custom_template_dir = False
    else:
        _custom_template_dir = True
        _template_dir = directory

def find_template_dir():
    """
    Find the template directory where bikey stores Spacar and Simulink templates.

    Returns:
    The path of the template directory.
    """
    if _custom_template_dir:
        # return the file path specified by user
        return _template_dir
    else:
        # find the directory where utils.py is located
        package_dir = os.path.dirname(os.path.realpath(__file__))
        return os.path.join(package_dir, "spacar_templates")


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

"""
from copy import deepcopy

import numpy as np
from numpy import (pi, zeros, exp, ndarray, sqrt, sign, dot, array, einsum, eye, ones, maximum, abs, transpose, all,
                   delete)
from numpy.linalg import solve, inv

from pyfem.fem.Timer import Timer
from pyfem.fem.constants import DTYPE
from pyfem.io.Material import Material
from pyfem.io.Section import Section
from pyfem.materials.BaseMaterial import BaseMaterial
from pyfem.materials.crystal_slip_system import generate_mn
from pyfem.utils.colors import error_style
from pyfem.utils.mechanics import get_transformation, get_voigt_transformation

class PlasticCrystalGNDs(BaseMaterial):
    r"""
    晶体塑性材料。

    支持的截面属性：('Volume', 'PlaneStress', 'PlaneStrain')

    :ivar tolerance: 判断屈服的误差容限
    :vartype tolerance: float

    :ivar total_number_of_slips: 总的滑移系数量
    :vartype total_number_of_slips: int

    :ivar C11: 弹性矩阵系数
    :vartype C11: float

    :ivar C12: 弹性矩阵系数
    :vartype C12: float

    :ivar C44: 弹性矩阵系数
    :vartype C44: float

    :ivar C: 旋转矩阵
    :vartype C: ndarray

    :ivar theta: 切线系数法参数
    :vartype theta: float

    :ivar H: 硬化系数矩阵
    :vartype H: ndarray

    :ivar tau_sol: 固溶强度
    :vartype tau_sol: float

    :ivar v_0: 位错滑移速度
    :vartype v_0: float

    :ivar b_s: 位错滑移柏氏矢量长度
    :vartype b_s: float

    :ivar Q_s: 位错滑移激活能
    :vartype Q_s: float

    :ivar p_s: 位错滑移阻力拟合参数
    :vartype p_s: float

    :ivar q_s: 位错滑移阻力拟合参数
    :vartype q_s: float

    :ivar k_b: 玻尔兹曼常数
    :vartype k_b: float

    :ivar d_grain: 平均晶粒尺寸
    :vartype d_grain: float

    :ivar i_slip: 平均位错间隔拟合参数
    :vartype i_slip: float

    :ivar c_anni: 位错消除拟合参数
    :vartype c_anni: float

    :ivar Q_climb: 位错攀移激活能
    :vartype Q_climb: float

    :ivar D_0: 自扩散系数因子
    :vartype D_0: float

    :ivar Omega_climb: 位错攀移激活体积
    :vartype Omega_climb: float

    :ivar G: 剪切模量
    :vartype G: float

    :ivar temperature: 温度
    :vartype temperature: float

    :ivar u: u方向矢量
    :vartype u: ndarray

    :ivar v: v方向矢量
    :vartype v: ndarray

    :ivar w: w方向矢量
    :vartype w: ndarray

    :ivar u_prime: 特征u方向矢量
    :vartype u_prime: ndarray

    :ivar v_prime: 特征v方向矢量
    :vartype v_prime: ndarray

    :ivar w_prime: 特征w方向矢量
    :vartype w_prime: ndarray

    :ivar T: 旋转矩阵
    :vartype T: ndarray

    :ivar T_vogit: Vogit形式旋转矩阵
    :vartype T_vogit: ndarray

    :ivar m: 特征滑移系滑移方向
    :vartype m: ndarray

    :ivar n: 特征滑移系滑移面法向
    :vartype n: ndarray

    :ivar MAX_NITER: 最大迭代次数
    :vartype MAX_NITER: ndarray

    """

    __slots_dict__: dict = {
        'tolerance': ('float', '判断屈服的误差容限'),
        'total_number_of_slips': ('int', '总的滑移系数量'),
        'elastic': ('dict', '弹性参数字典'),
        'C': ('ndarray', '旋转矩阵'),
        'slip_system': ('str', ''),
        'theta': ('float', '切线系数法参数'),
        'H': ('ndarray', '硬化系数矩阵'),
        'tau_sol': ('float', '固溶强度'),
        'v_0': ('float', '位错滑移速度'),
        'b_s': ('float', '位错滑移柏氏矢量长度'),
        'Q_s': ('float', '位错滑移激活能'),
        'p_s': ('float', '位错滑移阻力拟合参数'),
        'q_s': ('float', '位错滑移阻力拟合参数'),
        'k_b': ('float', '玻尔兹曼常数'),
        'd_grain': ('float', '平均晶粒尺寸'),
        'i_slip': ('float', '平均位错间隔拟合参数'),
        'c_anni': ('float', '位错消除拟合参数'),
        'Q_climb': ('float', '位错攀移激活能'),
        'D_0': ('float', '自扩散系数因子'),
        'Omega_climb': ('float', '位错攀移激活体积'),
        'G': ('float', '剪切模量'),
        'temperature': ('float', '温度'),
        'u': ('ndarray', 'u方向矢量'),
        'v': ('ndarray', 'v方向矢量'),
        'w': ('ndarray', 'w方向矢量'),
        'u_prime': ('ndarray', '特征u方向矢量'),
        'v_prime': ('ndarray', '特征v方向矢量'),
        'w_prime': ('ndarray', '特征w方向矢量'),
        'T': ('ndarray', '旋转矩阵'),
        'T_vogit': ('ndarray', 'Vogit形式旋转矩阵'),
        'm_s': ('ndarray', '特征滑移系滑移方向'),
        'n_s': ('ndarray', '特征滑移系滑移面法向'),
        'MAX_NITER': ('ndarray', '最大迭代次数'),
    }

    __slots__ = BaseMaterial.__slots__ + [slot for slot in __slots_dict__.keys()]

    def __init__(self, material: Material, dimension: int, section: Section) -> None:
        super().__init__(material, dimension, section)
        self.allowed_section_types = ('Volume', 'PlaneStress', 'PlaneStrain')

        self.data_keys = []

        if len(self.material.data) != len(self.data_keys):
            raise NotImplementedError(error_style(self.get_data_length_error_msg()))
        else:
            for i, key in enumerate(self.data_keys):
                self.data_dict[key] = material.data[i]

        self.data_dict = material.data_dict

        self.tolerance: float = 1.0e-6
        self.MAX_NITER = 8
        self.theta: float = 0.5
        self.total_number_of_slips: int = 12
        self.slip_system = self.data_dict['slip_system']

        self.elastic = self.data_dict['elastic']
        self.C = self.create_elastic_stiffness(self.elastic)

        self.tau_sol = self.data_dict['tau_sol']
        self.v_0 = self.data_dict['v_0']
        self.b_s = self.data_dict['b_s']
        self.Q_s = self.data_dict['Q_s']

        self.p_s = self.data_dict['p_s']
        self.q_s = self.data_dict['q_s']
        self.k_b = self.data_dict['k_b']
        self.d_grain = self.data_dict['d_grain']
        self.i_slip = self.data_dict['i_slip']
        self.c_anni = self.data_dict['c_anni']
        self.Q_climb = self.data_dict['Q_climb']
        self.D_0 = self.data_dict['D_0']
        self.Omega_climb = self.data_dict['Omega_climb_coefficient'] * self.b_s ** 3
        self.G = self.data_dict['G']
        self.temperature = self.data_dict['temperature']

        self.H = ones(shape=(self.total_number_of_slips, self.total_number_of_slips), dtype=DTYPE)
        self.u_prime = array([1, 0, 0])
        self.v_prime = array([0, 1, 0])
        self.w_prime = array([0, 0, 1])

        self.u = array([0.86602540378, -0.5, 0])
        self.v = array([0.5, 0.86602540378, 0])
        self.w = array([0, 0, 1])

        self.u = array([1, 0, 0])
        self.v = array([0, 1, 0])
        self.w = array([0, 0, 1])

        self.T = get_transformation(self.u, self.v, self.w, self.u_prime, self.v_prime, self.w_prime)
        self.T_vogit = get_voigt_transformation(self.T)

        _, self.m_s, self.n_s = generate_mn('slip', self.slip_system, 1.0)

        self.m_s = dot(self.m_s, self.T)
        self.n_s = dot(self.n_s, self.T)
        self.C = dot(dot(self.T_vogit, self.C), transpose(self.T_vogit))
        self.create_tangent()

    def create_tangent(self):
        if self.section.type in self.allowed_section_types:
            pass
        else:
            raise NotImplementedError(error_style(self.get_section_type_error_msg()))

    def create_elastic_stiffness(self, elastic: dict):
        symmetry = elastic['symmetry']
        if symmetry == 'isotropic':
            C11 = elastic['C11']
            C12 = elastic['C12']
            C44 = elastic['C44']
            C = array([[C11, C12, C12, 0, 0, 0],
                       [C12, C11, C12, 0, 0, 0],
                       [C12, C12, C11, 0, 0, 0],
                       [0, 0, 0, C44, 0, 0],
                       [0, 0, 0, 0, C44, 0],
                       [0, 0, 0, 0, 0, C44]], dtype=DTYPE)
        else:
            raise NotImplementedError(
                error_style(f'the symmetry type \"{symmetry}\" of elastic stiffness is not supported'))
        return C

    def get_tangent(self, variable: dict[str, ndarray],
                    state_variable: dict[str, ndarray],
                    state_variable_new: dict[str, ndarray],
                    element_id: int,
                    iqp: int,
                    ntens: int,
                    ndi: int,
                    nshr: int,
                    timer: Timer) -> tuple[ndarray, dict[str, ndarray]]:

        strain = variable['strain']
        dstrain = variable['dstrain']

        if self.section.type == 'PlaneStrain':
            strain = array([strain[0], strain[1], 0.0, strain[2], 0.0, 0.0])
            dstrain = array([dstrain[0], dstrain[1], 0.0, dstrain[2], 0.0, 0.0])

        np.set_printoptions(precision=12, linewidth=256, suppress=True)

        C = self.C
        total_number_of_slips = self.total_number_of_slips

        tau_sol = self.tau_sol
        v_0 = self.v_0
        b_s = self.b_s
        Q_s = self.Q_s

        p_s = self.p_s
        q_s = self.q_s
        k_b = self.k_b
        d_grain = self.d_grain
        i_slip = self.i_slip
        c_anni = self.c_anni
        Q_climb = self.Q_climb
        D_0 = self.D_0
        Omega_climb = self.Omega_climb
        G = self.G
        temperature = self.temperature

        d_min = c_anni * b_s

        dt = timer.dtime
        theta = self.theta

        H = self.H
        m_s = self.m_s
        n_s = self.n_s

        if state_variable == {} or timer.time0 == 0.0:
            state_variable['m_s'] = m_s
            state_variable['n_s'] = n_s
            m_sxn_s = transpose(array([m_s[:, 0] * n_s[:, 0],
                                       m_s[:, 1] * n_s[:, 1],
                                       m_s[:, 2] * n_s[:, 2],
                                       2.0 * m_s[:, 0] * n_s[:, 1],
                                       2.0 * m_s[:, 0] * n_s[:, 2],
                                       2.0 * m_s[:, 1] * n_s[:, 2]]))
            n_sxm_s = transpose(array([n_s[:, 0] * m_s[:, 0],
                                       n_s[:, 1] * m_s[:, 1],
                                       n_s[:, 2] * m_s[:, 2],
                                       2.0 * n_s[:, 0] * m_s[:, 1],
                                       2.0 * n_s[:, 0] * m_s[:, 2],
                                       2.0 * n_s[:, 1] * m_s[:, 2]]))
            P = 0.5 * (m_sxn_s + n_sxm_s)
            state_variable['stress'] = zeros(shape=6, dtype=DTYPE)
            state_variable['tau'] = dot(P, state_variable['stress'])
            state_variable['gamma'] = zeros(shape=total_number_of_slips, dtype=DTYPE)
            state_variable['tau_pass'] = zeros(shape=total_number_of_slips, dtype=DTYPE)
            state_variable['rho_m'] = zeros(shape=total_number_of_slips, dtype=DTYPE) + 1e12
            state_variable['rho_di'] = zeros(shape=total_number_of_slips, dtype=DTYPE) + 1.0

        rho_m = deepcopy(state_variable['rho_m'])
        rho_di = deepcopy(state_variable['rho_di'])
        m_s = deepcopy(state_variable['m_s'])
        n_s = deepcopy(state_variable['n_s'])
        gamma = deepcopy(state_variable['gamma'])
        stress = deepcopy(state_variable['stress'])
        tau = deepcopy(state_variable['tau'])

        delta_gamma = zeros(shape=total_number_of_slips, dtype=DTYPE)

        is_convergence = False

        for niter in range(self.MAX_NITER):
            m_sxn_s = transpose(array([m_s[:, 0] * n_s[:, 0],
                                       m_s[:, 1] * n_s[:, 1],
                                       m_s[:, 2] * n_s[:, 2],
                                       2.0 * m_s[:, 0] * n_s[:, 1],
                                       2.0 * m_s[:, 0] * n_s[:, 2],
                                       2.0 * m_s[:, 1] * n_s[:, 2]]))

            n_sxm_s = transpose(array([n_s[:, 0] * m_s[:, 0],
                                       n_s[:, 1] * m_s[:, 1],
                                       n_s[:, 2] * m_s[:, 2],
                                       2.0 * n_s[:, 0] * m_s[:, 1],
                                       2.0 * n_s[:, 0] * m_s[:, 2],
                                       2.0 * n_s[:, 1] * m_s[:, 2]]))

            P = 0.5 * (m_sxn_s + n_sxm_s)
            Omega = 0.5 * (m_sxn_s - n_sxm_s)
            Omega[:, 3:] *= 0.5

            # S = dot(P, C) + Omega * stress - stress * Omega
            S = dot(P, C)

            rho = rho_di + rho_m
            tau_pass = G * b_s * sqrt(dot(H, rho))

            X = (abs(tau) - tau_pass) / tau_sol
            X_bracket = maximum(X, 0.0) + self.tolerance
            X_heaviside = sign(X_bracket)
            A_s = Q_s / k_b / temperature

            d_di = 3.0 * G * b_s / (16.0 * pi * (abs(tau) + self.tolerance))
            one_over_lambda = 1.0 / d_grain + 1.0 / i_slip * tau_pass / G / b_s
            v_climb = 3.0 * G * D_0 * Omega_climb / (2.0 * pi * k_b * temperature * (d_di + d_min)) \
                      * exp(-Q_climb / k_b / temperature)
            gamma_dot = rho_m * b_s * v_0 * exp(-A_s * (1.0 - X_bracket ** p_s) ** q_s) * sign(tau)

            if niter == 0:
                gamma_dot_init = deepcopy(gamma_dot)

            term1 = dt * theta
            term2 = A_s * p_s * q_s * gamma_dot * X_bracket ** (p_s - 1.0) * (1.0 - X_bracket ** p_s) ** (q_s - 1.0) \
                    * sign(tau)
            term3 = X_heaviside / tau_sol
            term4 = einsum('ik, jk->ij', S, P)
            term5 = one_over_lambda / b_s - 2.0 * d_di * rho_m / b_s
            term6 = one_over_lambda / b_s - 2.0 * d_min * rho / b_s
            term7 = 4.0 * rho_di * v_climb / (d_di - d_min) * dt
            term8 = (G * b_s) ** 2 / (2.0 * tau_pass)

            I = eye(total_number_of_slips, dtype=DTYPE)
            A = deepcopy(I)
            A -= term1 * term2 * term5 * b_s * v_0 * exp(-A_s * (1.0 - X_bracket ** p_s) ** q_s) * I
            A += term1 * term2 * term3 * term4 * sign(tau)
            A += term1 * term2 * term3 * term8 * dot(H, term6 * sign(tau) * I)

            if niter == 0:
                rhs = dt * gamma_dot + term1 * term2 * term3 * sign(tau) * dot(S, dstrain) \
                      + term1 * term2 * term3 * term8 * dot(H, term7)
                # rhs = dt * gamma_dot + term1 * term2 * term3 * sign(tau) * dot(S, dstrain)
            else:
                rhs = dt * theta * (gamma_dot - gamma_dot_init) + gamma_dot_init * dt - delta_gamma

            d_delta_gamma = solve(transpose(A), rhs)
            delta_gamma += d_delta_gamma

            delta_elastic_strain = dstrain - dot(delta_gamma, P)
            delta_tau = dot(S, delta_elastic_strain)
            delta_stress = dot(C, delta_elastic_strain)
            delta_rho_m = (one_over_lambda / b_s - 2.0 * d_di * rho_m / b_s) * abs(delta_gamma)
            delta_rho_di = 2.0 * (rho_m * (d_di - d_min) - rho_di * d_min) / b_s * abs(delta_gamma) - term7
            delta_m_s = 0.0
            delta_n_s = 0.0

            m_s = deepcopy(state_variable['m_s']) + delta_m_s
            n_s = deepcopy(state_variable['n_s']) + delta_n_s
            gamma = deepcopy(state_variable['gamma']) + delta_gamma
            tau = deepcopy(state_variable['tau']) + delta_tau
            stress = deepcopy(state_variable['stress']) + delta_stress
            rho_m = deepcopy(state_variable['rho_m']) + delta_rho_m
            rho_di = deepcopy(state_variable['rho_di']) + delta_rho_di

            X = (abs(tau) - tau_pass) / tau_sol
            X_bracket = maximum(X, 0.0)
            gamma_dot = rho_m * b_s * v_0 * exp(-A_s * (1.0 - X_bracket ** p_s) ** q_s) * sign(tau)
            residual = dt * theta * gamma_dot + dt * (1.0 - theta) * gamma_dot_init - delta_gamma

            # if element_id == 0 and iqp == 0:
            #     print('residual', residual)

            if all(residual < self.tolerance):
                is_convergence = True
                break

        ddgdde = (term1 * term2 * term3 * sign(tau)).reshape((total_number_of_slips, 1)) * S
        ddgdde = dot(inv(A), ddgdde)
        ddsdde = C - einsum('ki, kj->ij', S, ddgdde)

        # if element_id == 0 and iqp == 0:
        #     print('rho_m', rho_m)
        #     print('rho_di', rho_di)

        if not is_convergence:
            timer.is_reduce_dtime = True

        state_variable_new['m_s'] = m_s
        state_variable_new['n_s'] = n_s
        state_variable_new['stress'] = stress
        state_variable_new['gamma'] = gamma
        state_variable_new['tau'] = tau
        state_variable_new['rho_m'] = rho_m
        state_variable_new['rho_di'] = rho_di

        if self.section.type == 'PlaneStrain':
            ddsdde = delete(delete(ddsdde, [2, 4, 5], axis=0), [2, 4, 5], axis=1)
            stress = delete(stress, [2, 4, 5])

        output = {'stress': stress}

        return ddsdde, output

if __name__ == "__main__":
    # from pyfem.utils.visualization import print_slots_dict
    #
    # print_slots_dict(PlasticCrystalGNDs.__slots_dict__)

    from pyfem.Job import Job

    job = Job(r'..\..\..\examples\mechanical\1element\hex20_crystal_GNDs\Job-1.toml')
    # job = Job(r'..\..\..\examples\mechanical\plane_crystal_GNDs\Job-1.toml')

    job.run()


class BankAccount:
    name = ""
    account_num = 0
    balance = 0

    def __init__(self, val1, val2):
        self.name = val1
        self.account_num = val2

    def __repr__(self):
        return self.name + "님의 계좌 " + str(self.account_num) + "의 잔고는 " + str(self.balance) + "원입니다."

    def deposit(self, money):
        self.balance += money
        print(str(money) + "원이 입금되었습니다. 잔고는 " + str(self.balance) + "원입니다.")

    def withdraw(self, money):
        if(self.balance < money):
            print("계좌 잔고는 " + str(self.balance) + "원으로 인출 요구 금액 " + str(money) + "보다 작습니다.")
        else:
            self.balance -= money

account1 = BankAccount("홍길동", "1234-0001")
print(account1)
account1.deposit(2000)
print(account1)
account1.withdraw(500)
print(account1)
account1.withdraw(5000)