from __future__ import absolute_import
from __future__ import division
from __future__ import print_function

from collections import defaultdict
from collections import OrderedDict
import logging
import os

from pycocotools.coco import COCO
from pycocotools.cocoeval import COCOeval
import json_tricks as json
import numpy as np

from dataset.JointsDataset import JointsDataset
from nms.nms import oks_nms
from nms.nms import soft_oks_nms

import time

logger = logging.getLogger(__name__)

class DeepFashion2Dataset(JointsDataset):
    '''
    "gt_class_keypoints_dict":{
        1: (0, 25),
        2: (25, 58),
        3: (58, 89),
        4: (89, 128),
        5: (128, 143),
        6: (143, 158),
        7: (158, 168),
        8: (168, 182),
        9: (182, 190),
        10: (190, 219),
        11: (219, 256),
        12: (256, 275),
        13: (275, 294)
    },
    '''
    def __init__(self, cfg, root, image_set, is_train, transform=None):
        super().__init__(cfg, root, image_set, is_train, transform)
        self.nms_thre = cfg.TEST.NMS_THRE
        self.image_thre = cfg.TEST.IMAGE_THRE
        self.soft_nms = cfg.TEST.SOFT_NMS
        self.oks_thre = cfg.TEST.OKS_THRE
        self.in_vis_thre = cfg.TEST.IN_VIS_THRE
        self.bbox_file = cfg.TEST.DEEPFASHION2_BBOX_FILE
        # self.bbox_file = cfg.TEST.COCO_BBOX_FILE
        self.use_gt_bbox = cfg.TEST.USE_GT_BBOX
        self.image_width = cfg.MODEL.IMAGE_SIZE[0]
        self.image_height = cfg.MODEL.IMAGE_SIZE[1]
        self.mini_dataset = cfg.DATASET.MINI_DATASET
        self.select_cat = cfg.DATASET.SELECT_CAT
        self.aspect_ratio = self.image_width * 1.0 / self.image_height
        self.pixel_std = 200

        self.coco = COCO(self._get_ann_file_keypoint())

        # deal with class names
        cats = [cat['name']
                for cat in self.coco.loadCats(self.coco.getCatIds())]
        self.classes = ['__background__'] + cats
        logger.info('=> classes: {}'.format(self.classes))
        self.num_classes = len(self.classes)
        self._class_to_ind = dict(zip(self.classes, range(self.num_classes)))
        self._class_to_coco_ind = dict(zip(cats, self.coco.getCatIds()))
        self._coco_ind_to_class_ind = dict(
            [
                (self._class_to_coco_ind[cls], self._class_to_ind[cls])
                for cls in self.classes[1:]
            ]
        )

        # load image file names
        self.image_set_index = self._load_image_set_index()
        self.num_images = len(self.image_set_index)
        logger.info('=> num_images: {}'.format(self.num_images))

        self.num_joints = 294
        self.gt_class_keypoints_dict = {1: (0, 25), 2: (25, 58), 3: (58, 89),
                4: (89, 128), 5: (128, 143), 6: (143, 158), 7: (158, 168),
                8: (168, 182), 9: (182, 190), 10: (190, 219),
                11: (219, 256), 12: (256, 275), 13: (275, 294)}

        _flip_pairs = [
            [[2,6],[3,5],[7,25],[8,24],[9,23],[10,22],[11,21],[12,20],[13,19],[14,18],[15,17]],
            [[2,6],[3,5],[7,33],[8,32],[9,31],[10,30],[11,29],[12,28],[13,27],[14,26],[15,25],[16,24],[17,23],[18,22],[19,21]],
            [[2,26],[3,5],[4,6],[7,25],[8,24],[9,23],[10,22],[11,21],[12,20],[13,19],[14,18],[15,17],[16,29],[27,30],[28,31]],
            [[2,6],[3,5],[4,34],[7,33],[8,32],[9,31],[10,30],[11,29],[12,28],[13,27],[14,26],[15,25],[16,24],[17,23],[18,22],[19,21],[20,37],[35,38],[36,39]],
            [[2,6],[3,5],[7,15],[8,14],[9,13],[10,12]],
            [[2,6],[3,5],[7,15],[8,14],[9,13],[10,12]],
            [[1,3],[4,10],[5,9],[6,8]],
            [[1,3],[4,14],[5,13],[6,12],[7,11],[8,10]],
            [[1,3],[4,8],[5,7]],
            [[2,6],[3,5],[7,29],[8,28],[9,27],[10,26],[11,25],[12,24],[13,23],[14,22],[15,21],[16,20],[17,19]],
            [[2,6],[3,5],[7,37],[8,36],[9,35],[10,34],[11,33],[12,32],[13,31],[14,30],[15,29],[16,28],[17,27],[18,26],[19,25],[20,24],[21,23]],
            [[2,6],[3,5],[7,19],[8,18],[9,17],[10,16],[11,15],[12,14]],
            [[2,6],[3,5],[7,19],[8,18],[9,17],[10,16],[11,15],[12,14]]
        ]
        self.flip_pairs = []
        for idx, _cat_pairs in enumerate(_flip_pairs):
            start_idx = self.gt_class_keypoints_dict[idx+1][0]
            cat_pairs = []
            for pair in _cat_pairs:
                x0 = pair[0] + start_idx - 1
                x1 = pair[1] + start_idx - 1
                cat_pairs.append([x0,x1])
            self.flip_pairs.append(cat_pairs)

        self.parent_ids = None

        self.joints_weight = np.ones((self.num_joints, 1), dtype=np.float32
                                    ).reshape((self.num_joints, 1))

        print('Generating samples...')
        tic = time.time()
        self.cls_stat = np.array([0 for i in range(self.num_classes)])
        self.sample_list_of_cls = []
        self.db = self._get_db()
        print('Done (t={:0.2f}s)'.format(time.time()- tic))

        if is_train and cfg.DATASET.SELECT_DATA:
            self.db = self.select_data(self.db)

        logger.info('=> load {} samples'.format(len(self.db)))

    def _get_ann_file_keypoint(self):
        if 'train'  in self.image_set:
            directory = self.image_set
            if self.mini_dataset:
                return os.path.join(self.root, directory, 'train-coco_style-32.json')
            else:
                return os.path.join(self.root, directory, 'train-coco_style.json')
        elif 'validation'  in self.image_set:
            directory = self.image_set
            if self.mini_dataset:
                return os.path.join(self.root, directory, 'val-coco_style-64.json')
            else:
                return os.path.join(self.root, directory, 'val-coco_style.json')
        elif 'test'  in self.image_set:
            directory = 'json_for_test'
            return os.path.join(self.root, directory, 'keypoints_test_information.json')
        else:
            raise NotImplementedError

    def _load_image_set_index(self):
        """ image id: int """
        image_ids = self.coco.getImgIds()
        return image_ids

    def _get_db(self):
        if self.is_train or self.use_gt_bbox:
            # use ground truth bbox
            gt_db = self._load_coco_keypoint_annotations()
        else:
            # use bbox from detection
            # gt_db = self._load_coco_person_detection_results()
            gt_db = self._load_deepfashion2_detection_results()
        return gt_db

    def _load_coco_keypoint_annotations(self):
        """ ground truth bbox and keypoints """
        gt_db = []
        for index in self.image_set_index:
            gt_db.extend(self._load_coco_keypoint_annotation_kernal(index))
        return gt_db

    def _load_coco_keypoint_annotation_kernal(self, index):
        """
        coco ann: [u'segmentation', u'area', u'iscrowd', u'image_id', u'bbox', u'category_id', u'id']
        iscrowd:
            crowd instances are handled by marking their overlaps with all categories to -1
            and later excluded in training
        bbox:
            [x1, y1, w, h]
        :param index: coco image id
        :return: db entry
        """
        im_ann = self.coco.loadImgs(index)[0]
        width = im_ann['width']
        height = im_ann['height']

        annIds = self.coco.getAnnIds(imgIds=index, iscrowd=False)
        objs = self.coco.loadAnns(annIds)

        # sanitize bboxes
        valid_objs = []
        for obj in objs:
            x, y, w, h = obj['bbox']
            x1 = np.max((0, x))
            y1 = np.max((0, y))
            x2 = np.min((width - 1, x1 + np.max((0, w - 1))))
            y2 = np.min((height - 1, y1 + np.max((0, h - 1))))
            if obj['area'] > 0 and x2 >= x1 and y2 >= y1:
                obj['clean_bbox'] = [x1, y1, x2-x1, y2-y1]
                valid_objs.append(obj)
        objs = valid_objs

        rec = []
        for obj in objs:
            cls = self._coco_ind_to_class_ind[obj['category_id']]

            # ignore objs of not chosen class, or without keypoints annotation
            if cls not in self.select_cat or max(obj['keypoints']) == 0:
                continue
            self.cls_stat[cls] += 1
            self.sample_list_of_cls.append(cls)

            joints_3d = np.zeros((self.num_joints, 3), dtype=np.float)
            joints_3d_vis = np.zeros((self.num_joints, 3), dtype=np.float)
            for ipt in range(self.num_joints):
                joints_3d[ipt, 0] = obj['keypoints'][ipt * 3 + 0]
                joints_3d[ipt, 1] = obj['keypoints'][ipt * 3 + 1]
                joints_3d[ipt, 2] = 0
                t_vis = obj['keypoints'][ipt * 3 + 2]
                if t_vis > 1:
                    t_vis = 1
                joints_3d_vis[ipt, 0] = t_vis
                joints_3d_vis[ipt, 1] = t_vis
                joints_3d_vis[ipt, 2] = 0

            center, scale = self._box2cs(obj['clean_bbox'][:4])
            rec.append({
                'image': self.image_path_from_index(index),
                'center': center,
                'scale': scale,
                'joints_3d': joints_3d,
                'joints_3d_vis': joints_3d_vis,
                'filename': '',
                'imgnum': 0,
                'category_id':obj['category_id'],
                'area': obj['area']
            })
        return rec

    def _box2cs(self, box):
        x, y, w, h = box[:4]
        return self._xywh2cs(x, y, w, h)

    def _xywh2cs(self, x, y, w, h):
        center = np.zeros((2), dtype=np.float32)
        center[0] = x + w * 0.5
        center[1] = y + h * 0.5

        if w > self.aspect_ratio * h:
            h = w * 1.0 / self.aspect_ratio
        elif w < self.aspect_ratio * h:
            w = h * self.aspect_ratio
        scale = np.array(
            [w * 1.0 / self.pixel_std, h * 1.0 / self.pixel_std],
            dtype=np.float32)
        if center[0] != -1:
            scale = scale * 1.25

        return center, scale

    def image_path_from_index(self, index):
        file_name = '%06d.jpg' % index
        file_name = os.path.join('image', file_name)

        image_path = os.path.join(self.root, self.image_set, file_name)

        return image_path

    def _load_deepfashion2_detection_results(self):
        all_boxes = None
        bbox_file_type = self.bbox_file.split('.')[-1]

        if bbox_file_type == 'json':
            with open(self.bbox_file, 'r') as f:
                all_boxes = json.load(f)

            if not all_boxes:
                logger.error('=> Load %s fail!' % self.bbox_file)
                return None

            logger.info('=> Total boxes: {}'.format(len(all_boxes)))

            kpt_db = []
            num_boxes = 0
            for n_img in range(0, len(all_boxes)):
                det_res = all_boxes[n_img]
                # if det_res['category_id'] != 1:
                #     continue
                img_name = self.image_path_from_index(det_res['image_id'])
                box = det_res['bbox']
                score = det_res['score']

                if score < self.image_thre:
                    continue

                num_boxes = num_boxes + 1

                center, scale = self._box2cs(box)
                joints_3d = np.zeros((self.num_joints, 3), dtype=np.float)
                joints_3d_vis = np.ones(
                    (self.num_joints, 3), dtype=np.float)
                kpt_db.append({
                    'image': img_name,
                    'center': center,
                    'scale': scale,
                    'score': score,
                    'joints_3d': joints_3d,
                    'joints_3d_vis': joints_3d_vis,
                })
        elif bbox_file_type == 'pkl':
            logger.info("Loading detection results from %s ..." % self.bbox_file)
            import pickle
            with open(self.bbox_file, 'rb') as f:
                raw_data = pickle.load(f)
                # all_boxes = self._process_pickle(raw_data)
                all_boxes = self._process_pickle(raw_data)
            if not all_boxes:
                logger.error('=> Load %s fail!' % self.bbox_file)
                return None

            logger.info('=> Total boxes: {}'.format(len(all_boxes)))

            kpt_db = []
            num_boxes = 0
            for n_img in range(0, len(all_boxes)):
                det_res = all_boxes[n_img]
                # if det_res['category_id'] != 1:
                #     continue
                img_name = self.image_path_from_index(det_res['image_id'])
                box = det_res['bbox']
                score = det_res['score']
                category_id = det_res['category_id']

                if score < self.image_thre:
                    continue

                num_boxes = num_boxes + 1

                center, scale = self._box2cs(box)
                joints_3d = np.zeros((self.num_joints, 3), dtype=np.float)
                joints_3d_vis = np.ones(
                    (self.num_joints, 3), dtype=np.float)
                kpt_db.append({
                    'image': img_name,
                    'center': center,
                    'scale': scale,
                    'score': score,
                    'joints_3d': joints_3d,
                    'joints_3d_vis': joints_3d_vis,
                    'category_id': det_res['category_id']
                })

        logger.info('=> Total boxes after fliter low score@{}: {}'.format(
            self.image_thre, num_boxes))
        return kpt_db

    def _process_pickle(self, data):
        all_boxes = []
        for n_img in range(len(data)):
            for i in range(13):
                for entry in data[n_img][0][i]:
                    # print('img:%07d cat:%02d' % (n_img, i+1))
                    # input()
                    if entry is not None:
                        x1, y1, x2, y2 = entry[0:4]
                        w = x2 - x1
                        h = y2 - y1
                        box = dict()
                        box['image_id'] = n_img + 1
                        box['bbox'] = [x1, y1, w, h]
                        box['score'] = entry[4]
                        box['category_id'] = i + 1
                    all_boxes.append(box)
        return all_boxes

    def evaluate(self, cfg, preds, output_dir, all_boxes, img_path,
                 *args, **kwargs):
        rank = cfg.RANK

        res_folder = os.path.join(output_dir, 'results')
        if not os.path.exists(res_folder):
            try:
                os.makedirs(res_folder)
            except Exception:
                logger.error('Fail to make {}'.format(res_folder))

        res_file = os.path.join(
            res_folder, 'keypoints_{}_results_{}.json'.format(
                self.image_set, rank)
        )

        # person x (keypoints)
        _kpts = []
        for idx, kpt in enumerate(preds):
            _kpts.append({
                'keypoints': kpt,
                'center': all_boxes[idx][0:2],
                'scale': all_boxes[idx][2:4],
                'area': all_boxes[idx][4],
                'score': all_boxes[idx][5],
                'category_id': all_boxes[idx][6],
                'image': int(img_path[idx][-10:-4])
            })
        # image x person x (keypoints)
        kpts = defaultdict(list)
        for kpt in _kpts:
            kpts[kpt['image']].append(kpt)

        # rescoring and oks nms
        num_joints = self.num_joints
        in_vis_thre = self.in_vis_thre
        oks_thre = self.oks_thre
        oks_nmsed_kpts = []
        for img in kpts.keys():
            img_kpts = kpts[img]
            for n_p in img_kpts:
                box_score = n_p['score']
                kpt_score = 0
                valid_num = 0
                for n_jt in range(0, num_joints):
                    t_s = n_p['keypoints'][n_jt][2]
                    if t_s > in_vis_thre:
                        kpt_score = kpt_score + t_s
                        valid_num = valid_num + 1
                if valid_num != 0:
                    kpt_score = kpt_score / valid_num
                # rescoring
                n_p['score'] = kpt_score * box_score
                # n_p['score'] = box_score

            if self.soft_nms:
                keep = soft_oks_nms(
                    [img_kpts[i] for i in range(len(img_kpts))],
                    oks_thre
                )
            else:
                keep = oks_nms(
                    [img_kpts[i] for i in range(len(img_kpts))],
                    oks_thre
                )

            if len(keep) == 0:
                oks_nmsed_kpts.append(img_kpts)
            else:
                oks_nmsed_kpts.append([img_kpts[_keep] for _keep in keep])

        # self._write_coco_keypoint_results(oks_nmsed_kpts, res_file)
        self._write_coco_keypoint_results_DeepFashion2(oks_nmsed_kpts, res_file)
        if 'test' not in self.image_set:
            info_str = self._do_python_keypoint_eval(
                res_file, res_folder)
            name_value = OrderedDict(info_str)
            return name_value, name_value['AP']
        else:
            return {'Null': 0}, 0

    def _write_coco_keypoint_results_DeepFashion2(self, keypoints, res_file):
        results = self._coco_keypoint_results_all_category_kernel(keypoints)
        logger.info('=> writing results json to %s' % res_file)
        with open(res_file, 'w') as f:
            json.dump(results, f, sort_keys=True, indent=4)
        try:
            json.load(open(res_file))
        except Exception:
            content = []
            with open(res_file, 'r') as f:
                for line in f:
                    content.append(line)
            content[-1] = ']'
            with open(res_file, 'w') as f:
                for c in content:
                    f.write(c)

    def _coco_keypoint_results_all_category_kernel(self, keypoints):
        # cat_id = data_pack['cat_id']

        keypoints = keypoints
        cat_results = []

        for img_kpts in keypoints:
            if len(img_kpts) == 0:
                continue

            for k in range(len(img_kpts)):
                image_id = img_kpts[k]['image']
                cat_id = img_kpts[k]['category_id']
                score = img_kpts[k]['score']

                _key_points = np.array([img_kpts[k]['keypoints']
                                        for k in range(len(img_kpts))])
                key_points = np.zeros(
                    (_key_points.shape[0], self.num_joints * 3), dtype=np.float
                )

                for ipt in range(self.num_joints):
                    key_points[:, ipt * 3 + 0] = _key_points[:, ipt, 0]
                    key_points[:, ipt * 3 + 1] = _key_points[:, ipt, 1]
                    key_points[:, ipt * 3 + 2] = _key_points[:, ipt, 2]  # keypoints score.

                result = [
                    {
                        'image_id': image_id,
                        'category_id': cat_id,
                        'keypoints': list(key_points[k]),
                        'score': score,
                        # 'score': img_kpts[k]['score'],
                        # 'center': list(img_kpts[k]['center']),
                        # 'scale': list(img_kpts[k]['scale'])
                    }
                ]
                cat_results.extend(result)

        return cat_results

    def _do_python_keypoint_eval(self, res_file, res_folder):
        coco_dt = self.coco.loadRes(res_file)
        coco_eval = COCOeval(self.coco, coco_dt, 'keypoints')
        coco_eval.params.useSegm = None
        coco_eval.evaluate()
        coco_eval.accumulate()
        coco_eval.summarize()

        stats_names = ['AP', 'Ap .5', 'AP .75', 'AP (M)', 'AP (L)', 'AR', 'AR .5', 'AR .75', 'AR (M)', 'AR (L)']

        info_str = []
        for ind, name in enumerate(stats_names):
            info_str.append((name, coco_eval.stats[ind]))

        return info_str

    def get_channel_index(self, class_id):
        gt_class_keypoints_dict =  {
            1: (0, 25), 2: (25, 58), 3: (58, 89), 4: (89, 128), 5: (128, 143),
            6: (143, 158), 7: (158, 168), 8: (168, 182), 9: (182, 190),
            10: (190, 219), 11: (219, 256), 12: (256, 275), 13: (275, 294)}

        if isinstance(class_id, int):
            return list(range(gt_class_keypoints_dict[class_id]))
        elif isinstance(class_id, list):
            return [list(range(gt_class_keypoints_dict[i])) for i in class_id]

    def generate_target(self, joints, joints_vis):
        '''
        :param joints:  [num_joints, 3]
        :param joints_vis: [num_joints, 3]
        :return: target, target_weight(1: visible, 0: invisible)
        '''
        # target_weight = np.ones((self.num_joints, 1), dtype=np.float32)
        target_weight = np.zeros((self.num_joints, 1), dtype=np.float32)
        target_weight[:, 0] = joints_vis[:, 0]
        feat_stride = self.image_size / self.heatmap_size

        if self.target_type == 'gaussian':
            target = np.zeros((self.num_joints,
                               self.heatmap_size[1],
                               self.heatmap_size[0]),
                              dtype=np.float32)

            tmp_size = self.sigma * 3

            for joint_id in range(self.num_joints):
                mu_x = int(joints[joint_id][0] / feat_stride[0] + 0.5)
                mu_y = int(joints[joint_id][1] / feat_stride[1] + 0.5)
                # Check that any part of the gaussian is in-bounds
                ul = [int(mu_x - tmp_size), int(mu_y - tmp_size)]
                br = [int(mu_x + tmp_size + 1), int(mu_y + tmp_size + 1)]
                if ul[0] >= self.heatmap_size[0] or ul[1] >= self.heatmap_size[1] \
                        or br[0] < 0 or br[1] < 0:
                    # If not, just return the image as is
                    target_weight[joint_id] = 0
                    continue

                # # Generate gaussian
                size = 2 * tmp_size + 1
                x = np.arange(0, size, 1, np.float32)
                y = x[:, np.newaxis]
                x0 = y0 = size // 2
                # The gaussian is not normalized, we want the center value to equal 1
                g = np.exp(- ((x - x0) ** 2 + (y - y0) ** 2) / (2 * self.sigma ** 2))

                # Usable gaussian range
                g_x = max(0, -ul[0]), min(br[0], self.heatmap_size[0]) - ul[0]
                g_y = max(0, -ul[1]), min(br[1], self.heatmap_size[1]) - ul[1]
                # Image range
                img_x = max(0, ul[0]), min(br[0], self.heatmap_size[0])
                img_y = max(0, ul[1]), min(br[1], self.heatmap_size[1])

                v = target_weight[joint_id]
                if v > 0.5:
                    target[joint_id][img_y[0]:img_y[1], img_x[0]:img_x[1]] = \
                        g[g_y[0]:g_y[1], g_x[0]:g_x[1]]
        elif self.target_type == 'coordinate':
            target = joints[:, 0:2]
            target /= feat_stride
        else:
            raise NotImplementedError('Only support gaussian map and coordinate now!')

        if self.use_different_joints_weight:
            target_weight = np.multiply(target_weight, self.joints_weight)

        return target, target_weight


