#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
Modified on Wed May 05 08:58:46 2021

@author: Felipe Jaramillo
"""
import os
import glob
import sys
import cv2
import numpy as np
import time

import h5py
import random

#------------------------------------------------------------------------------------------------------
# Angular downsampling from original subaperture images of each light field,
# - angular downsampled subaperture images synthesizing
# - angular upsampled via nearest, bicubic and lanczos subaperture images synthesizing
# - angular downsampled and original light field structure stuv synthesizing (for visual purposes)
# - angular downsampled, original and upsampled subaperture images video synthesizing (for visual purposes)

def LFuvst(imgs, st_hr, pth_LFuvst, folder):
  # Construct a spatial image with each spatial point compund by the angular
  # matrix corresponding to that u,v coordinate
  lfimg = np.zeros((imgs[0].shape[0]*st_hr, imgs[0].shape[1]*st_hr, 3), np.uint8)
  for u in range(imgs[0].shape[0]):
    print('.', end="")
    for v in range(imgs[0].shape[1]):
      i = 0
      for s in range(st_hr):
        for t in range(st_hr):
          img = imgs[i]
          lfimg[(u*st_hr+s),(v*st_hr+t), :] = img[u, v, :]
          i += 1
  if not os.path.exists(pth_LFuvst+folder):
    os.makedirs(pth_LFuvst+folder)
  name = pth_LFuvst + folder + '/' + folder + '_stuv.png'
  cv2.imwrite(name, lfimg)

def AngularDownsampling(imgs, st_hr, st_lr):

  dwnfactor = int(st_hr/st_lr)
  # Extract angular matrices for a single spatial point and then downsampling it
  ang_mtx = []
  nearest_ang_mtx = []
  bicubic_ang_mtx = []
  lanczos_ang_mtx = []
  height = imgs[0].shape[0]
  width = imgs[0].shape[1]
  for u in range(height):
    print('.', end="")
    for v in range(width):
      a_mtx = np.zeros((st_hr, st_hr, 3), np.uint8)
      i = 0
      for s in range(st_hr):
        for t in range(st_hr):
          img = imgs[i]
          a_mtx[s, t, :] = img[u, v, :]
          i += 1
      # angular downsampling
      fx = 1/dwnfactor
      fy = 1/dwnfactor
      amtx = cv2.resize(a_mtx, None, fx=fx, fy=fy, interpolation=cv2.INTER_AREA)
      ang_mtx.append(amtx)

      amtx = (np.float32(amtx) / 127.5) - 1 # Normalization between [-1, 1]
      amtx = np.uint8((amtx + 1) * 127.5)

      nr = cv2.resize(amtx, None, fx=2, fy=2, interpolation=cv2.INTER_NEAREST)
      bc = cv2.resize(amtx, None, fx=2, fy=2, interpolation=cv2.INTER_CUBIC)
      lc = cv2.resize(amtx, None, fx=2, fy=2, interpolation=cv2.INTER_LANCZOS4)
      nearest_ang_mtx.append(nr)
      bicubic_ang_mtx.append(bc)
      lanczos_ang_mtx.append(lc)

  return ang_mtx, nearest_ang_mtx, bicubic_ang_mtx, lanczos_ang_mtx

def SynthesizeImgs(a_mtxdwn, st_hr, h, w, pth_frames, folder, indx):
  '''
  Function to synthesize and save the new sub-aperture images from the angular
  upsampled matrices of the corresponding LF
  '''
  imgs_new = []
  for s in range(st_hr):
    for t in range(st_hr):
      img = np.zeros((int(h), int(w), 3), np.uint8)
      i = 0
      for u in range(int(h)):
        for v in range(int(w)):
          img[u, v, :] = a_mtxdwn[i][s, t, :]
          i += 1
      print('.', end="")
      imgs_new.append(img)

  if indx == 'adownsampled':
    # Path to save original LF organized by stuv coordinates
    pth_LFuvst = os.getcwd() + '/LF/LF_stuv/'
    print("Saving angular downsampled light field structure stuv into %s " % ((pth_LFuvst+folder+'_'+indx)), end="")
    LFuvst(imgs_new, st_lr, pth_LFuvst, (folder+'_adownsampled'))
    print()
    print("done")

  print("Saving angular new %s sub-aperture images into %s..." % (indx,(pth_frames+folder+'_'+indx)))
  if not os.path.exists(pth_frames+folder+'_'+indx):
    os.makedirs(pth_frames+folder+'_'+indx)
  cont = 1
  i = 0
  filenames = []
  for s in range(st_hr):
    auxx = imgs_new[i:(st_hr+i)]
    if s%2 == 0:
      init = 0
      step = 1
      finish = st_hr
    else:
      init = st_hr-1
      step = -1
      finish = -1
      auxx.reverse()
    j = 0
    for t in range(init, finish, step):
      name = "%s%s_%s/%s_%03d_%02d_%02d.png" % (pth_frames, folder, indx, folder, cont, s+1, t+1)
      cv2.imwrite(name, auxx[j])
      cont+=1
      j += 1
      filenames.append(name)
      print('.', end="")
    i += st_hr
  print()
  print("done")
  return filenames

def save_frames(files):
  '''
  Function to save sub-aperture images into list in order to pass to video
  constructor
    Input:
      files: list with complete file name of sub-aperture images
    Outputs:
      frame_array: list with the frames
      height: number of rows in frames
      width: number of columns in frames
  '''
  frame_array = []
  for i in files:
    img = cv2.imread(i)
    height, width = img.shape[0:2]
    frame_array.append(img)
  return frame_array, height, width

def write_video(frame_array, name, height, width):
  '''
  Function to invoke a video codec constructor in order to insert frames and
  generate a video with the sub-aperture images
    Inputs:
      frame_array: list with the frames
      name: name of the video to save
      height: number of rows in frames
      width: number of columns in frames
  '''
  #fourcc = cv2.VideoWriter_fourcc(*'XVID') - Linux
  #fourcc = cv2.VideoWriter_fourcc('M','J','P','G') - Windows, avi
  fourcc = cv2.VideoWriter_fourcc(*'mp4v') # MP4
  out = cv2.VideoWriter(name,fourcc, 23.0, (width,height))
  for i in range(len(frame_array)):
    out.write(frame_array[i]) # writing the frame into the codec constructor
  out.release()

# Path withl LF subimages
pth_frames = os.getcwd() + '/LF/Frames/'

f_list = os.listdir(pth_frames)
LRfolders = []
HRfolders = []
for i in f_list:
  if 'adownsampled' in i:
    LRfolders.append(i)
  elif ('adownsampled' not in i) and ('SRv9' not in i) and ('SRv10' not in i) and ('SRv8' not in i) and ('BC' not in i) and ('NR' not in i) and ('LC' not in i):
    HRfolders.append(i)
  LRfolders.sort()
  HRfolders.sort()

# Path to save original LF organized by stuv coordinates
pth_LFuvst = os.getcwd() + '/LF/LF_stuv/'

st_hr, st_lr = 10, 5 # original angular resolution, downsampled angular resolution

print("\nLF angular donwsampling: ")
for folder in HRfolders:

  start_time = time.time()
  print("\nProcessing light field %s " % (folder))
  subimgs_list = glob.glob(pth_frames+folder+'/*.png')
  subimgs_list.sort()

  #-7
  appnd = [f[-9:] for f in subimgs_list]
  appnd.sort()

  imgshr = []
  for i in appnd:
    for f in subimgs_list:
      #-7
      if i in f[-9:]:
        imghr = cv2.imread(f)
        imgshr.append(imghr)
        h, w, _ = imghr.shape
        break

  print("Saving original light field structure stuv into %s ..." % ((pth_LFuvst + folder)), end="")
  LFuvst(imgshr, st_hr, pth_LFuvst, folder)
  print('')
  print("done")

  print("Angular downsampling from %d to %d ..." % (st_hr, st_lr), end="")
  ang_mtx, nearest_ang_mtx, bicubic_ang_mtx, lanczos_ang_mtx = AngularDownsampling(imgshr, st_hr, st_lr)
  imgshr = 0
  print('')
  print("done")

  LRsubimgs_list = SynthesizeImgs(ang_mtx, st_lr, h, w, pth_frames, folder, 'adownsampled')
  NRsubimgs_list = SynthesizeImgs(nearest_ang_mtx, st_hr, h, w, pth_frames, folder, 'NR')
  BCsubimgs_list = SynthesizeImgs(bicubic_ang_mtx, st_hr, h, w, pth_frames, folder, 'BC')
  LCsubimgs_list = SynthesizeImgs(lanczos_ang_mtx, st_hr, h, w, pth_frames, folder, 'LC')

  print("Generating video for angular LR light field...")
  frame_array, height, width = save_frames(LRsubimgs_list)
  VD_pth = 'LF/Videos/'
  name = VD_pth + folder + '_adonwsampled.mp4'
  write_video(frame_array, name, height, width)
  print("Video %s has been saved correctly..." % (name))

  print("Generating video for angular HR light field...")
  HRsubimgs_list = glob.glob(pth_frames+folder+'/*.png')
  HRsubimgs_list.sort()
  frame_array, height, width = save_frames(HRsubimgs_list)
  VD_pth = 'LF/Videos/'
  name = VD_pth + folder + '.mp4'
  write_video(frame_array, name, height, width)
  print("Video %s has been saved correctly..." % (name))

  print("Generating video for angular nearest upsampled light field...")
  frame_array, height, width = save_frames(NRsubimgs_list)
  VD_pth = 'LF/Videos/'
  name = VD_pth + folder + '_NR.mp4'
  write_video(frame_array, name, height, width)
  print("Video %s has been saved correctly..." % (name))

  print("Generating video for angular bicubic upsampled light field...")
  frame_array, height, width = save_frames(BCsubimgs_list)
  VD_pth = 'LF/Videos/'
  name = VD_pth + folder + '_BC.mp4'
  write_video(frame_array, name, height, width)
  print("Video %s has been saved correctly..." % (name))

  print("Generating video for angular lanczos upsampled light field...")
  frame_array, height, width = save_frames(LCsubimgs_list)
  VD_pth = 'LF/Videos/'
  name = VD_pth + folder + '_LC.mp4'
  write_video(frame_array, name, height, width)
  print("Video %s has been saved correctly..." % (name))

  print("--- Elapsed time: %s seconds ---" % (time.time() - start_time))

#-----------------------------------------------------------------------------------------------------------------------
# - angular downsampled ando original light field structure uvst synthesizing

# Path withl LF subimages
pth_frames = os.getcwd() + '/LF/Frames/'

f_list = os.listdir(pth_frames)
LRfolders = []
HRfolders = []
for i in f_list:
  if 'adownsampled' in i:
    LRfolders.append(i)
  elif ('adownsampled' not in i) and ('SRv9' not in i) and ('SRv10' not in i) and ('SRv8' not in i) and ('BC' not in i) and ('NR' not in i) and ('LC' not in i):
    HRfolders.append(i)
  LRfolders.sort()
  HRfolders.sort()

if len(LRfolders)!=len(HRfolders):
  print("Number of LF are not symetric within different methods of upscaling... Exit program")
  sys.exit("aa! errors!")

def handleimgs(lf_folder):
  imgsfiles = glob.glob(pth_frames+lf_folder+'/*.png')
  imgsfiles.sort()
  return imgsfiles

pth_mosiacos = os.getcwd() + '/LF/LF_uvst/'
print("Saving original and angular donwsampled light field structure uvst into %s ..." % (pth_mosiacos), end="")

startglob_time = time.time()
for LRfolder, HRfolder in zip(LRfolders, HRfolders):

  start_time = time.time()

  print("\nEvaluation of light field %s " % (HRfolder))
  LRsubimgs_list = handleimgs(LRfolder)
  HRsubimgs_list = handleimgs(HRfolder)

  HRimg = cv2.imread(HRsubimgs_list[0])
  HRmosaico = np.zeros((HRimg.shape[0]*10,HRimg.shape[1]*10, 3), np.uint8)

  rowhr = 0
  colhr = 0
  for i in range(len(HRsubimgs_list)):

    HRimg = cv2.imread(HRsubimgs_list[i])

    yi = rowhr*HRimg.shape[1]
    yo = (rowhr*HRimg.shape[1]) + HRimg.shape[1]
    xi = colhr*HRimg.shape[0]
    xo = (colhr*HRimg.shape[0]) + HRimg.shape[0]
    HRmosaico[yi:yo, xi:xo, :] = HRimg
    rowhr += 1
    if rowhr == 10:
      rowhr = 0
      colhr += 1

  print("Saving mosaico images  into %s..." % (pth_mosiacos+HRfolder))
  if not os.path.exists(pth_mosiacos+HRfolder):
    os.makedirs(pth_mosiacos+HRfolder)
  hrname = pth_mosiacos + HRfolder + '/' + HRfolder + '_uvst.png'
  cv2.imwrite(hrname, HRmosaico)

  LRimg = cv2.imread(LRsubimgs_list[0])
  LRmosaico = np.zeros((LRimg.shape[0]*5,LRimg.shape[1]*5, 3), np.uint8)
  rowlr = 0
  collr = 0

  for i in range(len(LRsubimgs_list)):

    LRimg = cv2.imread(LRsubimgs_list[i])

    yi = rowlr*LRimg.shape[1]
    yo = (rowlr*LRimg.shape[1]) + LRimg.shape[1]
    xi = collr*LRimg.shape[0]
    xo = (collr*LRimg.shape[0]) + LRimg.shape[0]
    LRmosaico[yi:yo, xi:xo, :] = LRimg
    rowlr += 1
    if rowlr == 5:
      rowlr = 0
      collr += 1

  print("Saving mosaico images  into %s..." % (pth_mosiacos+LRfolder))
  if not os.path.exists(pth_mosiacos+LRfolder):
    os.makedirs(pth_mosiacos+LRfolder)
  lrname = pth_mosiacos + LRfolder + '/' + LRfolder + '_uvst.png'
  cv2.imwrite(lrname, LRmosaico)

  print("--- Elapsed time: %s seconds ---" % (time.time() - start_time))

print("--- Elapsed time: %s seconds ---" % (time.time() - startglob_time))

#-------------------------------------------------------------------------------------------------------------------------
# - create h5 dataset for training
import os
import glob
import sys
import cv2
import numpy as np
import time

import h5py
import random

def AngularDownsampling(imgs, st_hr, st_lr):
  dwnfactor = int(st_hr/st_lr)
  # Extract angular matrices for a single spatial point and then downsampling it
  angular_mtcs_hr = []
  angular_mtcs_lr = []
  for u in range(imgs[0].shape[0]):
    print('.', end="")
    for v in range(imgs[0].shape[1]):
      a_mtx = np.zeros((st_hr, st_hr, 3), np.uint8)
      i = 0
      for s in range(st_hr):
        for t in range(st_hr):
          img = imgs[i]
          a_mtx[s, t, :] = img[u, v, :]
          i += 1
      angular_mtcs_hr.append(a_mtx)
      # angular downsampling
      fx = 1/dwnfactor
      fy = 1/dwnfactor
      amtx = cv2.resize(a_mtx, None, fx=fx, fy=fy, interpolation=cv2.INTER_AREA)
      angular_mtcs_lr.append(amtx)
  return angular_mtcs_hr, angular_mtcs_lr

# Path withl LF subimages
pth_frames = os.getcwd() + '/LF/Frames/'

f_list = os.listdir(pth_frames)
LRfolders = []
HRfolders = []
for i in f_list:
  if 'adownsampled' in i:
    LRfolders.append(i)
  elif ('adownsampled' not in i) and ('SRv9' not in i) and ('SRv10' not in i) and ('SRv8' not in i) and ('BC' not in i) and ('NR' not in i) and ('LC' not in i):
    HRfolders.append(i)
  LRfolders.sort()
  HRfolders.sort()

# Randomly shuffle list
random.seed(118)
random.shuffle(HRfolders)

# Separate train and validation LFs
aux = int(len(HRfolders)*0.80)
HRfolders_Train = HRfolders[0:aux] # Training dataset by 80% of full dataset
HRfolders_Test = HRfolders[aux:] # Validation dataset by 20% of full dataset

st_hr, st_lr = 10, 5 # original angular resolution, downsampled angular resolution

#fileName = os.getcwd() + '/LF/HDF5_dataset/LF_angular_dataset.h5'
fileName = os.getcwd() + '/LF_angular_dataset_final.h5'

print(len(HRfolders_Train))
print(len(HRfolders_Test))

ang_smpls = 700 * 10 # angular samples to extract from each LF
#ang_smpls = 15 # angular samples to extract from each LF
train_ang_dataset_smpls = len(HRfolders_Train) * ang_smpls # number of angular samples in train dataset
test_ang_dataset_smpls = len(HRfolders_Test) * ang_smpls # number of angular samples in test dataset

print(train_ang_dataset_smpls)
print(test_ang_dataset_smpls)

with h5py.File(fileName, "w") as out:
  out.create_dataset("X_ang_train",(train_ang_dataset_smpls,5,5,3),dtype=np.uint8)
  out.create_dataset("Y_ang_train",(train_ang_dataset_smpls,10,10,3),dtype=np.uint8)
  out.create_dataset("X_ang_test",(test_ang_dataset_smpls,5,5,3),dtype=np.uint8)
  out.create_dataset("Y_ang_test",(test_ang_dataset_smpls,10,10,3),dtype=np.uint8)

anglr_train = []
anghr_train = []
for folder in HRfolders_Train:

  start_time = time.time()
  print("\nProcessing light field %s " % (folder))
  subimgs_list = glob.glob(pth_frames+folder+'/*.png')
  subimgs_list.sort()

  appnd = [f[-9:] for f in subimgs_list]
  appnd.sort()

  imgshr = []
  for i in appnd:
    for f in subimgs_list:
      if i in f[-9:]:
        imghr = cv2.imread(f)
        imghr = cv2.cvtColor(imghr,cv2.COLOR_BGR2RGB)
        imgshr.append(imghr)
        break

  print("Angular downsampling from %d to %d ..." % (st_hr, st_lr), end="")
  mtx_hr, mtx_lr = AngularDownsampling(imgshr, st_hr, st_lr)
  print('')
  print("done")

  if len(mtx_hr) != len(mtx_lr):
    sys.exit("aa! errors! Dataset is not symmetric.. Exit program")

  # Randomly select 'ang_smpls' samples from both hr and lr angular samples
  c = list(zip(mtx_lr, mtx_hr))
  d = random.sample(c, ang_smpls)
  mtx_lr, mtx_hr = zip(*d)

  for i in range(len(mtx_lr)):
    anglr_train.append(mtx_lr[i])
    anghr_train.append(mtx_hr[i])

  print("--- Elapsed time: %s seconds ---" % (time.time() - start_time))

c = list(zip(anglr_train, anghr_train)) # Randomly shuffle both lists in the same order
random.seed(len(anglr_train))
random.shuffle(c)
anglr_train, anghr_train = zip(*c)

def WriteHDF5(samples, dataset):
  k = 0
  with h5py.File(fileName, "a") as out:
    for sample in samples:
      out[dataset][k, ...] = sample
      k+=1

print("\nSaving X_ang_train samples into dataset file...")
WriteHDF5(anglr_train, 'X_ang_train')
print("done")
print("\nSaving Y_ang_train samples into dataset file...")
WriteHDF5(anghr_train, 'Y_ang_train')
print("done")

anglr_test = []
anghr_test = []

for folder in HRfolders_Test:

  start_time = time.time()
  print("\nProcessing light field %s " % (folder))
  subimgs_list = glob.glob(pth_frames+folder+'/*.png')
  subimgs_list.sort()

  appnd = [f[-9:] for f in subimgs_list]
  appnd.sort()

  imgshr = []
  for i in appnd:
    for f in subimgs_list:
      if i in f[-9:]:
        imghr = cv2.imread(f)
        imghr = cv2.cvtColor(imghr,cv2.COLOR_BGR2RGB)
        imgshr.append(imghr)
        break

  print("Angular downsampling from %d to %d ..." % (st_hr, st_lr), end="")
  mtx_hr, mtx_lr = AngularDownsampling(imgshr, st_hr, st_lr)
  print('')
  print("done")

  if len(mtx_hr) != len(mtx_lr):
    sys.exit("aa! errors! Dataset is not symmetric.. Exit program")

  # Randomly select 'ang_smpls' samples from both hr and lr angular samples
  c = list(zip(mtx_lr, mtx_hr))
  d = random.sample(c, ang_smpls)
  mtx_lr, mtx_hr = zip(*d)

  for i in range(len(mtx_lr)):
    anglr_test.append(mtx_lr[i])
    anghr_test.append(mtx_hr[i])

  print("--- Elapsed time: %s seconds ---" % (time.time() - start_time))

c = list(zip(anglr_test, anghr_test)) # Randomly shuffle both lists in the same order
random.seed(len(anglr_test))
random.shuffle(c)
anglr_test, anghr_test = zip(*c)

print("\nSaving X_ang_test samples into dataset file...")
WriteHDF5(anglr_test, 'X_ang_test')
print("done")
print("\nSaving Y_ang_test samples into dataset file...")
WriteHDF5(anghr_test, 'Y_ang_test')
print("done")


import random

class Node:
    def __init__(self, data):
        self.data = data
        self.left = None
        self.right = None

    def insert(self, data):
        if self.data:
            if data < self.data:
                if self.left is None:
                    self.left = Node(data)
                else:
                    self.left.insert(data)
            elif data > self.data:
                if self.right is None:
                    self.right = Node(data)
                else:
                    self.right.insert(data)
            else:
                self.data = data

    def find(self, data):
        if data == self.data:
            return True
        elif data < self.data:
            if self.left is None:
                return False
            else:
                return self.left.find(data)
        else:
            if self.right is None:
                return False
            else:
                return self.right.find(data)

    def find_min(self):
        current = self
        while current.left:
            current = current.left
        return current

    def delete(self, data):
        if self is None:
            return self
        if data < self.data:
            self.left = self.left.delete(data)
        elif data > self.data:
            self.right = self.right.delete(data)
        else:
            if self.left is None:
                return self.right
            elif self.right is None:
                return self.left
            temp = self.right.find_min()
            self.data = temp.data
            self.right = self.right.delete(temp.data)
        return self

def random_select_node(root):
    if root is None:
        return None
    nodes = []  # To store all nodes in the tree

    def inorder_traversal(node):
        if node:
            inorder_traversal(node.left)
            nodes.append(node)
            inorder_traversal(node.right)

    inorder_traversal(root)
    selected_node = random.choice(nodes)
    return selected_node

def main():
    # Create a binary search tree
    root = Node(50)
    root.insert(30)
    root.insert(70)
    root.insert(20)
    root.insert(40)
    root.insert(60)
    root.insert(80)

    # Randomly select a node from the tree
    selected_node = random_select_node(root)
    if selected_node:
        print("Selected node:", selected_node.data)
    else:
        print("Tree is empty.")

if __name__ == "__main__":
    main()


"""This class defines an agent for the Blokus Game"""

import random
import datetime as dt
import logging

class OutOfMoves(Exception):
    pass

class Agent:

    def __init__(self, player_id):
        self.player_id = player_id

    def get_move(self, game):
        raise RuntimeError("get_move is not implimented")

class RandomAgent(Agent):

    def get_move(self, game):
        valid_moves = list(game.get_players_moves(self.player_id))
        return self.pick_random_move(valid_moves)

    def pick_random_move(self, moves):
        if len(moves) == 0:
            raise OutOfMoves(f"Player {self.player_id} is out of moves")

        rand_int = random.randrange(len(moves))
        return moves[rand_int]

class GreedyAgent(RandomAgent):

    def get_move(self, game):
        valid_moves = list(game.get_players_moves(self.player_id))
        max_len = max([m.get_size() for m in valid_moves])
        largest_moves = list(filter(lambda m: m.get_size() == max_len, valid_moves))
        return self.pick_random_move(largest_moves)

class PointAgent(Agent):

    def __init__(self, player_id):
        self.turn_counter = 0
        super().__init__(player_id)

    def get_move(self, game):

        moves = list(game.get_players_moves(self.player_id))

        logging.info("Analizing %s potential moves on move: %s", len(moves), self.turn_counter)

        if len(moves) == 0:
            raise OutOfMoves(f"Player {self.player_id} is out of moves")

        max_move = None
        max_count = 0

        t0 = dt.datetime.now()
        for move in moves:

            game.make_move(move)
            move_num = len(list(game.get_players_moves(self.player_id)))

            if move_num >= max_count:
                max_count = move_num
                max_move = move

            game.pop()

        self.turn_counter += 1

        t1 = dt.datetime.now()

        logging.info("Completed in %s seconds", (t1 - t0).total_seconds())

        if max_move is None:
            raise ValueError(f"Not returning a Max Move Moves Length: {len(moves)}")

        return max_move

class GreedyPointAgent(Agent):

    def __init__(self, player_id):
        self.turn_counter = 0
        super().__init__(player_id)

    def get_move(self, game):

        moves = list(game.get_players_moves(self.player_id))

        biggest_piece_size = self.get_biggest_piece_size(moves)

        logging.info("Analizing %s potential moves on move: %s", len(moves), self.turn_counter)

        if len(moves) == 0:
            raise OutOfMoves(f"Player {self.player_id} is out of moves")

        max_move = None
        max_count = 0

        moves = filter(lambda m: m.get_size() == biggest_piece_size, moves)

        t0 = dt.datetime.now()
        for move in moves:

            game.make_move(move)
            move_num = len(list(game.get_players_moves(self.player_id)))

            if move_num >= max_count:
                max_count = move_num
                max_move = move

            game.pop()

        self.turn_counter += 1

        t1 = dt.datetime.now()

        logging.info("Completed in %s seconds", (t1 - t0).total_seconds())

        if max_move is None:
            raise ValueError(f"Not returning a Max Move Moves Length: {len(moves)}")

        return max_move

    def get_biggest_piece_size(self, moves):

        max_piece_size = 0

        for move in moves:

            piece_size = move.get_size()

            if piece_size > max_piece_size:
                max_piece_size = piece_size

            if max_piece_size == 5:
                return 5

        return max_piece_size

class HumanInput(Agent):

    def get_move(self, game):
        player = game.players[self.player_id]

        piece = self.pick_piece(player)

        corner = self.pick_corner(player, piece)

        move = self.pick_move(game, piece, corner)

        return move

    def pick_piece(self, player):

        pieces = player.pieces

        string = "Please Pick a piece from one of the following:\n"
        string += "\n".join(pieces)
        string += ": "

        while True:
            piece = input(string)
            if piece in pieces:
                return piece
            else:
                print("Invalid piece please try again")

    def pick_corner(self, player, piece):

        moves = player.valid_moves.get_piece_moves(piece)
        corners = list({move.corner for move in moves})
        string = "Please pick a corner from the following by its index"
        strings = [f"{str(c.p2)}, {i}" for i, c in enumerate(corners)]
        string += "\n".join(strings)

        return self.pick_by_index(corners, string)

    def pick_move(self, game, piece, corner):
        moves = game.players[self.player_id].valid_moves.get_corner_piece_moves(corner, piece)
        moves = list(moves)
        for i, move in enumerate(moves):
            b = game.board.copy()
            print(f"Move {i}")
            b.update(move)
            b.display()

        string = f"pick a move in range [0, {len(moves)}]"
        return self.pick_by_index(moves, string)

    def pick_by_index(self, values, string):

        while True:

            try:
                index = self.get_index(string)
                return values[index]

            except IndexError:
                print("Invalid Selection please try again.")

    def get_index(self, string):
        resp = input(string)
        try:
            return int(resp)

        except ValueError:
            print("Not a valid int try again")


#!/bin/python3
#
# Converts an AutoEq 10 band parametric EQ settings file to a CamillaDSP configuration file
# @bitkeeper 2021
#

import re
from base import Config2CdspConfigBase

class AutoEqImporter (Config2CdspConfigBase):

    re_gain = re.compile('([-+]?\d*\.?\d*)[ ]dB')
    re_setting = re.compile('ON PK Fc (\d*) Hz Gain ([-+]?\d*\.?\d*) dB Q (\d*\.?\d*)$')

    def __init__(self):
        super().__init__()
        self.description = 'ae2cdsp converts AutoEQ parametric EQ settings to a CamillaDSP configuration file.'

    def convert(self, file):
        gain = 0
        filters = []
        first_line = True
        for line in file:
            label, settings = line.strip().split(':')
            if label == 'Preamp':
                m = AutoEqImporter.re_gain.search(settings.strip())
                if m:
                    gain = float(m.group(1))
                    first_line = False
            elif first_line:
                raise "Error: This file isn't a Auto Eq paramatric equalizer settings file"
            elif 'Filter' in label:
                m = AutoEqImporter.re_setting.search(settings.strip())
                if m:
                    filter=dict( type= 'Peaking', freq=int(m.group(1)) , q=float(m.group(3)), gain=float(m.group(2)))
                    filters.append(filter)
        return gain, filters

if __name__ == "__main__":
    importer = AutoEqImporter()
    importer.main()


import pymongo

def test_1():
    # 实现 pymongo 数据库的增删改查
    # 连接数据库
    myclient = pymongo.MongoClient("mongodb://localhost:27017/")
    # 创建/使用数据库（有数据插入才会被创建）
    mydb = myclient["stark"]
    # 创建/使用集合（有数据插入才会被创建）
    mycol = mydb["sites"]
    try:
        # 插入一条数据
        data = {"name": "stark", "email": "starktan@163.com", "sn": 1}
        x = mycol.insert_one(data)
        # 插入的id
        print(x.inserted_id)
        # 插入多条数据
        data_list = [
            {"name": "stark", "email": "starktan@163.com", "sn": 2},
            {"_id": "my_id", "name": "stark", "email": "starktan@163.com", "sn": 3},
        ]
        x = mycol.insert_many(data_list)
        # 输出插入的所有文档对应的 _id 值
        print(x.inserted_ids)
        # 查询所有数据
        for x in mycol.find():
            print(x)
        print("*"*100)
        # 查询指定数据 （支持正则表达式）
        for x in mycol.find({"name": "stark", "sn": 3}):
            print(x)
        print("*" * 100)
        # 查询指定数据,获取指定字段 （除了 _id 你不能在一个对象中同时指定 0 和 1，如果你设置了一个字段为 0，则其他都为 1，反之亦然。）
        for x in mycol.find({"name": "stark", "sn": 3}, {"_id": 0, "name": 1}):
            print(x)
        print("*" * 100)
        # 修改第一条匹配数据
        myquery = {"sn": 1}
        newvalues = {"$set": {"name": "starktan"}}
        mycol.update_one(myquery, newvalues)
        # 修改所有匹配数据
        myquery = {"name": {"$regex": "^stark$"}}
        newvalues = {"$set": {"alexa": "123"}}
        mycol.update_many(myquery, newvalues)
        for x in mycol.find():
            print(x)
        print("*" * 100)
        # 排序
        mydoc = mycol.find().sort("sn", -1)
        for x in mydoc:
            print(x)
        print("*" * 100)
        # 修改第一条匹配数据
        mycol.delete_one({"name": "starktan"})
        # 修改第一条匹配
        mycol.delete_many({"name": "stark"})
        for x in mycol.find():
            print(x)
        print("*" * 100)
    finally:
        # 数据库列表
        dblist = myclient.list_database_names()
        print(dblist)
        # 数据库中的集合列表
        collist = mydb.list_collection_names()
        print(collist)
        # 删除 集合
        mydb.drop_collection("sites")
        # 删除 数据库
        myclient.drop_database("stark")

test_1()


from urllib import request
import re #正则表达式去除网页标签
# from fake_useragent import UserAgent
from bs4 import BeautifulSoup as bs   # 其中bs为BeautifulSoup的别名
import xlwt

bname_list = []#书名列表
author_list = []#作者
grade_list = []#评分
click_list = []#点击量

#正则表达式去除网页标签
def RemoveLabel(html):
    pre=re.compile(('>(.*)<'))
    return''.join(pre.findall(html))

def crawler(index,x):
    # 爬取数据
    url = "http://www.en8848.com.cn/fiction/fiction/gerneral/"+index

    headers = {
        # "USER-Agent":UserAgent(verify_ssl=False).random
    }
    req = request.Request(url, headers=headers)
    resp = request.urlopen(req)
    html_data = resp.read().decode()#整个网页

    soup = bs(html_data, "html.parser")  # 构建一个解析器

    nowplay = soup.find_all("div", class_="yd-book-item yd-book-item-pull-left")

    global bname_list,author_list,grade_list,click_list
    n=0
    for item in nowplay:
        bname_dict = []
        author_dict = []
        grade_dict = []
        click_dict = []
        IsGrade = True#评分和点击量的标签相同，用来做判断
        match="-"#加入日期的标签与评分和点击量相同，但是不需要，所以做筛选
        n = n + 1
        for name_item in item.find_all('h2'):
            if (x == 1):
                if (n >= 31):
                    break
            else:
                if (n >= 14):
                    break
            bname_dict = RemoveLabel(str(name_item))
            bname_list.append(bname_dict)

        for dl_item in item.find_all('div', class_="author-container"):
            if (x == 1):
                if (n >= 31):
                    break
            else:
                if (n >= 14):
                    break
            for author in dl_item.find_all("dd"):
                author_dict = RemoveLabel(str(author))
                author_list.append(author_dict)

        for dd_item in item.find_all('div', class_="price-container"):
            if (x == 1):
                if (n >= 31):
                    break
            else:
                if (n >= 14):
                    break
            for price in dd_item.find_all("dd"):
                if (IsGrade):
                    grade_dict = RemoveLabel(str(price))
                    if(match in grade_dict):
                        pass
                    else:
                        grade_list.append(grade_dict)
                        IsGrade = False
                else:
                    click_dict = RemoveLabel(str(price))
                    if (match in click_dict):
                        pass
                    else:
                        click_list.append(click_dict)
                        IsGrade = True

def excel():
    global  bname_list,author_list,grade_list,click_list
    workbook=xlwt.Workbook(encoding='utf-8')
    worksheet=workbook.add_sheet('book',cell_overwrite_ok=True)
    for i in range(0,4):
        for j in range(0,len(bname_list)+1):
            if(i==0):
                if(j==0):
                    worksheet.write(j, i, '书名')
                else:
                    worksheet.write(j, i,bname_list[j-1])
            elif(i==1):
                if (j == 0):
                    worksheet.write(j, i, '作者')
                else:
                    worksheet.write(j, i, author_list[j - 1])
            elif(i==2):
                if (j == 0):
                    worksheet.write(j, i, '评分')
                else:
                    worksheet.write(j, i, grade_list[j - 1])
            else:
                if (j == 0):
                    worksheet.write(j, i, '点击量')
                else:
                    worksheet.write(j, i, click_list[j - 1])
    workbook.save('book.xls')

crawler("index.html",1)
crawler("index_2.html",2)
excel()


"""This script can be used to rename files in a folder that are numbered such as 1.xyz, 20.xyz and should be renamed to 01.xyz, 20.xyz..."""

import os
import glob

files = glob.glob('/Volumes/Transcend/data_sets/dftb/*.xyz')
# files = glob.glob('/Users/walfits/Desktop/test_dir/*.xyz')
padding = "0"

for file in files:
    file_name = file.split("/")[-1]
    file_idx = file_name.split(".")[0]
    n = 5 - len(file_idx)
    new_idx = n * padding + file_idx

    os.rename(file, '/Volumes/Transcend/data_sets/dftb/{}.xyz'.format(new_idx))
    # os.rename(file, '/Users/walfits/Desktop/test_dir/{}.xyz'.format(new_idx))


import json
from calendar import monthrange
from dataclasses import dataclass, field
from datetime import date, datetime
from math import ceil
from typing import Any, NamedTuple
from zoneinfo import ZoneInfo

import typer
from rich import print
from rich.prompt import Prompt

from reportgen.utils.custom_types import CurrentAge, PatientData
from reportgen.utils.files import load_diagnostic, load_patient

def current_age(birthday: str) -> CurrentAge:
    start = datetime.strptime(birthday, "%Y-%m-%d %H:%M:%S").date()
    today = datetime.now(tz=ZoneInfo("America/Lima")).date()

    difference = today - start

    years = difference.days // 365
    months = (difference.days % 365) // 30
    days = (difference.days % 365) % 30

    return CurrentAge(
        years=abs(years),
        months=abs(months),
        days=abs(days),
        b=start,
        format=f"{start.day}     {start.month}     {start.year}",
        second_format=f"{start.day}/{start.month}/{start.year}",
    )

def input_patients(blocks: int) -> list[PatientData]:
    patients: list[PatientData] = []

    while True:
        print(f"\n[yellow]Queda(n) {blocks} espacio(s) en la hoja.[/yellow]")

        add_patient = typer.confirm("Agregar nuevo paciente?")
        if not add_patient:
            break

        dni = Prompt.ask("\n[blue]Número de DNI[/blue]")
        weight = Prompt.ask("[blue]Peso en kg[/blue]")
        size = Prompt.ask("[blue]Talla en cm[/blue]")
        hb = Prompt.ask("[blue]Valor de Hb[/blue]")

        patient = load_patient(dni=dni)
        age = current_age(birthday=patient.birthday)
        his = load_diagnostic(age=age)

        patients.append(
            PatientData(
                personal={
                    "dni": dni,
                    "weight": weight,
                    "size": size,
                    "hb": hb,
                },
                identification=patient,
                his=his,
                age=age,
            )
        )

        blocks -= ceil(len(his) / 3)

    return patients

GENDER = {0: "NO ESPECIFICADO", 1: "MASCULINO", 2: "FEMENINO"}

INSURANCE = {
    0: "NO ESPECIFICADO",
    1: "SIS",
    2: "ESSALUD",
    3: "OTRO",
}

class Age(NamedTuple):
    years: int
    months: int
    days: int

    def __str__(self) -> str:
        return (
            f"{self.years} año(s), {self.months} mes(es) y {self.days} día(s)"
        )

class Control(NamedTuple):
    cie: str
    description: str
    dx: str
    lab: tuple[str, str, str]

@dataclass
class TempPatient:
    dni: str
    hlc: str = field(init=False)
    district: str = field(init=False)
    establishment: str = field(init=False)
    sector: str = field(init=False)
    insurance: str = field(init=False)
    full_name: str = field(init=False)
    gender: str = field(init=False)
    birthday: date = field(init=False)
    age: Age = field(init=False)
    appointment: str = field(init=False)
    type_of_birth: int = field(init=False)
    diagnostic: list[Control] = field(init=False)
    age_diagnostic: Age = field(init=False)

    def __post_init__(self) -> None:
        patient = self.load_from_json()

        self.hlc = patient["hlc"]
        self.district = patient["district"]
        self.establishment = patient["establishment"]
        self.sector = patient["sector"]
        self.insurance = INSURANCE[int(patient["insurance"])]
        self.full_name = f"{patient['father_last_name']} {patient['mother_last_name']}, {patient['names']}"
        self.gender = GENDER[int(patient["gender"])]
        self.birthday = datetime.strptime(
            patient["birthday"], "%Y-%m-%d %H:%M:%S"
        ).date()
        self.age = self.current_age()
        self.appointment = patient["appointment"]
        self.type_of_birth = patient["type_of_birth"]
        self.diagnostic = self.load_diagnostic()

    def load_from_json(self) -> Any:
        with open("database/people.json", encoding="utf-8") as f:
            patients = json.load(f)

        return patients[f"{self.dni}"]

    def current_age(self) -> Age:
        year, month, day, *_ = datetime.now(
            tz=ZoneInfo("America/Lima")
        ).timetuple()

        if day < self.birthday.day:
            month -= 1
            day += monthrange(self.birthday.year, self.birthday.month)[1]

        if month < self.birthday.month:
            year -= 1
            month += 12

        return Age(
            year - self.birthday.year,
            month - self.birthday.month,
            day - self.birthday.day,
        )

    def load_diagnostic(self) -> list[Control]:
        with open("database/codes.json", encoding="utf-8") as f:
            diagnostics = json.load(f)

        # h = Age(0, 0, 0)

        try:
            if self.age.years == 0 and self.age.months == 0:
                raw_diagnostic = diagnostics["RN"][f"{self.age.days}_days"]
            elif self.age.years > 5:
                raw_diagnostic = diagnostics["5_years"][
                    f"{self.age.months}_months"
                ]
            else:
                raw_diagnostic = diagnostics[f"{self.age.years}_years"][
                    f"{self.age.months}_months"
                ]
        except KeyError:
            # for i in range(1, 8):
            # print(i)
            raw_diagnostic = []
            # print(key)

        return [
            Control(
                cie=d[0],
                description=d[1],
                dx=d[2],
                lab=tuple(d[3]),  # type: ignore
            )
            for d in raw_diagnostic
        ]


from operator import mod
from django.db import models
from django.core.exceptions import ValidationError
from django.utils.translation import gettext_lazy as _
import ipaddress
from .helperfunctions import validators as hvalidator

def validate_ip(address):
    # using custom validator in order to allow for check in private,public ip, ranges, locals, IPv6 etc
    try:
        ip = ipaddress.ip_address(address)
    except ValueError:
        raise ValidationError(
            _('%(value)s is not an IP address'),params={'value':address}
            )

# Create your models here.
class Device(models.Model):
    # ip = models.GenericIPAddressField is the more common declartion in django of an field representing IP Address
        # and it comes with built in validation and some usefull helper functions
    ip = models.CharField(max_length=15,unique=True,validators=[validate_ip])
    customer_code = models.CharField(max_length=255,default="",unique=True)

    def __str__(self):
        return f"{self.customer_code}  {self.ip}"

class ProvisioningStatus(models.Model):
    device = models.OneToOneField(Device, to_field='ip',db_column='ip',on_delete=models.CASCADE,primary_key=True)
    status = models.BooleanField(default=False)

    def __str__(self):
        return f"CUST:{self.device.customer_code} IP:{self.device.ip} STATUS:{self.status}"


from django import forms
from models import *
import re
from django.core import validators
from django.forms import CharField, Textarea, ValidationError
from django.utils.translation import ugettext as _
email_separator_re = re.compile(r'[,;]+')

def _is_valid_email(email):
    try:
        validators.validate_email(email)
        return True
    except forms.ValidationError:
        return False

class EmailsListField(CharField):
    widget = Textarea
    def clean(self, value):
        super(EmailsListField, self).clean(value)
        emails = email_separator_re.split(value)
        if not emails:
            raise ValidationError(_(u'Enter at least one e-mail address.'))
        for email in emails:
            if not _is_valid_email(email.strip()):
                raise ValidationError(_('%s is not a valid e-mail address.') % email)
        return emails

class CreateLeagueForm(forms.Form):
    name = forms.CharField(max_length = 30, label='League Name',
        widget=forms.TextInput(attrs={'class':'form-control', 'placeholder': 'League Name'}))
    description = forms.CharField(max_length = 200, label='League Description',
        widget=forms.TextInput(attrs={'class':'form-control', 'placeholder': 'Description'}))
    email_ids = EmailsListField(label='Invite Members',
    widget=forms.Textarea(attrs={'class':'form-control','placeholder': 'Enter Email address seperated by comma', 'cols': 30, 'rows': 10}))

    def clean(self):
        cleaned_data = super(CreateLeagueForm, self).clean()
        name = cleaned_data.get('name')
        description = cleaned_data.get('description')
        email_ids = cleaned_data.get('email_ids')
        return cleaned_data

class JoinLeagueForm(forms.Form):
    uniquecode = forms.CharField(max_length = 30, label='Enter League Unique Code',
        widget=forms.TextInput(attrs={'class':'form-control', 'placeholder': 'UniqueCode'}))

    def __init__(self, *args, **kwargs):
        self.user = kwargs.pop('user', None)
        self.tourn = kwargs.pop('tourn', None)
        self.g_type = kwargs.pop('gt', None)
        self.season = kwargs.pop('season', None)
        super(JoinLeagueForm, self).__init__(*args, **kwargs)

    def clean(self):
        cleaned_data = super(JoinLeagueForm, self).clean()
        uniqueCode = cleaned_data.get('uniqueCode')
        return cleaned_data

    def clean_uniquecode(self):
        uniquecode = self.cleaned_data.get('uniquecode')
        if not GameLeague.objects.filter(uniqueCode__exact=uniquecode):
            raise forms.ValidationError("Invalid UniqueCode")
        if not GameLeague.isValidCode(uniquecode, self.tourn, self.season, self.g_type):
            raise forms.ValidationError("UniqueCode does not match this tournament or game type")
        if GameLeague.isUserExist(self.user, uniquecode):
            raise forms.ValidationError("You have already joined this league")
        return uniquecode


from ....utils.utils import is_blender_4
from ...shader_base import Nodes
from ..source1_shader_base import Source1ShaderBase

class LightmapGeneric(Source1ShaderBase):
    SHADER = 'lightmappedgeneric'

    @property
    def isskybox(self):
        return self._vmt.get_int('%' + 'compilesky', 0) + self._vmt.get_int('%' + 'compile2Dsky', 0)

    @property
    def basetexture(self):
        texture_path = self._vmt.get_string('$basetexture', None)
        if texture_path is not None:
            return self.load_texture_or_default(texture_path, (0.3, 0, 0.3, 1.0))
        return None

    @property
    def bumpmap(self):
        texture_path = self._vmt.get_string('$bumpmap', None)
        if texture_path is not None:
            image = self.load_texture_or_default(texture_path, (0.6, 0.0, 0.6, 1.0))
            if self.ssbump:
                image = self.convert_ssbump(image)
            image.colorspace_settings.is_data = True
            image.colorspace_settings.name = 'Non-Color'
            return image
        return None

    @property
    def ssbump(self):
        return self._vmt.get_int('$ssbump', 0) == 1

    @property
    def phong(self):
        return self._vmt.get_int('$phong', 0) == 1

    @property
    def alpha(self):
        return self._vmt.get_int('$alpha', 0) == 1

    @property
    def alphatest(self):
        return self._vmt.get_int('$alphatest', 0) == 1

    @property
    def translucent(self):
        return self._vmt.get_int('$translucent', 0) == 1

    def create_nodes(self, material_name):
        if super().create_nodes(material_name) in ['UNKNOWN', 'LOADED']:
            return

        if self.isskybox:
            self.bpy_material.shadow_method = 'NONE'
            self.bpy_material.use_backface_culling = True
        material_output = self.create_node(Nodes.ShaderNodeOutputMaterial)
        shader = self.create_node(Nodes.ShaderNodeBsdfPrincipled, self.SHADER)
        self.connect_nodes(shader.outputs['BSDF'], material_output.inputs['Surface'])

        basetexture = self.basetexture

        if basetexture:
            basetexture_node = self.create_and_connect_texture_node(basetexture,
                                                                    shader.inputs['Base Color'],
                                                                    name='$basetexture')

            if self.alphatest:
                self.bpy_material.blend_method = 'HASHED'
                self.bpy_material.shadow_method = 'HASHED'
                self.connect_nodes(basetexture_node.outputs['Alpha'], shader.inputs['Alpha'])
            if self.translucent:
                self.bpy_material.blend_method = 'BLEND'
                self.bpy_material.shadow_method = 'HASHED'
                self.bpy_material.use_backface_culling = True
                self.bpy_material.show_transparent_back = False
                self.connect_nodes(basetexture_node.outputs['Alpha'], shader.inputs['Alpha'])

        bumpmap = self.bumpmap
        if bumpmap and not self.ssbump:
            bumpmap_node = self.create_node(Nodes.ShaderNodeTexImage, '$bumpmap')
            bumpmap_node.image = bumpmap

            normalmap_node = self.create_node(Nodes.ShaderNodeNormalMap)

            self.connect_nodes(bumpmap_node.outputs['Color'], normalmap_node.inputs['Color'])
            self.connect_nodes(normalmap_node.outputs['Normal'], shader.inputs['Normal'])

        if not self.phong:
            if is_blender_4():
                shader.inputs['Specular IOR Level'].default_value = 0
            else:
                shader.inputs['Specular'].default_value = 0

class ReflectiveLightmapGeneric(LightmapGeneric):
    SHADER = 'lightmappedreflective'

class SDKLightmapGeneric(LightmapGeneric):
    SHADER = 'sdk_lightmappedgeneric'


from detection_msgs.msg import BoundingBoxes
import numpy as np
import rospy as ros
from sensor_msgs import point_cloud2
from sensor_msgs.msg import PointCloud2
from robotica.msg import Coord
import open3d as o3d
import time

class vision():

    def __init__(self):
        ## Matrice di rotazione da camera frame a world frame
        self.w_R_c = np.array([[0.0, -0.49948, 0.86632],
                               [-1.0, 0.0, 0.0],
                              [-0.0, -0.86632, -0.49948]])
        ## Vettore di traslazione da robot frame a camera frame
        self.x_c = np.array([-0.4, 0.59, 1.4])

        self.point_cloud = PointCloud2()
        self.voxel_size = 0.003
        self.models="/home/lucaboschiero/ros_ws/src/locosim/ros_impedance_controller/worlds/models"

    def pointcloud_callback(self, msg):
        # Salva la pointcloud della camera
        self.point_cloud = msg

    def pointCloud_fpfh(self, pointCloud):

        #La pointcloud viene sottocampionata
        pointCloud_down = o3d.geometry.PointCloud.voxel_down_sample(pointCloud, self.voxel_size)

        # Calcolare le normali per ogni punto nella point cloud ridotta
        radius = self.voxel_size * 2
        o3d.geometry.PointCloud.estimate_normals(
            pointCloud_down,
            o3d.geometry.KDTreeSearchParamHybrid(radius=radius, max_nn=30))

        radius = self.voxel_size * 5
        # Calcola le feature FPFH sulla point cloud ridotta
        pointCloud_fpfh = o3d.pipelines.registration.compute_fpfh_feature(
            pointCloud_down,
            o3d.geometry.KDTreeSearchParamHybrid(radius=radius, max_nn=100))

        return pointCloud_down, pointCloud_fpfh

    def registration(self, inputPointCloud_down, stlPointCloud_down, inputPointCloud_fpfh, stlPointCloud_fpfh):
        # Esegue la registrazione tra due point cloud utilizzando Open3D

        # Esegue la registrazione RANSAC basata sulla corrispondenza delle feature
        distance_threshold = self.voxel_size * 1.5

        result = o3d.pipelines.registration.registration_ransac_based_on_feature_matching(
            inputPointCloud_down, stlPointCloud_down, inputPointCloud_fpfh, stlPointCloud_fpfh, True, distance_threshold,
            o3d.pipelines.registration.TransformationEstimationPointToPoint(False), 4, [
                o3d.pipelines.registration.CorrespondenceCheckerBasedOnEdgeLength(0.9),
                o3d.pipelines.registration.CorrespondenceCheckerBasedOnDistance(
                    distance_threshold)
            ], o3d.pipelines.registration.RANSACConvergenceCriteria(1000000, 500))

        distance_threshold = self.voxel_size * 0.4
        result1 = o3d.pipelines.registration.registration_icp(
            inputPointCloud_down, stlPointCloud_down, distance_threshold, result.transformation,
            o3d.pipelines.registration.TransformationEstimationPointToPlane())

        return result1

    def getModelPath(self, cl):

        # In base alla classe del blocco ritorna il path del modello stl

        if cl == "1" :
            return "/model0/meshes/X1-Y1-Z2.stl"

        elif cl == "2" :
            return "/model1/meshes/X1-Y2-Z1.stl"

        elif cl == "3" :
            return "/model2/meshes/X1-Y2-Z2.stl"

        elif cl == "4" :
            return "/model3/meshes/X1-Y2-Z2-CHAMFER.stl"

        elif cl == "5" :
            return "/model4/meshes/X1-Y2-Z2-TWINFILLET.stl"

        elif cl == "6" :
            return "/model5/meshes/X1-Y3-Z2.stl"

        elif cl == "6-FILLER" :
            return "/model6/meshes/X1-Y3-Z2-FILLET.stl"

        elif cl == "7" :
            return "/model7/meshes/X1-Y4-Z1.stl"

        elif cl == "8" :
            return "/model8/meshes/X1-Y4-Z2.stl"

        elif cl == "9" :
            return "/model9/meshes/X2-Y2-Z2.stl"

        elif cl == "9-FILLER" :
            return "/model10/meshes/X2-Y2-Z2-FILLET.stl"

    def pose_estimation(self, points, object_class):
        #Trasforma i punti della pointcloud di input in un vettore open3d
        points = np.asarray(points)
        inputPointCloud = o3d.geometry.PointCloud()
        inputPointCloud.points = o3d.utility.Vector3dVector(points)

        # Ottiene il path in base al tipo di blocco
        model_path = self.getModelPath(object_class)
        # Legge il file .stl
        stl_file_path = self.models + model_path
        try:
            print(stl_file_path)
            mesh = o3d.io.read_triangle_mesh(stl_file_path)
        except Exception as e:
            print(f"Error reading STL file: {str(e)}")
            return None

        # Crea una pointcloud a partire da una mesh tridimensionale
        nPoints = int (np.size(points))
        mesh_points = mesh.sample_points_uniformly(number_of_points=nPoints)
        stlPointCloud = o3d.geometry.PointCloud()
        stlPointCloud.points = mesh_points.points

        # Sottodimensiona le due pointcloud e estrae le fpfh features
        inputPointCloud_down, inputPointCloud_fpfh = self.pointCloud_fpfh(inputPointCloud)
        stlPointCloud_down, stlPointCloud_fpfh = self.pointCloud_fpfh(stlPointCloud)

        # Esegue la registrazione delle pointcloud
        result = self.registration(inputPointCloud_down, stlPointCloud_down, inputPointCloud_fpfh, stlPointCloud_fpfh)

        # Ottiene la matrice di rotazione
        R = result.transformation[:3, :3]

        return R

    def detection_callback(self, msg):

        # Topic dove pubblica le coordinate dei blocchi e la classe
        pubco = ros.Publisher("/coordinates", Coord, queue_size=100)

        # Crea un messaggio dove salvare i dati da pubblicare
        coordinate = Coord()

        print("Detection time: ",msg.time)

        #salva il tempo di inizio
        start_time = time.time()

        # Scorre tra gli elementi trovati da Yolo
        for i in range(msg.count):
            points_list = []

            x_min = msg.bounding_boxes[i].xmin
            x_max = msg.bounding_boxes[i].xmax
            y_min = msg.bounding_boxes[i].ymin
            y_max = msg.bounding_boxes[i].ymax

            # Riceve i punti della bounding box del blocco e calcola u e v
            u = int((msg.bounding_boxes[i].xmin + msg.bounding_boxes[i].xmax) / 2)
            v = int((msg.bounding_boxes[i].ymin + msg.bounding_boxes[i].ymax) / 2)
            cl = (msg.bounding_boxes[i].Class)

            # Trasnforma u e v in coordinate del camera frame
            for data in point_cloud2.read_points(self.point_cloud, field_names=['x', 'y', 'z'], skip_nans=False, uvs=[(u, v)]):
                points_list.append([data[0], data[1], data[2]])
                print("Data Optical frame: ", points_list)

            # Trasforma le coordinate nel world frame
            pointW = self.w_R_c.dot(points_list[0]) + self.x_c

            # Salva x, y, z e la classe del blocco per poi pubblicarle
            coordinate.x = pointW[0]
            coordinate.y = pointW[1]
            coordinate.z = pointW[2]
            coordinate.cl = cl

            # Genera un vettore di punti
            uv = [(x, y) for y in range(y_min, y_max + 1) for x in range(x_min, x_max + 1)]

            # Trasforma i punti in coordinate x, y e z rispetto al camera frame
            point_region = []
            for data in point_cloud2.read_points(self.point_cloud, field_names=['x', 'y', 'z'], skip_nans=False, uvs=uv):
                point_region.append([data[0], data[1], data[2]])

            # Trasforma i punti dal frame della camera al world frame
            points = []
            for point in point_region:
                points.append(self.w_R_c.dot(point) + self.x_c)

            # Ottiene il centro dei punti
            pointMiddle = np.mean(points, axis=0)

            # Applica l'offset di tutti i punti dal centro
            pointsOffset = []
            for point in points:
                pointsOffset.append((point - pointMiddle))

            # Ottiene la matrice di rotazione
            rotation_matrix = self.pose_estimation(pointsOffset, cl)
            print("Rotation matrix: ",rotation_matrix)

            # Inserisce nel messaggio la matrice di rotazione
            coordinate.R = rotation_matrix.flatten().tolist()

            end_time = time.time()
            # Calcola il tempo trascorso in secondi
            total_time = end_time - start_time

            print("Orientation detection time:", total_time, "secondi")

            # Pubblica il messaggio
            pubco.publish(coordinate)

def main(p):

    # Vengono definiti i topic a cui è sottoscritto il codice
    ros.init_node("listener")

    ros.Subscriber("/yolov5/detections", BoundingBoxes, p.detection_callback)
    ros.Subscriber("/ur5/zed_node/point_cloud/cloud_registered", PointCloud2, p.pointcloud_callback)

    ros.spin()

if __name__ == '__main__':

    p = vision()
    try:
        main(p)
    except ros.ROSInterruptException:
        pass


from .Generator import Generator
import os
import webbrowser

class GeneratorHTMLLists(Generator):
  def __init__(self):
    super().__init__()
    self.ignoreList = [
      'Component', 'Expand'
    ]

  def on_process(self, elements, out_folder):
    self.out_file = os.path.join(out_folder, 'html_generator_out/index.html')
    os.makedirs(os.path.dirname(self.out_file), exist_ok=True)
    #print('#######ELEMENTS', elements)
    generate_code(elements, self.out_file)

  def show(self):
    webbrowser.get('firefox').open(self.out_file)

main_grid_size = (8,12)
main_grid_subsize = 8
grid={}

randomID = 0
containerStack = []
ignoreList = [
  'Component', 'Expand'
]

def getHeader():
  return """
  <!doctype html>

      <meta charset="utf-8">
      <meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">

      <title>Hello, world!</title>

    """

def getElement(tag, attributes="", clss="", style="", content="", obj=None):
  attributes = " ".join(attributes)
  return '<{0} {1} class="{4}" style="{3}" > {2}</{0}>'.format(tag,attributes, content, style, clss)

def clamp(value, a, b):
  if value  b:
    return b
  return value

def getSpan(xMin, xMax, Value, span_width):
  b = xMax-xMin
  a = Value-xMin
  a = clamp(a, 0, b)
  span_width1 = span_width-1
  return clamp(int(a/b*span_width),1,99999)

def getElementSpanString(obj):
  return 'class="col-md-{0}"'.format(getElementSpan(obj))

def getElementSpan(obj):
  if obj == None: return ''
  container = containerStack[-1]
  xMin = container['x']
  xMax = xMin + container['w']

  span_width = container['grid-size']

  oXMin = obj['x']
  oXMax = oXMin + obj['w']
  s1 = getSpan(xMin,xMax, oXMin, span_width)
  s2 = getSpan(xMin,xMax, oXMax, span_width)

  span = s2-s1 + 1
  wC = container['w']
  wO = obj['w']

  print(span_width)
  return clamp( int(wO/wC * (span_width-1))+1, 1, span_width)
  #return span

def closeBody():
  return '
\n'

def wIMG(o):
  global randomID
  randomID+=1
  #return getElement('div', clss="fixed-size", style='background-color: red;', obj=o)
  return getElement('div', ['class="img"'], style='background-image:url(https://picsum.photos/200/300?random={});'.format(randomID), obj=o)

def wTF(o):
  #return getElement('div', clss="fixed-size", style='background-color: cyan;', obj=o)
  return getElement('input', ['type="text"'], obj=o)

def wTB(o):
  #return getElement('div', clss="fixed-size", style='background-color: black;', obj=o)
  return getElement('p', content="Some Text.....", obj=o)

def wB(o):
  #return getElement('div', clss="fixed-size", style='background-color: blue;', obj=o)
  return getElement('Button', content="Button", obj=o)

def wCB(o):
  #return getElement('div', clss="fixed-size", style='background-color: green;', obj=o)
  return getElement('input', ['type="checkbox"'], obj=o)

def wE(o):
  #return getElement('div', clss="fixed-size", style='background-color: pink;', obj=o)
  return getElement('b', content='UNKNOWN {0}'.format(o['class']), obj=o)

def select_content(count):
  template = '<option value="{0}">{1} </option>'
  text = ''
  for i in range(count):
    text += template.format(i, 'Option {0}'.format(i))
  return text

def wD(o):
  #return getElement('div', clss="fixed-size", style='background-color: orange;', obj=o)
  return getElement('select', ['type="select"'], content=select_content(5), obj=o)

def wRB(o):
  #return getElement('div', clss="fixed-size", style='background-color: yellow;', obj=o)
  return getElement('input', ['type="radio"'], obj=o)

def beginContainer(o):
  vertical = o.__contains__('orientation') and o['orientation'] == 'v'
  user = 'user' if o.__contains__('user') else ''
  return """

      """.format('column' if vertical else 'row', user)

def endContainer(o):
  return """

