# -*- coding: utf-8 -*-
import factory
from base_factory import BaseFactory
from internships.models import Field, Internship
from internships.models.internship import NEGOTIABLE_CHOICES
from datetime import date, timedelta
import random
from address.models import State, City

from default_values import FIELD_DEFAULTS, COMPANIES, ADDRESSES

## internship.Field ##
class FieldFactory(factory.Factory):
    FACTORY_FOR = Field

    @classmethod
    def make_for_test(cls):
        return [ cls(name=name) for name in FIELD_DEFAULTS ]

"""     internship.Internship      """

## Helpers
random_negotiable = lambda a: random.choice(NEGOTIABLE_CHOICES._choice_dict.values())
random_field = lambda a: random.choice( list(Field.objects.all()) )

ROLES = ['programador', 'designer', 'ilustrador', 'digitador', ]
random_role = lambda a: random.choice(ROLES)

## Factory
class InternshipFactory(factory.Factory):
    FACTORY_FOR = Internship

    field   = factory.LazyAttribute(random_field)
    role    = factory.LazyAttribute(random_role)

    description = 5 * 'Lorem Ipsum is simply dummy text of the printing and typesetting \n'

    weekly_hours = factory.LazyAttribute(lambda a: random.choice([20, 25, 30]))

    relevance   = -1
    featured    = False
    approved    = True
    active      = True
    expiration  = factory.LazyAttribute(lambda x: date.today() + timedelta(days=30))

    min_semester = 0

    transport       = factory.LazyAttribute(random_negotiable)
    health          = factory.LazyAttribute(random_negotiable)
    food            = factory.LazyAttribute(random_negotiable)
    flexible_hours  = factory.LazyAttribute(random_negotiable)

    city = factory.LazyAttribute(lambda a: City.objects.all()[0] )
    state = factory.LazyAttribute(lambda a: a.city.state )
    street = 'Rua de exemplo'
    number = '10'
    district = 'Bairro'
    cep = '24123010'

def fill_company(ins, company, **kwargs):
    data = COMPANIES[company]
    for k,v in kwargs:
        data[k] = v
    ins.company_name    = data['name']
    ins.company_url     = data['url']
    ins.company_img     = 'company_logos/' + data['img']
    ins.company_size    = data['size']
    return ins

def fill_address(ins, addr):
    data = ADDRESSES[addr]
    state = State.objects.get(uf=data['state'])
    city = City.objects.filter(state=state).filter(name__iexact=data['city'])[0]

    ins.street = data['street']
    ins.number = data['number']
    #ins.complement = data['complement']
    ins.district = data['district']
    ins.cep = data['cep']

    ins.city = city
    ins.state = state
    return ins

def fill_tags(ins, *args):
    for tag in args:
        ins.tags.add(tag)
    return ins


from datetime import datetime
from math import ceil
@outputSchema("int")
def DateDiff(d1,d2,days=1.0):
	try:
		if str(d1)[0:10] == "11000101" or str(d2)[0:10] == "11000101" or d1 is None or d2 is None:
			return 0
		else:
			d = (datetime.strptime(d1[0:10],'%Y%m%d')-datetime.strptime(d2[0:10],'%Y%m%d')).days/days
			return int(ceil(d))
	except ValueError:
		return 0

@outputSchema("var1: chararray")
def add_period_proc(grp):
	if '.' in list(grp):
		return str(grp)
	elif len(grp) == 4:
		return (str(grp[0:2]+'.'+grp[2:4]))
	elif len(grp) == 3:
		return (str(grp[0:2]+'.'+grp[2:3]))
	else:
		return str(grp)

@outputSchema("var1: chararray")
def remove_first_undersore_exists(grp):
	if grp is None or grp is 'null':
		return 'no_data'
	l = len(grp)
	if grp[0] == '_':
		return grp[1:l]
	else:
		return grp

@outputSchema("var1: chararray")
def remove_period_proc(g):
	if g is None or g is 'null':
		return 'no_data'
	proc = ''
	l = len(g)
	if g[0] == '_':
		grp=g[1:l]
	else:
		grp=g
	for i in grp:
		if i != '.':
			proc=proc+i
	return proc

@outputSchema("t:tuple(diag1: chararray,diag2: chararray,diag3: chararray,diag4: chararray,diag5: chararray,diag6: chararray,diag7: chararray,diag8: chararray,diag9: chararray,diag10: chararray,diag11: chararray,diag12: chararray,diag13: chararray,diag14: chararray,diag15: chararray,diag16: chararray,diag17: chararray,diag18: chararray,diag19: chararray,diag20: chararray,diag21: chararray,diag22: chararray,diag23: chararray,diag24: chararray,diag25: chararray,ediag1: chararray,ediag2: chararray,ediag3: chararray,ediag4: chararray,ediag5: chararray,ediag6: chararray,ediag7: chararray,ediag8: chararray,ediag9: chararray,ediag10: chararray)")
def diag_parser(grp):
    l=[]
    for item in grp.split('|'):
        if '.' in item:
            prec=item.split('.')[0]
            if prec not in l:
                l.append(prec)
        else:
            if item not in l:
                l.append(item)
    dump=[]
    edump=[]
    for diag in l:
        if diag is None or diag is '' or diag is 'null':
            continue
        else:
            if diag[:1] not in ('E'):
                dump.append('_'+str(diag))
            else:
                edump.append('_'+str(diag))
    if len(dump)>25:
        c = dump[0:25]
    else:
        c = dump
    if len(edump)>10:
        e = edump[0:10]
    else:
        e = edump
    nonelist1 = ['_no_data']*(25-len(c))
    nonelist2 = ['_no_data']*(10-len(e))
    diagdump = c + nonelist1
    ediagdump = e + nonelist2
    return tuple(diagdump + ediagdump)

@outputSchema("t:tuple(var1: chararray,var2: chararray,var3: chararray,var4: chararray,var5: chararray,var6: chararray,var7: chararray,var8: chararray,var9: chararray,var10: chararray)")
def proc_parser(grp):
	cnt = 10
	l = []
	for item in grp.split('|'):
		if item not in l:
			l.append(item)
	if "null" in l:
		l.remove("null")
	if len(l)>cnt:
		return tuple(l[0:cnt])
	else:
		n = ['_no_data']*(cnt-len(l))
		o = l+n
		return tuple(o)

import re
@outputSchema("t:tuple(var1: chararray,var2: chararray)")
def drg_soi(drg):
	r_soi='0'
	r_drg='000'
	if drg is None:
		drg='00000'
	l = len(drg)
	if len(drg) is 6:
		if (not re.search('000[0-9][0-9][0-9]$',drg) is None):
			r_drg=drg[3:6]
		elif (not re.search('00[1-9][0-9][0-9][1-4]$',drg) is None):
			r_drg=drg[2:5]
			r_soi=drg[5]
	elif len(drg) is 5:
		if (not re.search('00[0-9][0-9][0-9]$',drg) is None):
			r_drg=drg[2:5]
		elif (not re.search('0[1-9][0-9][0-9][1-4]$',drg) is None):
			r_drg=drg[1:4]
			r_soi=drg[4]
	elif len(drg) is 4:
		if (not re.search('0[0-9][0-9][0-9]$',drg) is None):
			r_drg=drg[1:4]
		elif (not re.search('[1-9][0-9][0-9][1-4]$',drg) is None):
			r_drg=drg[0:3]
			r_soi=drg[3]
	elif len(drg) is 3:
		if (not re.search('[0-9][0-9][0-9]$',drg) is None):
			r_drg=drg
	elif len(drg) is 2:
		if (not re.search('[0-9][1-9]$',drg) is None):
			r_drg='0'+drg
	elif len(drg) is 1:
		if (not re.search('[1-9]$',drg) is None):
			r_drg='00'+drg
	else:
		r_drg='000'
	a = []
	a.append(r_drg)
	a.append(r_soi)
	return tuple(a)

@outputSchema("t:tuple(var1: chararray,var2: chararray,var3: chararray,var4: chararray,var5: chararray,var6: chararray,var7: chararray,var8: chararray,var9: chararray,var10: chararray,var11: chararray,var12: chararray,var13: chararray,var14: chararray,var15: chararray,var16: chararray,var17: chararray,var18: chararray,var19: chararray,var20: chararray,var21: chararray,var22: chararray,var23: chararray,var24: chararray,var25: chararray)")
def pic_25_cols(grp):
	cnt = 25
	l = []
	for item in grp.split('|'):
		if item not in l:
			if item is not None:
				l.append('_'+item)
	if "null" in l:
		l.remove("null")
	if '_' in l:
		l.remove('_')
	if len(l)>cnt:
		return tuple(l[0:cnt])
	else:
		n = ['_no_data']*(cnt-len(l))
		o = l+n
		return tuple(o)

@outputSchema("t:tuple(var1: chararray,var2: chararray,var3: chararray,var4: chararray,var5: chararray,var6: chararray,var7: chararray,var8: chararray,var9: chararray,var10: chararray,var11: chararray,var12: chararray)")
def pic_12_cols(grp):
	cnt = 12
	l=[]
	for item in grp.split('|'):
		if item not in l:
			if item is not None:
				l.append('_'+item)
	if "null" in l:
		l.remove("null")
	if '_' in l:
		l.remove('_')
	if len(l)>cnt:
		return tuple(l[0:cnt])
	else:
		n = ['_no_data']*(cnt-len(l))
		o = l+n
		return tuple(o)

@outputSchema("t:tuple(var1: chararray,var2: chararray,var3: chararray,var4: chararray,var5: chararray,var6: chararray,var7: chararray,var8: chararray,var9: chararray,var10: chararray)")
def pic_10_cols(grp):
	cnt = 10
	l=[]
	for item in grp.split('|'):
		if item not in l:
			if item is not None:
				l.append('_'+item)
	if "null" in l:
		l.remove("null")
	if '_' in l:
		l.remove('_')
	if len(l)>cnt:
		return tuple(l[0:cnt])
	else:
		n = ['_no_data']*(cnt-len(l))
		o = l+n
		return tuple(o)

@outputSchema("var1: chararray")
def pic_1_col(grp):
	l=[]
	if len(grp)>0:
		for item in grp.split('|'):
			if item is not None:
				for ch in item:
					if '.' in item:
						prec=item.split('.')[0]
						if prec not in l:
							l.append('_'+prec)
					else:
						if item not in l:
							l.append('_'+item)
		if 'null' in l:
			l.remove('null')
		if len(l)>0:
			return l[0]
		else:
			return '_no_data'
	else:
		return '_no_data'


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

from django.conf.urls import patterns, url
from django.contrib import admin
from common.utils import direct_response
from django.shortcuts import get_object_or_404
from django.views.decorators.csrf import csrf_exempt
from valorizacion.models import *

class ClienteAdmin(admin.ModelAdmin):
    """
    Admin para un cliente
    """
    list_display = ("nombre", "numero", "procedencia")

class ObraAdmin(admin.ModelAdmin):
    """
    Admin para una obra
    """
    list_display = ("nombre", "cliente")

class ParteDiarioAdmin(admin.ModelAdmin):
    """
    Admin para un parte diario
    """
    list_display = ("maquina", "fecha", "numero", "obra", "operador",
                    "horometro_inicio", "horometro_final", "horas_trabajadas",
                    "calentamiento")
    list_filter = ("maquina", "fecha",)
    list_editable = ("calentamiento",)
    exclude = ("calentamiento",)

    def save_model(self, request, obj, form, change):
        """
        Ajusta el horómetro a la máquina según las horas trabajadas
        """
        if change:
            old = ParteDiario.objects.get(id=obj.id)
            anterior = old.horas_trabajadas + old.calentamiento
        else:
            anterior = 0
            try:
                horometro_anterior = ParteDiario.objects.filter(maquina=obj.maquina, fecha__lte=obj.fecha).latest().horometro_final
                calentamiento = obj.horometro_inicio - horometro_anterior
            except ParteDiario.DoesNotExist:
                calentamiento = 0
            if calentamiento > 0:
                obj.calentamiento = calentamiento
            else:
                obj.calentamiento = 0
        super(self.__class__, self).save_model(request, obj, form, change)
        obj.maquina.increase(obj.horas_trabajadas+obj.calentamiento-anterior)