import argparse
import glob

import netCDF4 as nc
import re
from datetime import datetime, timedelta
import pandas as pd
import tqdm
import numpy as np

from gfs_archive_0_25.gfs_processor.own_logger import logger
from gfs_archive_0_25.utils import prep_zeros_if_needed
from gfs_archive_0_25.gfs_processor.consts import *
from gfs_common.common import GFS_PARAMETERS
from util.coords import GFS_SPACE, Coords

OFFSET = 3

class ProcessingException(Exception):
    pass

def get_forecast_df_for_date_and_run(csv_path):
    if os.path.exists(csv_path):
        return pd.read_csv(csv_path, index_col=[0])
    else:
        return pd.DataFrame(columns=["date"])

def get_date_run_offset_from_netCDF_file_name(file):
    date_matcher = re.match(RAW_NETCDF_FILENAME_REGEX, file)
    if date_matcher is None:
        logger.warn(f"Filename {file} does not match raw netCDF file regex: {RAW_NETCDF_FILENAME_REGEX}")
        raise ProcessingException(f"Filename {file} does not match raw netCDF file regex: {RAW_NETCDF_FILENAME_REGEX}")

    date_from_filename = date_matcher.group(2)
    year = date_from_filename[:4]
    month = date_from_filename[4:6]
    day = date_from_filename[6:8]
    return datetime(int(year), int(month), int(day)), date_from_filename[8:10], date_matcher.group(3)