"""

def writeObj(file, obj):
  switch = {
    'Textfield': wTF,
    'Picture': wIMG,
    'Button': wB,
    'TextBlock': wTB,
    'Checkbox': wCB,
    'RadioButton': wRB,
    'Dropdown': wD,
  }
  #if(ignoreList.__contains__(obj['class'])):
  #  return

  option = wE
  if switch.__contains__(obj['class']):
    option = switch[obj['class']]

  file.write(option(obj))

def snap(value, base):
  return int(value/base)

def snapToGrid(objs, size=1):
  for obj in objs:
    x = obj['x']
    y = obj['y']
    xMax = x + obj['w']
    yMax = y + obj['h']
    x = snap(x, size)
    y = snap(y, size)
    xMax = snap(xMax, size)
    yMax = snap(yMax, size)
    obj['x'] = x
    obj['y'] = y
    obj['w'] = xMax - x
    obj['h'] = yMax - y

def parseContainer(file, objs):
  parent = containerStack[-1]
  snapToGrid(objs)
  #objs = sorted(objs, key=lambda obj: (obj['y'], obj['x']))
  #print([ [x['class'], x['x'], x['w']] for x in objs])
  for obj in objs:
    if obj['class'] == 'Container':
      file.write(beginContainer(obj))

      if obj.__contains__('childs'):

        containerStack.append(obj)
        parseContainer(file, obj['childs'])
        containerStack.pop()
        file.write(endContainer(obj))

    else:
      writeObj(file, obj)

def generate_code(objects, out_file):
  with open(out_file, 'w') as indexFile:
    indexFile.write(getHeader())
    containerStack.append(objects[0])
    objs = objects[0]['childs']
    # #print(objs)

    # maxW = max(objs, key=lambda o: o['x']+o['w'])
    # maxW = maxW['x']+maxW['w']
    # maxH = max(objs, key=lambda o: o['y']+o['h'])
    # maxH = maxH['y']+maxH['h']
    # containerStack.append(
    #   {
    #     'x':0,
    #     'y':0,
    #     'w': maxW,
    #     'h': maxH,
    #     'grid-size': main_grid_size
    #   }
    # )
    #snapToGrid(containerStack)
    parseContainer(indexFile, objs)
    indexFile.write(closeBody())


"""
文件说明
tensorflow计算过程可以表示为一个计算图（有向图），类似于流程图，可以直观看出数据的计算流程
每一个运算操作可以视为一个节点，每一个节点可以有任意输入输出
张量（tensor）就是在边中流动（flow）的数据，可以理解为数组，
计算图---tensorflow的计算模型

