def numUniqueEmails(emails):
        y = []
        for email in emails:
            local,domain = email.split('@')
            if '.' in local:
                local = local.replace('.','')
            if '+' in local:
                local = local[:local.index('+')]
            x = local +'@' + domain
            y.append(x)
        L = list(set(y))
        return len(L)
emails = ["test.email+alex@leetcode.com","test.e.mail+bob.cathy@leetcode.com","testemail+david@lee.tcode.com"]
print(numUniqueEmails(emails))


import os
import numpy as np
import tensorflow as tf
from model import L4, L8
from scipy.misc import imread
import auxi

os.environ["CUDA_DEVICE_ORDER"] = "PCI_BUS_ID"
os.environ["CUDA_VISIBLE_DEVICES"] = "4"
LEARNIN_RATE = 1e-5
LEARNIN_RATE_DECARY = 0.5
GLOBAL_STEP = 500000
DECAY_STEP = 50000
DISPLAY_STEP = 10
BATCH_SIZE = 4
PATCH_WIDTH = 128
PATCH_HEIGHT = 128

QF=20
train_O='/data1/zhanghx/crk/paper/data/trainO/'
train_J='/data1/zhanghx/crk/paper/data/trainJ/'+str(QF)+'/'
test_O='/data1/zhanghx/crk/paper/data/testO/'
test_J='/data1/zhanghx/crk/paper/data/testJ/'+str(QF)+'/'

model_dir = os.getcwd() + '/networkL8/'+str(QF)+ 'model/'
log_dir = os.getcwd() + '/networkL8/'  +str(QF)+ 'logs/'

output_dir = ['./result/' + '/' + '/output/O/',
              './result/' + '/' + '/output/J/',
              './result/' + '/' + '/output/G/']

mkdirs_func = lambda p: os.makedirs(p) if not os.path.exists(p) else 0
for d in [model_dir, log_dir] + output_dir: mkdirs_func(d)

def get_batch(path_train_x,path_train_y):  #train_x:original  train_y:jpeg
    list_fname = os.listdir(path_train_x)
    perm = np.arange(len(list_fname)).astype(np.int32)
    np.random.shuffle(perm)
    x_batch=np.zeros([BATCH_SIZE,PATCH_WIDTH,PATCH_HEIGHT,1])
    y_batch=np.zeros([BATCH_SIZE,PATCH_WIDTH,PATCH_HEIGHT,1])
    for i in range(BATCH_SIZE):
        file = list_fname[perm[i]]
        img_x = imread(path_train_x + file, mode='L')
        img_y = imread(path_train_y + file[:-3]+'jpg', mode='L')
        img_x = img_x.reshape([img_x.shape[0],img_x.shape[1],1])
        img_y = img_y.reshape([img_y.shape[0],img_y.shape[1],1])
        pos_w = np.random.randint(img_x.shape[0]-PATCH_WIDTH,size=1)
        pos_h = np.random.randint(img_x.shape[1]-PATCH_HEIGHT,size=1)
        x_batch[i,...] = img_x[pos_w[0]:pos_w[0]+PATCH_WIDTH,pos_h[0]:pos_h[0]+PATCH_HEIGHT,:]
        y_batch[i,...] = img_y[pos_w[0]:pos_w[0]+PATCH_WIDTH,pos_h[0]:pos_h[0]+PATCH_HEIGHT,:]
    return x_batch/256., y_batch/256.

with tf.name_scope('input') as scope:
    y = tf.placeholder(tf.float32, shape=[None, None, None, 1])  # J
    x = tf.placeholder(tf.float32, shape=[None, None, None, 1])  # O

x_gen = L8(y)

with tf.name_scope('loss') as scope:
    residual_loss = tf.norm(x - x_gen)
    tf.add_to_collection('losses', residual_loss)
    loss = tf.add_n(tf.get_collection('losses'))

vars = tf.trainable_variables()
var1_7 = tf.trainable_variables()[0:14]
var8 = tf.trainable_variables()[14:]
print(len(vars))
print(var1_7)
print(var8)

global_ = tf.Variable(0, trainable=False)
decayed_learning_rate = tf.train.exponential_decay(learning_rate=LEARNIN_RATE, global_step=global_,
                                                   decay_steps=DECAY_STEP, decay_rate=LEARNIN_RATE_DECARY,
                                                   staircase=True)
train_op1 = tf.train.AdamOptimizer(learning_rate=decayed_learning_rate).minimize(loss, global_step=global_,var_list=var1_7)
train_op2 = tf.train.AdamOptimizer(learning_rate=decayed_learning_rate * 0.1).minimize(loss, global_step=global_,var_list=var8)
train_op = tf.group(train_op1, train_op2)

with tf.Session() as sess:
    init = tf.global_variables_initializer()
    sess.run(init)
    saver = tf.train.Saver(max_to_keep=0)

    for step in range(GLOBAL_STEP + 1):
        x_batch, y_batch = get_batch(train_O, train_J)
        _,x_gens,loss_val=sess.run([train_op,x_gen,loss], feed_dict={x: x_batch, y: y_batch})
        if step % DISPLAY_STEP == 0:
            PSNR1, SSIM1 = auxi.eval_compare(x_batch, y_batch, batch_size=BATCH_SIZE)
            PSNR2, SSIM2 = auxi.eval_compare(x_batch, x_gens, batch_size=BATCH_SIZE)
            print('The', step, 'steps in training ', 'loss: ', loss_val)
            print('PSNR1 ', PSNR1, ' SSIM1 ', SSIM1)
            print('PSNR2 ', PSNR2, ' SSIM2 ', SSIM2)
    print('Train done')
    save_path = model_dir + '.ckpt'
    saver.save(sess, save_path)
    print('Model saved done')

    ckpt = tf.train.get_checkpoint_state(model_dir)
    saver.restore(sess, ckpt.model_checkpoint_path)
    print('Model loaded done')

    PSNR1_test, SSIM1_test,PSNR2_test, SSIM2_test=(0,0,0,0)
    list_fname = os.listdir(test_O)
    for i, file in enumerate(list_fname):
        img_x = imread(test_O + file, mode='L')
        img_y = imread(test_J + file[:-3] + 'jpg', mode='L')
        img_x = img_x.reshape([1, img_x.shape[0], img_x.shape[1], 1]) / 255.
        img_y = img_y.reshape([1, img_y.shape[0], img_y.shape[1], 1]) / 255.
        x_gens = sess.run(x_gen, feed_dict={x: img_x, y: img_y})

        PSNR1, SSIM1 = auxi.eval_compare(img_x, img_y, batch_size=1)
        PSNR2, SSIM2 = auxi.eval_compare(img_x, x_gens, batch_size=1)

        print('PSNR1 ', PSNR1, ' SSIM1 ', SSIM1)
        print('PSNR2 ', PSNR2, ' SSIM2 ', SSIM2)

        PSNR1_test=PSNR1+PSNR1_test
        SSIM1_test=SSIM1+SSIM1_test
        PSNR2_test=PSNR2+PSNR2_test
        SSIM2_test=SSIM2+SSIM2_test
    print('Text done')

    txt_file = open("all_resultsL8", "a")
    txt_file.write("L8 : \n")
    txt_file.write('QF:'+str(QF)+ '\n')
    txt_file.write('PSNR1:' + str(PSNR1_test/ len(list_fname)) + '\n')
    txt_file.write('SSIM1:' + str(SSIM1_test/ len(list_fname)) + '\n')
    txt_file.write('PSNR2:' + str(PSNR2_test/ len(list_fname)) + '\n')
    txt_file.write('SSIM2:' + str(SSIM2_test/ len(list_fname)) + '\n')
    txt_file.close()


''' Polak-Ribiere Conjugate Gradient Method for Approximating Minimizers to 2D Functions '''

#The Polak-Ribiere conjugate gradient method for approximating minimizers to a given function relys on the following:
#   Give intial guess of minimizer
#   Compute initial search direction
#   Compute optimal initial step size
#   Update minimizer
#   Iterate over the following:
#       Compute gradient at current minimizer
#       Compute search direction parameter (unique to Polak-Ribiere)
#       Update search direction
#       Compute optimal step size
#       Update minimizer
#       Compute error and check against given tolerance

import numpy as np
from scipy import optimize
from numpy import linalg as la
from CONT_FUNCS import f
from CONT_FUNCS import gradf
from CONT_FUNCS import g

def POLAK_RIBIERE(U):
    #initialize necessary values
    D = np.zeros([1,2]) #array to store search directions
    DF = np.zeros([1,2]) #array to store gradients
    D[0] = gradf(U[0]) #set initial search direction
    p = optimize.newton(g,0,args=(U[0],D[0])) #set initial step size
    U = np.append(U,[U[0]-p*D[0]],axis=0) #store first approximation of minimizer
    k=1 #set iteration counter
    error = 1 #initialize error
    #iterate method until tolerance is achienved
    while error > 10e-5:
        #calculate and store gradient at previous step
        DF = np.append(DF,[gradf(U[k])],axis=0)
        #calculate search direction parameter according to Polak-Ribiere
        b = (np.dot(gradf(U[k]), gradf(U[k])-gradf(U[k-1])))/(la.norm(gradf(U[k-1]))**2)
        #update and store search direction according to Polak-Ribiere
        D = np.append(D,[gradf(U[k]) + b*D[k-1]],axis=0)
        #update step size
        p = optimize.newton(g,0,args=(U[k],D[k]))
        #update and store minimizer
        U = np.append(U, [U[k] -p*D[k]],axis=0)
        #calculate relative error
        error = la.norm(U[k+1]-U[k], ord=np.inf)
        #update iteration counter
        k=k+1
    return {'Total Iterations': k-1 , 'Error': error , 'Minimizer': U[k-1], 'Function Value': f(U[k-1]), 'Gradient at Minimizer': gradf(U[k-1])}


class Solution:
    def combinationSum2(self, candidates: List[int], target: int) -> List[List[int]]:
        def dfs(remain, combo, index):
            if remain == 0 and combo not in res:#不重复
                res.append(combo)#找到
                return
            for i in range(index, len(candidates)):
                if candidates[i] > remain:#找不到不要
                    break
                dfs(remain - candidates[i], combo + [candidates[i]], i+1)#i+1 #不重复

        candidates.sort()
        res = []
        dfs(target, [], 0)
        return res

#有点难
class Solution:
    def combinationSum2(self, candidates, target):
        candidates.sort()
        def helper(candidates,target):
            candidates=[x for x in candidates if x <= target]#少一些候选集，减少时间消耗
            answers=[]
            if len(candidates)==0:
                return []
            for i in range(len(candidates)):
                if target==candidates[i]:
                    answers.append([candidates[i]])
                    break
                if i>0 and candidates[i]==candidates[i-1]:
                    continue
                answer=helper(candidates[i+1:],target-candidates[i])
                if answer:
                    for x in answer:
                        answers.append([candidates[i]]+x)
            return answers
        return helper(candidates,target)