def get_values_as_numpy_arr_from_file(netCDF_filepath, coords: Coords):
    ds = nc.Dataset(netCDF_filepath)
    lats, lons = ds.variables[[key for key in ds.variables.keys() if key.startswith('lat')][0]][:],\
                 ds.variables[[key for key in ds.variables.keys() if key.startswith('lon')][0]][:]
    if coords.nlat not in lats or coords.slat not in lats or coords.wlon not in lons or coords.elon not in lons:
        return None
    else:
        lats = lats.data.tolist()
        lons = lons.data.tolist()
        nlat_index, slat_index, wlon_index, elon_index = lats.index(coords.nlat), lats.index(coords.slat), \
                                                         lons.index(coords.wlon), lons.index(coords.elon)

        return ds.variables[[key for key in ds.variables.keys() if key[0].isupper()][0]][nlat_index:slat_index + 1, wlon_index:elon_index + 1].data

def get_value_from_netCDF(dataset, lat_index, lon_index):
    return next(iter(dataset.variables.values()))[0][lat_index][lon_index]

def process_netCDF_file_to_csv(file, parameter_level_tuple, output_dir):
    name, level = parameter_level_tuple
    ds = nc.Dataset(file)
    lats, lons = ds.variables['lat_0'][:], ds.variables['lon_0'][:]
    init_date, run, offset = get_date_run_offset_from_netCDF_file_name(file)
    date_str = (init_date + timedelta(hours=int(offset))).isoformat()

    for lat_index, lat in enumerate(lats):
        for lon_index, lon in list(enumerate(lons)):
            final_csv_dir = os.path.join(output_dir, str(lat).replace('.', '_') + '-' + str(lon).replace('.', '_'))
            if not os.path.exists(final_csv_dir):
                os.makedirs(final_csv_dir)

            value = get_value_from_netCDF(ds, lat_index, lon_index)
            param_name = name + '_' + level.replace("_", ":")

            final_csv_name = FINAL_CSV_FILENAME_FORMAT.format(init_date.year,
                                                              prep_zeros_if_needed(str(init_date.month), 1),
                                                              prep_zeros_if_needed(str(init_date.day), 1),
                                                              run)
            final_csv_path = os.path.join(final_csv_dir, final_csv_name)
            forecast_df = get_forecast_df_for_date_and_run(final_csv_path)

            if param_name not in forecast_df:
                forecast_df[param_name] = 0

            rows = forecast_df[forecast_df['date'] == date_str]
            if len(rows) == 0:
                forecast_df.loc[len(forecast_df.index), :] = ''
                forecast_df.loc[len(forecast_df.index) - 1, ['date', param_name]] = [date_str,
                                                                                value]
                forecast_df.sort_values('date')
            else:
                forecast_df.loc[forecast_df['date'] == date_str, param_name] = value

            forecast_df.to_csv(final_csv_path)
    # #os.remove(csv_file_path)

def check_if_any_file_for_year_exists(year, parameter_level_tuple):
    netCDF_file_glob = RDA_NETCDF_FILENAME_FORMAT.format(str(year),
                                                         '*',
                                                         '',
                                                         '',
                                                         '00' + str(OFFSET),
                                                         '*')
    netCDF_path_glob = os.path.join(NETCDF_DOWNLOAD_PATH, parameter_level_tuple[0],
                                    parameter_level_tuple['level'].replace(":", "_").replace(",", "-"), netCDF_file_glob)
    found_files = glob.glob(netCDF_path_glob)
    if len(found_files) > 0:
        return True
    return False

def process_to_numpy_array(parameter_level_tuple, input_dir: str, output_dir: str):
    for root, dirs, filenames in os.walk(input_dir):
        if len(filenames) > 0:
            output_dir = os.path.join(output_dir, parameter_level_tuple['name'], parameter_level_tuple['level'])

            if not os.path.exists(output_dir):
                os.makedirs(output_dir)

            for file in tqdm.tqdm(filenames):
                try:
                    date, run, offset = get_date_run_offset_from_netCDF_file_name(file)

                    output_path = os.path.join(output_dir, FINAL_NUMPY_FILENAME_FORMAT.format(
                        str(date.year),
                        prep_zeros_if_needed(str(date.month), 1),
                        prep_zeros_if_needed(str(date.day), 1),
                        run,
                        prep_zeros_if_needed(str(offset), 2)))

                    # consider as done if output file already exists
                    if not os.path.exists(output_path):
                        forecast = get_values_as_numpy_arr_from_file(os.path.join(input_dir, file), GFS_SPACE)
                        if forecast is not None:
                            np.save(output_path, forecast)
                except ProcessingException:
                    pass
        break

def process_to_csv(parameter_level_tuple, input_dir: str, output_dir: str):
    for root, level_dirs, filenames in os.walk(input_dir):
        if len(filenames) > 0:
            output_dir = os.path.join(output_dir, parameter_level_tuple['name'], parameter_level_tuple['level'])

            if not os.path.exists(output_dir):
                os.makedirs(output_dir)

            for file in tqdm.tqdm(filenames):
                file_name_match = re.match(RAW_NETCDF_FILENAME_REGEX, file)
                if file_name_match is not None:
                    process_netCDF_file_to_csv(os.path.join(input_dir, file), parameter_level_tuple, output_dir)

def process_netCDF_files_to_csv(output_dir: str):
    for param in GFS_PARAMETERS:
        logger.info(f"Converting parameter {param['name']} {param['level']}")
        process_to_csv(param, GFS_SPACE, output_dir)

def process_netCDF_files(mode: str, output_dir: str):
    for param in GFS_PARAMETERS:
        name = param['name']
        level = param['level']
        logger.info(f"Converting parameter {name} {level}")
        if name == 'T CDC':
            param_name_dir = 'L CDC' if level == 'LCY_0' else 'M CDC' if level == 'MCY_0' else 'H CDC'
        else:
            param_name_dir = name
        input_dir = os.path.join(NETCDF_DOWNLOAD_PATH, param_name_dir, level)

        if mode == "NPY":
            process_to_numpy_array(param, input_dir, output_dir)
        else:
            process_to_csv(param, input_dir, output_dir)

if __name__ == '__main__':
    parser = argparse.ArgumentParser()

    parser.add_argument('--mode', help='CSV or NPY - output format to which save the data. ', default="NPY", choices=["CSV", "NPY"])
    parser.add_argument('--output_dir', help='Output directory for the result files.', default="D:\\WindForecast\\gfs")
    args = parser.parse_args()

    process_netCDF_files(args.mode, args.output_dir)


from __future__ import print_function
from __future__ import division
import torch
from torch.autograd import Variable
import torch.nn as nn
import torch.nn.functional as F
import torchvision
import torchvision.transforms as transforms
import torch.optim as optim
import cPickle as pickle

class SaveVal():
    def __init__(self):
        self.testLoss = []
        self.trainLoss = []
        self.trainAcc = []
        self.testAcc = []

class Net(nn.Module):
    def __init__(self):
        super(Net, self).__init__()
        self.conv1 = nn.Conv2d(3, 32, 3, padding=1)
        self.conv2 = nn.Conv2d(32, 32, 3, padding=1)
        self.conv3 = nn.Conv2d(32, 64, 3, padding=1)
        self.conv4 = nn.Conv2d(64, 64, 3, padding=1)
        self.conv5 = nn.Conv2d(64, 128, 3, padding=1)
        self.conv6 = nn.Conv2d(128, 128, 3, padding=1)
        self.pool = nn.MaxPool2d(2, 2)
        self.fc1 = nn.Linear(128 * 8 * 8, 512)
        self.fc2 = nn.Linear(512, 10)
        # Part 1
        self.batchNorm = nn.BatchNorm1d(512)
        # Part 2
        self.fc_between = nn.Linear(512, 512)  # part 2

    def forward(self, x):
        x = F.relu(self.conv1(x))
        x = F.relu(self.conv2(x))
        x = self.pool(x)
        x = F.relu(self.conv3(x))
        x = F.relu(self.conv4(x))
        x = self.pool(x)
        x = F.relu(self.conv5(x))
        x = F.relu(self.conv6(x))
        x = x.view(-1, self.num_flat_features(x))
        # Part 1: Add batchnorm after fc1 and before ReLU
        x = F.relu(self.batchNorm(self.fc1(x)))
        # x = F.relu(self.fc1(x))

        # Part 2: add fc layer
        x = F.relu(self.fc_between(x))

        x = self.fc2(x)
        return x

    def num_flat_features(self, x):
        size = x.size()[1:]  # all dimensions except the batch dimension
        num_features = 1
        for s in size:
            num_features *= s
        return num_features

def eval_net(dataloader):
    correct = 0
    total = 0
    total_loss = 0
    net.eval() # Why would I do this? -> because the network eval and train mode are different
    criterion = nn.CrossEntropyLoss(size_average=False)
    for data in dataloader:
        images, labels = data
        images, labels = Variable(images), Variable(labels)
        outputs = net(images)
        _, predicted = torch.max(outputs.data, 1)
        total += labels.size(0)
        correct += (predicted == labels.data).sum()
        loss = criterion(outputs, labels)
        total_loss += loss.data[0]
    net.train() # Why would I do this? -> because the network eval and train mode are different
    return total_loss / total, correct / total

if __name__ == "__main__":
    # FOR SAVING
    save = SaveVal()

    BATCH_SIZE = 32 #mini_batch size
    MAX_EPOCH = 15 #maximum epoch to train

    transform = transforms.Compose(
        [transforms.ToTensor(),
         transforms.Normalize((0.5, 0.5, 0.5), (0.5, 0.5, 0.5))]) #torchvision.transforms.Normalize(mean, std)

    trainset = torchvision.datasets.CIFAR10(root='./data', train=True,
                                            download=True, transform=transform)
    trainloader = torch.utils.data.DataLoader(trainset, batch_size=BATCH_SIZE,
                                              shuffle=True, num_workers=2)

    testset = torchvision.datasets.CIFAR10(root='./data', train=False,
                                           download=True, transform=transform)
    testloader = torch.utils.data.DataLoader(testset, batch_size=BATCH_SIZE,
                                             shuffle=False, num_workers=2)

    classes = ('plane', 'car', 'bird', 'cat',
               'deer', 'dog', 'frog', 'horse', 'ship', 'truck')

    print('Building model...')
    net = Net()

    # **********************************************************************************************************************
    #                                       Loading Pretrained Model upto a certain layer
    # **********************************************************************************************************************
    # # Loading pickle
    # pretrained_dict = torch.load("part1_BN.pth")
    # # Current model's dict
    # model_dict = net.state_dict()
    # # Filtering keys
    # pretrained_dict = {k: v for k, v in pretrained_dict.items() if k in model_dict}
    # # 2. overwrite entries in the existing state dict
    # model_dict.update(pretrained_dict)
    # # 3. load the new state dict
    # net.load_state_dict(model_dict)
    # ******************************************************************************************************************

    net.train() # Training mode

    criterion = nn.CrossEntropyLoss()
    # optimizer = optim.SGD(net.parameters(), lr=0.01, momentum=0.9)
    optimizer = optim.Adam(net.parameters()) # part 3

    print('Start training...')
    for epoch in range(MAX_EPOCH):  # loop over the dataset multiple times

        running_loss = 0.0
        for i, data in enumerate(trainloader, 0):
            # get the inputs
            inputs, labels = data

            # wrap them in Variable
            inputs, labels = Variable(inputs), Variable(labels)

            # zero the parameter gradients
            optimizer.zero_grad()

            # forward + backward + optimize
            outputs = net(inputs)
            loss = criterion(outputs, labels)
            loss.backward()
            optimizer.step()
            # print statistics
            running_loss += loss.data[0]
            if i % 500 == 499:    # print every 2000 mini-batches
                print('    Step: %5d avg_batch_loss: %.5f' %
                      (i + 1, running_loss / 500))
                running_loss = 0.0
        print('    Finish training this EPOCH, start evaluating...')
        train_loss, train_acc = eval_net(trainloader)
        test_loss, test_acc = eval_net(testloader)
        print('EPOCH: %d train_loss: %.5f train_acc: %.5f test_loss: %.5f test_acc %.5f' %
              (epoch+1, train_loss, train_acc, test_loss, test_acc))
        # saving losses and accuracies
        save.trainLoss.append(train_loss)
        save.trainAcc.append(train_acc)
        save.testLoss.append(test_loss)
        save.testAcc.append(test_acc)

    pickle.dump(save, open("part4_save_test_train_loss_acc_BN_addedFC_Adam_ep15_addedConv.p", "wb"))

    print('Finished Training')
    print('Saving model...')
    torch.save(net.state_dict(), 'part4_BN_addedFC_Adam_ep15_addedConv.pth')