创建会话的两种方式：
sess = tf.compat.v1.Session
sess.run()
sess.close()

with/as环境上下文管理器

直接构建默认会话：tf.InteractiveSession()

eval和run的使用：用于运行会话（计算张量的值）
sess.run(result)
result.eval()
如果sess不是默认的会话，那么在执行的时候需要指明会话
result.eval(session=sess)
区别：
t.eval() 等价于 tf.get_default_session().run(t)
run()函数可以传入多个需要计算的张量，eval只能计算一个张量就调用一次eval函数

Session的参数配置：
config参数：配置会话的并行线程数、GPU分配策略、运算超时时间
ConfigProto()函数配置Session：
config = tf.ConfigSession(log_device_placement=True, allow_soft_lacement=True)
log_device_placement:日志中将会记录运行每个节点所用的计算设备，然后打印出来
allow_soft_lacement：当运行无法在GPU上执行的时候转移到CPU上执行
sess = tf.Session(config = config)

placeholder机制：

"""
import tensorflow as tf
# 使用graph创建一个计算图
g1 = tf.Graph()
# 设置为默认计算图
with g1.as_default():
    # 创建变量设置初始值
    a = tf.compat.v1.get_variable("a", [2], initializer=tf.ones_initializer())
    b = tf.compat.v1.get_variable("b", [2], initializer=tf.zeros_initializer())
# 开启会话，初始化计算图中的所有变量
with tf.compat.v1.Session(graph=g1) as sess:
    tf.compat.v1.global_variables_initializer().run()
    # 控制变量空间
    with tf.compat.v1.variable_scope("", reuse=True):
        print(sess.run(tf.compat.v1.get_variable("a")))  # [1. 1.]
        print(sess.run(tf.compat.v1.get_variable("b")))  # [0. 0.]

01 tensorflow编程策略/01 Computation Graph.py


# -*- coding: utf-8 -*-
"""
Created on Thu Nov 11 12:08:21 2021