class ValorizacionAdmin(admin.ModelAdmin):
    """
    Admin para la valorización
    """
    fields = ("valorizaciones", "costo_hora")
    filter_horizontal = ("valorizaciones",)

    def save_model(self, request, obj, form, change):
        """
        Saca los partes que están dentro de las fechas de cada valorización
        """
        super(self.__class__, self).save_model(request, obj, form, change)
        obj = Valorizacion.objects.get(id=obj.id)
        if change:
            obj.partes.clear()
        for valorizacion in obj.valorizaciones.all():
            partes = ParteDiario.objects.filter(fecha__gte=valorizacion.fecha_inicio,
                                                fecha__lte=valorizacion.fecha_fin,
                                                maquina=valorizacion.maquina)
            obj.partes.add(*partes)

    def get_urls(self):
        """
        URLs para modificar la lista de partes diarios
        """
        urls = super(self.__class__, self).get_urls()
        my_urls = patterns('',
            url(r'^partes_diarios/(?P<id>\d+)?$',
               self.admin_site.admin_view(self.partes_diarios),
               name='admin_partes_diarios'),
        )

        return my_urls + urls

    @csrf_exempt
    def partes_diarios(self, request, id=None):
        """
        Formulario para quitar partes de una valorización
        """
        obj = get_object_or_404(Valorizacion, id=id)
        messages = []
        if request.method == "POST":
            for i in range(1, obj.partes.all().count() + 1):
                if "parte_%s" % i in request.POST:
                    obj.partes.remove(ParteDiario.objects.get(
                        id=request.POST["parte_%s" % i])
                    )
            messages = [u"Se grabaron sus cambios correctamente"]

        return direct_response(request, 'admin/valorizacion/valorizacion/partes_diarios.html',
                               {"obj": obj,
                                "messages": messages})

admin.site.register(Cliente, ClienteAdmin)
admin.site.register(Obra, ObraAdmin)
admin.site.register(ParteDiario, ParteDiarioAdmin)
admin.site.register(Valorizacion, ValorizacionAdmin)
admin.site.register(ValorizacionSimple)


# TITLE: 후보키 (https://school.programmers.co.kr/learn/courses/30/lessons/42890)
# TAG: kakao, implementation, set, combination
# DATE: 20220823
# AUTHOR: squareyun

from itertools import combinations

def solution(relation):
    col = len(relation[0])
    candidates = []
    for i in range(1, col + 1):
        for combi in combinations(range(col), i):
            temp = []
            for r in relation:
                curr = [r[c] for c in combi]
                if curr in temp:
                    break
                else:
                    temp.append(curr)
            else:
                for ck in candidates:
                    if set(ck).issubset(set(combi)):
                        break
                else:
                    candidates.append(combi)
    return len(candidates)


# 10000보다 작거나 같은 셀프 넘버를 한 줄에 하나씩 출력하는 프로그램을 작성하시오.

def ans(n): #n 은 문자열로 받아야 한다.
    numlist = list(str(n))
    sum = 0 #자릿수 합
    for i in numlist:
        sum += int(i)
    dn = n + sum #d(n)을 구한다
    if dn > 10000:  #d(n)이 10000보다 커지면 종료
        return;
    try:
        num.remove(dn)  #1~ 10000까지 수 중에서 d(n)을 제거한다
    except:
        return;
    ans(dn) #재귀함수

### main ###
num = []
for i in range(10000):
    num.append(i + 1)

for i in num:
    ans(i)

for i in num:
    print(i)

# 1. ValueError: list.remove(x): x not in list == 중복된 수 처리. 이미 지워진 수를 또 지우게 됨 -> try: except:로 예외처리
# 2. 더 효율적인 방법이 있을 듯 하다.


#!/usr/bin/env python
# -*- coding: utf-8 -*-

# Configuration
import os
import sys
file_path = os.path.dirname(os.path.abspath(__file__))
config_path = os.path.sep.join(file_path.split(os.path.sep)[:-1])
sys.path.append(config_path)

import itertools
import pickle as pk
from tqdm import tqdm

from util import *
scci_path = SCCIPath()

from naver import QueryParser, ListScraper, Status
query_parser = QueryParser()
list_scraper = ListScraper()
status = Status()

def parse_query(query_file):
    date_start, date_end = query_file[0].split('\n')
    date_list = query_parser.build_date_list(date_start, date_end)
    query_list = query_parser.build_query_list(query_file[1:])
    return date_list, query_list

def save_url_list(query, date, url_list):
    fname_url_list = 'Q-{}_D-{}.pk'.format(query, date)
    fpath_url_list = os.path.join(scci_path.fdir_url_list, fname_url_list)
    makedir(fpath=fpath_url_list)
    with open(fpath_url_list, 'wb') as f:
        pk.dump(url_list, f)

def scrape_url_list(fname_query_list):
    fpath_query = os.path.join(scci_path.fdir_query, fname_query_list)
    with open(fpath_query, 'r', encoding='utf-8') as f:
        query_file = f.read().split('\n\n')
        date_list, query_list = parse_query(query_file)

    for date in sorted(date_list, reverse=False):
        cnt = 0

        print('Start: {}'.format(date))
        with tqdm(total=len(query_list)) as pbar:
            for query in query_list:
                url_list = list_scraper.get_url_list(query=query, date=date)
                save_url_list(query, date, url_list)
                cnt += len(url_list)
                pbar.update(1)

        print('Done : {} ({:,} articles)'.format(date, cnt))
        print('------------------------------------------------------------')

if __name__ == '__main__':
    fname_query_list = 'query_20210714.txt'
    scrape_url_list(fname_query_list)
    status.url_list_cnt()


import numpy as np
from pathlib import Path
from sklearn.metrics import accuracy_score, log_loss
from scipy.stats import entropy

paths = list(Path('./data').glob('*.npy'))

data = {}
labels = {}
for path in paths:
    if not str(path.stem).endswith('label'):
        *_, L, p = str(path.stem).split(',')
        data[(int(L), float(p))] = np.load(str(path))
    else:
        *_, L, p = str(path.stem).split(',')
        p, _ = p.split('_')
        labels[(int(L), float(p))] = np.load(str(path))

data = dict(sorted(data.items()))

to_del = []
for key in data:
    pass
#    if key[1] == 0.35:
#        to_del.append(key)
#    if key[1] == 0.5:
#        to_del.append(key)
for key in to_del:
    del data[key]

Lps = data.keys()
Ls = sorted(list(set([x[0] for x in Lps])))
ps = sorted(list(set([x[1] for x in Lps])))
collated = {}
label_collated = {}
for key, value in data.items():
    if key[0]  in collated:
        collated[key[0]].append(value)
        label_collated[key[0]].append(labels[key])
    else:
        collated[key[0]] = [value]
        label_collated[key[0]] = [labels[key]]

for key in collated:
    collated[key] = np.stack(collated[key])
    label_collated[key] = np.stack(label_collated[key])

print([x.shape for x in collated.values()])
print([x.shape for x in label_collated.values()])

size = np.max([x.shape[2] for x in list(collated.values())])
print(size)
results = [np.pad(a, ((0, 0), (0, 0), (0, (size-a.shape[2])))) for a in list(collated.values())]

results = np.stack(results)
labels = np.stack(list(label_collated.values()))
#labels = np.concatenate([np.eye(2)[:, 0:1] for _ in range(19947)]+[np.eye(2)[:, 1:2] for _ in range(19947)], axis=1).T
np.save('processed_data/raw_data.npy', results)
np.save('processed_data/labels.npy', labels)
np.save('processed_data/Ls.npy', np.array(Ls))
np.save('processed_data/ps.npy', np.array(ps))


#!/usr/bin/python3

import numpy as np
from scipy.stats import beta
from scipy.stats import norm
import matplotlib.pyplot as plt
from matplotlib import rc
rc('font',**{'family':'serif','serif':['Cardo']})
rc('text', usetex=True)

def q_of_Z_pi(Z, RHO, mu_sigma2_a_b):
    q = norm.pdf(Z, mu_sigma2_a_b[0], np.sqrt(mu_sigma2_a_b[1])) * beta.pdf(RHO, mu_sigma2_a_b[2], mu_sigma2_a_b[3]);
    return q

def update_filter_vogiatzis(z, tau2, mu_range, mu_sigma2_a_b):
    mu = mu_sigma2_a_b[0]
    sigma2 = mu_sigma2_a_b[1]
    a = mu_sigma2_a_b[2]
    b = mu_sigma2_a_b[3]

    norm_scale = np.sqrt(sigma2 + tau2)

    s2 = 1.0/(1.0/sigma2 + 1.0/tau2)
    m = s2*(mu/sigma2 + z/tau2)
    uniform_x = 1.0/mu_range
    C1 = a/(a+b) * norm.pdf(z, mu, norm_scale)
    C2 = b/(a+b) * uniform_x
    normalization_constant = C1 + C2
    C1 /= normalization_constant
    C2 /= normalization_constant
    f = C1*(a+1.0)/(a+b+1.0) + C2*a/(a+b+1.0)
    e = C1*(a+1.0)*(a+2.0)/((a+b+1.0)*(a+b+2.0)) \
      + C2*a*(a+1.0)/((a+b+1.0)*(a+b+2.0));

    # update parameters
    mu_new = C1*m+C2*mu
    sigma2 = C1*(s2 + m*m) + C2*(sigma2 + mu*mu) - mu_new*mu_new
    mu = mu_new
    a = (e - f) / (f - e / f)
    b = a * (1.0 - f) / f

    mu_sigma2_a_b = np.array([mu, sigma2, a, b])
    return mu_sigma2_a_b

def update_filter_gaussian(z, tau2, mu_sigma2):
    mu = mu_sigma2[0]
    sigma2 = mu_sigma2[1]

    denom = (sigma2 + tau2)
    mu = (sigma2 * z + tau2 * mu) / denom
    sigma2 = sigma2 * tau2 / denom
    mu_sigma2 = np.array([mu, sigma2])
    return mu_sigma2

def plot_distribution_vogiatzis(ax, mu_sigma2_a_b, Z, RHO):
    Q = q_of_Z_pi(Z, RHO, mu_sigma2_a_b)
    ax.imshow(Q, aspect='auto', origin='lower')

def plot_histogram(ax, z_meas_vec, z_min, z_max):
    bins = np.linspace(z_min, z_max, 40)
    ax.hist(z_meas_vec, bins, color='blue', edgecolor='w') # none
    ax.set_xlim([z_min, z_max])

def plot_gaussian(ax, mu_sigma2, z_min, z_max):
    x = np.linspace(z_min, z_max, 1000)
    y = norm.pdf(x, mu_sigma2[0], np.sqrt(mu_sigma2[1]))
    ax.plot(x, y, lw=2.5, color='b')
    ax.set_xlim([z_min, z_max])

def experiment_1(inlier_prob = 0.7):
    # init state
    z_max = 1.0/0.5
    z_min = 0.0
    z_true = 1.0/4.0
    z_init = 1.0/1.0
    tau = 0.1
    a_b_init = 1.5
    N = 30              # num updates
    mu_range = z_max - z_min
    sigma2_init = mu_range * mu_range / 36.0
    tau2 = tau*tau
    mu_sigma2_a_b = [z_init, sigma2_init, a_b_init, a_b_init] # for vogiatzis
    mu_sigma2 = [z_init, sigma2_init]                         # for gaussian

    # prepare plotting
    depth_samples = np.linspace(z_min, z_max, 400)
    inlier_ratios = np.linspace(0, 1, 100)
    Z, RHO = np.meshgrid(depth_samples, inlier_ratios)
    axes_vec = list()
    fig1, axes = plt.subplots(3, 1, figsize=(5, 3))
    axes_vec.append(axes)
    fig2, axes = plt.subplots(3, 1, figsize=(5, 3))
    axes_vec.append(axes)
    fig3, axes = plt.subplots(3, 1, figsize=(5, 3))
    axes_vec.append(axes)

    z_meas_vec = list()

    # perform measurement updates
    for i in range(N):

        # measurement is inlier with certain probability
        t = np.random.choice(['inlier', 'outlier'], p=[inlier_prob, (1.0-inlier_prob)])
        if t == 'inlier':
            z_meas = z_true  +  np.random.normal(0.0, tau)
        elif t == 'outlier':
            z_meas = np.random.uniform(z_min, z_max)
        z_meas_vec.append(z_meas)

        mu_sigma2_a_b = update_filter_vogiatzis(z_meas, tau2, mu_range, mu_sigma2_a_b)
        mu_sigma2 = update_filter_gaussian(z_meas, tau2, mu_sigma2)
        if(i == 2):
            plot_distribution_vogiatzis(axes_vec[0][2], mu_sigma2_a_b, Z, RHO)
            plot_gaussian(axes_vec[0][1], mu_sigma2, z_min, z_max)
            plot_histogram(axes_vec[0][0], z_meas_vec, z_min, z_max)
        if(i == N/2):
            plot_distribution_vogiatzis(axes_vec[1][2], mu_sigma2_a_b, Z, RHO)
            plot_gaussian(axes_vec[1][1], mu_sigma2, z_min, z_max)
            plot_histogram(axes_vec[1][0], z_meas_vec, z_min, z_max)
        if(i == N-1) :
            plot_distribution_vogiatzis(axes_vec[2][2], mu_sigma2_a_b, Z, RHO)
            plot_gaussian(axes_vec[2][1], mu_sigma2, z_min, z_max)
            plot_histogram(axes_vec[2][0], z_meas_vec, z_min, z_max)

    def format_axes(axes, n_iter):

        for i in range(3):
            ax = axes[i]

            ax.xaxis.set_ticks_position('none') # don't display tick marks
            ax.yaxis.set_ticks_position('none')

            if i%3 == 2: # vogiatzis:
              #ax.set_title('After '+str(int(n_iter))+' measurements, inlier probability = '+str(inlier_prob))
              ax.set_ylabel(r"$\gamma$", rotation=0)
              ax.set_yticks([0,50,100])
              ax.set_yticklabels([0,0.5,1])
              ax.set_xlabel('Inverse Depth')
            if i%3 == 1: # gaussian:
              #ax.locator_params(axis='y', nbins=3)
              ax.spines['top'].set_visible(False)
              ax.spines['right'].set_visible(False)
              ax.set_yticks([])
              ax.set_xticks([])
              ax.tick_params('x',top='off')
            if i%3 == 0: # histogram
              ax.spines['top'].set_visible(False)
              ax.spines['right'].set_visible(False)
              ax.set_yticks([])
              ax.set_xticks([])

            #width = 1.0 - 2*h_space
            #height = (1.0 - v_space) / n_plots - v_space
            #ax.set_position([h_space, 1-(i+1)*(height+v_space)+v_space/2, width, height])

    format_axes(axes_vec[0], 3)
    format_axes(axes_vec[1], N/2)
    format_axes(axes_vec[2], N)

    fig1.tight_layout()
    fig1.savefig('depth_estimation_1.pdf')
    fig2.tight_layout()
    fig2.savefig('depth_estimation_2.pdf')
    fig3.tight_layout()
    fig3.savefig('depth_estimation_3.pdf')

    print('error vogiatzis = ' + str(np.abs(mu_sigma2_a_b[0]-z_true)))
    print('error gaussian = ' + str(np.abs(mu_sigma2[0]-z_true)))