import constants
import pygame

class GameScreen:
    """The screen that is shown when the game is being played.
    """
    def __init__(self):
        pass

    def draw_screen(self, window, card_size, card_back, cards, poker, replace_button):
        """Draws the game screen on the screen.
        Args:
            window (pygame.Surface): the window to draw the game screen on
            card_size (tuple): the size of the cards
            card_back (pygame.Surface): the back of the cards
            cards (dict): the dictionary of the cards
            poker (Poker): the poker game
            replace_button (Button): the button to replace the cards
        """
        window.blit(pygame.font.SysFont(constants.FONT2[0], constants.FONT2[1]).render \
                    ("You", 1, constants.BLACK), (constants.WIDTH/3 + 150, \
                                                   constants.HEIGHT/5 - card_size[1]/2 - 50))

        window.blit(pygame.font.SysFont(constants.FONT2[0], constants.FONT2[1]).render \
                    ("Bot 1", 1, constants.BLACK), (constants.WIDTH/3 - card_size[0]/2 - 300 + 175, \
                                                    constants.HEIGHT/5 - card_size[1]/2 + 200))

        window.blit(pygame.font.SysFont(constants.FONT2[0], constants.FONT2[1]).render \
                    ("Bot 2", 1, constants.BLACK), ((constants.WIDTH/3 - card_size[0]/2 - 300 + 175) + 650, \
                                                    constants.HEIGHT/5 - card_size[1]/2 + 200))

        window.blit(pygame.font.SysFont(constants.FONT2[0], constants.FONT2[1]).render \
                    ("Bot 3", 1, constants.BLACK), (constants.WIDTH/3 - card_size[0]/2 + 175, \
                                                    constants.HEIGHT/5 - card_size[1]/2 + 450))

        window.blit(pygame.font.SysFont(constants.FONT3[0], constants.FONT3[1]).render \
                    ("Select cards to replace: ", 1, constants.BLACK), \
                    (constants.WIDTH/3, \
                        constants.HEIGHT/5 - card_size[1]/2 + 110))

        replace_button.draw(window)

        for i in range(5):
            window.blit(cards[str(poker.player_hand[i])], self.player_card_loc[i])
            window.blit(card_back, self.bot1_card_loc[i])
            window.blit(card_back, self.bot2_card_loc[i])
            window.blit(card_back, self.bot3_card_loc[i])

    def draw_scores(self, window, scoreboard):
        """Draws the scores on the screen.
        Args:
            window (pygame.Surface): the window to draw the scores on
            scoreboard (list): the list of scores
        """
        window.blit(pygame.font.SysFont(constants.FONT3[0], constants.FONT3[1]).render \
                         (f"Your score: {scoreboard[0]}", 1, constants.BLACK), \
                         (20, 20))

        window.blit(pygame.font.SysFont(constants.FONT3[0], constants.FONT3[1]).render \
                            (f"Bot 1 score: {scoreboard[1]}", 1, constants.BLACK), \
                            (20, 55))

        window.blit(pygame.font.SysFont(constants.FONT3[0], constants.FONT3[1]).render \
                            (f"Bot 2 score: {scoreboard[2]}", 1, constants.BLACK), \
                            (20, 90))

        window.blit(pygame.font.SysFont(constants.FONT3[0], constants.FONT3[1]).render \
                            (f"Bot 3 score: {scoreboard[3]}", 1, constants.BLACK), \
                            (20, 125))

    def set_locs(self, card_size):
        """Sets the locations of the cards.
        Args:
            card_size (tuple): the size of the cards
        """
        self.player_card_loc = []
        for i in range(5):
            self.player_card_loc.append(
                (constants.WIDTH/3 - card_size[0]/2 + i * 100, constants.HEIGHT/5 - card_size[1]/2))

        self.bot1_card_loc = []
        for i in range(5):
            self.bot1_card_loc.append(
                ((constants.WIDTH/3 - card_size[0]/2 - 300 + i * 100), \
                 constants.HEIGHT/5 - card_size[1]/2 + 250))

        self.bot2_card_loc = []
        for i in range(5):
            self.bot2_card_loc.append(
                (constants.WIDTH/3 - card_size[0]/2 - 300 + i * 100 + 650, \
                 constants.HEIGHT/5 - card_size[1]/2 + 250))

        self.bot3_card_loc = []
        for i in range(5):
            self.bot3_card_loc.append(
                (constants.WIDTH/3 - card_size[0]/2 + i * 100, constants.HEIGHT/5 - card_size[1]/2 + 500))

    def get_locs(self):
        """Gets the locations of the cards.
        Returns:
            list: the list of the locations of the player's cards
        """
        return self.player_card_loc

    def update_card_loc(self, window, card, card_loc):
        """Updates the location of the card.
        Args:
            window (pygame.Surface): the window to draw the card on
            card (pygame.Surface): the card to draw
            card_loc (tuple): the location of the card
        """
        window.blit(card, card_loc)


from flask import Flask, request, render_template
import math

app = Flask(__name__)

@app.route('/', methods=['GET', 'POST'])
def calculate_trig():
    if request.method == 'POST':
        angle = float(request.form['angle'])
        precision = int(request.form['precision'])
        unit = request.form['unit']

        if unit == 'degrees':
            angle_rad = math.radians(angle) # Перевод угла в радианы, если выбраны градусы
        else:
            angle_rad = angle

        # Расчет тригонометрических значений
        sin_value = round(math.sin(angle_rad), precision)
        cos_value = round(math.cos(angle_rad), precision)
        tan_value = round(math.tan(angle_rad), precision)

        return render_template('result.html', sin_value=sin_value, cos_value=cos_value, tan_value=tan_value)   # Отображение результатов на странице result.html

    return render_template('index.html')

if __name__ == '__main__':
    app.run()


import sqlite3
import sys
import os
import csv
import math
import datetime
import debugMessage as dm
import numpy as np
import matplotlib.pyplot as plt
from os import walk
from utilities import *
from averageCSVFiles import *
#---------------------------------------------------------------------#
# This python file takes in multiple runs and calculate how Average   #
# Marginal Regret  changes as the app user percentage changes and the #
# simulation time elapses. The main execution is at the bottom of this#
# file.                                                               #
# NOTE: All "ND" refer to "Nash Distance," which is the old name of   #
#       average marginal regret. This will be fixed in later changes  #
#---------------------------------------------------------------------#

def generatePlot(percentage, timeStep, absNash, outputDir, plotEvent, eventStart, eventEnd, NDType = 'abs'):
  #-------------------------------------------------------------------#
  # percentage: Sorted list containing all app user percentages       #
  # timeStep: Time step for grouping vehicles                         #
  # absNash: Absolute Nash Distance                                   #
  # plotEven: Set true to plot two dash lines that mark the start and #
  #           end of events, specified by eventStart and eventEnd     #
  #-------------------------------------------------------------------#
  font = {'weight':'bold',
          'size':24}
  plt.rc('font', **font)
  fig, ax = plt.subplots(figsize = (24, 14), dpi = 100)

  #-------------------------------------------------------------------#
  # Change timestep into minutes from seconds                         #
  #-------------------------------------------------------------------#
  for i in range(len(timeStep)):
    timeStep[i] /= 60

  for i in range(len(percentage)):
    if NDType == 'abs':
      ax.plot(timeStep, absNash[i], color = (1 - float(percentage[i])/100, 0, float(percentage[i])/100), \
            label = '{}% App Users'.format(percentage[i]), \
            linewidth = 4.0)
    else:
      ax.plot(timeStep, absNash[i], color = (0, 1 - float(percentage[i])/100, float(percentage[i])/100), \
            label = '{}% App Users'.format(percentage[i]), \
            linewidth = 4.0)
    hand, lab = ax.get_legend_handles_labels()
    plt.legend(handles = hand, loc = 2)
  ax.set_xlabel('Elapsed Time (min)')
  if NDType == 'abs':
    ax.set_ylabel('Absolute Average Marginal Regret \n(sec)')
    ax.set_title('Absolute Average Marginal Regret for \nDifferent Percentages of App Users')
  else:
    ax.set_ylabel('Relative Average Marginal Regret \n(%)')
    ax.set_title('Relative Average Marginal Regret for \nDifferent Percentages of App Users')
  #-------------------------------------------------------------------#
  # Uncomment next line if you have to fix the upper/lower bounds of  #
  # the y-axis                                                        #
  #-------------------------------------------------------------------#
  #ax.set_xlim([0, 400])

  if plotEvent:
    ymin, ymax = plt.ylim()
    ax.plot([eventStart, eventStart], [ymin, ymax], color = (0, 0, 0), dashes = [2, 2], linewidth = 4.0)
    ax.plot([eventEnd, eventEnd], [ymin, ymax], color = (0, 0, 0), dashes = [2, 2], linewidth = 4.0)
  if NDType == 'abs':
    plt.savefig(outputDir + 'absND.png', dpi = 'figure')
  else:
    plt.savefig(outputDir + 'rltND.png', dpi = 'figure')

def extractSingleDB(fileName, thisPercentage, oriId, desId, maxT, minT, stepSize):
  #-------------------------------------------------------------------#
  # Extraction of a single SQLite database and calculate how absolute #
  # Nash Distance changes over time                                   #
  #                                                                   #
  # maxTime/minTime: Max/Min allowed time of entrance for vehicles    #
  # odiId/desId: id of desired origin/destination                     #
  #-------------------------------------------------------------------#
  print(('extracting database ' + fileName))

  con = sqlite3.connect(fileName)
  cur = con.cursor()
  cur.execute('SELECT oid, entranceTime, (exitTime - entranceTime) FROM MIVEHTRAJECTORY WHERE exitTime != -1 AND entranceTime > {} AND entranceTime < {} AND origin = {} AND destination = {}'.format(minT, maxT, oriId, desId))
  vehTTime = cur.fetchall()
  con.close()

  tStepAccumTime = {}
  tStepAccumCount= {}
  tStepMinTime   = {}
  for i in range(len(vehTTime)):
    thisTStep = math.floor((vehTTime[i][1] - minT)/stepSize)
    if thisTStep in tStepAccumTime:
      tStepAccumTime[thisTStep] += vehTTime[i][2]
      tStepAccumCount[thisTStep]+= 1
      if vehTTime[i][2] < tStepMinTime[thisTStep]:
        tStepMinTime[thisTStep] = vehTTime[i][2]
    else:
      tStepAccumTime[thisTStep]  = vehTTime[i][2]
      tStepAccumCount[thisTStep] = 1
      tStepMinTime[thisTStep]    = vehTTime[i][2]
  tStep   = []
  absNash = []
  rltNash = []
  for i in range(int(math.ceil((maxT - minT) / stepSize))):
    tStep.append(i * stepSize)
    if i in tStepMinTime:
      absNash.append(tStepAccumTime[i]/tStepAccumCount[i] - tStepMinTime[i])
      rltNash.append(100 * absNash[-1] * tStepAccumCount[i] / tStepAccumTime[i])
    else:
      absNash.append(0)
      rltNash.append(0)
  return tStep, absNash, rltNash

def sortBasedOnPercentage(percentage, absNash, rltNash):
  #-------------------------------------------------------------------#
  # Helper function to sort all data based on the percentage of app   #
  # users                                                             #
  #-------------------------------------------------------------------#
  zipped = list(zip(percentage, absNash, rltNash))
  zipped.sort()
  unzip  = list(zip(*zipped))
  sPercentage, sAbsNash, sRltNash = list(map(list, unzip))
  return sPercentage, sAbsNash, sRltNash