@author: anshu
"""

# OS native files = txt/csv/tsv/json

# Writing data to a new file
data = """ Hi
My name is Anshu, I hope you are doing good.
How can I help you today. Thank you for calling"""

file = open("mydata.txt",'w')# w = write mode
file.write(data)
file.close()

# appending data to an existing file

data = """
Hy thanks for connecting
Thank you for calling today.
"""
file = open("mydata.txt",'a')# a = append mode
file.write(data)
file.close()

# reading data from a file

file = open('mydata.txt','r')
data = file.read() # reading whole content of file as one string
file.close()

print(data)

# reading each line sepearately

file = open('mydata.txt','r')
data = file.readlines() # a list of strings, each string = one line
file.close()

for line in data:print(line)


# -*- coding: utf-8 -*-
# @Author: far
# @Date:   2017-02-26 20:37:52
# @Last Modified by:   wujiyu
# @Last Modified time: 2017-02-28 11:22:52

errcode  = type('new', (object,), {})
desc = {}

errcode.ok = 0
desc[errcode.ok] = "成功"
errcode.wrong_user = 1
desc[errcode.wrong_user] = "登录用户名或者密码错误"
errcode.not_avilable_tabs = 2
desc[errcode.not_avilable_tabs] = "没有可订餐日期"
errcode.not_right_time_tabs = 3
desc[errcode.not_right_time_tabs] = "当前时间大于订餐日期"
errcode.not_index_tabs = 4
desc[errcode.not_index_tabs] = "订餐项大于当前可订项"
errcode.not_recommend = 5
desc[errcode.not_recommend] = "没有推荐菜品"
errcode.not_filter_recommend = 6
desc[errcode.not_filter_recommend] = "筛选后没有合适的推荐菜品"
errcode.money_dish_error = 7
desc[errcode.money_dish_error] = "没有找到合适价格的菜品"
errcode.order_error = 8
desc[errcode.order_error] = "订餐失败"


# Definition for singly-linked list.
class ListNode:
    def __init__(self, val=0, next=None):
        self.val = val
        self.next = next

# we need to use the merge two lists method
# first check if the lists has only 1 list else
# take two list at a time and merge them appending on to mergedlists
# do this until their is only one list

class Solution:
    def mergeKLists(self, lists: list[ListNode]) -> ListNode:
        if not lists or len(lists) == 0:
            return None

        while len(lists) > 1:
            mergedLists = []
            for i in range(0, len(lists), 2):
                l1 = lists[i]
                l2 = lists[i + 1] if (i + 1) < len(lists) else None
                mergedLists.append(self.mergeList(l1, l2))
            lists = mergedLists
        return lists[0]

    def mergeList(self, l1, l2):
        dummy = ListNode()
        tail = dummy

        while l1 and l2:
            if l1.val < l2.val:
                tail.next = l1
                l1 = l1.next
            else:
                tail.next = l2
                l2 = l2.next
            tail = tail.next
        if l1:
            tail.next = l1
        if l2:
            tail.next = l2
        return dummy.next


import torch
import torch.nn as nn

def double_conv(in_channels, out_channels):
    return nn.Sequential(
        nn.Conv2d(in_channels, out_channels, 3, padding=1),
        nn.ReLU(inplace=True),
        nn.Conv2d(out_channels, out_channels, 3, padding=1),
        nn.ReLU(inplace=True))

class UNet(nn.Module):

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

        self.conv_down1 = double_conv(3, 64)
        self.conv_down2 = double_conv(64, 128)
        self.conv_down3 = double_conv(128, 256)
        self.conv_down4 = double_conv(256, 512)

        self.maxpool = nn.MaxPool2d(2)
        self.upsample = nn.Upsample(scale_factor=2, mode='bilinear', align_corners=True)

        self.conv_up3 = double_conv(256 + 512, 256)
        self.conv_up2 = double_conv(128 + 256, 128)
        self.conv_up1 = double_conv(128 + 64, 64)

        self.last_conv = nn.Conv2d(64, n_classes, kernel_size=1)

    def forward(self, x):
        # Batch - 1d tensor.  N_channels - 1d tensor, IMG_SIZE - 2d tensor.
        # Example: x.shape >>> (10, 3, 256, 256).

        conv1 = self.conv_down1(x)
        x = self.maxpool(conv1)
        conv2 = self.conv_down2(x)
        x = self.maxpool(conv2)
        conv3 = self.conv_down3(x)
        x = self.maxpool(conv3)
        x = self.conv_down4(x)
        x = self.upsample(x)

        x = torch.cat([x, conv3], dim=1)

        x = self.conv_up3(x)
        x = self.upsample(x)
        x = torch.cat([x, conv2], dim=1)

        x = self.conv_up2(x)
        x = self.upsample(x)
        x = torch.cat([x, conv1], dim=1)

        x = self.conv_up1(x)

        out = self.last_conv(x)
        out = torch.sigmoid(out)

        return out


from string import Template

const_base = "data/const/degree_order_{}_{}.pkl"

#LRF settings
N = 500
minc = 100
maxc = 100
mu = 0.3
k = 5
#k = 10
#maxk = 20
maxk = 50
t1 = 2
t2 = 1

name_tmp = Template("LRF_${N}_${k}_${maxk}_${minc}_${maxc}_${mu}")
lrf_data_label = name_tmp.substitute(N=N, k=k, maxk=maxk, minc=minc, maxc=maxc,
                           mu=mu)

data_label = lrf_data_label

#data_label = "gn_1000_4"
#data_label = "polblogs"
exp_name = "{}_degree_order_asc".format(data_label)
print("*********************", exp_name)

#General settings
#densities =[0, 0.05, 0.1, 0.15, 0.2, 0.25, 0.3]
densities = [0, 0.01, 0.02, 0.03, 0.04, 0.05, 0.06, 0.07, 0.08, 0.09, 0.1]
trials = 5
K = 5
lr_adam = 0.01
lr_sgd = 0.01
threshold = 10e-9
threads = 8
used_models = ["abs_adam","update_rule"]
#used_models = ["abs_adam", "update_rule"]
#used_models = ["abs_adam"]
max_iters = 1000

mlambda = 2


import torch
import torch.nn.functional as F
from tqdm import tqdm
import numpy as np

class LSTMModel(torch.nn.Module):
    def __init__(self, diag_vocab_size, med_vocab_size, diag_embedding_size,
                 med_embedding_size, diag_hidden_size, med_hidden_size, hidden_size,
                 bidirectional=True):  # end_index, pad_index,
        super().__init__()
        # self.pad_index = pad_index
        # self.end_index = end_index
        self.diag_embedding = torch.nn.Linear(diag_vocab_size, diag_embedding_size, bias=False)
        self.med_embedding = torch.nn.Linear(med_vocab_size, med_embedding_size, bias=False)

        self.diag_encoder = torch.nn.LSTM(diag_embedding_size, diag_hidden_size, batch_first=True,
                                          bidirectional=bidirectional)  # , dropout=0.5)  # 1 layer, dropout not used

        self.med_encoder = torch.nn.LSTM(med_embedding_size, med_hidden_size, batch_first=True,
                                         bidirectional=bidirectional)  # , dropout=0.5)

        if bidirectional:
            diag_hidden_size = diag_hidden_size * 2
            med_hidden_size = med_hidden_size * 2

        self.attention_diag_encoder = torch.nn.Sequential(
            torch.nn.Linear(diag_hidden_size, 1),
            torch.nn.Tanh(),
        )
        self.attention_med_encoder = torch.nn.Sequential(
            torch.nn.Linear(med_hidden_size, 1),
            torch.nn.Tanh(),
        )

        # IPW   + 2 --> 2 dims of age and sex of demo features
        self.lstm2hidden_ipw = torch.nn.Sequential(
            torch.nn.Linear(med_hidden_size + diag_hidden_size + 3, hidden_size),
            torch.nn.ReLU(),
        )
        self.hidden2out_ipw = torch.nn.Linear(hidden_size, 1,
                                              bias=False)  # outputs logits, not using sigmoid here for probability

        # Outcome
        # self.lstm2hidden_outcome = torch.nn.Sequential(
        #     torch.nn.Linear(med_hidden_size + diag_hidden_size + 3, hidden_size),
        #     torch.nn.ReLU(),
        # )
        # self.hidden2out_outcome = torch.nn.Linear(hidden_size, 1, bias=False)

    def softmax_masked(self, inputs, mask, dim=1, epsilon=0.0000001):
        inputs_exp = torch.exp(inputs)
        inputs_exp = inputs_exp * mask.float()
        inputs_exp_sum = inputs_exp.sum(dim=dim)
        inputs_attention = inputs_exp / (inputs_exp_sum.unsqueeze(dim) + epsilon)

        return inputs_attention

    def diag_encode(self, inputs):
        inputs_mask = (inputs.sum(dim=-1) != 0).long()
        inputs_emb = self.diag_embedding(inputs.float())  # change this to graph convolution later
        outputs, (h, c) = self.diag_encoder(inputs_emb)

        att_enc = self.attention_diag_encoder(outputs).squeeze(-1)
        att_normalized = self.softmax_masked(att_enc, inputs_mask)
        hidden = torch.sum(outputs * att_normalized.unsqueeze(-1), dim=1)
        original = torch.sum(inputs.float() * att_normalized.unsqueeze(-1), dim=1)

        return hidden, original

    def med_encode(self, inputs):  # bs * Time * Dim
        inputs_mask = (inputs.sum(dim=-1) != 0).long()  # bs * Time  masking what?
        inputs_emb = self.med_embedding(
            inputs.float())  # bs * Time * HiddenDim  # change this to graph convolution later
        outputs, (h, c) = self.med_encoder(inputs_emb)  # Outputs: bs * Time * HiddenDim

        att_enc = self.attention_med_encoder(outputs).squeeze(-1)  # bs * Time
        att_normalized = self.softmax_masked(att_enc, inputs_mask)  # bs * Time
        hidden = torch.sum(outputs * att_normalized.unsqueeze(-1), dim=1)  # bs * HiddenDim
        original = torch.sum(inputs.float() * att_normalized.unsqueeze(-1),
                             dim=1)  # (bs * Time * Dim) * (bs * Time) attention over time --> (bs * Dim) time attention weighted sum of baseline features

        return hidden, original

    def forward(self, confounder):
        diag_inputs, med_inputs, sexes, ages, days = confounder
        diag_hidden, diag_original = self.diag_encode(diag_inputs)  # bs * T1 * D1 --> bs * hidden1, bs * D1
        med_hidden, med_original = self.med_encode(med_inputs)  # bs * T2 * D2 --> bs * hidden2, bs * D2
        original = torch.cat((diag_original, med_original,
                              sexes.float().view(sexes.size(0), 1),
                              ages.float().view(ages.size(0), 1),
                              days.float().view(days.size(0), 1)), dim=1)  # bs * (D1+D2+2)

        # IPW
        hidden = torch.cat((diag_hidden, med_hidden,
                            sexes.float().view(sexes.size(0), 1),
                            ages.float().view(ages.size(0), 1),
                            days.float().view(days.size(0), 1)), dim=1)  # bs * (hidden1+hidden2+2)
        hidden = self.lstm2hidden_ipw(hidden)  # bs * (hidden1+hidden2+2) --> bs * hidden3
        outputs_logits_ipw = self.hidden2out_ipw(hidden)  # bs * hidden3 --> bs * 1

        return outputs_logits_ipw.view(outputs_logits_ipw.size(0)), original

def lstm_fit(model, optimizer, epochs, train_loader_shuffled, cuda):
    for epoch in tqdm(range(epochs)):
        epoch_losses_ipw = []
        for confounder, treatment, outcome in train_loader_shuffled:
            model.train()
            # train IPW
            optimizer.zero_grad()

            if cuda:  # confounder = (diag, med, sex, age)
                for ii in range(len(confounder)):
                    confounder[ii] = confounder[ii].to('cuda')
                treatment = treatment.to('cuda')

            treatment_logits, _ = model(confounder)
            loss_ipw = F.binary_cross_entropy_with_logits(treatment_logits, treatment.float())

            loss_ipw.backward()
            optimizer.step()
            epoch_losses_ipw.append(loss_ipw.item())

        # just finish 1 epoch
        # scheduler.step()
        epoch_losses_ipw = np.mean(epoch_losses_ipw)

        print('epoch:{}, loss:{}'.format(epoch, epoch_losses_ipw))

    return model, epoch_losses_ipw

# def lstm_cross_validation_fit(dataset, indices, kfold=10, verbose=1, shuffle=True):


import getServerInfo
import asyncio
import time
import datetime
import json
import os
import discord
from discord.ext import commands
from discord import app_commands
from discord.ext import tasks

try:
	import config # import configuration stuff locally
except ImportError:
	print("Hey! You don't have a valid bot token yet! Go edit config.py before trying again!")
	import shutil
	shutil.copy('config.py.template', 'config.py')
	import sys
	sys.exit(1)

if not os.path.isfile("servers.txt"):
	open("servers.txt",'w').close()
servers = open('servers.txt','r').readlines()

if config.token == "your token here":
	print("Hey! You don't have a valid bot token yet! Go edit config.py before trying again!")
	import sys
	sys.exit(1)
else:
	token = config.token

imgDir = config.imageDir

cooldown = config.time_delay * 60

client = commands.Bot(command_prefix="!!!!!", intents = discord.Intents.default())

if config.owner_id == "-1":
	print("Hey! No owner ID is set up. Some commands may not work without the owner running them, and could crash the bot. To change this, edit config.py")
else:
	client.owner_id = config.owner_id

#class MyClient(discord.Client):
#	async def on_ready(self):
#		print("Logged in as {}".format(self.user))
#		owner = await self.fetch_user(280804464355573770)
#		if owner != None:
#			await owner.send("Ayo! Bot online!")
#			await owner.send("Current servers: {}".format(servers))
#		else:
#			print("Bad user id")

#	@client.command(name="testcommand")
#	async def testcommand(interaction: discord.Interaction, message: discord.Message):
#		await interaction.send_message(content="it Worked!")

updateStuff = []

def updateServers():
	updateStuff = []
	if os.stat("servers.txt").st_size != 0:
		file = open("servers.txt", 'r')
		for x in file.readlines():
#			print("ayo {}".format(x))
			x = x.split("\t")
			updateStuff.append([x[0],x[1],x[2].strip("\n")])
#		print("Persistent messages updated! {}".format(updateStuff))
#	else:
#		print("No persistent messages to update")
	return updateStuff

@discord.ext.tasks.loop(minutes=5,reconnect=True)
async def updateMessages():
	while True:
		updateStuff = updateServers()
#		print("messages updating: {}".format(updateStuff))
		if len(updateStuff) > 0:
			for x in updateStuff:
				if x[0] != '-1':
					ip = x[0]
					status = getServerInfo.getInfo(ip)
					if status != None:
						getServerInfo.getImage(ip)
						img = discord.File(imgDir + "image.png")
						embed = discord.Embed()
						embed.color = discord.Color.green()
						players = ""
						isOk = True
						if status["players"]["online"] > 0:
							for i in range(len(status["players"]["sample"])):
								temp = status["players"]["sample"][i]["name"]
								if temp.startswith('.'):
									temp = temp[1:]
								players = players + temp
								if i+1 < len(status["players"]["sample"]):
									players = players + ", "
								if not status["players"]["sample"][i]["name"].isalnum() and not status["players"]["sample"][i]["name"].startswith('.'):
									isOk = False
#								print("Length: {}".format(len(players)))
						if len(players) != 0 and isOk:
							if len(status["players"]["sample"]) < status["players"]["online"]:
								players = players + " + {} others.".format(status["players"]["online"] - len(status["players"]["sample"]))
							embed.description = "IP: {0}\nVersion: {1}\nPlayers count: {2}/{3}\nPlayers: {4}".format(ip,status["version"]["name"],status["players"]["online"],status["players"]["max"], players)
						elif status["players"]["online"] == 0:
							embed.description = "IP: {0}\nVersion: {1}\nPlayers count: {2}/{3}\nPlayers: None".format(ip,status["version"]["name"],status["players"]["online"],status["players"]["max"])
						else:
							embed.description = "IP: {0}\nVersion: {1}\nPlayers count: {2}/{3}\nPlayers: Not Available".format(ip,status["version"]["name"],status["players"]["online"],status["players"]["max"])
#						embed.description = "IP: {0}\nVersion: {1}\nPlayers count: {2}/{3}\nPlayers: {4}".format(ip,status["version"]["name"],status["players"]["online"],status["players"]["max"], players)
						embed.title="Server is Online!"
						embed.set_thumbnail(url="attachment://image.png")
#						if len(status["players"
						img = discord.File(imgDir + "image.png")
					else:
						embed = discord.Embed()
						embed.color = discord.Color.red()
						embed.title="Server is unreachable!"
						embed.description = "The server `{}` is either offline, or it doesn't exist.".format(ip)
						img = discord.File(imgDir + "fail.png")
						embed.set_thumbnail(url=f"attachment://fail.png")
#					embed.set_footer(text="Last updated: <t:{:.0f}:R>".format(time.time()))
					embed.timestamp = datetime.datetime.utcnow()
					channel = await client.fetch_channel(x[2])
					msg = await channel.fetch_message(x[1])
#					print("Message content: {}".format(msg.content))
					await msg.edit(embed=embed, content="", attachments=[img])
		await asyncio.sleep(cooldown)

@client.event
async def on_ready():
	owner = await client.fetch_user(client.owner_id)
#	await owner.send("Ayo 2!")
#	print("It worked maybe")
	await client.tree.sync()
#	print("Commands Synced")
#	updateStuff = []
	updateServers()
	updateMessages.start()
#	if len(updateStuff) > 0:
#		print("Servers: {}".format(updateStuff))
#	else:
#		print("No servers being updated")
##	asyncio.ensure_future(updateMessages())
#	asyncio.set_event_loop(updateMessages())
##	loop.run_forever
	print("Bot successfully connected to {0} at {1}:{2}".format(client.user.display_name, datetime.time().hour, datetime.time().minute))

@client.tree.command(name="testcommand", description="don't use, or do.")
async def testcommand(interaction: discord.Interaction):
	await interaction.response.send_message("No, you're a test", ephemeral=True)

@client.tree.command(name="serverstatus", description="Check on the status of a server!")
@app_commands.describe(ip="IP to get the status of")
async def serverstatus(interaction: discord.Interaction, ip: str):
	status = getServerInfo.getInfo(ip)

	if status != None:
		getServerInfo.getImage(ip)
		img = discord.File(imgDir + "image.png")
		embed = discord.Embed()
		embed.color = discord.Color.green()
		players = ""
		isOk = True
		if status["players"]["online"] > 0:
			for x in range(len(status["players"]["sample"])):
				temp = status["players"]["sample"][x]["name"]
				if temp.startswith('.'):
					temp = temp[1:]
				players = players + temp
				if x+1 < len(status["players"]["sample"]):
					players = players + ", "
				if not status["players"]["sample"][x]["name"].isalnum() and  not status["players"]["sample"][x]["name"].startswith('.'):
					isOk = False
#			print("Length: {}".format(len(players)))
		if len(players) != 0 and isOk:
			if len(status["players"]["sample"]) < status["players"]["online"]:
				players = players + " + {} others.".format(status["players"]["online"] - len(status["players"]["sample"]))

			embed.description = "IP: {0}\nVersion: {1}\nPlayers count: {2}/{3}\nPlayers: {4}".format(ip,status["version"]["name"],status["players"]["online"],status["players"]["max"], players)
		elif status["players"]["online"] == 0:
			embed.description = "IP: {0}\nVersion: {1}\nPlayers count: {2}/{3}\nPlayers: None".format(ip,status["version"]["name"],status["players"]["online"],status["players"]["max"])
		else:
			embed.description = "IP: {0}\nVersion: {1}\nPlayers count: {2}/{3}\nPlayers: Not Available".format(ip,status["version"]["name"],status["players"]["online"],status["players"]["max"])
#		embed.description = "IP: {0}\nVersion: {1}\nPlayers count: {2}/{3}\nPlayers: {4}".format(ip,status["version"]["name"],status["players"]["online"],status["players"]["max"], players)
		embed.title="Server is Online!"
		embed.set_thumbnail(url=f"attachment://image.png")
#		if len(status["players"
	else:
		embed = discord.Embed()
		embed.color = discord.Color.red()
		embed.title="Server is unreachable!"
		embed.description = "The server `{}` is either offline, or it doesn't exist.".format(ip)
		img = discord.File(imgDir + "fail.png")
		embed.set_thumbnail(url=f"attachment://fail.png")
#	embed.set_footer(text="Last updated: <t:{:.0f}:R>".format(time.time()))
	embed.timestamp = datetime.datetime.utcnow()
	await interaction.response.send_message(embed= embed, file=img)

@client.tree.command(name="watchserver", description="will create a permanent message to constantly update a server's status")
@app_commands.describe(ip="IP to keep updates for", channel_id="Which channel to put the message in. Use \"here\" for the current channel")
async def watchserver(interaction: discord.Interaction, ip: str, channel_id: str):
#	print("start")
	if channel_id == "here":
		channel_id = interaction.id
	try:
		Channel = await client.fetch_channel(channel_id)
	except NotFound:
		await interaction.response.send_message("Invalid Channel ID!", ephemeral=True)
	try:
		msgID = await Channel.send("Awaiting update!")
	except Forbidden:
		await interaction.response.send_message("Unable to send a message in that channel! Do I not have permission? :(", ephemeral=True)
	with open("servers.txt", "r+") as file:
		lines = file.readlines()
		lines = lines[:-1]
#		file.write(lines)

	file = open("servers.txt",'a')
	for i in lines:
		file.write(i)
	file.write("{}\t{}\t{}\n".format(ip,msgID.id,channel_id))
	file.write("-1\t-1\t-1")
	file.close()
	print("done")
	updateServers()
	await interaction.response.send_message("Message Sent!", ephemeral=True, delete_after=60)

@client.tree.command(name="serverjson")
@app_commands.describe(ip="IP for the json obtaining")
async def serverjson(interaction: discord.Interaction, ip: str):
	status = getServerInfo.getInfo(ip)
	if status != None:
		try:
			await interaction.response.send_message("Json response from {0}:\n{1}".format(ip,status))
		except discord.errors.HTTPException:
			await interaction.response.send_message("Error: json too long! Go to <https://api.mcstatus.io/v2/status/java/{0}>".format(ip), ephemeral=True)
	else:
		await interaction.response.send_message("Error: No server found. Either the server is offline, or check the IP and try again", ephemeral=True, delete_after=30)

@client.tree.command(name="removestatus", description="Remove messages from updates")
@app_commands.describe(message_id="Message ID to remove from updates (use * to remove all)")
async def removestatus(interaction: discord.Interaction, message_id: str):
	if channel_id == '*':
		file = open("servers.txt",'w')
		file.close()
		updateServers()
		await interaction.response.send_message("All update messages have been removed from memory!")
	else:
		with open("servers.txt", 'r') as file:
			lines = file.readlines()
		with open("servers.txt", 'w') as file:
			content = ""
			for x in lines:
				temp = x
				x.strip("\n")
				x = x.split("\t")
				if x[1] != message_id:
					file.write(temp)
		await interaction.response.send_message("Message has been removed from updates!")

@client.tree.command(name="help", description="display the list of commands, and their uses")
async def help(interaction: discord.Interaction):
	embed = discord.Embed()
	embed.color = discord.Color.blue()
	embed.title = "Minecraft Server Bot Help!"
	embed.description = "This bot is designed to allow you to easily check the status of different minecraft servers!\n**__Commands:__**\n> /serverstatus - check the status of a server\n> /watchserver - create an automatically-updating message, displays the same info as /serverstatus\n> /removestatus - tells the bot to stop updating the message set from /watchserver\n> /serverjson - get the raw json status from a server"
	embed.set_footer(text="Created by Nathan Fullerton")
	embed.set_thumbnail(url=client.user.avatar.url)
	await interaction.response.send_message(embed=embed, ephemeral = True)

if __name__ == "__main__":
#	await client.tree.sync()
#	await asyncio.gather()
#	updateMessages.start()
	client.run(token)


import sys
import os
import json
import requests
from flask import Flask, request, abort
import tokens
GITHUB_SECRET = tokens.github
bearer = tokens.webex
roomId = tokens.roomId
headers = {
    "Accept": "application/json",
    "Content-Type": "application/json; charset=utf-8",
    "Authorization": "Bearer " + bearer
}

#utils library

def send_get(url, payload=None,js=True):
    if payload == None:
        request = requests.get(url, headers=headers)
    else:
        request = requests.get(url, headers=headers, params=payload)
    if js == True:
        request= request.json()
    return request

def send_post(url, data):
    request = requests.post(url, json.dumps(data), headers=headers).json()
    return request

def help_me():
    return "Hello! Sure! I can help. Below are the commands that I understand: `Help me` - I will display what I can do. My job is to send you and the rest of your team notifications when something happens inside your repository on pull or push events"

def greetings():
    return "Hi, type `Help me` to see what I can do.<br/>"

def send_msg(data):
    if str(data['action']) == 'opened':
        msg = 'the user ' +str(data['pull_request']['user']['login'])+' opened a pull request at url: '+str(data['pull_request']['url'])
        send_post("https://api.ciscospark.com/v1/messages", {"roomId": roomId,"markdown": msg})
    elif str(data['action']) == 'unlabeled':
        msg = 'the user ' +str(data['pull_request']['user']['login'])+' made a request to unlabel at url: '+str(data['pull_request']['url'])
        send_post("https://api.ciscospark.com/v1/messages", {"roomId": roomId,"markdown": msg})
    elif str(data['action']) == 'labeled':
        msg = 'the user ' +str(data['pull_request']['user']['login'])+' made a request to label at url: '+str(data['pull_request']['url'])
        send_post("https://api.ciscospark.com/v1/messages", {"roomId": roomId,"markdown": msg})
    elif str(data['action']) == 'closed':
        msg = 'the user ' +str(data['pull_request']['user']['login'])+' closed a pull request at url: '+str(data['pull_request']['url'])
        send_post("https://api.ciscospark.com/v1/messages", {"roomId": roomId,"markdown": msg})
    else:
        msg = 'the user ' +str(data['pull_request']['user']['login'])+' made a request at url: '+str(data['pull_request']['url'])
        send_post("https://api.ciscospark.com/v1/messages", {"roomId": roomId,"markdown": msg})


import cv2 as cv
from collections import defaultdict
cvNet = cv.dnn.readNetFromTensorflow('/Users/Tinku/Desktop/RoboticsShit/Skystone-Vision/Final/image_tensor/PB_file/model.pb', '/Users/Tinku/Desktop/RoboticsShit/Skystone-Vision/Final/image_tensor/Pbtxt/model.pbtxt')

img = cv.imread('/Users/Tinku/Desktop/TestStuff/work.jpeg')
rows = img.shape[0]
cols = img.shape[1]
cvNet.setInput(cv.dnn.blobFromImage(img, size=(300, 300), swapRB=True, crop=False))
cvOut = cvNet.forward()
numOfRect = 0
objects_dict = {}
for detection in cvOut[0,0,:,:]:
    score = float(detection[2])
    objects = detection
    if score > 0.75:
        left = detection[3] * cols
        top = detection[4] * rows
        right = detection[5] * cols
        bottom = detection[6] * rows
        objects_dict[score]=[left,top,right,bottom]
        numOfRect += 1

        print(score)
#print(objects_dict)
l=list(objects_dict.keys())
l.sort(reverse=True)
print(l)
for i in l[:6] :
    print(i,objects_dict[i])
    cv.rectangle(img, (int(objects_dict[i][0]), int(objects_dict[i][1])), (int(objects_dict[i][2]), int(objects_dict[i][3])), (23, 230, 210), thickness=5)

cv.imshow('img', img)
print(numOfRect)
print(objects)
cv.waitKey()