experiment_1(0.7)


class Solution:
    def countBinarySubstrings(self, s):
        """
        :type s: str
        :rtype: int
        """
        one = []
        zero = []
        o_count, z_count, result = 0, 0, 0
        step_equal = 1 if s[0] == '0' else -1
        for i in range(len(s)):
            if s[i] == '0':
                z_count += 1
                if o_count:
                    one.append(o_count)
                o_count = 0
            else:
                o_count += 1
                if z_count:
                    zero.append(z_count)
                z_count = 0
        zero.append(z_count) if z_count else one.append(o_count)
        if not len(one) or not len(zero):
            return result
        for j in range(len(zero)):
            if len(zero) == len(one):
                if step_equal == 1:
                    result += min(zero[j], one[j]) + min(zero[j], one[j - step_equal] if j - step_equal >= 0 else 0)
                else:
                    result += min(zero[j], one[j]) + min(zero[j], one[j - step_equal] if j - step_equal < len(one) else 0)
            elif len(zero) > len(one):
                result += min(zero[j], one[j] if j < len(one) else 0) + min(zero[j], one[j - 1] if j - 1 >= 0 else 0)
            else:
                result += min(zero[j], one[j]) + min(zero[j], one[j + 1])
        print(one, zero)
        return result


from graph import Graph
from collections import deque

def dfs_rec(G, start, visited = None):
  if visited is None:
    visited = set()
  visited.add(start)
  D = G.get_vertex(start)
  S = set([key.data for key in D.keys()])
  for i in S - visited:
    dfs_rec(G, i, visited)

  return visited

def dfs_itr(G, start):
  visited = set()
  stack = deque()
  stack.append(start)
  while len(stack) > 0:
    u = stack.pop()
    if u not in visited:
      visited.add(u)
      D = G.get_vertex(u)
      if D is not None:
        for v, w in D.items():
          stack.append(v.data)
  return visited

def main():
  G = Graph()
  G.add_vertex('A')
  G.add_vertex('B')
  G.add_vertex('C')
  G.add_vertex('D')
  G.add_vertex('E')
  G.add_edge('A', 'B')
  G.add_edge('B', 'C')
  G.add_edge('B', 'D')
  G.add_edge('A', 'E')
  print(dfs_itr(G, 'A'))

if __name__ == "__main__":
  main()


def Tribonacci(n) :

    dpt =[0]*n
    dpt[0]=0;
    dpt[1]=0;
    dpt[2]=1;

    for i in range(3,n) :
        dpt[i] = dpt[i - 1] + dpt[i - 2] + dpt[i - 3];
    print(dpt[-1])

n = int(input("Enter the value of n:"))
Tribonacci(n)

DIVIDE AND CONQUER APPROACH/QUESTION 1/Tribonacci.py


from ..abs.io_abc import IoABC

__all__ = ["Factory"]

class Factory(IoABC):
    def __init__(self,operator,client,**kwargs):
        self.operator = operator
        self.client = client
        self.kwargs = kwargs
        self.objs = [self]

    def __add__(self,obj):
        self.objs.append(obj)
        return self

    def execute(self,shuttle):

        shuttle,shuttle_data,shuttle_meta = shuttle, [], []

        options = self.kwargs.get('options')
        original_name = shuttle.name

        if isinstance(shuttle.data,list) and isinstance(options,list):

            for option,data in zip(options,shuttle.data):

                shuttle.data = data
                shuttle = self.operator(self.client,**option).execute(shuttle)
                shuttle_data.append(shuttle.data)
                shuttle_meta.append(shuttle.meta)

        elif isinstance(options,list) and not isinstance(shuttle.data,list):

            for option in options:
                shuttle = self.operator(self.client,**option).execute(shuttle)
                shuttle_data.append(shuttle.data)
                shuttle_meta.append(shuttle.meta)

        elif not isinstance(options,list) and isinstance(shuttle.data,list):

            for data in shuttle.data:
                shuttle.data = data
                shuttle = self.operator(self.client).execute(shuttle)
                shuttle_data.append(shuttle.data)
                shuttle_meta.append(shuttle.meta)

        shuttle.data = shuttle_data
        shuttle.meta = shuttle_meta

        shuttle.name = '-'.join([original_name,
                                self.operator.__name__,
                                self.client.__class__.__name__])

        return shuttle


#!/usr/bin/env python
# -*- coding: utf-8 -*-
'''
Time    : 2022/8/10 14:12
Author  : zhuchunjin
Email   : chunjin.zhu@taurentech.net
File    : factory.py
Software: PyCharm
'''
from PyQt5 import QtGui, QtWidgets
from PyQt5.QtWidgets import QTreeWidgetItem, QHBoxLayout, QLineEdit, QGroupBox, QPushButton

class Create_data:
    def __init__(self):
        self.groupbox = None
        self.zero = QPushButton("0")
        self.one = QPushButton("0")
        self.two = QPushButton("0")
        self.three = QPushButton("0")
        self.four = QPushButton("0")
        self.five = QPushButton("0")
        self.six = QPushButton("0")
        self.seven = QPushButton("0")
        self.line = QLineEdit()
        self.line.setText("0x00")
        self.run_btn = QPushButton("apply")
        icon = QtGui.QIcon()
        icon.addPixmap(QtGui.QPixmap(":/images/run-c.png"), QtGui.QIcon.Normal, QtGui.QIcon.Off)
        self.run_btn.setIcon(icon)
        self.run_btn.setFixedSize(80,20)
        with open("qss/qushbutton_style.qss","r") as file:
            self.run_btn.setStyleSheet(file.read())
        self.h1_layout = QHBoxLayout()
        self.line.setDisabled(True)
        self.zero.clicked.connect(lambda: self.item_change(self.zero))
        self.one.clicked.connect(lambda: self.item_change(self.one))
        self.two.clicked.connect(lambda: self.item_change(self.two))
        self.three.clicked.connect(lambda: self.item_change(self.three))
        self.four.clicked.connect(lambda: self.item_change(self.four))
        self.five.clicked.connect(lambda: self.item_change(self.five))
        self.six.clicked.connect(lambda: self.item_change(self.six))
        self.seven.clicked.connect(lambda: self.item_change(self.seven))

    def groupbox_init(self, obj):
        self.groupbox = QGroupBox(obj)
        self.groupbox.setLayout(self.h1_layout)
        self.h1_layout.addWidget(self.seven)
        self.h1_layout.addWidget(self.six)
        self.h1_layout.addWidget(self.five)
        self.h1_layout.addWidget(self.four)
        self.h1_layout.addWidget(self.three)
        self.h1_layout.addWidget(self.two)
        self.h1_layout.addWidget(self.one)
        self.h1_layout.addWidget(self.zero)
        self.h1_layout.setContentsMargins(0, 0, 0, 0)
        self.h1_layout.setSpacing(0)
        return self.groupbox

    def item_change(self, btn):
        if btn.text() == "0":
            btn.setText("1")
            self.line_counting()
        else:
            btn.setText("0")
            self.line_counting()

    def setVisable(self, lis_num):
        for i in lis_num:
            if i == 0:
                self.zero.setDisabled(True)
                self.zero.setStyleSheet('''QPushButton{background:#5a586c}''')
            elif i == 1:
                self.one.setDisabled(True)
                self.one.setStyleSheet('''QPushButton{background:#5a586c}''')
            elif i == 2:
                self.two.setDisabled(True)
                self.two.setStyleSheet('''QPushButton{background:#5a586c}''')
            elif i == 3:
                self.three.setDisabled(True)
                self.three.setStyleSheet('''QPushButton{background:#5a586c}''')
            elif i == 4:
                self.four.setDisabled(True)
                self.four.setStyleSheet('''QPushButton{background:#5a586c}''')
            elif i == 5:
                self.five.setDisabled(True)
                self.five.setStyleSheet('''QPushButton{background:#5a586c}''')
            elif i == 6:
                self.six.setDisabled(True)
                self.six.setStyleSheet('''QPushButton{background:#5a586c}''')
            elif i == 7:
                self.seven.setDisabled(True)
                self.seven.setStyleSheet('''QPushButton{background:#5a586c}''')

    def line_counting(self):
        text_str = self.seven.text() + self.six.text() + self.five.text() + self.four.text() + self.three.text() + self.two.text() + self.one.text() + self.zero.text()
        self.line.setText(hex(int(text_str, 2)))


"""
Read and parse the grammar format as described in

    https://dfns.dyalog.com/s_Binding.htm
    https://dfns.dyalog.com/n_parse.htm
    https://dfns.dyalog.com/s_parse.htm

"""
from functools import reduce
from itertools import product
import re
from string import ascii_letters, digits, whitespace

import numpy as np