def traverseMultiDB(fileList, maxTime, minTime, stepSize):
  #-------------------------------------------------------------------#
  # Traverse multiple SQLite DB and return how Absolute Nash Distance #
  # changes with time                                                 #
  #-------------------------------------------------------------------#
  percentage = []
  absNash    = []
  rltNash    = []
  tStep      = []
  oriId, desId  = getODPair(fileList[0])
  for filename in fileList:
    thisPercentage  = getPercentage(filename)
    thisTStep, thisAbsNash, thisRltNash = extractSingleDB(filename, thisPercentage, oriId, desId, maxTime, minTime, stepSize)
    percentage.append(thisPercentage)
    absNash.append(thisAbsNash)
    rltNash.append(thisRltNash)
    tStep = thisTStep
  percentage, absNash, rltNash = sortBasedOnPercentage(percentage, absNash, rltNash)
  return percentage, tStep, absNash, rltNash

def printUsage():
  print('usage: \n\t python std4_timeND.py directoryName maxEntranceTime minEntranceTime stepSize')
  print('\t directoryName: the directory in which the sqlite databases are stored')
  print('\t stepSize: the time step size for grouping vehicles, in seconds')
  print('try \n\t python std4_timeND.py ../sqliteDatabases/DemoBenchmarkAccident/ 14400 7200 600')
  sys.exit()

def store2CSV(percentage, absND, runIdx, outputDir):
  outname = outputDir + 'run' + str(runIdx) + '_timeND.csv'
  with open(outname, 'w') as fout:
    for i in range(len(percentage)):
      fout.write(str(percentage[i]))
      for j in range(len(absND[i])):
        fout.write(',')
        fout.write(str(absND[i][j]))
      if i != (len(percentage) - 1):
        fout.write('\n')

# Main code starts here
if __name__ == '__main__':
  if len(sys.argv) != 5:
    printUsage()
  #-------------------------------------------------------------------#
  # Parsing input arguments and building list of all directories in   #
  # target (mother) directory                                         #
  #-------------------------------------------------------------------#
  dirList, outputDir, maxTime, minTime, stepSize = parseArgvTime(sys.argv, "timeAbsND")
  _, outputDirRlt, _, _, _ = parseArgvTime(sys.argv, "timeRltND")

  #-------------------------------------------------------------------#
  # Traverse, extract, and write data                                 #
  #-------------------------------------------------------------------#
  for dirName in dirList:
    runIdx   = getRunIdx(dirName)
    fileList = getAllFilenames(dirName)
    percentage, timeStep, absNash, rltNash = traverseMultiDB(fileList, maxTime, minTime, stepSize)
    store2CSV(percentage, absNash, runIdx, outputDir)
    store2CSV(percentage, rltNash, runIdx, outputDirRlt)

  #-------------------------------------------------------------------#
  # Read data from csv file and plot                                  #
  #-------------------------------------------------------------------#
  percentage, timeStep, absNash = averageTimeND(outputDir, stepSize)
  generatePlot(percentage, timeStep, absNash, '../outputFigures/', True, 2*60, 4*60)
  percentage, timeStep, rltNash = averageTimeND(outputDirRlt, stepSize)
  generatePlot(percentage, timeStep, rltNash, '../outputFigures/', True, 2*60, 4*60, 'rlt')


from datetime import datetime
import os

# import common methods for use in recipe from common.py
# (so other recipe can import from spack.pkg.k4.key4hep_stack)
# (which is the most convenient way to make that code available
#  without creation of a new module
import sys

sys.path.append(
    os.path.join(
        os.path.dirname(os.path.dirname(os.path.abspath(__file__))), "key4hep-stack"
    )
)
from common import *

class Key4hepStackTest(BundlePackage, Key4hepPackage):
    """Bundle package to install the Key4hep software stack (test version)."""

    homepage = "https://cern.ch/key4hep"

    ##################### versions ########################
    #######################################################
    ###  nightly builds
    version("master")
    # this version can be extended with additional version
    # fields to differentiate it, like 'master-2020-10-10'
    #
    ### stable builds
    # builds the latest release of each package
    # the preferred usage is to use the date as version, like:
    version(datetime.today().strftime("%Y-%m-%d"))
    # version('2020-10-06') # example, no need to add here.
    # more complex version configurations should be added in an
    # environment

    # this bundle package installs a custom setup script, so
    # need to add the install phase (which normally does not
    # exist for a bundle package)
    phases = ["install"]

    variant(
        "build_type",
        default="Release",
        description="CMake build type",
        values=("Debug", "Release", "RelWithDebInfo", "MinSizeRel"),
    )

    # depends_on("")

    def setup_run_environment(self, env):
        # set locale to avoid certain issues with xerces-c
        # (see https://github.com/key4hep/key4hep-spack/issues/170)
        env.set("LC_ALL", "C")
        env.set("KEY4HEP_STACK", os.path.join(self.spec.prefix, "setup.sh"))

        # this fixes loading the local emacs, see https://github.com/key4hep/key4hep-spack/issues/486
        env.unset("XDG_DATA_DIRS")

        # set vdt, needed for root, see https://github.com/spack/spack/pull/37278
        if "vdt" in self.spec:
            env.prepend_path("CPATH", self.spec["vdt"].prefix.include)

        # remove when https://github.com/spack/spack/pull/37881 is merged
        if "podio" in self.spec:
            env.prepend_path("LD_LIBRARY_PATH", self.spec["podio"].libs.directories[0])
        if "edm4hep" in self.spec:
            env.prepend_path(
                "LD_LIBRARY_PATH", self.spec["edm4hep"].libs.directories[0]
            )
        if "lcio" in self.spec:
            env.prepend_path("LD_LIBRARY_PATH", self.spec["lcio"].libs.directories[0])

        # remove when https://github.com/spack/spack/pull/38015 is merged
        if "dd4hep" in self.spec:
            env.prepend_path("LD_LIBRARY_PATH", self.spec["dd4hep"].prefix.lib)
            env.prepend_path("LD_LIBRARY_PATH", self.spec["dd4hep"].prefix.lib64)

        # remove when https://github.com/spack/spack/pull/38407 is merged
        if "edm4hep" in self.spec:
            env.prepend_path("PYTHONPATH", self.spec["edm4hep"].prefix.python)

        # Issue on ubuntu, whizard fails to load libomega.so.0
        if self.compiler.operating_system == "ubuntu22.04":
            if "whizard" in self.spec:
                env.prepend_path(
                    "LD_LIBRARY_PATH", self.spec["whizard"].libs.directories[0]
                )

    def install(self, spec, prefix):
        return install_setup_script(self, spec, prefix, "K4_LATEST_SETUP_PATH")


#!/usr/bin/env python

"""
Creates a gpx file from a FAAM core netcdf data file.

GPX_ files are a standard xml-format, which is understood by many programs.
The gpx file from a flight can for example be used to georeference photographs
taken during a flight (e.g. gpscorrelate_).

The geotagged images can then in a next step be overlaid on maps using the
GPS information from the image metadata.

.. _GPX: https://en.wikipedia.org/wiki/GPS_Exchange_Format
.. _gpscorrelate: https://github.com/freefoote/gpscorrelate

"""

import datetime
import netCDF4
import os
import sys

from matplotlib.dates import num2date

from faampy.core.utils import get_mpl_time, get_base_time, get_fid

_TIMESTAMP_FORMAT = '%Y-%m-%dT%H:%M:%SZ'

_GPX_HEADER = """<?xml version="1.0"?>
<gpx
 version="1.0"
 creator="ExpertGPS 1.1 - http://www.topografix.com"
 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
 xmlns="http://www.topografix.com/GPX/1/0"
 xsi:schemaLocation="http://www.topografix.com/GPX/1/0 http://www.topografix.com/GPX/1/0/gpx.xsd">
"""

_GPX_FOOTER = "</gpx>\n"

_GPX_RTE_TEMPLATE = "<rte>%s</rte>\n"

_GPX_RTEPT_TEMPLATE = """<rtept lat="%f" lon="%f">
 <ele>%f</ele>
 <time>%s</time>
</rtept>
"""

_GPX_TRK_TEMPLATE_START = "<trk><trkseg>\n"
_GPX_TRK_TEMPLATE_END = "</trkseg></trk>\n"

_GPX_TRKPT_TEMPLATE = """<trkpt lat="%f" lon="%f">
 <ele>%f</ele>
 <time>%s</time>
</trkpt>
"""

def lonlatalt_to_gpx(lon, lat, alt, *args):
    if args:
        timestamp = [t.strftime(_TIMESTAMP_FORMAT) for t in args[0]]
    else:
        now = datetime.datetime.utcnow()
        timestamp = [(now+datetime.timedelta(seconds=i)).strftime(_TIMESTAMP_FORMAT) for i in range(len(lon))]
    result = ""
    result += _GPX_HEADER
    result += _GPX_TRK_TEMPLATE_START
    trkp = [_GPX_TRKPT_TEMPLATE % (lat[i], lon[i], alt[i], timestamp[i]) for i in range(len(lat))]
    result += ''.join(trkp)
    result += _GPX_TRK_TEMPLATE_END
    result += _GPX_FOOTER
    return result

def nc_to_gpx(ncfile, outpath):
    ds = netCDF4.Dataset(ncfile, 'r')
    lon = ds.variables['LON_GIN'][:, 0]
    lat = ds.variables['LAT_GIN'][:, 0]
    alt = ds.variables['ALT_GIN'][:, 0]
    t = num2date(get_mpl_time(ds))

    outfilename = '%s_%s.gpx' % (get_fid(ds), get_base_time(ds).strftime('%Y%m%d'))
    outfile = os.path.join(outpath, outfilename)
    outtxt = lonlatalt_to_gpx(lon, lat, alt, t)
    f = open(outfile, 'w')
    f.write(outtxt)
    ds.close()
    f.close()

def _argparser():
    import argparse
    from argparse import RawTextHelpFormatter
    sys.argv.insert(0, 'faampy nc_to_gpx')
    parser = argparse.ArgumentParser(prog = 'faampy nc_to_gpx', description=__doc__,
                                     formatter_class=RawTextHelpFormatter)
    parser.add_argument('ncfile',
                        action="store",
                        type=str,
                        help='input netCDF-file')
    parser.add_argument('outpath',
                        action="store",
                        nargs='?',
                        type=str,
                        default=os.path.expanduser('~'),
                        help='file name of output file')
    return parser

def main():
    parser = _argparser()
    args = parser.parse_args()
    nc_to_gpx(args.ncfile, args.outpath)

if __name__ == '__main__':
    main()


import requests
import os

SHEETY_URL = os.environ.get("SHEETY_URL")
headers = {
    "Authorization": os.environ.get("headers")
}

class FetchItems:

    def __init__(self):
        self.items = []

    def get_items(self):
        response = requests.get(SHEETY_URL, headers=headers)
        response = response.json()['menuItems']
        items = [index for index in response]
        self.items = items


from django.shortcuts import redirect, render,get_object_or_404
from django.urls import reverse
from django.db.models import Q

from .models import Category, Product, SubCategory
from .utils import min_max_filter,get_paginated

def home(request):
    products = Product.objects.filter().order_by("-rating").all()[:12]

    context = {
        "products": products,
    }
    return render(request, "index.html",context)

def broad_search(items, word):
    return items.filter(Q(title__containes=word)| Q(description__contains=word))

def store(request):
    products = Product.objects.all()

    word = request.GET.get('q',None)
    if word:
        products = broad_search(request, word)

    paginated = get_paginated(request, products, 3)

    context = {
        "products":paginated["items"],
        "pages":paginated["pages"]
    }
    return render(request,"store.html",context)

def category_products(request, category_slug):
    category = get_object_or_404(Category,slug=category_slug)
    products = Product.objects.filter(sub_category__category=category)
    products = min_max_filter(request, products)
    paginated = get_paginated(request, products, 3)
    context = {
        "products":paginated["items"],
        "pages":paginated["pages"]
    }
    return render(request,"store.html",context)

def sub_category_products(request, category_slug , sub_category_slug):
    category = get_object_or_404(Category, slug=category_slug)
    subcategory = get_object_or_404(SubCategory,slug=sub_category_slug,category=category)
    products = Product.objects.filter(sub_category=subcategory)
    paginated = get_paginated(request, products, 3)
    context = {
        "products":paginated["items"],
        "pages":paginated["pages"]
    }
    return render(request,"store.html",context)