class Solution:
    def combinationSum2(self, candidates: List[int], target: int) -> List[List[int]]:

        def dfs(pos: int, rest: int):
            nonlocal sequence
            if rest == 0:
                ans.append(sequence[:])
                return
            if pos == len(freq) or rest < freq[pos][0]:
                return

            dfs(pos + 1, rest)

            most = min(rest // freq[pos][0], freq[pos][1])
            for i in range(1, most + 1):
                sequence.append(freq[pos][0])
                dfs(pos + 1, rest - i * freq[pos][0])
            sequence = sequence[:-most]

        freq = sorted(collections.Counter(candidates).items())
        ans = list()
        sequence = list()
        dfs(0, target)
        return ans


def flip(s):
    top_side = s[0]
    if (top_side=='-'):
        flip_to = '+'
    else:
        flip_to = '-'

    if flip_to in s :
        index = s.index(flip_to)
    else :
        index = len(s)

    s = flip_to*index+s[index:]
    return s

if __name__ == '__main__':
    inp = open("large_input.txt", "r")
    out = open("large_output.txt","w")
    test_cases = [x.strip('\n') for x in inp.readlines()]
    test_case_num = 1
    while test_case_num <= int(test_cases[0]):
        flips = 0
        stack = test_cases[test_case_num]
        while stack != '+'*len(stack):
            stack = flip(stack)
            flips += 1
        out.write('Case #{}: {}\n'.format(test_case_num,flips))
        test_case_num += 1


import random
import numpy as np
import numpy.linalg as la
import math

def py_ang(v1, v2):
    # Returns the angle in radians between np-vectors 'v1' and 'v2'
    cosang = np.dot(v1, v2)
    sinang = la.norm(np.cross(v1, v2))
    return np.arctan2(sinang, cosang)

def is_in(v, M) : #tests if np-vector v is in the list of np-vectors M
    return tuple(v) in [tuple(x) for x in M]

def removed(a,A): #removes np-vector from the list of np-vectors A
    y=[]
    for i in range(len(A)):
        if  np.any(A[i]!=a) :
            y.append(A[i])
    return(y)

class Autopoiesis:
    def __init__(self, n, K): #takes as the disintegration constant
        self.n=n
        x=[[['S'] for i in range(self.n)] for j in range(self.n)]
        x[int(n/2)][int(n/2)]=['K']
        self.K=K
        M=np.array([(0,-1),(-1,-1),(-1,0),(-1,1),(0,1),(1,1),(1,0),(1,-1)])
        for i in range(self.n):
            for j in range(self.n):
                y=x[i][j]
                if len(y)==2:
                    y[1]=M[int(y[1])]
                if len(y)==3:
                    y[1]=M[int(y[1])]
                    y[2]=M[int(y[2])]
        self.x=x

    def R_p(self): #returns random direction from (West,North,East, South)
        return np.array(random.choice(((0,-1),(-1,0),(0,1),(1,0))))

    def R_s(self, state, pos) : #creates a list of directions (West,North,East, South) from pos that are on the given state
                                #and returns one at random

        M_1=(pos[0]-1,pos[1])
        M_2=(pos[0]+1,pos[1])
        M_3=(pos[0],pos[1]-1)
        M_4=(pos[0],pos[1]+1)
        D=[]
        for p in {M_1,M_2,M_3,M_4}  :
            if p[0] in range(self.n) and p[1] in range(self.n):
                if state != 'B' :
                    if self.x[p[0]][p[1]][0]==state :
                        D.append((p[0]-pos[0],p[1]-pos[1]))
                elif self.B(p) :
                    D.append((p[0]-pos[0],p[1]-pos[1]))

        if D!=[]:
            return np.array(random.choice(D))
        else:
            return (-self.n-1,-self.n -1)

    def reorder(self, u, v):  #u=[position_1,...,position_m] , v=[f(1),...,f(n)] , f is a permutation of {1,...,n}
        temp=[u[i] for i in v]
        A=np.array(self.x)
        for i in range(len(u)):
            self.x[u[i][0]][u[i][1]] = [z for z in A[temp[i][0]][temp[i][1]] ]

    #pos is a 2-element-np.array
    #each method tests if position pos is at some state (H,S,C,L,B,B1,B2)
    def H(self,pos):
        if pos[0] in range(self.n) and pos[1] in range(self.n)  :
            if self.x[pos[0]][pos[1]][0]=='H':
                return 1
            else:
                return 0
    def S(self,pos):
         if pos[0] in range(self.n) and pos[1] in range(self.n)  :
            if self.x[pos[0]][pos[1]][0]=='S'  :
                return 1
            else:
                return 0
    def L(self,pos):
        if pos[0] in range(self.n) and pos[1] in range(self.n)  :
            if self.x[pos[0]][pos[1]][0]=='L' and len(self.x[pos[0]][pos[1]])==1  :
                return 1
            else:
                return 0
    def C(self,pos):
        if pos[0] in range(self.n) and pos[1] in range(self.n)  :
            if self.x[pos[0]][pos[1]][0]=='K'   :
                return 1
            else:
                return 0
    def B1(self,pos):
        if pos[0] in range(self.n) and pos[1] in range(self.n)  :
            if len(self.x[pos[0]][pos[1]])==2 :
                return 1
            else:
                return 0

    def B2(self,pos):
        if pos[0] in range(self.n) and pos[1] in range(self.n)  :
            if len(self.x[pos[0]][pos[1]])==3 :
                return 1
            else:
                return 0
    def B(self,pos):
        if self.B1(pos) or self.B2(pos):
            return 1
        else:
            return 0

    def motion1(self):
        H_list=[]
        for i in range(self.n):
            for j in range(self.n):
                pos=np.array((i,j))
                if self.H(pos) :
                    H_list.append(pos)
        random.shuffle(H_list)
        y=[]
        for pos in H_list :
            R_r=self.R_p()
            if self.S(pos+R_r) or self.L(pos+R_r) or self.C(pos+R_r):
                u=[pos,pos+R_r]
                v=[1,0]
                self.reorder(u,v)
                if self.L(pos):
                    y.append(pos)
            if self.B(pos+R_r) and self.S(pos+2*R_r) :
                u=[pos,pos+R_r,pos+2*R_r]
                v=[2,1,0]
                self.reorder(u,v)
        for pos in y :
            self.bonding(pos)

    def motion2(self):
        L_list=[]
        for i in range(self.n):
            for j in range(self.n):
                pos=np.array((i,j))
                if self.L(pos) :
                    L_list.append(pos)
        random.shuffle(L_list)
        y=[]
        for pos in L_list :
            R_r=self.R_p()
            R_H=self.R_s('H',pos+R_r)
            R_B=self.R_s('B',pos+R_r)
            if self.S(pos+R_r) and self.H(pos+R_r+R_H) :
                u=[pos, pos+R_r, pos+R_r+R_H]
                v=[2,0,1]
                self.reorder(u,v)
                y.append(pos+R_r)
            elif self.S(pos+R_r) and self.B(pos+R_r+R_B) and self.H(pos+R_r+2*R_B) :
                u=[pos, pos+R_r, pos+R_r+R_B, pos+R_r+2*R_B]
                v=[3,0,2,1]
                self.reorder(u,v)
                y.append(pos+R_r)
            elif self.S(pos+R_r) or self.H(pos+R_r):
                u=[pos, pos+R_r]
                v=[1,0]
                self.reorder(u,v)
                y.append(pos+R_r)
        for p in y :
            self.bonding(pos)

    def motion3(self):
        C_list=[]
        for i in range(self.n):
            for j in range(self.n):
                pos = np.array((i,j))
                if self.C(pos) :
                    C_list.append(pos)
        random.shuffle(C_list)
        y=[]
        for pos in C_list :
            R_r=self.R_p()
            R_H=self.R_s('H',pos+2*R_r)
            R_B=self.R_s('B',pos+2*R_r)
            if self.L(pos+R_r) :
                if self.S(pos+2*R_r):
                    if self.H(pos+2*R_r+R_H):
                        u=[pos,pos+R_r,pos+2*R_r,pos+2*R_r+R_H]
                        v=[3,0,1,2]
                        self.reorder(u,v)
                        y.append(pos+2*R_r)
                    elif self.B(pos+2*R_r+R_B) and self.H(pos+2*R_r+2*R_B):
                        u=[pos,pos+R_r,pos+2*R_r,pos+2*R_r+R_B,pos+2*R_r+2*R_B]
                        v=[4,0,1,3,2]
                        self.reorder(u,v)
                        y.append(pos+2*R_r)
                elif self.H(pos+2*R_r):
                    u=[pos,pos+R_r,pos+2*R_r]
                    v=[2,0,1]
                    self.reorder(u,v)
                    y.append(pos+2*R_r)
            elif self.S(pos+R_r):
                R_H=self.R_s('H',pos+R_r)
                R_B=self.R_s('B',pos+R_r)
                if self.H(pos+R_r+R_H):
                    u=[pos,pos+R_r,pos+R_r+R_H]
                    v=[2,0,1]
                elif self.B(pos+R_r+R_B) and self.H(pos+R_r+2*R_B):
                    u=[pos,pos+R_r,pos+R_r+R_B,pos+R_r+2*R_B]
                    v=[3,0,2,1]
                    self.reorder(u,v)
                else:
                    u=[pos,pos+R_r]
                    v=[1,0]
                    self.reorder(u,v)
            if  self.L(pos+R_r) :
                if self.B(pos+2*R_r) or self.L(pos+2*R_r) or self.C(pos+2*R_r):
                    u=[pos,pos+R_r,pos+2*R_r]
                    v=[1,0,2]
                    y.append(pos+R_r)
            if self.H(pos+R_r):
                u=[pos,pos+R_r]
                v=[1,0]
                self.reorder(u,v)

        for p in y :
            self.bonding(p)

    def find_B(self, pos):
        list=[]
        M=np.array([(0,-1),(-1,-1),(-1,0),(-1,1),(0,1),(1,1),(1,0),(1,-1)])
        for d in M :
            if self.B(pos+d):
                list.append(d)
        return list

    def rename(self, u, v): #u=[position_1,...,position_m , v=[state_1,...,state_m]
        i=0
        for pos in u :
            if self.B(pos) :
                for d in self.x[pos[0]][pos[1]][1:] :
                    p=pos+d
                    self.x[p[0]][p[1]] = removed(-d, self.x[p[0]][p[1]])
            self.x[pos[0]][pos[1]] = [v[i]]
            i+=1

    def production(self):
        M=np.array([(0,-1),(-1,-1),(-1,0),(-1,1),(0,1),(1,1),(1,0),(1,-1)])
        C_list=[]
        for i in range(self.n):
            for j in range(self.n):
                pos=np.array((i,j))
                if self.C(pos) :
                    C_list.append(pos)
        random.shuffle(C_list)
        y=[]
        for pos in C_list:
            S=[]
            for direction in M:
                if self.S(pos+direction):
                    S.append(direction)
            pairs=[]
            for p in S:
                for q in S:
                    if la.norm(p-q)==1:
                        pairs.append((p,q))
            if pairs !=[]:
                (R_S1,R_S2)=random.choice(pairs)
                u=[pos+R_S1,pos+R_S2]
                v=['L','H']
                self.rename(u,v)
                y.append(pos+R_S1)

        for p in y:
            self.bonding(p)

    def disintegration(self):
        M=np.array(((0,-1),(-1,0),(0,1),(1,0)))
        LB_list=[]
        for i in range(self.n):
            for j in range(self.n):
                pos = np.array((i,j))
                if self.L(pos) or self.B(pos) :
                    LB_list.append(pos)
        random.shuffle(LB_list)
        for pos in LB_list:
            R_N=random.random()
            if R_N <= self.K :
                R_H=self.R_s('H',pos)
                T1=[]
                for S1 in range(4):
                    if self.S(pos+M[S1]):
                        for i in {(S1-1)%4,S1%4,(S1+1)%4}:
                            if self.H(pos+M[S1]+M[i]):
                                T1.append(M[S1])

                T2=[]
                for S2 in range(4):
                    if self.S(pos+M[S2]):
                        for i in {(S2-1)%4,S2%4,(S2+1)%4}:
                            if self.B(pos+M[S2]+M[i]) and self.H(pos+M[S2]+2*M[i]) :
                                T2.append(M[S2])
                if self.H(pos+R_H):
                    u=[pos,pos+R_H]
                    v=['S','S']
                    self.rename(u,v)
                    self.rebond(pos)
                elif T1!=[]:
                    R_T1=random.choice(T1)
                    R_H=self.R_s('H',pos+R_T1)
                    u=[pos,pos+R_T1+R_H]
                    v=['S','S']
                    self.rename(u,v)
                    self.rebond(pos)
                elif T2!=[] :
                    R_T2=random.choice(T2)
                    R_B=self.R_s('B',pos+R_T2) #!!!
                    if self.H(pos+R_T2+2*R_B):
                        u=[pos,pos+R_T2+2*R_B]
                        v=['S','S']
                        self.rename(u,v)
                        self.rebond(pos)

    def find_L(self, pos): #creates a list the positions is the Moore neighbourhood of pos that are in the L state
        list=[]
        M=np.array([(0,-1),(-1,-1),(-1,0),(-1,1),(0,1),(1,1),(1,0),(1,-1)])
        for d in M :
            if self.L(pos+d):
                list.append(pos+d)
        return list

    def find_B1(self, pos): #creates a list the positions is the Moore neighbourhood of pos that are in the B1 state
        list=[]
        M=np.array([(0,-1),(-1,-1),(-1,0),(-1,1),(0,1),(1,1),(1,0),(1,-1)])
        for d in M :
            if self.B1(pos+d):
                list.append(pos+d)
        return list

    def bondable(self, p, q): #tests if positions p,q can be bonded
        key=0
        if np.any(q!=p) and (self.L(p) or self.B1(p)) and is_in(q, self.find_B1(p)+self.find_L(p) ):
            key=1
            if self.B1(p):
                v=self.x[p[0]][p[1]][1]
                u=q-p
                if py_ang(v,u) < math.pi/2 :
                    key=0
            if self.B1(q):
                v=self.x[q[0]][q[1]][1]
                u=p-q
                if py_ang(v,u) < math.pi/2 :
                    key=0
        return key

    def bond(self,p,q) :
        if self.bondable(p,q) :
            self.x[p[0]][p[1]].append(q-p)
            self.x[q[0]][q[1]].append(p-q)

    def bonding(self,pos) :
        N = self.find_L(pos)
        M = self.find_B1(pos)
        l=len(M)

        for i in range(l) :
            if self.bondable(pos,M[i]) :
                M.append(M[i])
        M=M[l:]

        if M !=[] :
            m1=random.choice(M)
            self.bond(pos,m1)

        M = self.find_B1(pos)
        l=len(M)
        for i in range(l) :
            if self.bondable(pos,M[i]) :
                M.append(M[i])
        M=M[l:]

        if M !=[] :
            m2=random.choice(M)
            self.bond(pos,m2)

        l=len(N)
        for i in range(l) :
            if self.bondable(pos,N[i]) :
                N.append(N[i])
        N=N[l:]

        if N !=[] :
            n1=random.choice(N)
            self.bond(pos,n1)

        N = self.find_L(pos)
        l=len(N)
        for i in range(l) :
            if self.bondable(pos,N[i]) :
                N.append(N[i])
        N=N[l:]

        if N !=[] :
            n2=random.choice(N)
            self.bond(pos,n2)

    def rebond(self,pos) :
        L=self.find_B1(pos)
        pairs=[]
        for i in range(len(L)) :
            for j in range(len(L)) :
                if self.bondable(L[i],L[j]):
                    pairs.append((L[i],L[j]))
        while pairs != [] :
            random_pair = random.choice(pairs)
            self.bond(random_pair[0],random_pair[1])
            L=self.find_B1(pos)
            pairs=[]
            for i in range(len(L))  :
                for j in range(len(L)) :
                    if self.bondable(L[i],L[j]):
                        pairs.append((L[i],L[j]))
        L = self.find_B1(pos)+self.find_L(pos)
        pairs=[]
        for i in range(len(L)) :
            for j in range(len(L)) :
                if self.bondable(L[i],L[j]):
                    pairs.append((L[i],L[j]))
        while pairs != [] :
            random_pair = random.choice(pairs)
            self.bond(random_pair[0],random_pair[1])
            L=self.find_B1(pos)+self.find_L(pos)
            pairs=[]
            for i in range(len(L)) :
                for j in range(len(L)) :
                    if self.bondable(L[i],L[j]):
                        pairs.append((L[i],L[j]))

    def __str__(self) :
        M=np.array(((-1,1),(0,1),(1,1),(1,0)))
        D=('/','-','\\','|')
        m=[[' ' for i in range(3*self.n -2)] for j in range(3*self.n -2)]
        for i in range(self.n) :
            for j in range(self.n) :
                m[3*i][3*j] = self.x[i][j][0]
                for k in range(len(M)) :
                    if is_in(M[k], self.x[i][j] ) :
                        p=3*np.array((i,j)) + M[k]
                        q=3*np.array((i,j)) + 2*M[k]
                        m[p[0]][p[1]]=D[k]
                        m[q[0]][q[1]]=D[k]
        S='\n'.join([''.join(m[i]) for i in range(len(m))]) +'\n' +  len(m)*'-'
        return S

def main(t_s) :
    n=int(input('Give length: '))
    K=float(input('Give disintegration rate: '))
    A=Autopoiesis(n,K)
    print(0)
    print(A)
    for i in range(t_s):
        print(i+1)
        A.motion1()

        A.motion2()

        A.motion3()

        A.production()

        A.disintegration()

        print()
        print(A)

t_s=int(input('Give number of time steps: '))
main(t_s)


from mio import runtime
from mio.object import Object
from mio.utils import method, Null

class State(Object):

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

        self.isContinue = False
        self.isReturn = False
        self.isBreak = False

        self.create_methods()
        self.parent = runtime.find("Object")

    def __repr__(self):
        if self.isContinue:
            type = "Continue"
        elif self.isReturn:
            type = "Return"
        elif self.isBreak:
            type = "Break"
        else:
            type = "Normal"

        value = repr(self.value) if self.value is not Null else ""

        return "{0:s}State({1:s})".format(type, value)

    def reset(self):
        keys = ("isContinue", "isReturn", "isBreak",)
        for key in keys:
            setattr(self, key, False)
        self.value = Null

    @property
    def stop(self):
        keys = ("isContinue", "isReturn", "isBreak",)
        return any((getattr(self, key) for key in keys))

    @method("stop")
    def _stop(self, receiver, context, m):
        return runtime.find("True") if receiver.stop else runtime.find("False")

    @method()
    def setContinue(self, receiver, context, m, value=None):
        if context.type != "Locals":
            return receiver

        value = bool(value.eval(context)) if value is not None else True
        receiver.isContinue = value
        return receiver

    @method()
    def setReturn(self, receiver, context, m, value=None):
        if context.type != "Locals":
            return receiver

        value = value.eval(context) if value is not None else Null
        receiver.isReturn = True
        receiver.value = value
        return receiver

    @method()
    def setBreak(self, receiver, context, m, value=None):
        if context.type != "Locals":
            return receiver

        value = bool(value.eval(context)) if value is not None else True
        receiver.isBreak = value
        return receiver


import cv2
import numpy as np
import math

# from cocoNLP.extractor import extractor
import cv2
import numpy as np
import os
import time
import glob
from tqdm import tqdm

def predict(img, ocr):
    ocr_data = ocr.ocr(img, cls=True)
    return ocr_data

def rotate_bound(image, angle):
    # 旋转中心点，默认为图像中心点
    (h, w) = image.shape[:2]
    (cX, cY) = (w // 2, h // 2)
    # 给定旋转角度后，得到旋转矩阵
    # 数学原理：
    #       https://blog.csdn.net/liyuan02/article/details/6750828
    M = cv2.getRotationMatrix2D((cX, cY), angle, 1.0)  # 得到旋转矩阵，1.0表示与原图大小一致
    # print("RotationMatrix2D：\n", M)
    cos = np.abs(M[0, 0])
    sin = np.abs(M[0, 1])

    # 计算旋转后的图像大小（避免图像裁剪）
    nW = int((h * sin) + (w * cos))
    nH = int((h * cos) + (w * sin))

    # 调整旋转矩阵（避免图像裁剪）
    M[0, 2] += (nW / 2) - cX
    M[1, 2] += (nH / 2) - cY
    # print("RotationMatrix2D：\n", M)

    # 执行仿射变换、得到图像
    return cv2.warpAffine(
        image, M, (nW, nH),
        # borderMode=cv2.BORDER_DEFAULT
        borderValue=(255, 255, 255)
    )  # BORDER_REPLICATE)
    # borderMode=cv2.BORDER_REPLICATE 使用边缘值填充
    # 或使用borderValue=(255,255,255)) # 使用常数填充边界（0,0,0）表示黑色

def get_points(coordinate):
    center = coordinate[0]
    for _ in range(1, 4):
        center = center + coordinate[_]
    center = center / 4
    coordinate_temp = coordinate.copy()  # 复制一份坐标，避免原坐标被破坏
    left_coordinate = []  # 存储x轴小于中心坐标点的点
    delete_index = []
    left_top, right_top, right_bottom, left_bottom = 0, 0, 0, 0
    # 将 x轴小于中心坐标点的点 存储进left_coordinate
    for _ in range(4):
        if (coordinate[_][0] < center[0]):
            left_coordinate.append(coordinate[_])
            delete_index.append(_)
    # 将存储进 left_coordinate 的元素从coordinate_temp中删除
    coordinate_temp = np.delete(coordinate_temp, delete_index, axis=0)
    left_coordinate_temp = left_coordinate.copy()  # 避免程序过程因为left_coordinate的变动而导致最初的条件判断错误

    if len(left_coordinate_temp) == 2:
        # 比较左边两个点的y轴，大的为左上
        if left_coordinate[0][1] < left_coordinate[1][1]:
            left_bottom = left_coordinate[0]
            left_top = left_coordinate[1]
        elif left_coordinate[0][1] > left_coordinate[1][1]:
            left_bottom = left_coordinate[1]
            left_top = left_coordinate[0]
        # 比较右边两个点的y轴，大的为右上
        if coordinate_temp[0][1] < coordinate_temp[1][1]:
            right_bottom = coordinate_temp[0]
            right_top = coordinate_temp[1]
        elif coordinate_temp[0][1] > coordinate_temp[1][1]:
            right_bottom = coordinate_temp[1]
            right_top = coordinate_temp[0]
    elif (len(left_coordinate_temp) == 1):
        left_bottom = left_coordinate[0]
        delete_index = []
        for _ in range(3):
            if (coordinate_temp[_][0] == center[0] and coordinate_temp[_][1] > center[1]):
                left_top = coordinate_temp[_]
                delete_index.append(_)
            if (coordinate_temp[_][0] == center[0] and coordinate_temp[_][1] < center[1]):
                right_bottom = coordinate_temp[_]
                delete_index.append(_)
        coordinate_temp = np.delete(coordinate_temp, delete_index, axis=0)
        right_top = coordinate_temp[0]
    return left_top, right_top, right_bottom, left_bottom

def get_rotate_angle_with_boxes(boxes, img):
    lines = []
    out_boxes = []
    for box in boxes:
        p1, p2, p3, p4 = get_points(box)
        if len(np.array(p1).shape) == 0 or len(np.array(p2).shape) == 0:
            continue
        x1, y1 = p1
        x2, y2 = p2
        length = ((x1 - x2) ** 2 + (y1 - y2) ** 2) ** 0.5
        angle = math.atan((y2 - y1) / (x2 - x1))
        angle = angle * (180 / math.pi)
        lines.append([x1, y1, x2, y2, angle, length])
        out_boxes.append([box, angle, length])
    lines.sort(key=lambda x: x[-1])
    if len(lines)>6:
        angles = [x[-2] for x in lines[-5:-1]]
        angle = np.mean(angles)
    else:
        angle=0
    #
    out_boxes.sort(key=lambda x: x[-1])
    filtered_boxes = out_boxes[-5:-1]
    for b in filtered_boxes:
        box, _, _ = b
        cv2.fillPoly(img,[np.array(box,np.int32)], (255,255,255))
    # cv2.imshow('im', img)
    # cv2.waitKey(0)
    # longest_line = lines[-1]
    # x1, y1, x2, y2, length = longest_line
    # cv2.line(image, (x1, y1), (x2, y2), (0, 0, 255), 4)  # 绘制直线（红色）
    #
    # if x2 == x1:
    #     angle = 0
    # else:
    #     angle = math.atan((y2 - y1) / (x2 - x1))
    #     # print("angle-radin:", angle)  # 弧度形式
    #     angle = angle * (180 / math.pi)
    #     # print("angle-degree:", angle)  # 角度形式
    return angle

def get_rotation_angle(image, show_longest_line=True, show_all_lines=False):
    # image = image.copy()  # 复制备份，因为line（）函数为in-place
    gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
    edges = cv2.Canny(gray, 100, 150, apertureSize=3)  # canny， 便于hough line减少运算量
    lines = cv2.HoughLinesP(edges, 1, np.pi / 180, 100, minLineLength=50, maxLineGap=60)  # 参数很关键
    # minLineLengh(线的最短长度，比这个短的都被忽略)
    # maxLineCap（两条直线之间的最大间隔，小于此值，认为是一条直线）
    # 函数cv2.HoughLinesP()是一种概率直线检测，原理上讲hough变换是一个耗时耗力的算法，
    # 尤其是每一个点计算，即使经过了canny转换了有的时候点的个数依然是庞大的，
    # 这个时候我们采取一种概率挑选机制，不是所有的点都计算，而是随机的选取一些个点来计算，相当于降采样。
    lengths = []  # 存储所有线的坐标、长度
    if lines is None:
        return 0
    for line in lines:
        x1, y1, x2, y2 = line[0]
        length = ((x1 - x2) ** 2 + (y1 - y2) ** 2) ** 0.5  # 勾股定理，求直线长度
        angle = math.atan((y2 - y1) / (x2 - x1))
        angle = angle * (180 / math.pi)
        lengths.append([x1, y1, x2, y2, angle, length])
        # print(line, length)
        if show_all_lines:
            cv2.line(image, (x1, y1), (x2, y2), (255, 0, 0), 2)  # 绘制所有直线（黑色）
    # 绘制最长的直线
    lengths.sort(key=lambda x: x[-1])
    longest_line = lengths[-1]
    x1, y1, x2, y2, angle, length = longest_line
    cv2.line(image, (x1, y1), (x2, y2), (0, 0, 255), 2)
    return angle
    # for i in range(len(lengths)-1,-1):
    #     line = lengths[i]
    #     x1, y1, x2, y2, angle, length = line
    #     if angle<-45 or angle>45:
    #         return 0
    #     else:
    #         return angle
    # longest_line = lengths[-1]
    # # print("longest_line: ", longest_line)
    # x1, y1, x2, y2, length = longest_line
    # if show_longest_line:
    #     cv2.line(image, (x1, y1), (x2, y2), (0, 0, 255), 2)  # 绘制直线（红色）
    # # 计算这条直线的旋转角度
    # if x2 == x1:
    #     angle = 0
    # else:
    #     angle = math.atan((y2 - y1) / (x2 - x1))
    #     # print("angle-radin:", angle)  # 弧度形式
    #     angle = angle * (180 / math.pi)
    #     # print("angle-degree:", angle)  # 角度形式

def inpaint_with_ocr(ocr_data, img: np.ndarray):
    bboxes = [x[0] for x in ocr_data]
    ocr_img = img.copy()
    for box in bboxes:
        cv2.fillPoly(ocr_img, [np.array(box, np.int32)], (255, 255, 255))
    return ocr_img

def run(src_img):

    ocr_data = predict(src_img, ocr)
    ocr_img = inpaint_with_ocr(ocr_data, src_img)
    ret, dst = cv2.threshold(ocr_img, 150, 230, cv2.THRESH_TOZERO_INV)
    dst = 255 - dst
    angle = get_rotation_angle(dst, False, False)
    imag = rotate_bound(src_img, angle)
    return imag

def run2(src_img):
    img = src_img.copy()
    gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
    kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (3, 3))
    dilate = cv2.dilate(img, kernel,iterations=5)
    erode = cv2.erode(img, kernel)
    res = cv2.absdiff(dilate, erode)
    retval, result = cv2.threshold(res, 127, 255, cv2.THRESH_BINARY)
    result = cv2.dilate(result, kernel)
    # cnts, _ = cv2.findContours(result.astype(np.uint8), cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
    # boxes = []
    # for cnt in cnts:
    #     rect = cv2.minAreaRect(cnt)
    #     box = cv2.boxPoints(rect)  # cv.boxPoints(rect) for OpenCV 3.x 获取最小外接矩形的4个顶点
    #     box = np.int0(box)
    #     cv2.drawContours(img, [box], -1, (0, 0, 0), -1)
    #     boxes.append(box)
    # angle = get_rotation_angle(img, True, False)
    angle = get_rotation_angle(result)
    print(angle)
    # out_im = cv2.resize(np.concatenate((img, src_img), axis=1), (960, 480))
    # cv2.imshow(f'{angle}', out_im)
    # cv2.waitKey(0)
    # cv2.destroyAllWindows()
    imag = rotate_bound(src_img, angle)
    return imag

def get_rotate_imgs():
    src_img_dir = '/home/zhaohj/Documents/dataset/signed_dataset/YMDS/TableSegmentation'
    output_img_dir = '/home/zhaohj/Documents/dataset/signed_dataset/YMDS/TableSegmentation_rotated_opencv'
    os.makedirs(output_img_dir, exist_ok=True)
    imgs_list = glob.glob(f'{src_img_dir}/*.png')
    for i in tqdm(range(len(imgs_list))):
        src_img_path = imgs_list[i]
        _, filename = os.path.split(src_img_path)
        output_filepath = os.path.join(output_img_dir, filename)
        src_img = cv2.imread(src_img_path)
        imag = run2(src_img)
        cv2.imwrite(output_filepath, imag)

def merge_img(img1, img2):
    h, w, c = img1.shape
    img2 = cv2.resize(img2, (w, h))
    out_img = np.concatenate((img1, img2), axis=1)
    pt1 = [0, h // 2]
    pt2 = [2 * w, h // 2]
    cv2.line(out_img, pt1, pt2, (255, 0, 0), 3)
    out_img = cv2.resize(out_img, (960, 480))
    return out_img

def compare_imgs():
    img1_dir = '/home/zhaohj/Documents/dataset/signed_dataset/YMDS/TableSegmentation_rotated'
    img2_dir = '/home/zhaohj/Documents/dataset/signed_dataset/YMDS/TableSegmentation_rotated_opencv'
    imgs = os.listdir(img1_dir)
    imgs.sort()
    for i in tqdm(range(len(imgs))):
        filename = imgs[i]
        img1_path = os.path.join(img1_dir, filename)
        img2_path = os.path.join(img2_dir, filename)
        img1 = cv2.imread(img1_path)
        img2 = cv2.imread(img2_path)
        out_img = merge_img(img1, img2)
        cv2.imshow('win', out_img)
        cv2.waitKey(0)

if __name__ == '__main__':
    # get_rotate_imgs()
    compare_imgs()


import os.path
import unittest
from lxml.etree import _Element, ElementTree
from nineml import read
from nineml.abstraction_layer.random import ComponentClass
import tempfile

examples_dir = os.path.join(os.path.dirname(__file__), '..', '..', '..', '..',
                            '..', '..', '..', 'catalog', 'randomdistributions')

class TestRandomDistribution(unittest.TestCase):

    def test_load(self):
        context = read(os.path.join(examples_dir, 'normal.xml'))
        self.assertEquals(type(context['NormalDistribution']), ComponentClass)

    def test_to_xml(self):
        context = read(os.path.join(examples_dir, 'normal.xml'))
        comp_class = context['NormalDistribution']
        xml = comp_class.to_xml()
        self.assertEquals(_Element, type(xml))
        with tempfile.TemporaryFile() as f:
            ElementTree(xml).write(f, encoding="UTF-8", pretty_print=True,
                                   xml_declaration=True)


string = input().strip()
substring = input().strip()
substring_len = len(substring)

bottom = len(string) - len(substring)
top = len(string)
counter = 0

while bottom >= 0:
    if substring in string[bottom:top]:
        counter += 1
        bottom -= substring_len - 1
        top -= substring_len - 1
    else:
        bottom -= 1
        top -= 1

print(counter)


#!/usr/bin/python3

# This file creates the indexes for Elastic 6.x as mappings format is different (sigh)
import urllib.parse
import os
import glob
import datetime
import json
import time

import sys
sys.path.append("../api")
import elasticsearch
sys.path.append("../www/scripts")
import maas_conf

def delete_indices ():
  x = elasticsearch.delete_index(es,"maas_config_fragments")
  x = elasticsearch.delete_index(es,"maas_config_entity_publish")
  x = elasticsearch.delete_index(es,"maas_config_entity_require")
  x = elasticsearch.delete_index(es,"maas_config_alert")
  x = elasticsearch.delete_index(es,"maas_alert_log_current")
  x = elasticsearch.delete_index(es,"maas_alert_log_history")
  x = elasticsearch.delete_index(es,"maas_entity_log_config")

def create_indices ():
  settings = {"settings":{ "number_of_shards" : 1, "number_of_replicas":0 } }
  # Templates used to build up host configirations
  x = elasticsearch.create_index(es,"maas_config_fragments",settings)

  settings = {"settings":{ "number_of_shards" : 1, "number_of_replicas":0 }, "mappings":{ "_doc":{"properties":{"last_updated":{"type":"date","format":"dd/MM/yyyy HH:mm:ss"}}}}}
  # Fully populated config per host
  x = elasticsearch.create_index(es,"maas_config_entity_publish",settings)
  # Custom monitoring requirements
  x = elasticsearch.create_index(es,"maas_config_entity_require",settings)
  # Alert settings
  x = elasticsearch.create_index(es,"maas_config_alert",settings)

  settings = {"settings":{ "number_of_shards" : 1, "number_of_replicas":0 }, "mappings":{ "_doc": {"properties":{"timestamp":{"type":"date","format":"dd/MM/yyyy HH:mm:ss"},"metric_timestamp":{"type":"date","format":"yyyy-MM-dd HH:mm:ss"}}}}}
  # Latest results from alert run
  x = elasticsearch.create_index(es,"maas_alert_log_current",settings)
  # History of all alerts generated
  x = elasticsearch.create_index(es,"maas_alert_log_history",settings)

  # Log of incoming configuration requests
  settings = {"settings":{ "number_of_shards" : 1, "number_of_replicas":0 }, "mappings":{ "_doc": {"properties":{"timestamp":{"type":"date","format":"dd/MM/yyyy HH:mm:ss"}}}}}
  x = elasticsearch.create_index(es,"maas_entity_log_config",settings)
  x = elasticsearch.show_indices(es)
  for a in x:
    print(a.decode("UTF-8").rstrip())

es = { "url" : maas_conf.conf['elastic']['url'], "user" : maas_conf.conf['elastic']['user'], "pass" : maas_conf.conf['elastic']['pass'] }

#delete_indices()
time.sleep(2)
create_indices()


import PySimpleGUI as sg
import glob
import torch

import os
import random
import shutil

import datetime
import cv2

import sys
import subprocess
import traceback

# def ExecuteCommandSubprocess(command, *args, wait=False):
#     try:
#         if sys.platform == 'linux':
#             arg_string = ''
#             arg_string = ' '.join([str(arg) for arg in args])
#             # for arg in args:
#             #     arg_string += ' ' + str(arg)
#             print('python3 ' + arg_string)
#             sp = subprocess.Popen(['python3 ', arg_string],
#                                   shell=True,
#                                   stdout=subprocess.PIPE,
#                                   stderr=subprocess.PIPE)
#         else:
#             arg_string = ' '.join([str(arg) for arg in args])
#             sp = subprocess.Popen([command, arg_string],
#                                   shell=True,
#                                   stdout=subprocess.PIPE,
#                                   stdin= subprocess.PIPE,
#                                   stderr=subprocess.PIPE,)
#                                   #cwd=True)
#             print("the commandline is {}".format(sp.args))
#             print("Ter {}".format(sp.returncode))
#             # sp = subprocess.Popen([command, list(args)], shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE)

#         if wait:
#             out, err = sp.communicate()
#             if out:
#                 print(out.decode("utf-8"))
#             if err:
#                 print(err.decode("utf-8"))
#     except:
#         pass

def time_to_name():
    current_time = datetime.datetime.now()
    name_folder = str(current_time)
    name_folder = list(name_folder)
    for i in range(len(name_folder)):
        if name_folder[i] == ':':
            name_folder[i] = '-'
        if name_folder[i] == ' ':
            name_folder[i] ='_'
        if name_folder[i] == '.':
            name_folder[i] ='-'
    name_folder = ''.join(name_folder)
    return name_folder

theme_dict = {'BACKGROUND': '#2B475D',
                'TEXT': '#FFFFFF',
                'INPUT': '#F2EFE8',
                'TEXT_INPUT': '#000000',
                'SCROLL': '#F2EFE8',
                'BUTTON': ('#000000', '#C2D4D8'),
                'PROGRESS': ('#FFFFFF', '#C7D5E0'),
                'BORDER': 1,'SLIDER_DEPTH': 0, 'PROGRESS_DEPTH': 0}

# # sg.theme_add_new('Dashboard', theme_dict)     # if using 4.20.0.1+
sg.LOOK_AND_FEEL_TABLE['Dashboard'] = theme_dict
sg.theme('Dashboard')

BORDER_COLOR = '#C7D5E0'
#BORDER_COLOR = '#fcfffd'
DARK_HEADER_COLOR = '#1B2838'
MYBPAD = ((20,10), (10, 10))

mypath1 = 'D:/FILE_TRAIN_A17/file_train_c4/A17_C4_06_12_2022.pt'
model1 = torch.hub.load('./levu','custom', path= mypath1, source='local',force_reload =False)

file_weights = [('Weights (*.pt)', ('*.pt'))]

def make_window():
    # top  = [[sg.Text('Auto Training', size=(80,1), justification='center', pad=MYBPAD, font='Any 25', text_color='red')],]

    # Step_1 = [
    #             [sg.T('1.Choose file weights', font='Any 15', text_color = 'orange')],
    #             [sg.Input(size=(35,1), font=('Helvetica',12), key='input_weight1',readonly= True, text_color='navy',enable_events= True),
    #             sg.FileBrowse(file_types= file_weights,size=(12,1), font=('Helvetica',10),key= 'directory_weight1',enable_events=True) ],
    #             [sg.T('2.Choose confident', font='Any 15', text_color = 'orange')],
    #             [sg.Slider(range=(1,100),orientation='h',size=(48,20),font=('Helvetica',11),default_value=25, key= 'input_conf1')],
    #             [sg.T('3.Choose folder image', font='Any 15', text_color = 'orange')],
    #             [sg.Input(size=(35,1), font=('Helvetica',12), key='input_image1',readonly= True, text_color='navy',enable_events= True),
    #             sg.FolderBrowse(size=(12,1), font=('Helvetica',10),key= 'directory_image1',enable_events=True) ],
    #             # [sg.T('4.Choose folder model', font='Any 15', text_color = 'orange')],
    #             # [sg.Input(size=(35,1), font=('Helvetica',12), key='input_model1',readonly= True, text_color='navy',enable_events= True),
    #             # sg.FolderBrowse(size=(12,1), font=('Helvetica',10),key= 'directory_model1',enable_events=True) ],
    #             [sg.T('4.Choose folder save', font='Any 15', text_color = 'orange')],
    #             [sg.Input(size=(35,1), font=('Helvetica',12), key='input_save1',readonly= True, text_color='navy',enable_events= True),
    #             sg.FolderBrowse(size=(12,1), font=('Helvetica',10),key= 'directory_save1',enable_events=True) ],
    #             #[sg.Listbox(values=CLASSES1,size=(23,4), text_color= 'navy',select_mode= sg.LISTBOX_SELECT_MODE_MULTIPLE, key='classes1')],
    #             [sg.T('5.Start create auto label', font='Any 15', text_color = 'orange')],
    #             [sg.Button('Start', size=(12,1), font=('Helvetica',10),key= 'start1')],
    #         ]

    Step_1 =[
                [sg.Text('Step 1: Get image in folder', font='Any 20', text_color='yellow')],
                [sg.T('1.Choose folder get image             ', font='Any 15', text_color = 'orange')],
                [sg.Input(size=(30,1), font=('Helvetica',12), key='input_image0',readonly= True, text_color='navy',enable_events= True),
                sg.FolderBrowse(size=(12,1), font=('Helvetica',10),key= 'directory_image0',enable_events=True) ],
                [sg.T('2.Choose folder save image             ', font='Any 15', text_color = 'orange')],
                [sg.Input(size=(30,1), font=('Helvetica',12), key='input_save0',readonly= True, text_color='navy',enable_events= True),
                sg.FolderBrowse(size=(12,1), font=('Helvetica',10),key= 'directory_save0',enable_events=True) ],
                [sg.T('3.Enter name image you want get             ', font='Any 15', text_color = 'orange')],
                [sg.Multiline('',size=(40,10),text_color='navy' ,key='input_names0')],
                [sg.Button('OK', size=(12,1), font=('Helvetica',10),key= 'button_names0')],
                [sg.T('4.Start get image           ', font='Any 15', text_color = 'orange')],
                [sg.Button('Start', size=(12,1), font=('Helvetica',10),key= 'start0')],
    ]

    Step_2 = [
                #[sg.Frame('',[
                [sg.Frame('',
                [
                    [sg.Text('Step 2: Auto filter image', font='Any 20', text_color='yellow')],
                    [sg.T('1.Choose file weights              ', font='Any 15', text_color = 'orange'),
                    sg.Input(size=(60,1), font=('Helvetica',12), key='input_weight1',readonly= True, text_color='navy',enable_events= True),
                    sg.FileBrowse(file_types= file_weights, size=(12,1), font=('Helvetica',10),key= 'file_browse1',enable_events=True)],
                    [sg.T('2.Choose confident                 ', font='Any 15', text_color = 'orange'),
                    sg.Slider(range=(1,100),orientation='h',size=(60,20),font=('Helvetica',11),key= 'input_conf1'),]
                ], relief=sg.RELIEF_FLAT),
                ],
                [sg.T('3.Choose Parameter', font='Any 15', text_color = 'orange')],
                [sg.Frame('',[
                    [sg.Text('Name',size=(15,1),font=('Helvetica',15), text_color='orange'),
                    sg.Text('Join',size=(7,1),font=('Helvetica',15), text_color='orange'),
                    sg.Text('OK',size=(7,1),font=('Helvetica',15), text_color='orange'),
                    sg.Text('Num',size=(7,1),font=('Helvetica',15), text_color='orange'),
                    sg.Text('NG',size=(8,1),font=('Helvetica',15), text_color='orange'),
                    sg.Text('Width Min',size=(11,1),font=('Helvetica',15), text_color='orange'),
                    sg.Text('Width Max',size=(11,1),font=('Helvetica',15), text_color='orange'),
                    sg.Text('Height Min',size=(11,1),font=('Helvetica',15), text_color='orange'),
                    sg.Text('Height Max',size=(9,1),font=('Helvetica',15), text_color='orange')],
                ], relief=sg.RELIEF_FLAT)],
                [sg.Frame('',[
                    [
                        sg.Text(f'{model1.names[i1]}_1',size=(15,1),font=('Helvetica',15), text_color='pink'),
                        sg.Checkbox('',size=(5,5),default=True,font=('Helvetica',15),  key=f'{model1.names[i1]}_1',enable_events=True),
                        sg.Checkbox('',size=(5,5),font=('Helvetica',15),  key=f'{model1.names[i1]}_OK_1',enable_events=True),
                        sg.Input('1',size=(2,1),font=('Helvetica',15),key= f'{model1.names[i1]}_Num_1',text_color='navy',enable_events=True),
                        sg.Text('',size=(4,1),font=('Helvetica',15), text_color='red'),
                        sg.Checkbox('',size=(5,5),font=('Helvetica',15),  key=f'{model1.names[i1]}_NG_1',enable_events=True),
                        sg.Input('0',size=(8,1),font=('Helvetica',15),key= f'{model1.names[i1]}_Wn_1',text_color='navy',enable_events=True),
                        sg.Text('',size=(2,1),font=('Helvetica',15), text_color='red'),
                        sg.Input('100000',size=(8,1),font=('Helvetica',15),key= f'{model1.names[i1]}_Wx_1',text_color='navy',enable_events=True),
                        sg.Text('',size=(2,1),font=('Helvetica',15), text_color='red'),
                        sg.Input('0',size=(8,1),font=('Helvetica',15),key= f'{model1.names[i1]}_Hn_1',text_color='navy',enable_events=True),
                        sg.Text('',size=(2,1),font=('Helvetica',15), text_color='red'),
                        sg.Input('100000',size=(8,1),font=('Helvetica',15),key= f'{model1.names[i1]}_Hx_1',text_color='navy',enable_events=True),
                    ] for i1 in range(len(model1.names))
                ], relief=sg.RELIEF_FLAT)],
                [sg.T('4.Choose folder image              ', font='Any 15', text_color = 'orange'),
                sg.Input(size=(60,1), font=('Helvetica',12), key='input_image1',readonly= True, text_color='navy',enable_events= True),
                sg.FolderBrowse(size=(12,1), font=('Helvetica',10),key= 'directory_image1',enable_events=True) ],
                # [sg.T('4.Choose folder model', font='Any 15', text_color = 'orange')],
                # [sg.Input(size=(35,1), font=('Helvetica',12), key='input_model1',readonly= True, text_color='navy',enable_events= True),
                # sg.FolderBrowse(size=(12,1), font=('Helvetica',10),key= 'directory_model1',enable_events=True) ],
                [sg.T('5.Choose folder save                ', font='Any 15', text_color = 'orange'),
                sg.Input(size=(60,1), font=('Helvetica',12), key='input_save1',readonly= True, text_color='navy',enable_events= True),
                sg.FolderBrowse(size=(12,1), font=('Helvetica',10),key= 'directory_save1',enable_events=True) ],
                #[sg.Listbox(values=CLASSES1,size=(23,4), text_color= 'navy',select_mode= sg.LISTBOX_SELECT_MODE_MULTIPLE, key='classes1')],
                [sg.T('6.Start create auto label            ', font='Any 15', text_color = 'orange')],
                [sg.Button('Start', size=(12,1), font=('Helvetica',10),key= 'start1')],
                ]
                #,expand_x=True)]
    #]

    Step_3 = [
                [sg.Text('Step 3: Auto create label', font='Any 20', text_color='yellow')],
                [sg.T('1.Choose file weights', font='Any 15', text_color = 'orange')],
                [sg.Input(size=(35,1), font=('Helvetica',12), key='input_weight2',readonly= True, text_color='navy',enable_events= True),
                sg.FileBrowse(file_types= file_weights,size=(12,1), font=('Helvetica',10),key= 'directory_weight2',enable_events=True) ],
                [sg.T('2.Choose confident', font='Any 15', text_color = 'orange')],
                [sg.Slider(range=(1,100),orientation='h',size=(48,20),font=('Helvetica',11),default_value=25 ,key= 'input_conf2')],
                [sg.T('3.Choose folder image', font='Any 15', text_color = 'orange')],
                [sg.Input(size=(35,1), font=('Helvetica',12), key='input_image2',readonly= True, text_color='navy',enable_events= True),
                sg.FolderBrowse(size=(12,1), font=('Helvetica',10),key= 'directory_image2',enable_events=True) ],
                # [sg.T('4.Choose folder model', font='Any 15', text_color = 'orange')],
                # [sg.Input(size=(35,1), font=('Helvetica',12), key='input_model1',readonly= True, text_color='navy',enable_events= True),
                # sg.FolderBrowse(size=(12,1), font=('Helvetica',10),key= 'directory_model2',enable_events=True) ],
                [sg.T('4.Choose folder save', font='Any 15', text_color = 'orange')],
                [sg.Input(size=(35,1), font=('Helvetica',12), key='input_save2',readonly= True, text_color='navy',enable_events= True),
                sg.FolderBrowse(size=(12,1), font=('Helvetica',10),key= 'directory_model2',enable_events=True) ],
                [sg.T('5.Enter all name labels', font='Any 15', text_color = 'orange')],
                [sg.Multiline('',size=(40,10),text_color='navy' ,key='input_classes2')],
                [sg.Button('OK', size=(12,1), font=('Helvetica',10),key= 'button_classes2')],
                [sg.T('6.Enter labels and index edit', font='Any 15', text_color = 'orange')],
                [sg.Multiline('',size=(40,10),text_color='navy' ,key='input_classes2_1')],
                [sg.Button('OK', size=(12,1), font=('Helvetica',10),key= 'button_classes2_1')],
                #[sg.Listbox(values=CLASSES1,size=(23,4), text_color= 'navy',select_mode= sg.LISTBOX_SELECT_MODE_MULTIPLE, key='classes1')],
                [sg.T('7.Start create auto label', font='Any 15', text_color = 'orange')],
                [sg.Button('Start', size=(12,1), font=('Helvetica',10),key= 'start2')],

            ]

    Step_4 = [
                [sg.Text('Step 4: Create label by program', font='Any 20', text_color='yellow')],
                [sg.T('1.Enter all name labels', font='Any 15', text_color = 'orange')],
                [sg.Multiline('',size=(40,10),text_color='navy' ,key='input_classes3')],
                [sg.Button('OK', size=(12,1), font=('Helvetica',10),key= 'button_classes3')],
                [sg.T('2.Open Program', font='Any 15', text_color = 'orange')],
                [sg.Button('Open Program', size=(12,1), font=('Helvetica',10),key= 'program3')],
            ]

    Step_5 = [
                [sg.Text('Step 5: Auto split image and label', font='Any 20', text_color='yellow')],
                [sg.T('1.Choose folder image', font='Any 15', text_color = 'orange')],
                [sg.Input(size=(35,1), font=('Helvetica',12), key='input_image4',readonly= True, text_color='navy',enable_events= True),
                sg.FolderBrowse(size=(12,1), font=('Helvetica',10),key= 'directory_image4',enable_events=True) ],
                [sg.T('2.Choose folder save', font='Any 15', text_color = 'orange')],
                [sg.Input(size=(35,1), font=('Helvetica',12), key='input_save4',readonly= True, text_color='navy',enable_events= True),
                sg.FolderBrowse(size=(12,1), font=('Helvetica',10),key= 'directory_save4',enable_events=True) ],
                #[sg.Listbox(values=CLASSES1,size=(23,4), text_color= 'navy',select_mode= sg.LISTBOX_SELECT_MODE_MULTIPLE, key='classes1')],
                [sg.T('3.Start split image and label', font='Any 15', text_color = 'orange')],
                [sg.Button('Start', size=(12,1), font=('Helvetica',10),key= 'start4')],
            ]

    Step_6 = [
                [sg.Text('Step 6: Auto Training', font='Any 20', text_color='yellow')],
                [sg.T('1.Choose folder contain folder train and valid', font='Any 15', text_color = 'orange')],
                [sg.Input(size=(35,1), font=('Helvetica',12), key='input_move5',readonly= True, text_color='navy',enable_events= True),
                sg.FolderBrowse(size=(12,1), font=('Helvetica',10),key= 'directory_move5',enable_events=True) ],
                [sg.T('2.Move folder', font='Any 15', text_color = 'orange')],
                [sg.Button('Move', size=(12,1), font=('Helvetica',10),key= 'move5')],
                [sg.T('3.Enter all name labels', font='Any 15', text_color = 'orange')],
                [sg.Multiline('',size=(40,8),text_color='navy' ,key='input_classes5')],
                [sg.Button('OK', size=(12,1), font=('Helvetica',10),key= 'button_classes5')],
                [sg.T('4.Enter image size', font='Any 15', text_color = 'orange'),
                sg.InputCombo((416,512,608,896,1024,1280,1408,1536),size=(23,30),default_value=416,key='imgsz5')],
                [sg.T('5.Choose epoch', font='Any 15', text_color = 'orange')],
                [sg.Slider(range=(1,500),orientation='h',size=(48,20),font=('Helvetica',11),default_value=300,key= 'input_epoch5')],
                [sg.T('6.Choose folder save model', font='Any 15', text_color = 'orange')],
                [sg.Input(size=(35,1), font=('Helvetica',12), key='input_save5',readonly= True, text_color='navy',enable_events= True),
                sg.FolderBrowse(size=(12,1), font=('Helvetica',10),key= 'directory_image5',enable_events=True) ],
                [sg.T('7.Start auto training', font='Any 15', text_color = 'orange')],
                [sg.Button('Start', size=(12,1), font=('Helvetica',10),key= 'start5')],
                [sg.T('8.Get file model', font='Any 15', text_color = 'orange')],
                [sg.Button('Get', size=(12,1), font=('Helvetica',10),key= 'get5')],
            ]

    # layout_1 = [
    #     [sg.Text('VDM AI VISION', font='Any 40', text_color='blue',justification='center',expand_x=True,background_color='white')],
    #     [sg.Frame('',[
    #     [sg.Frame('',
    #     [
    #         [sg.Text('Step 1: Auto filter image', font='Any 20', text_color='yellow')],
    #         [sg.T('1.Choose file weights              ', font='Any 15', text_color = 'orange'),
    #         sg.Input(size=(60,1), font=('Helvetica',12), key='input_weight1',readonly= True, text_color='navy',enable_events= True),
    #         sg.FileBrowse(file_types= file_weights, size=(12,1), font=('Helvetica',10),key= 'file_browse1',enable_events=True)],
    #         [sg.T('2.Choose confident                 ', font='Any 15', text_color = 'orange'),
    #         sg.Slider(range=(1,100),orientation='h',size=(60,20),font=('Helvetica',11),key= 'input_conf1'),]
    #     ], relief=sg.RELIEF_FLAT),
    #     ],
    #     [sg.T('3.Choose Parameter', font='Any 15', text_color = 'orange')],
    #     [sg.Frame('',[
    #         [sg.Text('Name',size=(15,1),font=('Helvetica',15), text_color='orange'),
    #         sg.Text('Join',size=(7,1),font=('Helvetica',15), text_color='orange'),
    #         sg.Text('OK',size=(7,1),font=('Helvetica',15), text_color='orange'),
    #         sg.Text('Num',size=(7,1),font=('Helvetica',15), text_color='orange'),
    #         sg.Text('NG',size=(8,1),font=('Helvetica',15), text_color='orange'),
    #         sg.Text('Width Min',size=(11,1),font=('Helvetica',15), text_color='orange'),
    #         sg.Text('Width Max',size=(11,1),font=('Helvetica',15), text_color='orange'),
    #         sg.Text('Height Min',size=(11,1),font=('Helvetica',15), text_color='orange'),
    #         sg.Text('Height Max',size=(9,1),font=('Helvetica',15), text_color='orange')],
    #     ], relief=sg.RELIEF_FLAT)],
    #     [sg.Frame('',[
    #         [
    #             sg.Text(f'{model1.names[i1]}_1',size=(15,1),font=('Helvetica',15), text_color='pink'),
    #             sg.Checkbox('',size=(5,5),default=True,font=('Helvetica',15),  key=f'{model1.names[i1]}_1',enable_events=True),
    #             sg.Checkbox('',size=(5,5),font=('Helvetica',15),  key=f'{model1.names[i1]}_OK_1',enable_events=True),
    #             sg.Input('1',size=(2,1),font=('Helvetica',15),key= f'{model1.names[i1]}_Num_1',text_color='navy',enable_events=True),
    #             sg.Text('',size=(4,1),font=('Helvetica',15), text_color='red'),
    #             sg.Checkbox('',size=(5,5),font=('Helvetica',15),  key=f'{model1.names[i1]}_NG_1',enable_events=True),
    #             sg.Input('0',size=(8,1),font=('Helvetica',15),key= f'{model1.names[i1]}_Wn_1',text_color='navy',enable_events=True),
    #             sg.Text('',size=(2,1),font=('Helvetica',15), text_color='red'),
    #             sg.Input('100000',size=(8,1),font=('Helvetica',15),key= f'{model1.names[i1]}_Wx_1',text_color='navy',enable_events=True),
    #             sg.Text('',size=(2,1),font=('Helvetica',15), text_color='red'),
    #             sg.Input('0',size=(8,1),font=('Helvetica',15),key= f'{model1.names[i1]}_Hn_1',text_color='navy',enable_events=True),
    #             sg.Text('',size=(2,1),font=('Helvetica',15), text_color='red'),
    #             sg.Input('100000',size=(8,1),font=('Helvetica',15),key= f'{model1.names[i1]}_Hx_1',text_color='navy',enable_events=True),
    #         ] for i1 in range(len(model1.names))
    #     ], relief=sg.RELIEF_FLAT)],
    #     [sg.T('4.Choose folder image              ', font='Any 15', text_color = 'orange'),
    #     sg.Input(size=(60,1), font=('Helvetica',12), key='input_image1',readonly= True, text_color='navy',enable_events= True),
    #     sg.FolderBrowse(size=(12,1), font=('Helvetica',10),key= 'directory_image1',enable_events=True) ],
    #     # [sg.T('4.Choose folder model', font='Any 15', text_color = 'orange')],
    #     # [sg.Input(size=(35,1), font=('Helvetica',12), key='input_model1',readonly= True, text_color='navy',enable_events= True),
    #     # sg.FolderBrowse(size=(12,1), font=('Helvetica',10),key= 'directory_model1',enable_events=True) ],
    #     [sg.T('5.Choose folder save                ', font='Any 15', text_color = 'orange'),
    #     sg.Input(size=(60,1), font=('Helvetica',12), key='input_save1',readonly= True, text_color='navy',enable_events= True),
    #     sg.FolderBrowse(size=(12,1), font=('Helvetica',10),key= 'directory_save1',enable_events=True) ],
    #     #[sg.Listbox(values=CLASSES1,size=(23,4), text_color= 'navy',select_mode= sg.LISTBOX_SELECT_MODE_MULTIPLE, key='classes1')],
    #     [sg.T('6.Start create auto label            ', font='Any 15', text_color = 'orange')],
    #     [sg.Button('Start', size=(12,1), font=('Helvetica',10),key= 'start1')],
    #     ],expand_x=True)]
    # ]

    layout_1 = [
        [sg.Text('VDM AI VISION', font='Any 40', text_color='blue',justification='center',expand_x=True,background_color='white')],
        [
            sg.Column(Step_1, size=(425,700),  pad=MYBPAD),
            sg.Column(Step_2,  pad=MYBPAD),
        ]
    ]

    layout_2 = [
            [sg.Text('VDM AI VISION', font='Any 40', text_color='blue',justification='center',expand_x=True,background_color='white')],
            [#sg.Column([[sg.Column(Step_1, size=(450,700), pad=MYBPAD)],], pad=MYBPAD, background_color=BORDER_COLOR),

            #sg.Column(Step_2, size=(450,700),  pad=MYBPAD),
                sg.Column(Step_3, size=(480,900),  pad=MYBPAD),
                sg.Column([
                            [sg.Column(Step_4, size=(480,395), pad=MYBPAD)],
                            [sg.Column(Step_5, size=(480,285), pad=MYBPAD)]], pad=MYBPAD, background_color=BORDER_COLOR),
                sg.Column(Step_6, size=(480,700),  pad=MYBPAD),
                ]]

    layout = [[
                sg.TabGroup([[
                            sg.Tab('Page 1', layout_1,background_color=BORDER_COLOR),
                            sg.Tab('Page 2', layout_2,background_color=BORDER_COLOR),
                            #sg.Tab('Page 3', layout_option,background_color=BORDER_COLOR),
                            ]],background_color=BORDER_COLOR,selected_background_color= BORDER_COLOR,selected_title_color='black')
                ]]
    window = sg.Window('Huynh Le Vu', layout, margins=(0,0), background_color=BORDER_COLOR, grab_anywhere=True)
    return window

mypath1 = 'D:/FILE_TRAIN_A17/file_train_c4/A17_C4_06_12_2022.pt'
model1 = torch.hub.load('./levu','custom', path= mypath1, source='local',force_reload =False)
window = make_window()

while True:             # Event Loop
    event, values = window.read(timeout=20)
    if event == sg.WIN_CLOSED or event == 'Exit':
        break

#1
    if event == 'button_names0' :
        if (values['input_names0'] != ''):
            mynames0 = []
            texts = values['input_names0'].split('\n')
            for text in texts:
                mynames0.append(text)
        else:
            sg.popup_error('Error')

    if event == 'start0':
        if (values['input_image0'] != '') & (values['input_save0'] !='') & (values['input_names0'] != ''):
            i=0
            filedir0= values['input_image0'] + '/*'
            for filename0 in glob.glob(filedir0):
                for path0 in glob.glob(filename0 + '/*'):
                    for myname0 in mynames0:
                        length = -len(myname0)
                        if myname0 == str(path0[length:]):
                            img0 = cv2.imread(path0)
                            cv2.imwrite(values['input_save0'] + '/' + str(i) + '.jpg',img0)
                            i+=1

            window['input_image0'].update(value='')
            window['input_save0'].update(value='')
            window['input_names0'].update(value='')
        else:
            sg.popup_error('Error')

#2

    for i1 in range(len(model1.names)):
        if event == f'{model1.names[i1]}_OK_1':
            if values[f'{model1.names[i1]}_OK_1'] == True:
                window[f'{model1.names[i1]}_NG_1'].update(disabled=True)
            else:
                window[f'{model1.names[i1]}_NG_1'].update(disabled=False)
        if event == f'{model1.names[i1]}_NG_1':
            if values[f'{model1.names[i1]}_NG_1'] == True:
                window[f'{model1.names[i1]}_OK_1'].update(disabled=True)
            else:
                window[f'{model1.names[i1]}_OK_1'].update(disabled=False)

    if event == 'input_weight1':
        mypath = values['input_weight1']
        model1 =torch.hub.load('./levu','custom', path= mypath, source='local', force_reload =False)
        window.close()
        window = make_window()
        event, values = window.read(timeout=20)
        window['input_weight1'].update(value=mypath)

    dem = 0
    if event == 'start1':
        if (values['input_weight1'] != '') & (values['input_image1'] !='') & (values['input_save1'] != ''):
            #mypath = values['input_weight1']
            #model1 =torch.hub.load('./levu','custom', path= mypath, source='local', force_reload =False)
            size=416
            conf = values['input_conf1']/100
            mydir = values['input_image1'] + '/*.jpg'

            def time_to_name():
                current_time = datetime.datetime.now()
                name_folder = str(current_time)
                name_folder = list(name_folder)
                for i in range(len(name_folder)):
                    if name_folder[i] == ':':
                        name_folder[i] = '-'
                    if name_folder[i] == ' ':
                        name_folder[i] ='_'
                    if name_folder[i] == '.':
                        name_folder[i] ='-'
                name_folder = ''.join(name_folder)
                return name_folder

            for i,a in zip(reversed(range(len(mydir))),reversed(mydir)):
                if a == '/':
                    index = i
                    break

            for path1 in glob.glob(mydir):
                name = path1[index+1:-4]
                dem += 1
                img1 = cv2.imread(path1)

                result1 = model1(path1,size= size,conf = conf)

                table1 = result1.pandas().xyxy[0]

                area_remove1 = []

                myresult1 =0

                for item in range(len(table1.index)):
                    width1 = table1['xmax'][item] - table1['xmin'][item]
                    height1 = table1['ymax'][item] - table1['ymin'][item]
                    #area1 = width1*height1
                    label_name = table1['name'][item]
                    for i1 in range(len(model1.names)):
                        if values[f'{model1.names[i1]}_1'] == True:
                            #if values[f'{model1.names[i1]}_WH'] == True:
                            if label_name == model1.names[i1]:
                                if width1 < int(values[f'{model1.names[i1]}_Wn_1']):
                                    table1.drop(item, axis=0, inplace=True)
                                    area_remove1.append(item)
                                elif width1 > int(values[f'{model1.names[i1]}_Wx_1']):
                                    table1.drop(item, axis=0, inplace=True)
                                    area_remove1.append(item)
                                elif height1 < int(values[f'{model1.names[i1]}_Hn_1']):
                                    table1.drop(item, axis=0, inplace=True)
                                    area_remove1.append(item)
                                elif height1 > int(values[f'{model1.names[i1]}_Hx_1']):
                                    table1.drop(item, axis=0, inplace=True)
                                    area_remove1.append(item)

                names1 = list(table1['name'])

                for i1 in range(len(model1.names)):
                    if values[f'{model1.names[i1]}_OK_1'] == True:
                        len_name1 = 0
                        for name1 in names1:
                            if name1 == model1.names[i1]:
                                len_name1 +=1
                        if len_name1 != int(values[f'{model1.names[i1]}_Num_1']):
                            print(str(dem)+' NG')
                            name_folder_ng = time_to_name()
                            cv2.imwrite(values['input_save1'] +'/' + name_folder_ng + '.jpg',img1)
                            myresult1 = 1
                            if os.path.isfile(path1):
                                os.remove(path1)
                            break

                    if values[f'{model1.names[i1]}_NG_1'] == True:
                        if model1.names[i1] in names1:
                            print(str(dem)+' NG')
                            name_folder_ng = time_to_name()
                            cv2.imwrite(values['input_save1'] +'/' + name_folder_ng + '.jpg',img1)
                            myresult1 = 1
                            if os.path.isfile(path1):
                                os.remove(path1)
                            break

                if myresult1 == 0:
                    print(str(dem)+' OK')
            window['input_weight1'].update(value='')
            window['input_image1'].update(value='')
            window['input_save1'].update(value='')
        else:
            sg.popup_error('Error')

#3
    if event == 'button_classes2' :
        if (values['input_classes2'] != ''):
            #print(values['input_classes2'])
            myclasses2 = []
            texts = values['input_classes2'].split('\n')
            for text in texts:
                myclasses2.append(text)
            #print(myclasses2)
        else:
            sg.popup_error('Error')

    if event == 'button_classes2_1' :
        if (values['input_classes2_1'] != ''):
            myclasses2_1 = []
            mynumberes2_1 = []
            texts = values['input_classes2_1'].split('\n')
            for text in texts:
                myclasses2_1.append(text.split(' ')[0])
                mynumberes2_1.append(text.split(' ')[1])

        else:
            sg.popup_error('Error')

    if event == 'start2':
        if (values['input_weight2'] != '') & (values['input_image2'] !='') & (values['input_save2'] != '') & (values['input_classes2'] != ''):
            mypath = values['input_weight2']
            model = torch.hub.load('./levu','custom', path= mypath, source='local',force_reload =False)

            mydir = values['input_image2'] + "/*.jpg"
            mysave = values['input_save2'] + '/'
            #print(mysave)
            for i,a in zip(reversed(range(len(mydir))),reversed(mydir)):
                if a == '/':
                    index = i
                    break
            for path in glob.glob(mydir):
                name = path[index+1:-4]
                #print(name)
                result = model(path,size=416,conf=values['input_conf2']/100)
                f = open(mysave + name + '.txt', "a")
                for detect in result.xywhn:
                    mydetects = detect.tolist()
                    for item in range(len(mydetects)):
                        mydetect = mydetects[item]
                        number_label = mydetect[-1]
                        number_label = int(number_label)
                        name_label = result.names[number_label]
                        for i,myclass2 in zip(range(len(myclasses2)),myclasses2):
                            if name_label == myclass2:
                                label_text = str(i)

                        for index_classes in range(len(myclasses2_1)):
                            if name_label == myclasses2_1[index_classes]:
                                print(name)
                                f.write(str(mynumberes2_1[index_classes]) + " " + str(mydetect[0]) + " " + str(mydetect[1]) + " " + str(mydetect[2]) + " " + str(mydetect[3]))
                                f.write("\n")
                    f.close()
            with open(mysave + 'classes.txt', "w") as f:
                for myclass in myclasses2:
                    f.write(myclass)
                    if myclass != myclasses2[-1]:
                        f.write('\n')

            window['input_weight2'].update(value='')
            window['input_image2'].update(value='')
            window['input_save2'].update(value='')
            window['input_classes2'].update(value='')
            window['input_classes2_1'].update(value='')
        else:
            sg.popup_error('Error')

#4
    if event == 'button_classes3':
        if values['input_classes3'] != '':
            myclasses3 = []
            texts = values['input_classes3'].split('\n')
            for text in texts:
                myclasses3.append(text)
            with open(os.getcwd() + '/labelImg/data/predefined_classes.txt', "w") as f:
                for myclass3 in myclasses3:
                    f.write(myclass3)
                    f.write('\n')
        else:
            sg.popup_error('Error')

    if event == 'program3':
        if values['input_classes3'] != '':
            program_dir = os.path.join(os.getcwd()  + '/labelImg/' , 'labelImg.py')
            #ExecuteCommandSubprocess('python', program_dir)
            subprocess.call(['python',program_dir])
            #subprocess.call(['python', 'test2.py'])
            window['input_classes3'].update(value='')
        else:
            sg.popup_error('Error')

#5
    if event == 'start4':
        if (values['input_image4'] !='') & (values['input_save4'] != ''):
            dir = values['input_image4']
            dir = dir + ('/*')
            list_image = []
            list_text = []
            list_image_train = []
            list_image_valid = []
            list_text_train = []
            list_text_valid = []

            list_name_train = []
            list_name_valid = []

            os.mkdir(values['input_save4'] + '/train')
            os.mkdir(values['input_save4'] + '/train/images')
            os.mkdir(values['input_save4'] + '/train/labels')

            os.makedirs(values['input_save4'] + '/valid')
            os.mkdir(values['input_save4'] + '/valid/images')
            os.mkdir(values['input_save4'] + '/valid/labels')

            for i,a in zip(reversed(range(len(dir))),reversed(dir)):
                if a == '/':
                    index = i
                    break

            for path in glob.glob(dir):
                name = path[index+1:-4]
                extension = path[-3:]

                if extension == 'jpg':
                    list_image.append(path)

                if extension == 'txt':
                    list_text.append(path)

            #random.seed(0)
            list_image_train = random.sample(list_image,int(len(list_image)*0.85))

            for item_image in list_image:
                if item_image not in list_image_train:
                    list_image_valid.append(item_image)

            for path_train in list_image_train:
                name_train = path_train[index+1:-4]
                list_name_train.append(name_train)

            for path_valid in list_image_valid:
                name_valid = path_valid[index+1:-4]
                list_name_valid.append(name_valid)

            for item_text in list_text:
                name_text = item_text[index+1:-4]
                if name_text in list_name_train:
                    list_text_train.append(item_text)
                elif name_text in list_name_valid:
                    list_text_valid.append(item_text)

            for path1 in list_image_train:
                name1 = path1[index+1:-4]
                shutil.copyfile(path1,values['input_save4']+'/train/images/'+ name1 + '.jpg')

            for path2 in list_text_train:
                name2 = path2[index+1:-4]
                shutil.copyfile(path2,values['input_save4']+'/train/labels/'+ name2 + '.txt')

            for path3 in list_image_valid:
                name3 = path3[index+1:-4]
                shutil.copyfile(path3,values['input_save4']+'/valid/images/'+ name3 + '.jpg')

            for path4 in list_text_valid:
                name4 = path4[index+1:-4]
                shutil.copyfile(path4,values['input_save4']+'/valid/labels/'+ name4 + '.txt')

            window['input_image4'].update(value='')
            window['input_save4'].update(value='')

        else:
            sg.popup_error('Error')

#6

    if event == 'move5':
        if values['input_move5'] != '':
            try:
                if os.path.isdir(os.getcwd() + '/train'):
                    shutil.rmtree(os.getcwd() + '/train')
                if os.path.isdir(os.getcwd() + '/valid'):
                    shutil.rmtree(os.getcwd() + '/valid')
                shutil.copytree(values['input_move5'] + '/train',os.getcwd() + '/train')
                shutil.copytree(values['input_move5'] + '/valid',os.getcwd() + '/valid')
            except:
                sg.popup_error('Error')
                print(traceback.format_exc())
        else:
            sg.popup_error('Error')

    if event == 'button_classes5' :
        if (values['input_classes5'] != ''):
            myclasses5 = []
            texts5 = values['input_classes5'].split('\n')
            for text in texts5:
                myclasses5.append(text)

            with open(os.getcwd() + '/levu/data.yaml', "w") as f:
                f.write('train: ' + os.getcwd() + '/train/images')
                f.write('\n')
                f.write('val: ' + os.getcwd() + '/valid/images')
                f.write('\n')
                f.write('nc: '  + str(len(myclasses5)))
                f.write('\n')
                f.write('names: '  + str(myclasses5))

            with open(os.getcwd() + '/levu/models/levu.yaml', "w") as f:
                f.write('nc: ' +  str(len(myclasses5)) + '\n' +
                        'depth_multiple: 0.33  # model depth multiple' + '\n' +
                        'width_multiple: 0.50  # layer channel multiple' + '\n' +
                        'anchors:' + '\n' +
                        '  - [10,13, 16,30, 33,23]  # P3/8' + '\n' +
                        '  - [30,61, 62,45, 59,119]  # P4/16' + '\n' +
                        '  - [116,90, 156,198, 373,326]  # P5/32' + '\n' +

                        'backbone:' + '\n' +

                        '  [[-1, 1, Conv, [64, 6, 2, 2]],  # 0-P1/2' + '\n' +
                        '   [-1, 1, Conv, [128, 3, 2]],  # 1-P2/4' + '\n' +
                        '   [-1, 3, C3, [128]],' + '\n' +
                        '   [-1, 1, Conv, [256, 3, 2]],  # 3-P3/8' + '\n' +
                        '   [-1, 6, C3, [256]],' + '\n' +
                        '   [-1, 1, Conv, [512, 3, 2]],  # 5-P4/16' + '\n' +
                        '   [-1, 9, C3, [512]],' + '\n' +
                        '   [-1, 1, Conv, [1024, 3, 2]],  # 7-P5/32' + '\n' +
                        '   [-1, 3, C3, [1024]],' + '\n' +
                        '   [-1, 1, SPPF, [1024, 5]],  # 9' + '\n' +
                        '  ]' + '\n' +

                        'head:' + '\n' +
                        '  [[-1, 1, Conv, [512, 1, 1]],' + '\n' +
                        "   [-1, 1, nn.Upsample, [None, 2, 'nearest']]," + '\n' +
                        '   [[-1, 6], 1, Concat, [1]],  # cat backbone P4' + '\n' +
                        '   [-1, 3, C3, [512, False]],  # 13' + '\n' +

                        '   [-1, 1, Conv, [256, 1, 1]],' + '\n' +
                        "   [-1, 1, nn.Upsample, [None, 2, 'nearest']]," + '\n' +
                        '   [[-1, 4], 1, Concat, [1]],  # cat backbone P3' + '\n' +
                        '   [-1, 3, C3, [256, False]],  # 17 (P3/8-small)' + '\n' +

                        '   [-1, 1, Conv, [256, 3, 2]],' + '\n' +
                        '   [[-1, 14], 1, Concat, [1]],  # cat head P4' + '\n' +
                        '   [-1, 3, C3, [512, False]],  # 20 (P4/16-medium)' + '\n' +

                        '   [-1, 1, Conv, [512, 3, 2]],' + '\n' +
                        '   [[-1, 10], 1, Concat, [1]],  # cat head P5' + '\n' +
                        '   [-1, 3, C3, [1024, False]],  # 23 (P5/32-large)' + '\n' +

                        '   [[17, 20, 23], 1, Detect, [nc, anchors]],  # Detect(P3, P4, P5)' + '\n' +
                        '  ]'
                        )

        else:
            sg.popup_error('Error')

    if event == 'start5':
        if values['input_classes5'] != '':
            #program_dir5 = os.path.join(os.getcwd()  + '/levu/' , 'train.py')
            dir_py5 = os.path.join(os.getcwd()  + '/levu/' , 'hlvtrain.py')
            dir_data5 = os.path.join(os.getcwd()  + '/levu/' , 'data.yaml')
            dir_model5 = os.path.join(os.getcwd()  + '/levu/models/' , 'levu.yaml')
            name_folder = time_to_name()
            program_dir5 = [ dir_py5, ' --img ', str(values['imgsz5']), ' --batch ', '4' ,' --epochs ', '{}'.format(int(values['input_epoch5'])) , ' --data ', dir_data5 , ' --cfg ', dir_model5, ' --weights ', '""', ' --name ', 'my_results' + '{}'.format(name_folder),  ' --cache']

            subprocess.call(['python', program_dir5])
            #subprocess.Popen(program_dir5)

        else:
            sg.popup_error('Error')

    if event == 'get5':
        try:
            if values['input_classes5'] != '':
                shutil.copyfile(os.getcwd() + '/levu/runs/train/my_results'+ name_folder +'/weights/best.pt',values['input_save5'] + '/best.pt')
                window['input_classes5'].update(value='')
                window['input_move5'].update(value='')
                window['input_save5'].update(value='')
            else:
                sg.popup_error('Error')

        except:
            sg.popup_error('Error')

# p = subprocess.Popen(['python', 'demo_oled_v01.py', '--display',
# 'ssd1351', '--width', '128', '--height', '128', '--interface', 'spi',
# '--gpio-data-command', '20'])
        # print('a')
        # program_dir5 = os.path.join(os.getcwd()  + '/levu/' , 'train.py' + " --img 416 --batch 4 --epochs 300 --data C:/Users/Administrator/Desktop/vu/auto_training/levu/data.yaml --cfg .levu/models/custom_yolov5s.yaml --weights '' --my_results  --cache")
        # ExecuteCommandSubprocess('python', program_dir5)

        #     for myclass5 in myclasses5:
        #         f.write(myclass3)
        #         f.write('\n')
        #window['input_classes5'].update(value='')

#python train.py --img 416 --batch 4 --epochs 300 --data "C:\Users\Administrator\Desktop\vu\mytrain7\data.yaml" --cfg ./models/custom_yolov5s.yaml --weights '' --name yolov5s_results  --cache
#C:/Users/Administrator/Desktop/vu/auto_training/levu/train.py
#C:\Users\Administrator\Desktop\vu\autob        if values['input_classes3'] != '':


# %%
import glob
import torch
import torchvision
import numpy as np
from torch.utils.data import Dataset, DataLoader
import matplotlib.pyplot as plt
import torchvision.transforms.functional as F
import torch.nn.modules as modules

import data_processing.arc.plotter as plotter
from importlib import reload

reload(plotter)

def clop_img(img: np.ndarray, rng, clop_max: float = 1.0, clop_min: float = 0.0):
    """
    img: [..., H, W]のnumpy配列
    rng: 乱数生成器
    clop_max :[0.0, 1.0)で指定。画像の最大どこまで切り取るかの割合を指定する。
    clop_min :[0.0, 1.0)で指定。画像を最小どこまで切り取るかの割合を指定する。
    """
    if clop_max < clop_min:
        raise ValueError("clop_max must be bigger than clop_min")
    H_W_shape = img.shape[-2:]
    clop_rand = rng.uniform(high=clop_max, low=clop_min, size=2)
    clop_size = (H_W_shape * clop_rand).astype(int)
    clop_point = ((H_W_shape - clop_size) * rng.uniform(size=2)).astype(int)
    point_x = clop_point[0]
    point_y = clop_point[1]

    copy_img = np.copy(img)
    copy_img[
        ..., point_x : point_x + clop_size[0], point_y : point_y + clop_size[1]
    ] = 0.0
    return copy_img

if __name__ == "__main__":
    plotter_instance = plotter.Plotter()
    original = np.tile(np.arange(12).reshape(2, 1, 6), (1, 6, 1)) + 1
    plotter_instance.plot_some(original, "original")
    pad_size = 30
    cropped = clop_img(original, np.random.default_rng(5), clop_max=1.0, clop_min=0.0)
    plotter_instance.plot_some(cropped, "cropped")
    for _ in range(100):
        cropped = clop_img(
            original, np.random.default_rng(), clop_max=0.5, clop_min=0.0
        )
        # 最大でも半分しか削らない=>元の画像の半分以上の大きさは残る
        assert np.sum(cropped == 0) <= int(np.prod(original.shape[-2:]) / 2)
        cropped = clop_img(
            original, np.random.default_rng(), clop_max=1.0, clop_min=0.5
        )
        # 最小でも半分以上削る=>元の画像の半分以下の大きさになる。
        assert np.sum(cropped == 0) >= int(np.prod(original.shape[-2:]) / 2)

    # clop_max,clop_minをお互いに0.0や1.0にしてもおかしくならないか？
    plotter_instance.plot_some(original, "original")
    cropped = clop_img(original, np.random.default_rng(), clop_max=0.0, clop_min=0.0)
    plotter_instance.plot_some(cropped, "not cropped")
    cropped = clop_img(original, np.random.default_rng(), clop_max=1.0, clop_min=1.0)
    plotter_instance.plot_some(cropped, "all cropped")

def shuffle_color(img, rng):
    """
    img: [..., H, W]のnumpy配列
    rng: 乱数生成器
    return :整数をランダムに入れ替えた配列を返す
    """

    minval = np.min(img)
    img -= minval
    lut = np.arange(start=0, stop=np.max(img) + 1, step=1)
    rng.shuffle(lut)
    return np.take(lut, img) + minval

if __name__ == "__main__":
    plotter_instance = plotter.Plotter()
    original = np.tile(np.arange(12).reshape(2, 1, 6), (1, 6, 1)) + 1
    plotter_instance.plot_some(original, "original")
    shuffled = shuffle_color(original, np.random.default_rng())
    plotter_instance.plot_some(shuffled, "shuffled")

#%%
def pad_img(img, rng, pad_size, mode, random_align=True):
    """
    img: [..., H, W]のnumpy配列
    rng: 乱数生成器
    pad_size :intで指定。画像をどこまでパディングするかのサイズを指定する。pad_size<H,Wの場合そのサイズまでH,Wをカットする。
    mode:パディングの方法を指定する。"wrap", "symmetric", "constant"等がある。詳しくはnp.padを参照。
    return :[..., pad_size, pad_size]のnumpy配列
    """

    img_rank = len(img.shape)
    img_x = img.shape[-1]
    img_y = img.shape[-2]
    if img_x >= pad_size:
        img = img[..., :, :pad_size]
        point_x = 0
    else:
        if random_align == True:
            point_x = rng.integers(0, max(pad_size - img_x, 1))
        else:
            point_x = 0
    pad_x = (point_x, max(pad_size - img_x - point_x, 0))

    if img_y >= pad_size:
        img = img[..., :pad_size, :]
        point_y = 0
    else:
        if random_align == True:
            point_y = rng.integers(0, max(pad_size - img_y, 1))
        else:
            point_y = 0
    pad_y = (point_y, max(pad_size - img_y - point_y, 0))

    pad_len = [(0, 0) for _ in range(img_rank - 2)] + [pad_y]+[pad_x]
    padded_img = np.pad(
        img,
        pad_width=pad_len,
        mode=mode,
    )
    return padded_img

if __name__ == "__main__":
    plotter_instance = plotter.Plotter()
    original = np.tile(np.arange(12).reshape(2, 1, 6), (1, 6, 1)) + 1
    plotter_instance.plot_some(original, "original")
    pad_size = 9
    padded = pad_img(original, np.random.default_rng(), pad_size=pad_size, mode="wrap")
    plotter_instance.plot_some(padded, "wrap paded")
    #!constantでpaddingする時は、初めに1を足しておくこと。paddingされる値は0なので、paddingされた値と通常の部分の見分けがつかなくなる。
    padded = pad_img(
        original + 1, np.random.default_rng(), pad_size=pad_size, mode="constant"
    )
    plotter_instance.plot_some(padded, "const paded")
    # print(padded.shape)
    assert padded.shape[-2] == padded.shape[-1] == pad_size

#%%

def rotate_img(img, rng):
    """画像をランダムに回転
    Args:
        img (np.ndarray):[...H, W]のnumpy配列
        rng: 乱数生成器
    Returns:
        _type_: _description_
    """

    img = np.rot90(img, k=rng.integers(0, 4), axes=(-2, -1))
    return img

if __name__ == "__main__":
    plotter_instance = plotter.Plotter()
    original = np.tile(np.arange(12).reshape(2, 1, 6), (1, 6, 1)) + 1
    plotter_instance.plot_some(original, "original")
    rotated = rotate_img(original, np.random.default_rng())
    plotter_instance.plot_some(rotated, "rotate")
    rotate90 = np.rot90(original, k=1, axes=(-2, -1))
    rotate180 = np.rot90(original, k=2, axes=(-2, -1))
    rotate270 = np.rot90(original, k=3, axes=(-2, -1))
    ans = np.array([0, 0, 0, 0])
    for _ in range(300):
        rotated = rotate_img(original, np.random.default_rng())
        ans += np.array(
            [
                np.all(rotated == original),
                np.all(rotated == rotate90),
                np.all(rotated == rotate180),
                np.all(rotated == rotate270),
            ]
        )
    assert np.all(ans >= 1)
    # どの角度での回転も生成されているかチェック

def flip_img(img, rng):
    if rng.uniform() > 0.5:
        img = np.flip(img, axis=-2)
    if rng.uniform() > 0.5:
        img = np.flip(img, axis=-1)
    return img

if __name__ == "__main__":
    plotter_instance = plotter.Plotter()
    original = np.arange(50).reshape(2, 5, 5)
    original %= 8
    plotter_instance.plot_some(original, "original")

    lr_flip = np.flip(original, axis=-1)
    ud_flip = np.flip(original, axis=-2)
    lrud_flip = np.flip(original, axis=(-2, -1))
    ans = np.array([0, 0, 0, 0])
    for i in range(100):
        flipped = flip_img(original, np.random.default_rng())
        if i <= 20:
            plotter_instance.plot_some(flipped, "flipped")
        ans += np.array(
            [
                np.all(flipped == original),
                np.all(flipped == lr_flip),
                np.all(flipped == ud_flip),
                np.all(flipped == lrud_flip),
            ]
        )
    print(ans)
    assert np.all(ans >= 1)
    # どの反転も生成されているかチェック

# %%
class ArcDataset(Dataset):
    CH = 10  # 0 ~ 9までの10個の値がある。

    def one_hot(self, x):
        return np.eye(self.CH + 2)[x]

    def __init__(
        self,
        root,
        pad,
        mode="reflect",
        clop_max=1.0,
        clop_min=0.0,
        inbatch_random=False,
        seed=0,
    ):
        self.file_list = glob.glob(root)
        if clop_max < clop_min:
            raise ValueError("clop_max must be larger than clop_min")
        self.mode = mode
        self.clop_max = clop_max
        self.clop_min = clop_min
        self.pad = pad
        self.seed = seed
        self.inbatch_random = inbatch_random
        self.rng = np.random.default_rng(seed)

    def rng_reset(self):
        self.rng = np.random.default_rng(self.seed)

    def __len__(self):
        return len(self.file_list)

    def __getitem__(self, idx):
        # if self.inbatch_random:
        #     original = np.load(self.file_list[self.rng.integers(0, len(self.file_list))])
        # else:
        #     original = np.load(self.file_list[idx])
        original = np.load(self.file_list[idx])

        original += 1
        shuffled = shuffle_color(original, self.rng)
        rotated = rotate_img(shuffled, self.rng)
        flipped = flip_img(rotated, self.rng)
        padded = pad_img(flipped, self.rng, pad_size=self.pad, mode=self.mode)

        cropped = clop_img(padded, self.rng, self.clop_max, self.clop_min)

        return {
            "padded": self.one_hot(padded),
            "reconst": self.one_hot(padded),
            "cropped": self.one_hot(cropped),
        }

if __name__ == "__main__":
    pad_size = 10
    num_classes = 100
    check_len = 6
    ds = ArcDataset(
        root="C:\\Users\\taeya\\Documents\\ARK\\data\\abstraction-and-reasoning-challenge\\training\\one_photos\\*.npy",
        pad=pad_size,
        mode = "constant"
    )
    train_dataloader = DataLoader(ds, batch_size=1, shuffle=True)
    plotter_instance = plotter.Plotter()
    for i, data in enumerate(train_dataloader):
        if check_len > i:
            plotter_instance.plot_some(data["padded"], "padded")
            plotter_instance.plot_some(data["cropped"], "cropped")
    # %%
    test_ds = ArcDataset(
        root="C:\\Users\\taeya\\Documents\\ARK\\data\\abstraction-and-reasoning-challenge\\test\\one_photos\\*.npy",
        pad=pad_size,
        seed=0,
    )

    # rng_resetを使って同じ順番でデータがloadされているかをチェック
    cropped_imgs = []
    test_dataloader = DataLoader(test_ds, batch_size=1)
    for i, data in enumerate(test_dataloader):
        cropped_imgs.append(data["cropped"])
        if i == check_len:
            break

    test_ds.rng_reset()
    cropped_imgs2 = []
    for i, data in enumerate(test_dataloader):
        cropped_imgs2.append(data["cropped"])
        if i == check_len:
            break
    for i in range(check_len):
        assert np.all(cropped_imgs[i].numpy() == cropped_imgs2[i].numpy())

# %%