class Grammar:
    functions = '+-×÷*=≥>≠∨∧⍒⍋⌽⍉⊖⍟⍱⍲!?∊⍴~↑↓⍳○*⌈⌊∇⍎⍕⊃⊂∩∪⊥⊤|≡≢,⍪⊆⌹'
    hybrids = '/⌿\⍀'
    monadic_operators = '⌸¨⍨'
    dyadic_operators = '⍣⌺@⍥⍤'

    def __init__(self, cats, zmat, bmat, xmat, bkts, bcats, lbs, rbs, blabs):
        self.cats = cats
        self.zmat = zmat
        self.bmat = bmat
        self.xmat = xmat
        self.bkts = bkts
        self.bcats = bcats
        self.lbs = lbs
        self.rbs = rbs
        self.blabs = blabs

    @classmethod
    def compile(cls, grammar: list[str]):
        sep = [r.startswith('⍝⍝⍝⍝⍝⍝⍝⍝') for r in grammar]
        idx = [i for i, s in enumerate(sep) if s]

        categories = grammar[idx[0]:idx[1]]
        macros = grammar[idx[1]+1:idx[2]]
        bindings = grammar[idx[2]+1:]

        # Categories & brackets
        if categories[-1] == '': # Sometimes we have an empty line at the end :/
            categories = categories[:-1]

        cats = [r[:r.index(' ')] for r in categories[1:] if r != ''] # Last are the brackets
        brackets = None
        if cats[-1].startswith('()'):
            b = categories.pop(-1)
            brackets = b[:b.index('⍝')].strip()
            cats.pop(-1)

        lcats = len(cats)

        # Macros
        if macros[-1] == '': # Sometimes we have an empty line at the end :/
            macros = macros[:-1]
        macro_tab = dict([mk[:mk.index('⍝')].strip().split('=') for mk in macros]) # Trim

        # Bindings -- strip comments. Separating lines are sometimes empty, and sometimes
        # they contain a lamp :/
        bb = []
        for b in bindings:
            b = b.strip()
            if b == '':
                bb.append(b)
            else:
                bb.append(b[:b.index('⍝')].strip())

        bindings = bb

        # The bindings section has sub-sections, now delineated by a
        # an empty line

        sep = [r=='' for r in bindings]
        idx = [i for i, s in enumerate(sep) if s]

        # Partition
        pidx = [e.tolist() for e in np.split(np.arange(len(bindings)), idx)]
        sections = []
        for sect in pidx:
            if len(sect) == 1:
                sections.append([bindings[sect[0]]])
            else:
                sections.append(bindings[sect[1]:sect[-1]+1])

        # Expand macros and separate multiple entries on space
        split_sections = []
        for s in sections:
            new_s = []
            for item in s:
                new_s.extend(macro_expand(item, macro_tab).split())
            split_sections.append(new_s)

        # Expand the dots
        dot_sections = []
        for s in split_sections:
            new_s = []
            for item in s:
                new_s.extend(dot_expand(item))
            dot_sections.append(new_s)

        # Build the complete bindings table
        zmat = np.zeros(lcats*lcats, dtype=int).reshape((lcats, lcats)) # Resulting categories
        bmat = np.zeros(lcats*lcats, dtype=int).reshape((lcats, lcats)) # Binding strengths

        for i, s in enumerate(dot_sections):
            for (left, right), target in s:  # type: ignore
                l_index = cats.index(left)   # type: ignore
                r_index = cats.index(right)  # type: ignore
                t_index = cats.index(target) # type: ignore

                zmat[l_index, r_index] = t_index
                bmat[l_index, r_index] = len(dot_sections) - i

        assert brackets
        bkts = [a for a in brackets if a not in ascii_letters + digits + whitespace] # Bracket pairings
        lbs, rbs = np.array(list(zip(bkts[::2], bkts[1::2]))).T.tolist()             # Lefts and rights of brackets
        p = f'[{re.escape("".join(lbs))}](.*?)[{re.escape("".join(rbs))}]'
        blabs = re.findall(p, brackets)                                              # Bracket labels
        bcats = []                                                                   # Bracket categories

        for b in blabs:
            try:
                bcats.append(cats.index(b))
            except ValueError:
                bcats.append(len(cats))

        xmat = np.pad(bmat, ((1, 1), (1, 1)), 'constant') # Extended bmat: pad with zeros in x and y

        return cls(cats, zmat, bmat, xmat, bkts, bcats, lbs, rbs, blabs)

    def classify(self, src: str) -> list[tuple]:
        i = 0
        pairs: list[tuple] = []
        while i<len(src):
            ch = src[i]
            if ch == '⍝':
                i = skip_comment(src, i)
                continue
            elif ch in whitespace:
                pass
            elif ch in self.bkts:
                pairs.append((-1, ch))
            elif ch == "'":
                i, s = getstring(src, i)
                pairs.append((0, s))
                continue
            elif ch == '¯' or ch.isdigit() or ch == '.' and peek(src, i).isdigit():
                i, num = getnum(src, i)
                pairs.append((0, num))
                continue
            elif ch in ascii_letters+"⎕_": # Named arrays, functions or operators
                i, name = getname(src, i)
                pairs.append((self.cats.index('N'), name))
                continue
            elif ch in Grammar.functions:
                pairs.append((self.cats.index('F'), ch))     # Primitive function
            elif ch in Grammar.hybrids:
                pairs.append((self.cats.index('H'), ch))     # Hybrid function/operator
            elif ch in Grammar.monadic_operators:
                pairs.append((self.cats.index('MOP'), ch))   # Primitive monadic operator
            elif ch in Grammar.dyadic_operators:
                pairs.append((self.cats.index('DOP'), ch))   # Primitive dyadic operator
            elif ch == '∘':
                pairs.append((self.cats.index('JOT'), ch))   # Jot: compose / null operand
            elif ch == ';':
                pairs.append((self.cats.index('LST'), ch))   # Subscript list separator
            elif ch == ':':
                pairs.append((self.cats.index('CLN'), ch))   # Expression list separator
            elif ch == '⋄':
                pairs.append((self.cats.index('XL'), ch))    # Colon for guard
            elif ch == '.':
                pairs.append((self.cats.index('DOT'), ch))   # Dot: ref / product
            elif ch == '←':
                pairs.append((self.cats.index('ARO'), ch))   # Assignment arrow
            elif ch in '⍺⍵':
                pairs.append((0, ch))                        # Dfn arg arrays
            i += 1
        return pairs

    def bkt(self, bracket: str, t: tuple) -> tuple:
        """
        bkt ← {                       ⍝ bind of bracketed node [ ⍵ ].
            (cat expr)←⍵              ⍝ category of bracketed expr.
            zcat←(cat,1↓bcats)[lbs⍳⍺] ⍝ resulting category.
            zcat(⍺ expr)              ⍝ ⍺-bracketed node.
        }                             ⍝ :: left_bkt ∇ node → node
        """
        cat, expr = t
        zcat = ([cat]+self.bcats[1:])[self.lbs.index(bracket)]

        return (zcat, (bracket, expr))

    def ebk(self, bracket: str) -> tuple:
        """
        Tag empty brackets with the category of the bracketed node:

            [] ⍝ Empty index list
            {} ⍝ Empty dfn
        """
        return (self.bcats[self.lbs.index(bracket)], bracket)

    def bind(self, stream: tuple) -> tuple:
        Aa, Bb, Cc = stream[1:4]
        D_, L = _unpack(stream[0])
        R, _D = _unpack(stream[4])

        if type(Aa) == int and Aa == Cc == -1: # Single node; we're done
            return Bb,

        if type(Aa) == int and Aa == Bb == -1:
            # Partial parse; we can't reduce further. This is either a
            # syntax error, or we've landed on a name that would need
            # looking up.
            return stream

        # Separate the tuples into categories and tokens
        A, a = _unpack(Aa)
        B, b = _unpack(Bb)
        C, c = _unpack(Cc)

        if a in self.bkts[2:] and b in self.bkts[2:]: # empty brackets []
            return self.bind((rgt((D_, L)), Aa, self.ebk(b), R, _D)) # rgt(∆_ L)Aa(ebk b)R _∆

        if a in self.bkts and c in self.bkts: # bracketed single value Bb
            return self.bind((D_, L, self.bkt(a, Bb), R, _D))  # (⊂a c)∊bkts:∇ rgt ∆_ L(a bkt Bb)R _∆

        if a in self.rbs: # right bracket: skip left.
            return self.bind(lft(lft(stream))) # (⊂a)∊rbs:∇ lft lft ⍵

        if self.xmat[(A+1, B+1)] >= self.xmat[(B+1, C+1)]: # A:B ≥ B:C → skip left.
            return self.bind(lft(stream))

        BbCc = (self.zmat[(B, C)], (b, c)) # BbCc←zmat[B;C],⊂b c ⍝ B bound with C.
        return self.bind(((D_, L), Aa, BbCc, R, _D)) # binds with token to the right?

def rgt(stream: tuple) -> tuple:
    """
    Skip right

    rgt ← {
        ∆_ A B C (R _∆) ← ⍵
        (∆_ A) B C R _∆
    }
    """
    D_, A, B, C = stream[:-1]
    (R, _D) = _unpack(stream[-1])

    return (D_, A), B, C, R, _D

def lft(stream: tuple) -> tuple:
    """
    Skip left

    lft ← {
        (∆_ L) A B C _∆ ← ⍵
        ∆_ L A B (C _∆)
    }
    """
    D_, L = _unpack(stream[0])
    A, B, C, _D = stream[1:]

    return D_, L, A, B, (C, _D)

def macro_expand(str, macros):
    """
    Expand macros in a string.
    """
    s = str
    while True:
        changed = False
        for k, v in macros.items():
            s_r = s.replace(k, v)
            if s_r != s:
                changed = True
                s = s_r
        if not changed:
            break
    return s

def _unpack(item: int|tuple) -> tuple:
    """
    Python doesn't do scalar extension, so we have to do it ourselves.
    """
    if type(item) == int:
        return (item, item)
    else:
        return item # type: ignore

def dot_expand(str):
    """
    A:F.H => AF

    means

    A:F => AF
    A:H => AF
    """
    rule, target = str.split('→')
    left, right = rule.split(':')

    lefts = left.split('.')
    rights = right.split('.')
    targets = target.split('.')

    rules = list(product(lefts, rights))
    if len(targets) == 1: # Scalar extension on the right
        targets = targets * len(rules)
    if len(rules) != len(targets):
        raise SyntaxError('SYNTAX ERROR')
    return list(zip(rules, targets))

def peek(src: str, idx: int) -> str:
    try:
        return src[idx+1]
    except IndexError:
        return ''

def skip_comment(src: str, i: int) -> int:
    while i < len(src) and src[i] != '\n':
        i += 1
    return i

def getstring(src: str, idx: int) -> tuple[int, str]:
    m = re.match(r"'((?:''|[^'])*)'", src[idx:]) # Note: APL escapes single quotes with single quotes
    if not m:
        raise SyntaxError("SYNTAX ERROR: Unpaired quote")
    data = m.group(1)
    return (2+idx+len(data), data.replace("''", "'"))

def get_cmplx(tok: str) -> complex:
    parts = tok.split('J')
    if len(parts) != 2:
        raise SyntaxError('SYNTAX ERROR: malformed complex scalar')
    (re, im) = parts
    try:
        cmplx = complex(float(re), float(im))
    except TypeError:
        raise SyntaxError('SYNTAX ERROR: malformed complex scalar')
    return cmplx

def getnum(src: str, idx: int) -> tuple[int, int|float|complex]:
    tok = ''
    start = idx
    m = re.match(r"[¯0-9eEjJ.]+", src[idx:])
    if not m:
        raise SyntaxError('SYNTAX ERROR: malformed numeric scalar')
    tok = m.group(0).upper()
    tok = tok.replace('¯', '-')
    if 'J' in tok:
        return (idx+len(tok), get_cmplx(tok))
    if '.' in tok:
        val = float(tok)
    else:
        val = int(tok)
    return (idx+len(tok), val)

def getname(src: str, idx: int) -> tuple[int, str]:
    m = re.match(r'(^[⎕_a-z][_a-z0-9]*)', src[idx:], re.IGNORECASE)
    if not m:
        raise SyntaxError('SYNTAX ERROR: malformed name')
    data = m.group(1)
    if data[0] == '⎕':
        return (idx+len(data), data.upper())
    return (idx+len(data), data)

if __name__ == "__main__":
    with open('grammar') as f:
        grammar = f.read().splitlines()
    g = Grammar.compile(grammar)
    # Ok, we have parsed the grammar, yay: cats, zmat, bmat, bkts, blabs

    src = '{⍺+⍵}/⍳5'
    # src = '+/⍳5'
    # src = '⍳5'
    # src = 'x ← ⍳5 ⋄ x×3'
    pairs = g.classify(src)
    eos = -1
    ll = [eos]+pairs[:-2]
    if ll == [-1]:
        D_ = -1
    else:
        # Left cons list: ∆_←↑{⍺ ⍵}⍨/⌽eos,¯2↓pairs
        D_ = tuple(reduce(lambda x, y: (x, y), ll)) # type: ignore
    Aa, Bb, Cc = (eos, eos, *pairs, eos)[-3:] # 3-token window
    stream = (D_, Aa, Bb, Cc, eos)
    tree = g.bind(stream)

    print(tree)


#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
Created on Sat Jun 30 00:06:13 2018