def product_detail(request,slug):
    products = Product.objects.filter(slug=slug)
    if not products.exists():
        return redirect(reverse("home-page"))
    else:
        product = products.first()

    context = {
        "product": product
    }
    return render(request,"product_detail.html",context)


# Kenneth Otis
# Youtube Video Downloader
from pytube import YouTube
from pytube import exceptions
import time

# getting the link from the user
link=input("Please enter the link of the YouTube Video you would like to download: ")
yt=YouTube(link)

# showing the video's details
print("Title: ", yt.title)
time.sleep(1)
print ("Views: ", yt.views)
time.sleep(1)
print("Length of video: ", yt.length)
time.sleep(1)
print ("Rating of the video: ", yt.rating)
time.sleep(1)

# Get the highest resolution
stream= yt.streams.first()

#Starting download
print ("\nDownloading to Desktop...")
stream.download('Desktop')
time.sleep(1)
print("\nDownload complete!\n")


import numpy as np
import time
import cv2

# using weights and configs from
# https://www.pyimagesearch.com/2018/11/12/yolo-object-detection-with-opencv/
class YoloV3Detector:
    def __init__(self):
        self.min_confidence = 0.5
        self.threshold = 0.3
        self.scale_factor = 1/255.0
        self.image_size = (416,416)
        self.detection_color = (0,255,0)
        self.tracking_color = (255,0,0)
        self.label_path = 'yolo/coco.names'
        self.weights_path = 'yolo/yolov3.weights'
        self.config_path = 'yolo/yolov3.cfg'
        self.labels = open(self.label_path).read().strip().split("\n")
        self.yolo_detector = cv2.dnn.readNetFromDarknet(self.config_path,
                self.weights_path)
        self.layer_names = self.yolo_detector.getLayerNames()
        # yolo3 has three different output layers - we can use all three
        self.output_layers = self.yolo_detector.getUnconnectedOutLayers()
        # these are all the yolo_layers (-1 bc i don't think the layers are returned in
        # 0 index fashion)
        self.output_layer_names = [self.layer_names[i[0]-1] for i in
                self.output_layers]
        self.image_shape = None
        self.outputs = None
        self.boxes = []
        self.confidences = []
        self.classIDs = []
        self.COLORS = None
        self.image = None

    def createBlobAndForwardPass(self, image):
        # create blob from image and perform a forward pass
        # blob performs mean subtraction & scaling for us see here
        # https://www.pyimagesearch.com/2017/11/06/deep-learning-opencvs-blobfromimage-works/
        self.image = image
        self.image_shape = image.shape[:2]
        blob = cv2.dnn.blobFromImage(image, self.scale_factor, self.image_size, swapRB=True,
                crop=False)
        self.yolo_detector.setInput(blob)
        self.outputs = self.yolo_detector.forward(self.output_layer_names)

    def createBoundingBoxes(self):
        # get image dimensions
        (h, w) = self.image_shape

        # reset bins
        self.boxes = []
        self.confidences = []
        self.classIDs = []

        for output in self.outputs:
            for detection in output:
                # each row is a candidate detection, the 1st 4 numbers are
                # [center_x, center_y, width, height], followed by (N-4) class
                # probabilities/confidence
                scores = detection[5:]
                classID = np.argmax(scores)
                confidence = scores[classID]

                # filter out weak predictions
                if confidence < self.min_confidence:
                    continue

                # for this assignment, only care about sports ball label
                if self.labels[classID] != 'sports ball':
                    continue

                # scale bounding box to size of image
                (center_x, center_y, width, height) = (detection[0:4] * np.array([w, h,
                    w, h])).astype('int')

                # grab the corners of the box
                left = int(center_x - width/2)
                top = int(center_y - height/2)

                # add new values to their arrays
                self.boxes.append([left, top, int(width), int(height)])
                self.confidences.append(float(confidence))
                self.classIDs.append(classID)

    def applyNonMaxSuppression(self):
        # apply non-maxima suppression to overlapping bounding boxes
        self.final_detections = cv2.dnn.NMSBoxes(self.boxes, self.confidences,
                self.min_confidence, self.threshold)

    def drawBoundingBoxesWithLabels(self):
        if len(self.final_detections) > 0:
            boxes = self.boxes
            for d in self.final_detections.flatten():
                # draw bounding box
                color = [int(c) for c in self.COLORS[self.classIDs[d]]]
                self.drawBoundingBox(self.image, boxes[d], color)
                text = "{}: {:.4f}".format(self.labels[self.classIDs[d]], self.confidences[d])
                cv2.putText(self.image, text, (x,y-5), cv2.FONT_HERSHEY_SIMPLEX, 0.5, color,
                    1)

    def drawBoundingBox(self, image, bbox, color=None):
        color = color if color != None else self.detection_color
        print(bbox)
        (x, y) = (int(bbox[0]), int(bbox[1]))
        (w, h) = (int(bbox[2]), int(bbox[3]))
        # draw bounding box
        cv2.rectangle(image, (x,y), (x+w, y+h), color, 2)

    def returnSingleBoundingBox(self):
         if len(self.final_detections) > 0:
            boxes = self.boxes
            # this is based on the assumption that there is only a single sports
            # ball in the image and we care about nothing else
            singleBox = self.final_detections.flatten()[0]
            print('singleBox', boxes[singleBox])
            return tuple(boxes[singleBox])
         else:
            # could not find the ball
            return None

    def showImage(self):
        cv2.imshow("image", self.image)
        # cv2.waitKey(0)
        cv2.waitKey(25)

    def showImageWithAnnotations(self, image, bbox, color, annotation1,
            annotation2):
        if bbox != None:
            self.drawBoundingBox(image, bbox, color)
            # Display tracker type on frame
            cv2.putText(image, annotation1, (20,20),
                    cv2.FONT_HERSHEY_SIMPLEX, 0.75, color, 2);

            # Display FPS on frame
            cv2.putText(image, annotation2, (20,50),
                    cv2.FONT_HERSHEY_SIMPLEX, 0.75, color, 2);
        else:
            # Tracking failure
            cv2.putText(image, "Tracking failure detected", (20,80),
                      cv2.FONT_HERSHEY_SIMPLEX, 0.75, (0, 0, 255), 2)

        cv2.imshow("video", image)

    def createColors(self):
        np.random.seed(42) # keeps colors the same everytime
        self.COLORS = np.random.randint(0, 255, size=(len(self.labels), 3), dtype='uint8')

    def detectAndShow(self, image):
       self.createColors()
       self.createBlobAndForwardPass(image)
       self.createBoundingBoxes()
       self.applyNonMaxSuppression()
       self.drawBoundingBoxesWithLabels()
       self.showImage()

    def detectAndReturnBoundingBox(self, image):
       self.createColors()
       self.createBlobAndForwardPass(image)
       self.createBoundingBoxes()
       self.applyNonMaxSuppression()
       return self.returnSingleBoundingBox()

# load image for testing
image_path = './images/soccer.jpg'
image = cv2.imread(image_path)

# load video
videoPath = './videos/soccer_game.mp4'
video = cv2.VideoCapture(videoPath)

# Exit if video not opened.
if not video.isOpened():
    print("Could not open video")

# Read first frame.
ok, frame = video.read()
if not ok:
    print('Cannot read video file')

# initalize yolov3 detector
yolov3 = YoloV3Detector()
bbox = yolov3.detectAndReturnBoundingBox(frame)

count = 0
ok = True
fps = 0

while True:
    okay, frame = video.read()
    if not okay:
        break

    # Start timer
    timer = cv2.getTickCount()

    if count % 20 == 0 or not ok:
        method = 'detection'
        color = yolov3.detection_color
        #detection takes some time, so im showing that we're detecting here too
        yolov3.showImageWithAnnotations(frame, bbox, color, method, "FPS : " +
                    str(int(fps)))
        # detect sports ball
        bbox = yolov3.detectAndReturnBoundingBox(frame)
        # create KCF tracker
        tracker = cv2.TrackerKCF_create()
        tracker.init(frame, bbox)
        ok = bbox != None
    else:
        # Update tracker
        ok, bbox = tracker.update(frame)
        method = 'tracking'
        color = yolov3.tracking_color

    # Calculate processing time and display results.
    # Calculate Frames per second (FPS)
    fps = cv2.getTickFrequency() / (cv2.getTickCount() - timer);
    yolov3.showImageWithAnnotations(frame, bbox, color, method, "FPS : " +
            str(int(fps)))

    cv2.waitKey(1)
    count += 1


from django.shortcuts import render
from django.http import HttpResponse, JsonResponse
from django.views.decorators.csrf import csrf_exempt
from Product.models import Product, Category

posts = [
    {
        'author': 'holey',
        'title': 'shit',
        'description': 'is',
        'text': 'that shit!?'
    },
    {
        'author': 'that',
        'title': 'is',
        'description': 'unbelievable',
        'text': 'shit!'
    }
]

@csrf_exempt
def index(request):
    if request.method == 'POST':
        return JsonResponse({'profile': posts})
    return HttpResponse("Hello, world. You're at the /api index page.")

def products(request):
    if request.method == 'GET':
        products = Product.objects.all()
        return JsonResponse({
            'products': list(products.values())
        })

@csrf_exempt
def categories(request):
    if request.method == 'GET':
        categories = Category.objects.all()
        return JsonResponse({
            'categories': list(categories.values())
        })
    if request.method == 'POST':
        name = request.GET.get("category_name", None)
        if not name:
            return JsonResponse({"status": False, "msg": "Bad name param"})

        new_category = Category()
        new_category.category_text = name

        existed_category = Category.objects.filter(category_text=name)

        if len(existed_category) > 0:
            return JsonResponse({"status": False, "msg": "Item with that name already exist"})
        else:
            new_category.save()
            return JsonResponse({
                "status": True,
                "msg": "Item was added",
                'Id': new_category.id
            })

@csrf_exempt
def find_categories(request):
    if request.method == 'POST':
        name = request.GET.get("category_name", None)
        queryset = Category.objects.filter(category_text__icontains=name).values()
        return JsonResponse({
            'category': list(queryset)
        })

@csrf_exempt
def category(request, category_id):
    if request.method == 'GET':
        queryset = Category.objects.filter(id=category_id).values()
        return JsonResponse({
            'category': list(queryset)
        })

    elif request.method == 'POST':
        name = request.GET.get("category_name", None)
        if not name:
            return JsonResponse({"status": False, "msg": "Bad name param"})

        categories = Category.objects.filter(id=category_id)

        if len(categories) <= 0:
            return JsonResponse({"status": False, "msg": "Item with that id not exist"})

        for cat in categories:
            cat.category_text = name
            cat.save()

        return JsonResponse({"status": True, "msg": "Item was updated"})

    elif request.method == 'DELETE':
        categories = Category.objects.filter(id=category_id)

        if len(categories) <= 0:
            return JsonResponse({"status": False, "msg": "Item with that id not exist"})

        for cat in categories:
            cat.delete()

        return JsonResponse({"status": True, "msg": "Item was deleted"})


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

# Distributed under the Boost Software License, Version 1.0.
# See accompanying file LICENSE or copy at http://www.boost.org/LICENSE

from lxml import etree, html
from object.constant import reduce_constants, print_constants
from object.function import reduce_functions, print_functions
from parser.dotspec import dotspec_constant_parser, dotspec_function_parser
from parser.dottm import dottm_parser
from printer.cpp import cpp_printer
from resolver import resolver
from utils import log, option_parser
import re
from printer.basic import basic_printer
from parser.header import header_parser

parser = option_parser()
(o, a) = parser.parse_args()

# Registering the Resolver as the default DTD Resolver
xml_parser = etree.XMLParser(load_dtd=True)
xml_parser.resolvers.add(resolver())
etree.set_default_parser(xml_parser)

