from pathlib import Path
import fnmatch
import os
import math
import numpy as np

# SETTINGS ###################################################################################


# FOLDERS ####################################################################################

# path of merge parameters
path_parameters = Path(r"")

# TYPE SELECTION #############################################################################
# class (airplane, bird, drone, helicopter, insect)
class_name = [20, 20, 20, 20, 20]
# complexity of image (50% low; 50% high) # parameter [%]
complexity = [50, 50]
# area of object (40% low, 40% medium, 20% high) [%]
area = [40, 40, 20]
# weather in image (50% sunny, 50% not_sunny)
weather = [50, 50]
# number of images with multiple objects (just for print, only information)
multiple_object_min = 10


# number of multiple object has minimum value
# percentage representation of all parameters is valid across all sub-groups created
# by parameters (example: in sub-groups [class: bird, complexity: low, ...] is valid:
# area: percentage representation as specify)
# number of object in single object (min value of images with multiple object)
# has recommended value in whole database
##############################################################################################

# get all files of defined type from folder
def listdir(dir_name, pattern="*"):
    return fnmatch.filter(os.listdir(dir_name), pattern)


# GET DATA ###################################################################################
# find all parameters and images in path folder
parameters_array = listdir(str(path_parameters), "*.txt")

# get parameters from file name
valid = 1
parameters = []
for i in range(len(parameters_array)):
    name1 = parameters_array[i][:-4]
    parameters.append(name1[len(name1)-5:])
    # print(parameters[-1])
##############################################################################################


# ANALYSIS ###################################################################################
number_of_multiple_object_in_images = 0
number_of_types = [0] * 60
number_of_types_ideal = [0] * 60

# calculate optimal number of image types
for i in range(60):
    # ideal numbers images of certain type
    p_class = math.floor(i / 12)
    p_area = math.floor((i % 12) / 4)
    p_complexity = math.floor(((i % 12) % 4) / 2)
    p_weather = i % 2
    # calculating
    number_of_types_ideal[i] = float(class_name[p_class]/100 * area[p_area]/100
                                     * complexity[p_complexity]/100 * weather[p_weather])

for i in range(len(parameters_array)):
    string = parameters[i]
    # get parameters
    p_class = int(string[0])
    p_complexity = int(string[1])
    p_area = int(string[2])
    p_number = int(string[3])
    p_weather = int(string[4])
    type_number = p_weather + 2*p_complexity + 4*p_area + 12*p_class
    # increment of multiple
    number_of_multiple_object_in_images += p_number
    # increment of type counter
    number_of_types[type_number] += 1
    # append name of file to type array
##############################################################################################

# PRINT DIVERSITY OF MERGE FOLDER ############################################################
class_count = [0, 0, 0, 0, 0]
area_count = [0, 0, 0]
complexity_count = [0, 0]
weather_count = [0, 0]
enough = []

for i in range(60):
    # get parameters from parameter file name
    par_class = math.floor(i / 12)
    par_area = math.floor((i % 12) / 4)
    par_complexity = math.floor(((i % 12) % 4) / 2)
    par_weather = i % 2

    if par_class == 0:
        str_class = "airplane"
        class_count[0] += number_of_types[i]
    elif par_class == 1:
        str_class = "bird"
        class_count[1] += number_of_types[i]
    elif par_class == 2:
        str_class = "drone"
        class_count[2] += number_of_types[i]
    elif par_class == 3:
        str_class = "helicopter"
        class_count[3] += number_of_types[i]
    else:
        str_class = "insect"
        class_count[4] += number_of_types[i]

    if par_area == 0:
        str_area = "small"
        area_count[0] += number_of_types[i]
    elif par_area == 1:
        str_area = "medium"
        area_count[1] += number_of_types[i]
    else:
        str_area = "large"
        area_count[2] += number_of_types[i]

    if par_complexity == 0:
        str_complexity = "small"
        complexity_count[0] += number_of_types[i]
    else:
        str_complexity = "big"
        complexity_count[1] += number_of_types[i]

    if par_weather == 0:
        str_weather = "sunny"
        weather_count[0] += number_of_types[i]
    else:
        str_weather = "not_sunny"
        weather_count[1] += number_of_types[i]

    print("class: " + str_class + ", area: " + str_area + ", complexity: " + str_complexity +
          ", weather: " + str_weather)
    print("percentage of files of given parameters: " + str(number_of_types[i]/len(parameters_array)*100) +
          ", ideal percentage of files: " + str(number_of_types_ideal[i]))
    if (number_of_types[i]/len(parameters_array)*100) > (1.25*number_of_types_ideal[i]):
        print(i)
        enough.append(i)
    print("")

print(class_count)
print("class distribution in dataset (Airplane) [%]: "+str(round(class_count[0]/len(parameters_array)*100,2)))
print("class distribution in dataset (Bird) [%]: "+str(round(class_count[1]/len(parameters_array)*100,2)))
print("class distribution in dataset (Drone) [%]: "+str(round(class_count[2]/len(parameters_array)*100,2)))
print("class distribution in dataset (Helicopter) [%]: "+str(round(class_count[3]/len(parameters_array)*100,2)))
print("class distribution in dataset (Insect) [%]: "+str(round(class_count[4]/len(parameters_array)*100,2)))
print("")
print("area distribution in dataset (small) [%]: "+str(round(area_count[0]/len(parameters_array)*100,2)))
print("area distribution in dataset (medium) [%]: "+str(round(area_count[1]/len(parameters_array)*100,2)))
print("area distribution in dataset (large) [%]: "+str(round(area_count[2]/len(parameters_array)*100,2)))
print("")
print("complexity distribution in dataset (small) [%]: "+str(round(complexity_count[0]/len(parameters_array)*100,2)))
print("complexity distribution in dataset (big) [%]: "+str(round(complexity_count[1]/len(parameters_array)*100,2)))
print("")
print("weather distribution in dataset (sunny) [%]: "+str(round(weather_count[0]/len(parameters_array)*100,2)))
print("weather distribution in dataset (not_sunny) [%]: "+str(round(weather_count[1]/len(parameters_array)*100,2)))
print("")
print("indexes of image types with sufficient contribution "+str(enough))

np.savetxt('analyze_merge_dataset_output.txt', enough, fmt='%d')

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