@author: vivek
"""

import numpy as np # linear algebra
import pandas as pd # data processing, CSV file I/O (e.g. pd.read_csv)

from sklearn.feature_extraction.text import CountVectorizer
from keras.preprocessing.text import Tokenizer
from keras.preprocessing.sequence import pad_sequences
from keras.models import Sequential
from keras.layers import Dense, Embedding, LSTM
from sklearn.model_selection import train_test_split
from keras.utils.np_utils import to_categorical
from sklearn.externals import joblib
import re

df = pd.read_csv("~/Downloads/train.csv")
df = df.dropna()
data = df["title"]
data = data.apply(lambda x: x.lower())

batch_size = 5000
tokenizer = Tokenizer(nb_words=batch_size, split=' ')

tokenizer.fit_on_texts(data.values)
X = tokenizer.texts_to_sequences(data.values)

maxx = 0
c=0
for ll in X:
    c=len(ll)
    if c>maxx:
        maxx=c
print('Max',maxx)
X = pad_sequences(X)
print(len(X[0]))

embed_dim = 128
lstm_out = 256
model = Sequential()
model.add(Embedding(batch_size, embed_dim,input_length = X.shape[1], dropout=0.2))
model.add(LSTM(lstm_out, dropout_U=0.2, dropout_W=0.2))
model.add(Dense(2,activation='softmax'))
model.compile(loss = 'categorical_crossentropy', optimizer='adam',metrics = ['accuracy'])
print(model.summary())

Y = pd.get_dummies(df['label']).values
print(Y)
X_train, X_test, Y_train, Y_test = train_test_split(X,Y, test_size = 0.20, random_state = 42)
print(X_train.shape,Y_train.shape)
print(X_test.shape,Y_test.shape)

model.fit(X_train, Y_train, nb_epoch = 2, batch_size=64, verbose = 2)

def predict_news(inp):
    input_val = inp
    z = tokenizer.texts_to_sequences([input_val])
    z = pad_sequences(z, maxlen=59)
    z = np.array(z[0]).reshape(1, 59)
    pred = model.predict(z)
    if pred[0][0] > 0.5:
        result="true"
    else:
        result="fake"
    return result

print(predict_news("Pope has a new baby"))
print(predict_news("Pope is praying"))

model.save('fake_news.h5')


#!/usr/bin/env python
# encoding: utf-8
'''
@Author  : pentiumCM
@Email   : 842679178@qq.com
@Software: PyCharm
@File    : wheel_filter.py
@Time    : 2020/9/9 17:09
@desc	 :
'''

import pandas as pd
import seaborn as sns
import matplotlib.pyplot as plt
import numpy as np

from filterpy.kalman import KalmanFilter
from filterpy.common import Q_discrete_white_noise

def get_data(csv_path):
    """
    读取数据
    :param csv_path: 数据源的路径
    :return:
    """
    wheel_df = pd.read_csv(csv_path)

    sns.set()
    # Seaborn 要求原始数据的输入类型为 pandas 的 Dataframe 或 Numpy 数组
    sns.scatterplot(x=wheel_df['frame_index'], y=wheel_df['left_wheel_center_x'],
                    data=wheel_df, s=100)
    sns.relplot(x="frame_index", y="left_wheel_center_x", kind="line", data=wheel_df)
    plt.show()
    return wheel_df

def kalman_filter(measure_data):
    """
    卡尔曼滤波处理
    :param measure_data: 滤波数据（测量数据）
    :return:
    """
    # 构造具有所需尺寸的 filter
    kf = KalmanFilter(dim_x=2, dim_z=1)  # dim_x:隐状态大小，dim_z:量测大小

    # 为状态分配初始值
    # x = np.array([measure_data[0][0], measure_data[1][0]])
    x = np.array([0, 500])
    kf.x = x

    # 定义状态转换矩阵
    dt = 1
    F = np.array([[1, dt],
                  [0, 1]])
    kf.F = F

    # 定义状态协方差矩阵
    P = np.array([[1000, 20],
                  [20, 1000]])
    kf.P = P

    # 定义过程噪声
    kf.Q = Q_discrete_white_noise(dim=2, dt=0.1, var=0.13)

    # 定义测量矩阵
    kf.H = np.array([[1, 0]])

    # 定义测量噪声
    kf.R = 2

    iteration = measure_data.shape[1]

    filter_result = list()
    filter_result.append(x)
    for i in range(1, iteration):
        z = np.array(measure_data[1][i])
        kf.predict()
        kf.update(z)
        filter_result.append(kf.x)
    filter_result = np.squeeze(np.array(filter_result))

    return filter_result

def plot_result(measure_data, filter_result):
    plt.figure(figsize=(8, 4))
    plt.plot(range(0, measure_data.shape[1]), measure_data[1][0:], label='measure_data')
    plt.plot(range(0, filter_result.shape[0]), filter_result[0:, 0], label='Kalman Filter')
    plt.legend()
    plt.xlabel('Time', fontsize=14)
    plt.ylabel('velocity [m]', fontsize=14)
    plt.show()

if __name__ == '__main__':
    df = get_data('F:/project/tx/three_wheel_test.csv')

    measure_data = np.array([df['frame_index'].values, df['left_wheel_center_x'].values])

    filter_result = kalman_filter(measure_data)

    plot_result(measure_data, filter_result)

    print(measure_data[1])
    print(filter_result[0:, 0])


from sklearn.feature_extraction.text import CountVectorizer
from text import morphological_analysis

morpho_list = list()
text1 = "私はラーメンが好き"
text2 = "私は餃子が好き"
text3 = "私はラーメンが嫌い"
morpho_list.append(' '.join(morphological_analysis(text1)))
morpho_list.append(' '.join(morphological_analysis(text2)))
morpho_list.append(' '.join(morphological_analysis(text3)))  # 3行4列の行列になる
cv = CountVectorizer()
# 特徴量に変換
features = cv.fit_transform(morpho_list)
print(features)
vocab = cv.vocabulary_

# 次に、学習と分類を行う
# 学習はtrain(LinearSVC,)
# 分類はclassify(predict)
# テストデータと学習用データを分けるコードも書かないといけない

# matrix = cv.fit_transform(morpho_list) # 行列
# print(features.toarray())
# print(cv.get_feature_names())
# print(cv.vocabulary_)


# coding=utf-8

import sys

import petsc4py

petsc4py.init(sys.argv)

# from time import time
# from scipy.io import loadmat
# from src.stokes_flow import problem_dic, obj_dic
# from src.geo import *
from petsc4py import PETSc
from src import stokes_flow as sf
from src.myio import *
from src.objComposite import createEcoliComp_tunnel
from src.myvtk import save_singleEcoli_vtk
from codeStore.ecoli_common import *

# def get_problem_kwargs(**main_kwargs):
#     problem_kwargs = get_solver_kwargs()
#     OptDB = PETSc.Options()
#     fileHandle = OptDB.getString('f', 'ecoliInPipe')
#     OptDB.setValue('f', fileHandle)
#     problem_kwargs['fileHandle'] = fileHandle
#
#     kwargs_list = (get_vtk_tetra_kwargs(), get_ecoli_kwargs(), get_forcefree_kwargs(), main_kwargs,)
#     for t_kwargs in kwargs_list:
#         for key in t_kwargs:
#             problem_kwargs[key] = t_kwargs[key]
#     return problem_kwargs
#
#
# def print_case_info(**problem_kwargs):
#     fileHandle = problem_kwargs['fileHandle']
#     PETSc.Sys.Print('-->Ecoli in pipe case, force free case.')
#     print_solver_info(**problem_kwargs)
#     print_forcefree_info(**problem_kwargs)
#     print_ecoli_info(fileHandle, **problem_kwargs)
#     return True

# @profile
def main_fun(**main_kwargs):
    OptDB = PETSc.Options()
    fileHandle = OptDB.getString('f', 'ecoliInPipe')
    OptDB.setValue('f', fileHandle)
    main_kwargs['fileHandle'] = fileHandle
    problem_kwargs = get_problem_kwargs(**main_kwargs)

    if not problem_kwargs['restart']:
        forcepipe = problem_kwargs['forcepipe']
        print_case_info(**problem_kwargs)
        ecoli_comp = createEcoliComp_tunnel(name='ecoli_0', **problem_kwargs)
        problem = sf.StokesletsInPipeforcefreeProblem(**problem_kwargs)
        problem.set_prepare(forcepipe)
        problem.do_solve_process((ecoli_comp,), pick_M=False)
        # post process
        head_U, tail_U = print_single_ecoli_forcefree_result(ecoli_comp, **problem_kwargs)
        ecoli_U = ecoli_comp.get_ref_U()
        save_singleEcoli_vtk(problem, createHandle=createEcoliComp_tunnel)
    else:
        head_U, tail_U, ecoli_U = ecoli_restart(**main_kwargs)
    return head_U, tail_U, ecoli_U
    # t_name = check_file_extension(fileHandle, '_pick.bin')
    # with open(t_name, 'rb') as myinput:
    #     unpick = pickle.Unpickler(myinput)
    #     problem = unpick.load()
    # problem.unpick_myself()
    # ecoli_comp = problem.get_obj_list()[0]
    #
    # problem_kwargs = problem.get_kwargs()
    # problem_kwargs1 = get_problem_kwargs(**main_kwargs)
    # problem_kwargs['matname'] = problem_kwargs1['matname']
    # problem_kwargs['bnodesHeadle'] = problem_kwargs1['bnodesHeadle']
    # problem_kwargs['belemsHeadle'] = problem_kwargs1['belemsHeadle']
    # problem_kwargs['ffweightx'] = problem_kwargs1['ffweightx']
    # problem_kwargs['ffweighty'] = problem_kwargs1['ffweighty']
    # problem_kwargs['ffweightz'] = problem_kwargs1['ffweightz']
    # problem_kwargs['ffweightT'] = problem_kwargs1['ffweightT']
    # # PETSc.Sys.Print([attr for attr in dir(problem) if not attr.startswith('__')])
    # # PETSc.Sys.Print(problem_kwargs1['ffweightT'])
    #
    # problem.set_kwargs(**problem_kwargs)
    # print_case_info(**problem_kwargs)
    # problem.print_info()
    # problem.set_force_free()
    # problem.solve()

if __name__ == '__main__':
    main_fun()


from joblib import Parallel, delayed
import rir_generator as rir
import numpy as np

from .util import *

def get_source_position(room_dimension):
    # distance from source position and wall is 0.5 meter
    return np.random.rand() * (np.array(room_dimension) - 1) + 0.5

def get_random_direction(dim=2):
    direction = np.random.rand(dim)
    direction = direction / np.sqrt(np.sum(direction ** 2))
    return direction

def get_mic_positions(room_dimension, num_mic=8, d_mic=0.04):
    origin = get_source_position(room_dimension)
    origin = np.array(origin)
    direction = get_random_direction() * d_mic
    # scale ra 8 mic
    mic_positions = [list(origin.copy())]
    current_mic_position = list(origin.copy())
    for mic in range(num_mic - 1):
        current_mic_position[:2] += direction
        mic_positions.append(list(current_mic_position.copy()))
    return mic_positions

def generate_rir_wrapper(mic_positions, source_position, room_dimension):
    return rir.generate(c=340,                          # Sound velocity (m/s)
                        fs=16000,                       # Sample rate (samples/s)
                        r=mic_positions,                # Microphone position(s) [x y z] (m)
                        s=source_position,              # Source position [x y z] (m)
                        L=room_dimension,               # Room dimensions [x y z] (m)
                        reverberation_time=0.5,         # Reverberation time (s)
                        nsample=8000)                   # Number of output samples

def generate_one_rir(room_dimension):
    clean_position = get_source_position(room_dimension)
    noise_position = get_source_position(room_dimension)
    mic_positions  = get_mic_positions(room_dimension)
    clean_rir      = generate_rir_wrapper(mic_positions, clean_position, room_dimension)
    noise_rir      = generate_rir_wrapper(mic_positions, noise_position, room_dimension)
    rir = np.concatenate([clean_rir, noise_rir], axis=1)
    return rir

def f(mode, room_dimension, idx):
    folder = create_mixed_folder(mode, 'rir')
    x      = generate_one_rir(room_dimension)
    path   = os.path.join(folder, f'{idx}.npz')
    np.savez_compressed(path, x=x)

def gen_rir(args):
    # configuration
    room_dimensions = {
        'train': [(3, 3, 2), (5, 4, 6), (8, 9, 10)],
        'dev'  : [(5, 8, 3), (4, 7, 8)],
        'test' : [(4, 5, 3), (6, 8, 5)]
    }
    modes = ['train', 'dev', 'test']

    num_sample = {
        'train': 1000,
        'dev'  : 1000,
        'test' : 1000,
    }

    # generate rirs
    for mode in modes:
        args_list = []
        idx = 0
        for room_dimension in room_dimensions[mode]:
            for i in range(num_sample[mode]):
                args_list.append((mode, room_dimension, idx))
                idx += 1
        Parallel(n_jobs=os.cpu_count())(
            delayed(f)(*args) for args in args_list)


######
#Date: 07.10.2022
##Version Log:
#
#
#
######

from cProfile import label
from math import sqrt
import re
from socket import EAI_SOCKTYPE
from turtle import color
from typing import Mapping
from cv2 import mean
from matplotlib.pyplot import axis, plot, show
from pip import main
import pymap3d as map
import numpy as np
import pandas as pd
import copy
import matplotlib.pyplot as plt

###Import

##Real Flight Test Data
val_data1 = pd.read_csv('../Flight_Logs/Flight_Test/DJIFlightRecord_2022-08-25_[10-38-43].csv', sep=',')
val_data2 = pd.read_csv('../Flight_Logs/Flight_Test/DJIFlightRecord_2022-08-25_[10-42-05].csv', sep=',')
val_data3 = pd.read_csv('../Flight_Logs/Flight_Test/DJIFlightRecord_2022-08-25_[10-45-30].csv', sep=',')
val_flights = [val_data1,val_data2,val_data3]

##Simulation Data
sim_data1 = pd.read_csv('../Flight_Logs/Simulation/verification_final1.csv', sep=';')
sim_data2 = pd.read_csv('../Flight_Logs/Simulation/verification_final2.csv', sep=';')
sim_data3 = pd.read_csv('../Flight_Logs/Simulation/verification_final3.csv', sep=';')

# sim_datatest = pd.read_csv('Validation/validation_test.csv', sep=';') #Only for test flight data
# sim_datatest= sim_datatest.iloc[:,1:] #Only for test flight data

#Removing first line (Time)
sim_data1 = sim_data1.iloc[:,1:]
sim_data2 = sim_data2.iloc[:,1:]
sim_data3 = sim_data3.iloc[:,1:]
sim_flights = [sim_data1,sim_data2,sim_data3]

# sim_flights = [sim_datatest,sim_datatest,sim_datatest] #Only for test flight data

##Simulation Data before Model Tuning
sim_data_comparison = pd.read_csv('../Flight_Logs/Simulation/verification_no_adjustments.csv', sep=';')
sim_data_comparison2 = pd.read_csv('../Flight_Logs/Simulation/verification_no_adjustments2.csv', sep=';')
sim_data_comparison3 = pd.read_csv('../Flight_Logs/Simulation/verification_no_adjustments3.csv', sep=';')
sim_data_comparison = sim_data_comparison.iloc[:,1:]
sim_data_comparison2 = sim_data_comparison2.iloc[:,1:]
sim_data_comparison3 = sim_data_comparison3.iloc[:,1:]
sim_compare = [sim_data_comparison,sim_data_comparison2,sim_data_comparison3]

##Waypoints
waypoints = pd.read_excel('../Script/Flight_Plans/Flight_Plan.xlsx')
waypoints = waypoints.iloc[0:waypoints.shape[0]-1,:]
waypoints = waypoints.rename(columns={waypoints.columns[1]:'latitude',waypoints.columns[2]:'longitude',waypoints.columns[3]:'height'})

###Data Post Processing

def real_post_process(real_data,logsteps,start,end):
    '''Takes a data frame with 3 single flight logs from the flight testing as input. Extracts the most interesting columns.
    Turns them into correct units if needed, removes the starting and landing procedure and takes the average of the 3 logs.
    The function returns the averaged data set and the shortened flight logs of all 3 flights in one data frame'''

    ## Initial Variables
    real = pd.DataFrame()
    lat_waypoint1 = 46.9765208  #Latitude of Waypoint 1
    long_waypoint1 = 7.179124   #Longitude of Waypoint 1

    ## Post Processing Real Data
    # Iterating through Data Sets
    for i in real_data:

        #Exporting important columns
        real_single = copy.deepcopy(i.iloc[:,4])                    #Add latitude
        real_single = pd.concat([real_single,i.iloc[:,5]],axis=1)   #Add longitude
        real_single = pd.concat([real_single,i.iloc[:,6]],axis=1)   #Add height [ft]
        real_single = pd.concat([real_single,i.iloc[:,9]],axis=1)   #Add altitude [ft]
        real_single = pd.concat([real_single,i.iloc[:,10]],axis=1)  #Add speed [mph]
        real_single = real_single.rename({' OSD.latitude':'latitude',' OSD.longitude':'longitude',' OSD.height [ft]':'height',' OSD.altitude [ft]':'altitude',' OSD.hSpeed [MPH]':'speed'},axis=1)

        # Imperial Unit in SI
        real_single.loc[:,'height'] = real_single.loc[:,'height']/3.33      #ft --> m
        real_single.loc[:,'altitude'] = real_single.loc[:,'altitude']/3.33  #ft --> m
        real_single.loc[:,'speed'] = real_single.loc[:,'speed']*0.44704     #mph --> m/s

        #Removing Start Procedure
        real_start = copy.deepcopy(real_single)
        real_start.loc[:,'latitude'] = abs(real_start.loc[:,'latitude']-lat_waypoint1)
        real_start.loc[:,'longitude'] = abs(real_start.loc[:,'longitude']-long_waypoint1)
        summe = real_start.loc[:,'latitude'] + real_start.loc[:,'longitude']
        summe_start = summe.iloc[start:end]
        idx_start = summe_start.idxmin()
        summe_end = summe.iloc[end+1:]
        idx_end = summe_end.idxmin()

        #Merging all runs in one data sate
        real_add = copy.deepcopy(real_single.iloc[idx_start:idx_end,:])
        new_idx = pd.Index(range(0,idx_end-idx_start,1))
        real_add.set_index(new_idx,inplace=True)
        real = pd.concat([real,real_add], axis=1, ignore_index=True)

    #Averaging Date of the runs
    cols = real_add.shape[1]
    lat_start = 0; long_start = 1; height_start = 2
    alt_start = 3; speed_start = 4

    lat = real[[lat_start,lat_start+cols,lat_start+2*cols]].mean(axis = 1, skipna = True) #Selecting necessary columns for mean
    long = real[[long_start,long_start+cols,long_start+2*cols]].mean(axis = 1, skipna = True)
    height = real[[height_start,height_start+cols,height_start+2*cols]].mean(axis = 1, skipna = True)
    alt = real[[alt_start,alt_start+cols,alt_start+2*cols]].mean(axis = 1, skipna = True)
    speed = real[[speed_start,speed_start+cols,speed_start+2*cols]].mean(axis = 1, skipna = True)

    #Create column with frequency of logged data
    time = pd.Series(np.arange(0,real.shape[0]/logsteps,1/logsteps))
    real = pd.concat([time,real], axis=1, ignore_index=True)     #Add them also to the data sets containing all runs

    real_avg = pd.DataFrame({
        'time': time,
        'latitude':lat,
        'longitude': long,
        'height': height,
        'altitude':alt,
        'speed':speed})

    return real_avg, real

##Post Processing Sim Data
def sim_post_process(sim,logsteps,start,end):
    '''Takes a data frame with 3 single flight logs from the simulation as input.
    Removes the starting and landing procedure and takes the average of the 3 logs.
    The function returns the averaged data set and flight logs of all 3 flights in one data frame'''

    sim_all = pd.DataFrame()
    lat_waypoint1 = 46.9765208  #Latitude of Waypoint 1
    long_waypoint1 = 7.179124   #Longitude of Waypoint 1

    ##Iterating through Sim Runs
    for i in sim:
        #Deleting Start Procedure
        sim_start = copy.deepcopy(i)
        sim_start.loc[:,'latitude'] = abs(sim_start.loc[:,'latitude']-lat_waypoint1)
        sim_start.loc[:,'longitude'] = abs(sim_start.loc[:,'longitude']-long_waypoint1)
        summe = sim_start.loc[:,'latitude'] + sim_start.loc[:,'longitude']
        summe_start = summe.iloc[start:end]
        idx_start = summe_start.idxmin()
        summe_end = summe.iloc[end+1:]
        idx_end = summe_end.idxmin()

        #Merging all runs in one data sate
        sim_add = copy.deepcopy(i.iloc[idx_start:idx_end,:])
        new_idx = pd.Index(range(0,idx_end-idx_start,1))
        sim_add.set_index(new_idx,inplace=True)
        sim_all = pd.concat([sim_all,sim_add], axis=1, ignore_index=True)

    ##Averaging Date of the runs
    cols = sim_add.shape[1]
    lat_start = 1; long_start = 2; height_start = 3
    pitch_start = 5; roll_start = 6; yaw_start = 7

    lat = sim_all[[lat_start,lat_start+cols,lat_start+2*cols]].mean(axis = 1, skipna = True) #Selecting necessary columns for mean
    long = sim_all[[long_start,long_start+cols,long_start+2*cols]].mean(axis = 1, skipna = True)
    height = sim_all[[height_start,height_start+cols,height_start+2*cols]].mean(axis = 1, skipna = True)
    pitch = sim_all[[pitch_start,pitch_start+cols,pitch_start+2*cols]].mean(axis = 1, skipna = True)
    roll = sim_all[[roll_start,roll_start+cols,roll_start+2*cols]].mean(axis = 1, skipna = True)
    yaw = sim_all[[yaw_start,yaw_start+cols,yaw_start+2*cols]].mean(axis = 1, skipna = True)

    #Create column with frequency of logged data
    time = pd.Series(np.arange(0,sim_all.shape[0]/logsteps,1/logsteps))
    sim_all = pd.concat([time,sim_all], axis=1, ignore_index=True)     #Add them also to the data sets containing all runs

    sim_avg = pd.DataFrame({
        'time':time,
        'latitude':lat,
        'longitude': long,
        'height': height,
        'pitch':pitch,
        'roll':roll,
        'yaw':yaw})

    return sim_avg, sim_all

def gps2enu(log):
    '''Turn GPS Coordinates in ENU coordinates'''

    enu_coord=[]
    ##Home Coordinates
    gps_home_lat = 46.9765208
    gps_home_long = 7.179124
    gps_home_alt = 59

    for i in log:
        enu = map.geodetic2enu(i.loc[:,'latitude'],i.loc[:,'longitude'],i.loc[:,'height'],gps_home_lat,gps_home_long,gps_home_alt)
        i.loc[:,'latitude'] = enu[1]  #north
        i.loc[:,'longitude'] = enu[0] #east
        i.loc[:,'height'] = enu[2]    #up
        mapping = {i.columns[1]:'north',i.columns[2]:'east',i.columns[3]:'up'}
        p = i.rename(columns = mapping)
        enu_coord.append(p)

    return enu_coord

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

####DATA POSTPROCESSING

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

###Apply Post-Process Function
avg_real, real_flights = real_post_process(val_flights,10,440,600)
avg_sim, sim_flights = sim_post_process(sim_flights,5,0,400)
avg_compare, compare_flights = sim_post_process(sim_compare,5,200,290)

###Apply GPS to ENU Function
gps_coord = copy.deepcopy([avg_real,avg_sim,waypoints,avg_compare])
enu_coord = gps2enu(gps_coord)
avg_real_enu = enu_coord[0]
avg_sim_enu = enu_coord[1]
waypoints_enu = enu_coord[2]
avg_compare_enu = enu_coord[3]

###Interpolate Coordiantes

# Creates 3 Data Sets (north, east, up) with real, sim and comparison data and
# Interpolates Coordinates as the real and sim flight logs doesn't contain same logging frequency
# Real Data 10Hz, Sim Data 5Hz

##North
north = pd.DataFrame({'real':pd.Series.to_numpy(avg_real_enu.loc[:,'north'])},index=avg_real_enu.loc[:,'time'])
north_sim = pd.DataFrame({'sim':pd.Series.to_numpy(avg_sim_enu.loc[:,'north'])},index=avg_sim_enu.loc[:,'time'])
north_comp = pd.DataFrame({'comp':pd.Series.to_numpy(avg_compare_enu.loc[:,'north'])},index=avg_compare_enu.loc[:,'time'])
north = pd.concat([north,north_sim,north_comp],axis=1)

north['sim'] = north['sim'].interpolate()
north['real'] = north['real'].interpolate()
north['comp'] = north['comp'].interpolate()

##East
east = pd.DataFrame({'real':pd.Series.to_numpy(avg_real_enu.loc[:,'east'])},index=avg_real_enu.loc[:,'time'])
east_sim = pd.DataFrame({'sim':pd.Series.to_numpy(avg_sim_enu.loc[:,'east'])},index=avg_sim_enu.loc[:,'time'])
east_comp = pd.DataFrame({'comp':pd.Series.to_numpy(avg_compare_enu.loc[:,'east'])},index=avg_compare_enu.loc[:,'time'])
east = pd.concat([east,east_sim,east_comp],axis=1)

east['sim'] = east['sim'].interpolate()
east['real'] = east['real'].interpolate()
east['comp'] = east['comp'].interpolate()

##Up
up = pd.DataFrame({'real':pd.Series.to_numpy(avg_real_enu.loc[:,'up'])},index=avg_real_enu.loc[:,'time'])
up_sim = pd.DataFrame({'sim':pd.Series.to_numpy(avg_sim_enu.loc[:,'up'])},index=avg_sim_enu.loc[:,'time'])
up_comp = pd.DataFrame({'comp':pd.Series.to_numpy(avg_compare_enu.loc[:,'up'])},index=avg_compare_enu.loc[:,'time'])
up = pd.concat([up,up_sim,up_comp],axis=1)

up['sim'] = up['sim'].interpolate()
up['real'] = up['real'].interpolate()
up['comp'] = up['comp'].interpolate()

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

####RESULT: FLIGHT PAHT PLOTTINGS

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

###Plottings

##North vs. East (2D Plot)

fig = plt.figure()
ax = plt.axes()
ax.plot(avg_real_enu['north'],avg_real_enu['east'],'r--',label = 'Flight Test')
ax.plot(avg_sim_enu['north'],avg_sim_enu['east'],'g',label= 'Simulation')
ax.scatter(waypoints_enu['north'],waypoints_enu['east'],marker='o',color='black')
ax.set_title('Coordinates relative to Waypoint 1')
ax.set_ylabel('East [m]')
ax.set_xlabel('North [m]')
ax.legend(loc='upper right')
annotations=["WP-1","WP-2","WP-3","WP-4"]
for i, label in enumerate(annotations):
    plt.text(waypoints_enu['north'][i], waypoints_enu['east'][i],label)
ax.grid()
plt.show()

##North vs. East vs Up (3D Plot)

fig = plt.figure()
ax = plt.axes(projection='3d')
ax.plot3D(avg_real_enu['north'],avg_real_enu['east'],avg_real['height'],'r--',label='Flight Test')
ax.plot3D(avg_sim_enu['north'],avg_sim_enu['east'],avg_sim['height'],'g',label='Simulation')
ax.scatter(waypoints_enu['north'],waypoints_enu['east'],waypoints['height'],marker='o',color='black')
ax.set_title('Coordinates relative to Waypoint 1')
ax.set_xlabel('North [m]')
ax.set_ylabel('East [m]')
annotations=["WP-1","WP-2","WP-3","WP-4"]
for i, label in enumerate(annotations):
    ax.text(waypoints_enu['north'][i], waypoints_enu['east'][i],waypoints['height'][i],  label, zorder=1)
ax.legend()
plt.show()

##North vs. Time / East vs. Time (1D Plots)

fig, (ax1, ax2, ax3) = plt.subplots(3, 1)

fig.suptitle('ENU coordinates with respect to time')

ax2.plot(north['real'],'r--',label = 'Flight Test')
ax2.plot(north['sim'],'g',label = 'Simulation')
ax2.plot(north['comp'],'b',alpha = 0.2 ,label = 'Unadjusted')
ax2.set_xlabel('Time [s]')
ax2.set_ylabel('North [m]')
ax2.legend()
ax2.grid()

ax3.plot(east['real'],'r--',label = 'Flight Test')
ax3.plot(east['sim'],'g',label = 'Simulation')
ax3.plot(east['comp'],'b',alpha = 0.2 ,label = 'Unadjusted')
ax3.set_xlabel('Time [s]')
ax3.set_ylabel('East [m]')
ax3.grid()

ax1.plot(up['real'],'r--',label = 'Flight Test')
ax1.plot(up['sim'],'g',label = 'Simulation')
ax1.plot(up['comp'],'b',alpha = 0.2 ,label = 'Unadjusted')
ax1.set_xlabel('Time [s]')
ax1.set_ylabel('Height [m]')
ax1.grid()

plt.show()

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

####RESULTS: RUN VARIATION INCLUDING PLOTS AND ERROR EVALUATION

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

###Run Variation

# Analysis the amount of variation between the 3 runs. Performs post processing of the data and plottings.
# Some Data must be post processed as the post processing before mainly focuses on the averaged data where
# here each run must be post processed as well.

##Turn each run from GPS to ENU coordinates
gps_home_lat = 46.9765208
gps_home_long = 7.179124
gps_home_alt = 59

enu_real1= map.geodetic2enu(real_flights.loc[:,1],real_flights.loc[:,2],real_flights.loc[:,3],gps_home_lat,gps_home_long,gps_home_alt)
enu_real2= map.geodetic2enu(real_flights.loc[:,6],real_flights.loc[:,7],real_flights.loc[:,8],gps_home_lat,gps_home_long,gps_home_alt)
enu_real3= map.geodetic2enu(real_flights.loc[:,11],real_flights.loc[:,12],real_flights.loc[:,13],gps_home_lat,gps_home_long,gps_home_alt)

enu_sim1= map.geodetic2enu(sim_flights.loc[:,2],sim_flights.loc[:,3],sim_flights.loc[:,4],gps_home_lat,gps_home_long,gps_home_alt)
enu_sim2= map.geodetic2enu(sim_flights.loc[:,10],sim_flights.loc[:,11],sim_flights.loc[:,12],gps_home_lat,gps_home_long,gps_home_alt)
enu_sim3= map.geodetic2enu(sim_flights.loc[:,18],sim_flights.loc[:,19],sim_flights.loc[:,20],gps_home_lat,gps_home_long,gps_home_alt)

enu_comp1= map.geodetic2enu(compare_flights.loc[:,2],compare_flights.loc[:,3],compare_flights.loc[:,4],gps_home_lat,gps_home_long,gps_home_alt)
enu_comp2= map.geodetic2enu(compare_flights.loc[:,10],compare_flights.loc[:,11],compare_flights.loc[:,12],gps_home_lat,gps_home_long,gps_home_alt)
enu_comp3= map.geodetic2enu(compare_flights.loc[:,18],compare_flights.loc[:,19],compare_flights.loc[:,20],gps_home_lat,gps_home_long,gps_home_alt)

##Interpolation and Creation of North, East, Up data sets

#North Interpolation
north_sens =pd.DataFrame({'real':pd.Series.to_numpy(avg_real_enu.loc[:,'north'])},index=avg_real_enu.loc[:,'time'])
north1 = pd.DataFrame({'north1':pd.Series.to_numpy(enu_real1[1])},index=real_flights.loc[:,0])
north2 = pd.DataFrame({'north2':pd.Series.to_numpy(enu_real2[1])},index=real_flights.loc[:,0])
north3 = pd.DataFrame({'north3':pd.Series.to_numpy(enu_real3[1])},index=real_flights.loc[:,0])
north_avg_sim = pd.DataFrame({'sim':pd.Series.to_numpy(avg_sim_enu.loc[:,'north'])},index=avg_sim_enu.loc[:,'time'])
north1_sim = pd.DataFrame({'north1_sim':pd.Series.to_numpy(enu_sim1[1])},index=sim_flights.loc[:,0])
north2_sim = pd.DataFrame({'north2_sim':pd.Series.to_numpy(enu_sim2[1])},index=sim_flights.loc[:,0])
north3_sim = pd.DataFrame({'north3_sim':pd.Series.to_numpy(enu_sim3[1])},index=sim_flights.loc[:,0])
north_avg_comp = pd.DataFrame({'comp':pd.Series.to_numpy(avg_compare_enu.loc[:,'north'])},index=avg_compare_enu.loc[:,'time'])
north1_comp = pd.DataFrame({'north1_comp':pd.Series.to_numpy(enu_comp1[1])},index=compare_flights.loc[:,0])
north2_comp = pd.DataFrame({'north2_comp':pd.Series.to_numpy(enu_comp2[1])},index=compare_flights.loc[:,0])
north3_comp = pd.DataFrame({'north3_comp':pd.Series.to_numpy(enu_comp3[1])},index=compare_flights.loc[:,0])
north_sens = pd.concat([north_sens,north1,north2,north3,north_avg_sim,north1_sim,north2_sim,north3_sim,north_avg_comp,north1_comp,north2_comp,north3_comp],axis=1)

north_sens['real'] = north_sens['real'].interpolate()
north_sens['sim'] = north_sens['sim'].interpolate()
north_sens['comp'] = north_sens['comp'].interpolate()
north_sens['north1_sim'] = north_sens['north1_sim'].interpolate()
north_sens['north2_sim'] = north_sens['north2_sim'].interpolate()
north_sens['north3_sim'] = north_sens['north3_sim'].interpolate()
north_sens['north1'] = north_sens['north1'].interpolate()
north_sens['north2'] = north_sens['north2'].interpolate()
north_sens['north3'] = north_sens['north3'].interpolate()
north_sens['north1_comp'] = north_sens['north1_comp'].interpolate()
north_sens['north2_comp'] = north_sens['north2_comp'].interpolate()
north_sens['north3_comp'] = north_sens['north3_comp'].interpolate()

#East Interpolation
east_sens =pd.DataFrame({'real':pd.Series.to_numpy(avg_real_enu.loc[:,'east'])},index=avg_real_enu.loc[:,'time'])
east1 = pd.DataFrame({'east1':pd.Series.to_numpy(enu_real1[0])},index=real_flights.loc[:,0])
east2 = pd.DataFrame({'east2':pd.Series.to_numpy(enu_real2[0])},index=real_flights.loc[:,0])
east3 = pd.DataFrame({'east3':pd.Series.to_numpy(enu_real3[0])},index=real_flights.loc[:,0])
east_avg_sim = pd.DataFrame({'sim':pd.Series.to_numpy(avg_sim_enu.loc[:,'east'])},index=avg_sim_enu.loc[:,'time'])
east1_sim = pd.DataFrame({'east1_sim':pd.Series.to_numpy(enu_sim1[0])},index=sim_flights.loc[:,0])
east2_sim = pd.DataFrame({'east2_sim':pd.Series.to_numpy(enu_sim2[0])},index=sim_flights.loc[:,0])
east3_sim = pd.DataFrame({'east3_sim':pd.Series.to_numpy(enu_sim3[0])},index=sim_flights.loc[:,0])
east_avg_comp = pd.DataFrame({'comp':pd.Series.to_numpy(avg_compare_enu.loc[:,'east'])},index=avg_compare_enu.loc[:,'time'])
east1_comp = pd.DataFrame({'east1_comp':pd.Series.to_numpy(enu_comp1[0])},index=compare_flights.loc[:,0])
east2_comp = pd.DataFrame({'east2_comp':pd.Series.to_numpy(enu_comp2[0])},index=compare_flights.loc[:,0])
east3_comp = pd.DataFrame({'east3_comp':pd.Series.to_numpy(enu_comp3[0])},index=compare_flights.loc[:,0])
east_sens = pd.concat([east_sens,east1,east2,east3,east_avg_sim,east1_sim,east2_sim,east3_sim,east_avg_comp,east1_comp,east2_comp,east3_comp],axis=1)

east_sens['real'] = east_sens['real'].interpolate()
east_sens['sim'] = east_sens['sim'].interpolate()
east_sens['comp'] = east_sens['comp'].interpolate()
east_sens['east1_sim'] = east_sens['east1_sim'].interpolate()
east_sens['east2_sim'] = east_sens['east2_sim'].interpolate()
east_sens['east3_sim'] = east_sens['east3_sim'].interpolate()
east_sens['east1'] = east_sens['east1'].interpolate()
east_sens['east2'] = east_sens['east2'].interpolate()
east_sens['east3'] = east_sens['east3'].interpolate()
east_sens['east1_comp'] = east_sens['east1_comp'].interpolate()
east_sens['east2_comp'] = east_sens['east2_comp'].interpolate()
east_sens['east3_comp'] = east_sens['east3_comp'].interpolate()

#Up Interpolation
up_sens =pd.DataFrame({'real':pd.Series.to_numpy(avg_real_enu.loc[:,'up'])},index=avg_real_enu.loc[:,'time'])
up1 = pd.DataFrame({'up1':pd.Series.to_numpy(enu_real1[2])},index=real_flights.loc[:,0])
up2 = pd.DataFrame({'up2':pd.Series.to_numpy(enu_real2[2])},index=real_flights.loc[:,0])
up3 = pd.DataFrame({'up3':pd.Series.to_numpy(enu_real3[2])},index=real_flights.loc[:,0])
up_avg_sim = pd.DataFrame({'sim':pd.Series.to_numpy(avg_sim_enu.loc[:,'up'])},index=avg_sim_enu.loc[:,'time'])
up1_sim = pd.DataFrame({'up1_sim':pd.Series.to_numpy(enu_sim1[2])},index=sim_flights.loc[:,0])
up2_sim = pd.DataFrame({'up2_sim':pd.Series.to_numpy(enu_sim2[2])},index=sim_flights.loc[:,0])
up3_sim = pd.DataFrame({'up3_sim':pd.Series.to_numpy(enu_sim3[2])},index=sim_flights.loc[:,0])
up_avg_comp = pd.DataFrame({'comp':pd.Series.to_numpy(avg_compare_enu.loc[:,'up'])},index=avg_compare_enu.loc[:,'time'])
up1_comp = pd.DataFrame({'up1_comp':pd.Series.to_numpy(enu_comp1[2])},index=compare_flights.loc[:,0])
up2_comp = pd.DataFrame({'up2_comp':pd.Series.to_numpy(enu_comp2[2])},index=compare_flights.loc[:,0])
up3_comp = pd.DataFrame({'up3_comp':pd.Series.to_numpy(enu_comp3[2])},index=compare_flights.loc[:,0])
up_sens = pd.concat([up_sens,up1,up2,up3,up_avg_sim,up1_sim,up2_sim,up3_sim,up_avg_comp,up1_comp,up2_comp,up3_comp],axis=1)

up_sens['real'] = up_sens['real'].interpolate()
up_sens['sim'] = up_sens['sim'].interpolate()
up_sens['comp'] = up_sens['comp'].interpolate()
up_sens['up1_sim'] = up_sens['up1_sim'].interpolate()
up_sens['up2_sim'] = up_sens['up2_sim'].interpolate()
up_sens['up3_sim'] = up_sens['up3_sim'].interpolate()
up_sens['up1'] = up_sens['up1'].interpolate()
up_sens['up2'] = up_sens['up2'].interpolate()
up_sens['up3'] = up_sens['up3'].interpolate()
up_sens['up1_comp'] = up_sens['up1_comp'].interpolate()
up_sens['up2_comp'] = up_sens['up2_comp'].interpolate()
up_sens['up3_comp'] = up_sens['up3_comp'].interpolate()

##Distance Analysis between Mean and Run (3D Distance Deviation from Mean)

sd1 = np.std(((north_sens['real']-north_sens['north1'])**2+(east_sens['real']-east_sens['east1'])**2+(up_sens['real']-up_sens['up1'])**2)**0.5)
sd2 = np.std(((north_sens['real']-north_sens['north2'])**2+(east_sens['real']-east_sens['east2'])**2+(up_sens['real']-up_sens['up2'])**2)**0.5)
sd3 = np.std(((north_sens['real']-north_sens['north3'])**2+(east_sens['real']-east_sens['east3'])**2+(up_sens['real']-up_sens['up3'])**2)**0.5)
sd_real = (sd1+sd2+sd3)/3

mean1 = np.mean(((north_sens['real']-north_sens['north1'])**2+(east_sens['real']-east_sens['east1'])**2+(up_sens['real']-up_sens['up1'])**2)**0.5)
mean2 = np.mean(((north_sens['real']-north_sens['north2'])**2+(east_sens['real']-east_sens['east2'])**2+(up_sens['real']-up_sens['up2'])**2)**0.5)
mean3 = np.mean(((north_sens['real']-north_sens['north3'])**2+(east_sens['real']-east_sens['east3'])**2+(up_sens['real']-up_sens['up3'])**2)**0.5)

sd1_sim = np.std(((north_sens['sim']-north_sens['north1_sim'])**2+(east_sens['sim']-east_sens['east1_sim'])**2+(up_sens['sim']-up_sens['up1_sim'])**2)**0.5)
sd2_sim = np.std(((north_sens['sim']-north_sens['north2_sim'])**2+(east_sens['sim']-east_sens['east2_sim'])**2+(up_sens['sim']-up_sens['up2_sim'])**2)**0.5)
sd3_sim = np.std(((north_sens['sim']-north_sens['north3_sim'])**2+(east_sens['sim']-east_sens['east3_sim'])**2+(up_sens['sim']-up_sens['up3_sim'])**2)**0.5)
sd_sim = (sd1_sim+sd2_sim+sd3_sim)/3

mean1_sim = np.mean(((north_sens['sim']-north_sens['north1_sim'])**2+(east_sens['sim']-east_sens['east1_sim'])**2+(up_sens['sim']-up_sens['up1_sim'])**2)**0.5)
mean2_sim = np.mean(((north_sens['sim']-north_sens['north2_sim'])**2+(east_sens['sim']-east_sens['east2_sim'])**2+(up_sens['sim']-up_sens['up2_sim'])**2)**0.5)
mean3_sim = np.mean(((north_sens['sim']-north_sens['north3_sim'])**2+(east_sens['sim']-east_sens['east3_sim'])**2+(up_sens['sim']-up_sens['up3_sim'])**2)**0.5)

sd1_comp = np.std(((north_sens['comp']-north_sens['north1_comp'])**2+(east_sens['comp']-east_sens['east1_comp'])**2+(up_sens['comp']-up_sens['up1_comp'])**2)**0.5)
sd2_comp = np.std(((north_sens['comp']-north_sens['north2_comp'])**2+(east_sens['comp']-east_sens['east2_comp'])**2+(up_sens['comp']-up_sens['up2_comp'])**2)**0.5)
sd3_comp = np.std(((north_sens['comp']-north_sens['north3_comp'])**2+(east_sens['comp']-east_sens['east3_comp'])**2+(up_sens['comp']-up_sens['up3_comp'])**2)**0.5)

mean1_comp = np.mean(((north_sens['comp']-north_sens['north1_comp'])**2+(east_sens['comp']-east_sens['east1_comp'])**2+(up_sens['comp']-up_sens['up1_comp'])**2)**0.5)
mean2_comp = np.mean(((north_sens['comp']-north_sens['north2_comp'])**2+(east_sens['comp']-east_sens['east2_comp'])**2+(up_sens['comp']-up_sens['up2_comp'])**2)**0.5)
mean3_comp = np.mean(((north_sens['comp']-north_sens['north3_comp'])**2+(east_sens['comp']-east_sens['east3_comp'])**2+(up_sens['comp']-up_sens['up3_comp'])**2)**0.5)

run_dev = pd.DataFrame(
  {
    'mean_real':    [mean1,mean2,mean3],
    'sd_real':      [sd1,sd2,sd3],
    'mean_sim':     [mean1_sim,mean2_sim,mean3_sim],
    'sd_sim':       [sd1_sim,sd2_sim,sd3_sim],
    'mean_comp':    [mean1_comp,mean2_comp,mean3_comp],
    'sd_comp':      [sd1_comp, sd2_comp, sd3_comp]

  },
  index=['run1','run2','run3']
)

## Plotting of the Standard Deviation
fig, ax1 = plt.subplots()

barwidth = 0.25

r1 = [1,2,3]
r2 = [x + barwidth for x in r1]
r3 = [x - 2*barwidth for x in r2]

ax1.bar(r1, run_dev['sd_real'], width=barwidth, alpha=0.5, color='r',label = 'Flight Test')
ax1.bar(r2, run_dev['sd_sim'], width=barwidth, alpha=0.5, color='g',label = 'Simulation')
ax1.bar(r3, run_dev['sd_comp'], width=barwidth, alpha=0.5, color='b',label = 'Unadjusted')

ax1.set_ylabel('Standard Deviation [m]')
ax1.set_title('3D distance deviation between runs and run mean')
ax1.legend(loc = 'upper right')
ax1.axes.set_xticks(r1, ['Run 1','Run 2','Run 3'])
plt.show()

## Plotting Run Deviation from the mean including the 95% confidence interval over all runs

#Standard Deviation over all 3 runs for ENU coordinates (Sim & Real)
error_sd_east = (np.std(east_sens['real']-east_sens['east1'])+np.std(east_sens['real']-east_sens['east2'])+np.std(east_sens['real']-east_sens['east3']))/3
error_sd_east_sim = (np.std(east_sens['sim']-east_sens['east1_sim'])+np.std(east_sens['sim']-east_sens['east2_sim'])+np.std(east_sens['sim']-east_sens['east3_sim']))/3
error_sd_north = (np.std(north_sens['real']-north_sens['north1'])+np.std(north_sens['real']-north_sens['north2'])+np.std(north_sens['real']-north_sens['north3']))/3
error_sd_north_sim = (np.std(north_sens['sim']-north_sens['north1_sim'])+np.std(north_sens['sim']-north_sens['north2_sim'])+np.std(north_sens['sim']-north_sens['north3_sim']))/3
error_sd_up = (np.std(up_sens['real']-up_sens['up1'])+np.std(up_sens['real']-up_sens['up2'])+np.std(up_sens['real']-up_sens['up3']))/3
error_sd_up_sim = (np.std(up_sens['sim']-up_sens['up1_sim'])+np.std(up_sens['sim']-up_sens['up2_sim'])+np.std(up_sens['sim']-up_sens['up3_sim']))/3

#Plot
fig, (ax1, ax2, ax3) = plt.subplots(3, 1)

fig.suptitle('Deviations from mean, including 95% confidence intervall')

ax2.plot(north_sens['real']-north_sens['north1'],'r',alpha = 0.5, label = 'Flight Test')
ax2.plot(north_sens['real']-north_sens['north2'],'r',alpha = 0.3)
ax2.plot(north_sens['real']-north_sens['north3'],'r',alpha = 0.1)
ax2.fill_between(north_sens.index,(north_sens['real']-north_sens['real']+2*error_sd_north),(north_sens['real']-north_sens['real']-2*error_sd_north),color='r',alpha=0.1)
ax2.plot(north_sens['sim']-north_sens['north1_sim'],'g',alpha = 0.5, label = 'Simulation')
ax2.plot(north_sens['sim']-north_sens['north2_sim'],'g',alpha = 0.3)
ax2.plot(north_sens['sim']-north_sens['north3_sim'],'g',alpha = 0.1)
ax2.fill_between(north_sens.index,(north_sens['sim']-north_sens['sim']+2*error_sd_north_sim),(north_sens['sim']-north_sens['sim']-2*error_sd_north_sim),color='g',alpha=0.2)
ax2.set_xlabel('Time [s]')
ax2.set_ylabel('North [m]')
ax2.set_ylim([-3,3])
ax2.grid()

ax3.plot(east_sens['real']-east_sens['east1'],'r',alpha = 0.5, label = 'Flight Test')
ax3.plot(east_sens['real']-east_sens['east2'],'r',alpha = 0.3)
ax3.plot(east_sens['real']-east_sens['east3'],'r',alpha = 0.1)
ax3.fill_between(east_sens.index,(east_sens['real']-east_sens['real']+2*error_sd_east),(east_sens['real']-east_sens['real']-2*error_sd_east),color='r',alpha=0.1)
ax3.plot(east_sens['sim']-east_sens['east1_sim'],'g',alpha = 0.5, label = 'Simulation')
ax3.plot(east_sens['sim']-east_sens['east2_sim'],'g',alpha = 0.3)
ax3.plot(east_sens['sim']-east_sens['east3_sim'],'g',alpha = 0.1)
ax3.fill_between(east_sens.index,(east_sens['sim']-east_sens['sim']+2*error_sd_east_sim),(east_sens['sim']-east_sens['sim']-2*error_sd_east_sim),color='g',alpha=0.2)
ax3.set_xlabel('Time [s]')
ax3.set_ylabel('East [m]')
ax3.set_ylim([-3,3])
ax3.grid()

ax1.plot(up_sens['real']-up_sens['up1'],'r',alpha = 0.5, label = 'Flight Test')
ax1.plot(up_sens['real']-up_sens['up2'],'r',alpha = 0.3)
ax1.plot(up_sens['real']-up_sens['up3'],'r',alpha = 0.1)
ax1.fill_between(up_sens.index,(up_sens['real']-up_sens['real']+2*error_sd_up),(up_sens['real']-up_sens['real']-2*error_sd_up),color='r',alpha=0.1)
ax1.plot(up_sens['sim']-up_sens['up1_sim'],'g',alpha = 0.5, label = 'Simulation')
ax1.plot(up_sens['sim']-up_sens['up2_sim'],'g',alpha = 0.3)
ax1.plot(up_sens['sim']-up_sens['up3_sim'],'g',alpha = 0.1)
ax1.fill_between(up_sens.index,(up_sens['sim']-up_sens['sim']+2*error_sd_up_sim),(up_sens['sim']-up_sens['sim']-2*error_sd_up_sim),color='g',alpha=0.2)
ax1.set_xlabel('Time [s]')
ax1.set_ylabel('Height [m]')
ax1.legend()
ax1.grid()

plt.show()

##3D Distance Deviation (real vs sim) incl. 95% confidence intervall

err = ((north['real']-north['sim'])**2+(east['real']-east['sim'])**2+(up['real']-up['sim'])**2)**0.5
sd_err = np.sqrt(sd_real**2+(-sd_sim)**2)

#North vs. Time / East vs. Time / Up vs. Tim / Distance Error (1D Plots)

fig, (ax1, ax2, ax3, ax4) = plt.subplots(4, 1)

fig.suptitle('ENU coordinates and spatial difference')

ax2.plot(north['real'],'r--',label = 'Flight Test')
ax2.plot(north['sim'],'g',label = 'Simulation')
ax2.set_xlabel('Time [s]')
ax2.set_ylabel('North [m]')
ax2.grid()

ax3.plot(east['real'],'r--',label = 'Flight Test')
ax3.plot(east['sim'],'g',label = 'Simulation')
ax3.set_xlabel('Time [s]')
ax3.set_ylabel('East [m]')
ax3.grid()

ax1.plot(up['real'],'r--',label = 'Flight Test')
ax1.plot(up['sim'],'g',label = 'Simulation')
ax1.set_xlabel('Time [s]')
ax1.set_ylabel('Height [m]')
ax1.legend()
ax1.grid()

ax4.plot(err.index,err,'r')
ax4.plot(err.index,np.zeros(np.shape(err.index)[0]),color='black')
ax4.fill_between(err.index,(err+2*(sd_err)),(err-2*(sd_err)),color='r',alpha = 0.2)
ax4.set_xlabel('Time [s]')
ax4.set_ylabel('Difference [m]')
ax4.grid()

plt.show()

##Distance Errors

#Mean Error Spacial Distance (MAE)

actual = ((north['real'])**2+(east['real'])**2+(up['real'])**2)**0.5
simulated = ((north['sim'])**2+(east['sim'])**2+(up['sim'])**2)**0.5

mae = np.mean(np.abs(actual-simulated))
print(mae)

#MAPE
per_err = (pd.Series.to_numpy(actual)-pd.Series.to_numpy(simulated))/pd.Series.to_numpy(actual)
mape = (sum(abs(per_err))/len(per_err))*100
print(mape)

#SDMAE

sdmae = (mae/np.std(actual))*100
print(sdmae)

#MSE
sqr_err = (pd.Series.to_numpy(actual)-pd.Series.to_numpy(simulated))**2
mse = sum(sqr_err)/len(sqr_err)
print(mse)

#Summary
print('MAE:',mae, 'MAPE:',mape, 'MSE:',mse, 'SDMAE', sdmae)

sd_literature = np.std(np.array([99.46,99.03,98.78,98.69,99.72,100.25,100.17,98.61,99.84,99.3])/3.33)