class source(object):
  def __init__(self, library_name, parser, **kwargs):
    self.library_name = library_name
    self.parser = parser(self.library_name)
    self.files = []

    if 'index' in kwargs:
      local_file = resolver.cache(kwargs['index'])
      root = html.parse(local_file)
      uris = root.xpath(kwargs['xpath'])

      self.files.extend([ kwargs['base'] + f for f in filter(lambda x : re.match(kwargs['regexp'], x), uris) ])
      self.files.sort()
    else:
      self.files = kwargs['files']

    for f in self.files:
      log.debug(self.library_name + ': ' + f)

  def parse(self):
    for url in self.files:
      local_file = resolver.cache(url)
      self.parser.parse(local_file)

sources = []

# 'base' and 'index' shoud be the same in 99% of cases,
# but it's faster to download .xml on http rather than webdav over https
#sources.append(source('gl2', docbook_parser(),
#    regexp=r'^gl[A-Z][a-zA-Z0-9]*\.xml$',
#    xpath='//file/@name',
#    index='https://cvs.khronos.org/svn/repos/ogl/trunk/ecosystem/public/sdk/docs/man/',
#    base='http://www.opengl.org/sdk/docs/man/'))
#
#sources.append(source('gl3', docbook_parser(),
#    regexp=r'^gl[A-Z][a-zA-Z0-9]*\.xml$',
#    xpath='//file/@name',
#    index='https://cvs.khronos.org/svn/repos/ogl/trunk/ecosystem/public/sdk/docs/man3/',
#    base='http://www.opengl.org/sdk/docs/man3/'))
#
#sources.append(source('gl4', docbook_parser(),
#    regexp=r'^gl[A-Z][a-zA-Z0-9]*\.xml$',
#    xpath='//file/@name',
#    index='https://cvs.khronos.org/svn/repos/ogl/trunk/ecosystem/public/sdk/docs/man4/',
#    base='http://www.opengl.org/sdk/docs/man4/'))
#
#sources.append(source('glu', docbook_parser(),
#    regexp=r'^glu[A-Z][a-zA-Z0-9]*\.xml$',
#    xpath='//file/@name',
#    index='https://cvs.khronos.org/svn/repos/ogl/trunk/ecosystem/public/sdk/docs/man/',
#    base='http://www.opengl.org/sdk/docs/man/'))
#
#sources.append(source('glX', docbook_parser(),
#    regexp=r'^glX[A-Z][a-zA-Z0-9]*\.xml$',
#    xpath='//file/@name',
#    index='https://cvs.khronos.org/svn/repos/ogl/trunk/ecosystem/public/sdk/docs/man/',
#    base='http://www.opengl.org/sdk/docs/man/'))
#
#sources.append(source('glext', extension_parser(),
#    regexp=r'^specs/[A-Z]+/[a-zA-Z0-9_]+\.txt$',
#    xpath='//a/@href',
#    index='http://www.opengl.org/registry/',
#    base='http://www.opengl.org/registry/'))

sources.append(source('gl', dotspec_constant_parser, regexp=r'^api/enumext\.spec$', xpath='//a/@href', index='http://www.opengl.org/registry/', base='http://www.opengl.org/registry/'))
sources.append(source('gl', dotspec_function_parser, regexp=r'^api/gl(?:ext)?\.spec$', xpath='//a/@href', index='http://www.opengl.org/registry/', base='http://www.opengl.org/registry/'))
sources.append(source('gl', dottm_parser, regexp=r'^api/gl\.tm$', xpath='//a/@href', index='http://www.opengl.org/registry/', base='http://www.opengl.org/registry/'))
sources.append(source('gl', header_parser, regexp=r'^api/gl(?:ext)?\.h$', xpath='//a/@href', index='http://www.opengl.org/registry/', base='http://www.opengl.org/registry/'))
sources.append(source('gl', header_parser, regexp=r'^api/gl3(?:ext)?\.h$', xpath='//a/@href', index='http://www.opengl.org/registry/', base='http://www.opengl.org/registry/'))
sources.append(source('gl', header_parser, files=['file:///usr/include/GL/gl.h']))

sources.append(source('glX', dotspec_constant_parser, regexp=r'^api/glxenumext\.spec$', xpath='//a/@href', index='http://www.opengl.org/registry/', base='http://www.opengl.org/registry/'))
sources.append(source('glX', dotspec_function_parser, regexp=r'^api/glx(?:ext)?\.spec$', xpath='//a/@href', index='http://www.opengl.org/registry/', base='http://www.opengl.org/registry/'))
sources.append(source('glX', dottm_parser, regexp=r'^api/glx\.tm$', xpath='//a/@href', index='http://www.opengl.org/registry/', base='http://www.opengl.org/registry/'))
sources.append(source('glX', header_parser, regexp=r'^api/glx(?:ext)?\.h$', xpath='//a/@href', index='http://www.opengl.org/registry/', base='http://www.opengl.org/registry/'))
#sources.append(source('glX', header_parser, files=['file:///usr/include/GL/glx.h']))

sources.append(source('wgl', dotspec_constant_parser, regexp=r'^api/wglenumext\.spec$', xpath='//a/@href', index='http://www.opengl.org/registry/', base='http://www.opengl.org/registry/'))
sources.append(source('wgl', dotspec_function_parser, regexp=r'^api/wgl(?:ext)?\.spec$', xpath='//a/@href', index='http://www.opengl.org/registry/', base='http://www.opengl.org/registry/'))
sources.append(source('wgl', dottm_parser, regexp=r'^api/wgl\.tm$', xpath='//a/@href', index='http://www.opengl.org/registry/', base='http://www.opengl.org/registry/'))
sources.append(source('wgl', header_parser, regexp=r'^api/wgl(?:ext)?\.h$', xpath='//a/@href', index='http://www.opengl.org/registry/', base='http://www.opengl.org/registry/'))

#sources.append(source('glu', header_parser, files=['file:///usr/include/GL/glu.h']))

sources.append(source('egl', dotspec_constant_parser, regexp=r'^api/eglenum\.spec$', xpath='//a/@href', index='http://www.khronos.org/registry/egl/', base='http://www.khronos.org/registry/egl/'))

for s in sources:
  s.parse()

reduce_constants()
reduce_functions()

print_constants(basic_printer())
print_functions(basic_printer())

#print '#include <cstdint>'
#for n in sorted(set([ e.name for e in enums ])):
#  print 'enum class', n, ': std::uint32_t {'
#  for v, c in sorted(set([ (c.value, c.name) for c in constants if c.enum_name == n])):
#    print '  ', c, '=', v, ','
#  print '};'


# -*- coding: utf-8 -*-
"""
Created on Thu Dec  2 12:11:01 2021

@author: ievdv
"""

import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
from sklearn.linear_model import LinearRegression

def Weighted_Region(data, mask_3D, land_mask, ar6_all):
    weights = np.cos(np.deg2rad(data.lat))

    regional = data.weighted(mask_3D * weights).mean(dim=("lat", "lon")) # mean value per region
    land     = data.weighted(land_mask * weights).mean(dim=("lat", "lon")) # 1 value for all land cells
    all_cells= data.weighted(weights).mean(dim=("lat", "lon")) # 1 value for all cells

    list_region_no  = []
    list_abbrevs    = []
    list_names      = []
    list_means      = []

    for rno in range(len(mask_3D.region.values)):
        if rno < 56:
            mean = regional.isel(region=rno).values
        elif rno == 56:
            mean = land.isel(region=0).values
        elif rno == 58:
            mean = all_cells.values
        list_means.append(mean)
        list_region_no.append(rno)
        if rno < 56:
            list_abbrevs.append(ar6_all[rno].abbrev)
            list_names.append(ar6_all[rno].name)
        elif rno == 56:
            list_abbrevs.append('GLD')
            list_names.append('Global.land')
        elif rno == 57:
            list_abbrevs.append('GAL')
            list_names.append('Global.all')

    df = pd.DataFrame()
    df['mean']    = list_means
    df['region_no'] = list_region_no
    df['abbrevs']   = list_abbrevs
    df['names']     = list_names

    not_included = ['RAR','ARO','NPO','NAO','EPO','EAO','ARS','BOB','EIO','SPO','SAO','SIO','SOO','WAN','EAN']
    not_included_no = [28,46,47,50,48,51,53,54,55,49,52,45,44]
    included = list(set(list_abbrevs) - set(not_included))

    list_region_no  = []
    list_abbrevs    = []
    list_names      = []
    list_means      = []
    for i in range(len(df)):
        for j in range(len(included)):
            if df['abbrevs'][i] == included[j]:
                list_region_no.append(df['region_no'][i])
                list_abbrevs.append(df['abbrevs'][i])
                list_names.append(df['names'][i])
                list_means.append(df['mean'][i])

    df_new = pd.DataFrame()
    df_new['mean']    = list_means
    df_new['region_no'] = list_region_no
    df_new['abbrevs']   = list_abbrevs
    df_new['names']     = list_names

    return df_new

def plotting(data,label,data2=np.array([0]),label2=None,data3=np.array([0]),label3=None,data4=np.array([0]),label4=None):
    plt.figure(figsize=(12,3))
    plt.plot(data['abbrevs'],data['mean'],'ro',label=f'{label}')
    plt.plot(data['abbrevs'],data['mean'],'r')
    if data2.shape[0] != 1:
        plt.plot(data2['abbrevs'],data2['mean'],'bo',label=f'{label2}')
        plt.plot(data2['abbrevs'],data2['mean'],'b')
    if data3.shape[0] != 1:
        plt.plot(data3['abbrevs'],data3['mean'],'go',label=f'{label3}')
        plt.plot(data3['abbrevs'],data3['mean'],'g')
    if data4.shape[0] != 1:
        plt.plot(data4['abbrevs'],data4['mean'],'mo',label=f'{label4}')
        plt.plot(data4['abbrevs'],data4['mean'],'m')
    plt.legend()
    plt.xticks(rotation=90)
    plt.grid()
    plt.xlabel('IPCC region')
    plt.ylabel('Mean heaviness [-]')
    plt.show()

    return

def plotting_control(heaviness,control,label1,label2,yaxis):
    fig,ax = plt.subplots(figsize=(12,3))
    lns1 = ax.plot(heaviness['abbrevs'],heaviness['mean'],'ro',label=f'{label1}')
    ax.plot(heaviness['abbrevs'],heaviness['mean'],'r')
    ax.set_ylabel('Heaviness [-]')
    plt.xticks(rotation=90)
    ax2 = ax.twinx()
    lns2 = ax2.plot(control['abbrevs'],control['mean'],'bo',label=f'{label2}')
    ax2.plot(control['abbrevs'],control['mean'],'b')
    ax2.set_ylabel(f'{yaxis}')

    lns = lns1+lns2
    labs = [l.get_label() for l in lns]
    ax.legend(lns, labs, loc='upper right')
    plt.show()

    return

def plotting_scatter(data_mean,data,h1,h1_mean,h5_mean,h10_mean,xlabel):
    plt.scatter(data_mean['mean'],h1_mean['mean'],label='h1')
    plt.scatter(data_mean['mean'],h5_mean['mean'],label='h5')
    plt.scatter(data_mean['mean'],h10_mean['mean'],label='h10')
    plt.xlabel(f'{xlabel}')
    plt.ylabel('Heaviness [-]')
    plt.grid()
    plt.legend()
    plt.show()

    plt.scatter(data,h1)
    plt.scatter(data_mean['mean'],h1_mean['mean'])
    plt.xlabel(f'{xlabel}')
    plt.ylabel('Heaviness [-]')
    plt.grid()
    plt.show()

    return

def fit_scatter(data_mean,h1,data_label,unit):
    X = data_mean.iloc[:,0].values.reshape(-1, 1)
    Y = h1.iloc[:,0].values.reshape(-1, 1)

    fit = LinearRegression().fit(X, Y)

    x = np.linspace(X.min(),X.max(),45)
    x = x.reshape(-1,1)
    Y_pred = fit.predict(x)
    plt.scatter(X, Y)
    plt.plot(x, Y_pred,'r--')
    plt.title(f'{data_label} --- R$^{2}$ = {fit.score(X,Y):.3f}')
    plt.xlabel(f'{data_label} [{unit}]')
    plt.ylabel('Heaviness [-]')
    plt.grid()
    plt.show()

    return fit.coef_, fit.intercept_


from setuptools import setup, find_packages

with open("requirements.txt") as f:
    content = f.readlines()
requirements = [x.strip() for x in content]

setup(name="api-tagger",
      version="1.0",
      description="Automatic question tagging system using multi classification model",
      packages=find_packages(),
      include_package_data=True,  # includes in package files from MANIFEST.in
      install_requires=requirements)


from django import template
from django.conf import settings
from django.contrib.staticfiles.finders import find as find_static_file
from django.core.exceptions import FieldDoesNotExist
from django.urls import reverse
from mighty.functions import get_model
import datetime, base64

register = template.Library()

guardian = False
if 'guardian' in settings.INSTALLED_APPS:
    from guardian.core import ObjectPermissionChecker
    guardian = True

"""
Simple tag
"""
@register.simple_tag(name='has_perm')
def has_perm(obj, user, perm):
    if hasattr(obj, 'perm'):
        return ObjectPermissionChecker(user).has_perm(perm, obj) if guardian else user.has_perm(obj.perm(perm))
    else:
        return False

@register.simple_tag(name='verbose_name')
def verbose_name(obj):
    return obj._meta.verbose_name

@register.simple_tag(name='verbose_name_plural')
def verbose_name_plural(obj):
    return obj._meta.verbose_name_plural

@register.simple_tag(name='field_name')
def field_name(obj, field):
    if field == '__str__':
        return obj._meta.verbose_name
    else:
        try:
            return obj._meta.get_field(field).verbose_name
        except FieldDoesNotExist:
            try:
                return getattr(obj, field).short_description
            except Exception:
                pass
    return ""

@register.simple_tag(name='field_value')
def field_value(obj, field):
    if field == '__str__':
        return str(obj)
    else:
        attr = getattr(obj, field)
    attr = attr() if callable(attr) else attr
    return None if attr is None else attr

@register.simple_tag(name='join_or_concat')
def join_or_concat(delimiter, inputlist, istuple=False):
    if istuple:
        inputlist = [ipt[1] for ipt in inputlist]
    return delimiter.join(filter(None, inputlist))

@register.simple_tag(name='add_attr')
def add_attr(field, attr, value):
    return field.as_widget(attrs={attr: value})

@register.simple_tag(name='number_hread')
def number_hread(number, separator=None):
    return '{:,}'.format(int(number)).replace(",", separator) if separator else '{:,}'.format(int(number))

@register.simple_tag(name='is_type')
def is_type(data):
    return type(data).__name__.lower()

@register.simple_tag(name='define')
def define(val=None):
  return val

@register.simple_tag(name='convert_date')
def convert_date(date, origin, convert):
    return datetime.datetime.strptime(date, origin).strftime(convert)

"""
Filter based templatetag
"""
@register.simple_tag(name='get_most_used_apps')
def get_most_used_apps(parser, limit=10):
    from mighty.apps import MightyConfig
    apps = []
    for app in MightyConfig.most_used_app:
        bm = get_model(*app.split("."))()
        apps.append({
            "url": bm.admin_list_url,
            "name": bm.get_content_type().name,
        })
    return apps

@register.filter(name='add_attrs')
def add_attrs(field, css):
    attrs = {}
    definition = css.split(',')
    for d in definition:
        if ':' not in d:
            attrs['class'] = d
        else:
            key, val = d.split(':')
            attrs[key] = val
    return field.as_widget(attrs=attrs)

@register.filter
def index(indexable, i):
    return indexable[i]

@register.filter
def indexkey(dct, key):
    return dct.get(key)

@register.filter(name='split')
def split(value, key):
  return value.split(key)

@register.filter(name='has_m2m')
def has_m2m(m2mfield, m2m, field='id'):
    m2m_id = int(getattr(m2m, field))
    return m2mfield.filter(**{field: m2m_id}).count()

from django.contrib.contenttypes.models import ContentType

@register.filter(name='contenttype_id')
def contenttype_id(model):
    try:
        return ContentType.objects.get(app_label=model._meta.app_label, model=model._meta.model_name).id
    except ContentType.DoesNotExist:
        return

# FILE
@register.simple_tag
def encode_b64(path):
    """
    a template tag that returns a encoded string representation of a staticfile
    Usage::
        {% encode_static path [encoding] %}
    Examples::

    """
    file_path = find_static_file(path)
    ext = file_path.split('.')[-1]
    with open(file_path, "rb") as image_file:
        file_str = base64.b64encode(image_file.read()).decode()
        src = u"data:{0}/{1};{2},{3}".format("image", ext, "base64", file_str)
        return src

@register.simple_tag
def encode_static(path, encoding='base64', file_type='image'):
    """
    a template tag that returns a encoded string representation of a staticfile
    Usage::
        {% encode_static path [encoding] %}
    Examples::

    """
    file_path = find_static_file(path)
    ext = file_path.split('.')[-1]
    file_str = get_file_data(file_path).encode(encoding)
    return u"data:{0}/{1};{2},{3}".format(file_type, ext, encoding, file_str)

@register.simple_tag
def raw_static(path):
    """
    a template tag that returns a raw staticfile
    Usage::
        {% raw_static path %}
    Examples::

    """
    if path.startswith(settings.STATIC_URL):
        # remove static_url if its included in the path
        path = path.replace(settings.STATIC_URL, '')
    file_path = find_static_file(path)
    return get_file_data(file_path)

def get_file_data(file_path):
    with open(file_path, 'rb') as f:
        data = f.read()
        f.close()
        return data


from django.db import models
from django.core.validators import MaxValueValidator, MinValueValidator
from django.core.exceptions import ValidationError
import json

def validate_ticks(value):
    """Validates that ticks list has 15 integers between -10 and -100"""
    # Verify format of ticks object/validation conditions
    # ticks_list = value.ticks
    if len(value) != 15:
        raise ValidationError(
            ('15 Audio ticks required'),
            params={'value': value},
            )
    for x in value:
        if not -100 > x > -10 :
            raise ValidationError(
                ('Ticks must all be between -10 and -100'),
                params={'value': value},
                )

class Step(models.Model):
    session = models.ForeignKey("Session", on_delete=models.CASCADE, related_name="session_steps")
    step_count = models.IntegerField(
        default=0,
        validators=[MaxValueValidator(9), MinValueValidator(0)]
    )
    ticks = models.JSONField(max_length=200, validators=[validate_ticks])
    selected_tick = models.IntegerField(
        default=0,
        validators=[MaxValueValidator(14), MinValueValidator(0)]
    )


from pyecharts import options as opts
from pyecharts.charts import Map, Geo
from pyecharts.faker import Faker
from pyecharts.globals import ChartType

data = [['杭州市', 200], ['宁波市', 200], ['温州市', 30],
        ['嘉兴市', 40], ['湖州市', 50], ['绍兴市', 60],
        ['金华市', 70], ['衢州市', 8], ['舟山市', 90],
        ['台州市', 10], ['丽水市', 110]]

# map = (Map().add("CO2 emission", data, "浙江", zoom = 1).set_global_opts(
#     title_opts = opts.TitleOpts(title = "Map-浙江地图"),
#     visualmap_opts = opts.VisualMapOpts(max_ = 300, is_piecewise = True)
# ).render("map_Zhejiang.html"))
# def map_yunnan() -> Map:
#     c = (
#         Map()
#             .add("CO2 emission", data, "浙江", zoom = 1,maptype="zhejiang" )
#             .set_series_opts(label_opts = opts.LabelOpts(is_show = False))
#             .set_global_opts(
#             title_opts = opts.TitleOpts(title = "浙江碳排放"),
#             visualmap_opts = opts.VisualMapOpts(max_ = 300, is_pziecewise = True
#                                                 # pieces = [{"max": 0, "min": 0, "label": "0", "color": "#FFFFFF"},
#                                                 #           {"max": 9, "min": 1, "label": "0-9", "color": "#FFE4E1"},
#                                                 #           {"max": 99, "min": 10, "label": "10-99", "color": "#FF7F50"},
#                                                 #           {"max": 499, "min": 100, "label": "100-499",
#                                                 #            "color": "#F08080"},
#                                                 #           {"max": 999, "min": 500, "label": "500-999",
#                                                 #            "color": "#CD5C5C"},
#                                                 #           {"max": 9999, "min": 1000, "label": ">=1000",
#                                                 #            "color": "#8B0000"}]
#                                                 ),
#         )
#     )
#
#     return c
#
#
# d_map = map_yunnan()
# d_map.render("map_zhejiang.html")

citys = ['杭州市', '宁波市', '温州市',
         '嘉兴市', '湖州市', '绍兴市',
         '金华市', '衢州市', '舟山市',
         '台州市', '丽水市']
values = [365, 656, 524, 455, 411, 174, 125, 121, 666, 123, 444]
c = (
    Geo().add_schema(maptype = "浙江")
     .add("CO2 emission", [list(z) for z in zip(citys, values)], type_ = ChartType.SCATTER)
     .set_global_opts(visualmap_opts = opts.VisualMapOpts(), title_opts = opts.TitleOpts(title = "Geo-浙江地图"))
     .set_series_opts(label_opts = opts.LabelOpts(is_show = True)).render("zj.html")
     )
# c = (
#     Geo()
#         .add_schema(maptype = "china")
#         .add("geo", [list(z) for z in zip(Faker.provinces, Faker.values())])
#         .set_series_opts(label_opts = opts.LabelOpts(is_show = False))
#         .set_global_opts(
#         visualmap_opts = opts.VisualMapOpts(), title_opts = opts.TitleOpts(title = "Geo-基本示例")
#     )
#         .render("geo_base.html")
# )


from django.urls import path
from . import views

app_name = 'student'
urlpatterns = [
    path('', views.main, name='main'),
    path('currenttasks', views.currenttasks, name='currenttasks'),
    path('generatetask', views.generatetask, name='generatetask'),
    path('generatetask/find_templates', views.find_templates, name='find_templates'),
    path('generatetask/gen_templates', views.generateManyJobs, name='gen_templates'),
    path('history', views.history, name='history'),
    path('statistics', views.statistics, name='statistics'),
    path('statistics/change_topic', views.change_topic, name='change_topic'),
    path('profile', views.profile, name='profile'),
    path('support', views.support, name='support'),
    path('toLogin', views.toLogin, name='toLogin'),
    path('changepassword', views.ChangePassword, name='changepassword'),
    path('sendmail', views.sendmail, name='sendmail'),
    path('chp', views.chp, name='chp'),
    path('task/<int:task_id>', views.task, name='task'),
    path('task/<int:task_id>/answer_check', views.checkAnswer, name='answer_check'),
]


from datetime import datetime, date, time, timedelta

class Learn_how_to_use_time():

    '''
        调用构造函数,创建三个时间对象

    '''
    Ian_time = time(19, 12, 10)
    Ian_date = date(2018, 5, 7)
    Ian_datetime = datetime(2018, 5, 7, 19, 12, 10)
    date_str = '2018-5-7'
    time_str = '19:12:10'
    '''
        时间对象=> str
    '''

    def class_to_str(self):
        self.Ian_time = self.Ian_time.strftime('%H:%M:%S')
        self.Ian_date = self.Ian_date.strftime('%Y-%m-%d')
        self.Ian_datetime = self.Ian_datetime.strftime('%Y-%m-%d %H:%M:%S')

    '''
        str => 对象
    '''

    def str_to_class(self):
        self.date_str = datetime.strptime(self.date_str, '%Y-%m-%d')
        self.time_str = datetime.strptime(self.time_str, '%H:%M:%S')

    '''
        日期 运算
    '''

    def add_date(self):
        res = date(2013,10,2) + timedelta(days=10)
        return date(2013,10,2).strftime('%Y-%m-%d'), res.strftime('%Y-%m-%d')

user = Learn_how_to_use_time()
print(type(user.Ian_date), user.Ian_time, user.Ian_datetime)
user.class_to_str()
print(type(user.Ian_date), user.Ian_time, user.Ian_datetime)
user.str_to_class()
print(type(user.date_str), user.time_str)
print(user.add_date())