{"cells":[{"metadata":{"trusted":true},"cell_type":"code","source":"import glob \nimport os\nimport pandas as pd\nimport json\nimport plotly.graph_objects as go\nimport numpy as np\nfrom PIL import Image\nimport re\nimport plotly\nimport matplotlib.pyplot as plt\nfrom collections import Counter\nimport ipywidgets as widgets\nfrom ipywidgets import interact, interact_manual\nimport re\n\nfrom helper import FLOOR_MAP, RELEVANT_BUILDINGS, is_interactive, GEODATA_OFFSETS, LINKS, get_folders\nBUILDING_IDS = get_folders('/kaggle/input/indoor-location-navigation/metadata/*')","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"class Floor:\n    def __init__(self, building_id, name, level=None):\n        self.building_id = building_id\n        self.level = FLOOR_MAP[name] if level is None else level \n        self.name = name\n        \n        with open(f\"../input/indoor-location-navigation/metadata/{self.building_id}/{self.name}/floor_info.json\") as f:\n            self.info = json.load(f)[\"map_info\"]\n            \n        self.shops = self._scale_to_map(self._extract_shops_on_floor())\n        self.trajectories = self._get_trajectories()  # Access: [trajectory_id][trajectory_type] contains the trajectory log\n\n    def _get_trajectories(self):\n        # import pdb; pdb.set_trace()\n        return {\n            os.path.basename(trajectory_path).split(\".\")[0]: \n                {info_type: pd.read_csv(f\"{trajectory_path}/{info_type}.csv\") for info_type in (\"waypoint\",)}\n            for trajectory_path in glob.glob(f\"/kaggle/input/waypointwificsv/train/{self.building_id}/{self.name}/**\")\n        }\n    \n    def _scale_to_map(self, shops):\n        min_x, min_y = min([x_poly for shop in shops for x_poly in shop[\"x_poly\"]]), min([y_poly for shop in shops for y_poly in shop[\"y_poly\"]])\n        max_x, max_y = max([x_poly for shop in shops for x_poly in shop[\"x_poly\"]]), max([y_poly for shop in shops for y_poly in shop[\"y_poly\"]])\n        x_offset, y_offset, x_factor, y_factor = 0, 0, 1, 1\n        if (self.building_id, self.name) in GEODATA_OFFSETS:\n            x_offset, y_offset = GEODATA_OFFSETS[(self.building_id, self.name)][0], GEODATA_OFFSETS[(self.building_id, self.name)][1]\n            x_factor, y_factor = GEODATA_OFFSETS[(self.building_id, self.name)][2], GEODATA_OFFSETS[(self.building_id, self.name)][3]\n        for shop in shops:\n            shop[\"x_poly\"] = ((shop[\"x_poly\"] - min_x) / (max_x-min_x) * self.info[\"width\"]) * x_factor + x_offset\n            shop[\"y_poly\"] = ((shop[\"y_poly\"] - min_y) / (max_y-min_y) * self.info[\"height\"]) * y_factor + y_offset\n            shop[\"x_center\"] =  (max(shop[\"x_poly\"]) + min(shop[\"x_poly\"])) / 2\n            shop[\"y_center\"] =  (max(shop[\"y_poly\"]) + min(shop[\"y_poly\"])) / 2\n            \n        return shops\n        \n    def _extract_shops_on_floor(self):\n        with open(f\"../input/indoor-location-navigation/metadata/{self.building_id}/{self.name}/geojson_map.json\") as f:\n            floor_features = json.load(f)\n        shops = []\n        for feature_n, feature in enumerate(floor_features[\"features\"]): \n            if feature[\"geometry\"][\"type\"] == \"MultiPolygon\":\n                continue  # this is the overall shape\n            if (\"type\" in feature and feature[\"type\"] != \"Feature\") or feature[\"geometry\"][\"type\"] != \"Polygon\":\n                print(\"this is not a Polygon, type: \", feature[\"geometry\"][\"type\"] )\n                continue\n            if \"properties\" not in feature:\n                continue\n            shops.append({\n                \"x_poly\": np.array([xy_poly[0] for xy_poly in feature[\"geometry\"][\"coordinates\"][0]]),\n                \"y_poly\": np.array([xy_poly[1] for xy_poly in feature[\"geometry\"][\"coordinates\"][0]]),\n                \"z_poly\": np.array([self.level]*len(feature[\"geometry\"][\"coordinates\"][0])),\n                \"name\": feature[\"properties\"][\"name\"] if \"name\" in feature[\"properties\"] else None,\n            })\n        return shops\n\n    def visualize(self, store=False):\n        im = Image.open(f\"../input/indoor-location-navigation/metadata/{self.building_id}/{self.name}/floor_image.png\")\n\n        fig = go.Figure()\n        for shop in self.shops:\n            fig.add_trace(go.Scatter(x=shop[\"x_poly\"], y=shop[\"y_poly\"],mode='lines', line={\"color\": \"black\", \"width\": 2}, name=shop[\"name\"], showlegend=False))\n\n        for trajectory_id, trajectory in self.trajectories.items():\n            waypoint_trajectory = trajectory[\"waypoint\"]\n            fig.add_trace(go.Scatter(x=waypoint_trajectory.x, y=waypoint_trajectory.y, name=trajectory_id))\n\n        fig.add_layout_image(dict(source=im, xref=\"x\", yref=\"y\", x=0, y=self.info[\"height\"], sizex=self.info[\"width\"], sizey=self.info[\"height\"], sizing=\"stretch\", opacity=0.9, layer=\"below\"))\n        fig.update_layout(\n            template=\"plotly_white\",\n            sliders=[\n                dict(active=0, currentvalue= {\"prefix\": \"+x: \"},\n            )]\n        )\n        if store:\n            folder = f\"/kaggle/working/train/{self.building_id}/{self.name}/\"\n            os.makedirs(folder, exist_ok=True)\n            try:\n                fig.write_image(folder + \"trajectory.png\")\n            except: \n                import sys\n                !conda install --yes --prefix {sys.prefix} -c plotly plotly-orca\n                fig.write_image(folder + \"trajectory.png\")\n        else:\n            fig.show()","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"f0 = Floor(building_id=RELEVANT_BUILDINGS[10], name=\"F1\")\nf0.visualize(store=False)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"f0 = Floor(building_id=RELEVANT_BUILDINGS[0], name=\"B1\")\nf0.visualize(store=False)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"f1 = Floor(building_id=RELEVANT_BUILDINGS[0], name=\"F1\")\nf1.visualize(store=False)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"f2 = Floor(building_id=RELEVANT_BUILDINGS[0], name=\"F2\")\nf2.visualize(store=False)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"f4 = Floor(building_id=RELEVANT_BUILDINGS[0], name=\"F4\")\nf4.visualize(store=False)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"class Building:\n    def __init__(self, building_id):\n        print(f\"creating: {building_id}\", end=\" \")\n        self.plotly_data = []\n        self.building_id = building_id\n        self.positions = pd.read_csv(f\"../input/wifipositions/{self.building_id}-p.csv\")\n        self.wifi = pd.read_csv(f\"../input/wifipositions/{self.building_id}.csv\")\n        self.wifi.drop(columns=self.wifi.columns[0], inplace=True)\n        self.wifi[\"index\"] = [(v[\"f\"], v[\"x\"], v[\"y\"]) for v in self.positions.T.to_dict().values()]\n        self.wifi.set_index(\"index\", inplace=True)\n        \n        self.floors = {}\n        for filepath in glob.glob(f\"../input/indoor-location-navigation/metadata/{building_id}/**\"):\n            floor_name = os.path.basename(filepath)\n            try:\n                level = FLOOR_MAP[floor_name]\n            except KeyError:\n                print(f\"Floor {floor_name} is not standard identifier\")\n                continue                \n            self.floors[floor_name] = Floor(building_id=building_id, name=floor_name, level=level)\n\n    def display_shops(self):\n        plotly.offline.init_notebook_mode()\n        self.plotly_data.append(go.Scatter3d(x=[None], y=[None], z=[None], legendgroup=\"shops\", name=\"shops\",\n                                line={\"color\": \"black\", \"width\": 1}, marker={\"color\": 'black'}, visible=True, showlegend=True))\n        self.plotly_data.extend([\n            go.Scatter3d(x=shop['x_poly'], y=shop['y_poly'], z=shop['z_poly'], line={\"color\": \"black\", \"width\": 1}, mode=\"lines\", showlegend=False, legendgroup=\"shops\", name=shop[\"name\"])\n            for floor in self.floors.values() for shop in floor.shops])    \n        \n    def display_waypoints(self):\n        plotly.offline.init_notebook_mode()\n        self.plotly_data.append(go.Scatter3d(x=[None], y=[None], z=[None], legendgroup=\"trajectories\", name=\"trajectories\",\n                                line={\"color\": \"gray\", \"width\": 1}, marker={\"color\": 'gray'}, visible=True, showlegend=True))\n        for floor in self.floors.values():\n            for trajectory_id, trajectory in floor.trajectories.items():\n                waypoint_trajectory = trajectory[\"waypoint\"]\n                self.plotly_data.append(go.Scatter3d(x=waypoint_trajectory.x, y=waypoint_trajectory.y, z=[floor.level]*len(waypoint_trajectory.x), \n                                                     line={\"color\": \"gray\", \"width\": 2}, mode=\"lines\", name=trajectory_id, legendgroup=\"trajectories\", showlegend=False))\n            \n    def visualize_bssids(self, no_bssids=5):\n        cmap = plt.get_cmap('Spectral')\n        norm = plt.Normalize(-90, -20)\n\n        def get_color(v):\n            c = cmap(norm(v))\n            return f\"rgb({int(c[0]*255)}, {int(c[1]*255)}, {int(c[2]*255)})\"\n\n        for nn, bssid in enumerate(self.wifi.columns[1:6]):\n            occurences = list((-90 < self.wifi[bssid]) & (self.wifi[bssid] < -20))\n            self.plotly_data.append(\n                go.Scatter3d(x=self.positions[\"x\"][occurences], y=self.positions[\"y\"][occurences], z=[FLOOR_MAP[f] for f in self.positions[\"f\"][occurences]],\n                             mode=\"markers\", showlegend=True, name=bssid[:7], visible=True if nn == 0 else \"legendonly\",\n                             text=self.wifi[bssid][occurences],\n                             marker=dict(color=[get_color(c) for nn, c in enumerate(self.wifi[bssid]) if occurences[nn]])))\n            \n    def show_position(self, this_positions, show=\"all\"):    \n        cmap = plt.get_cmap('Spectral')\n        norm = plt.Normalize(0, 1)\n\n        def get_color(v):\n            c = cmap(norm(v))\n            return f\"rgb({int(c[0]*255)}, {int(c[1]*255)}, {int(c[2]*255)})\"\n\n        for nn, t in enumerate(sorted(this_positions.keys())):\n            if show == \"ends\" and nn not in [0, len(this_positions)-1]:\n                continue\n            if len(this_positions[t]) == 0: continue\n            pp = list(this_positions[t].keys())\n\n            self.plotly_data.append(\n                go.Scatter3d(x=[p[1] for p in pp], y=[p[2] for p in pp], z=[FLOOR_MAP[p[0]] for p in pp],\n                             mode=\"markers\", showlegend=True, name=f\"{t}\", visible=True if nn == 0 else \"legendonly\",\n                             text=[c for c in this_positions[t].values()],\n                             marker=dict(color=[get_color(c) for c in this_positions[t].values()],\n                                        )))\n    \n    def show_trajectory(self, trajectory_dict, name=\"test_trajectory\"):\n        trajectory_list = sorted(trajectory_dict.items())\n        self.plotly_data.append(go.Scatter3d(x=[t[1][1] for t in trajectory_list], y=[t[1][2] for t in trajectory_list], z=[FLOOR_MAP[t[1][0]] for t in trajectory_list],\n                                             text=[(mm, t[0]) for mm, t in enumerate(trajectory_list)], name=name,\n                                             line={\"color\": \"blue\", \"width\": 2}, mode=\"lines\"))\n    \n    def show(self):\n        clean_axis = dict(autorange=True, showgrid=False, zeroline=False, ticks='', showticklabels=False, showline=False)\n        plot_figure = go.Figure(data=self.plotly_data)\n        plot_figure.update_layout(scene=dict(xaxis=clean_axis, yaxis=clean_axis, zaxis=clean_axis))\n        plotly.offline.iplot(plot_figure)\n        ","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"all_buildings = {building_id: Building(building_id) for building_id in RELEVANT_BUILDINGS \n                 if not is_interactive() or building_id == \"5a0546857ecc773753327266\"}","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"b1 = all_buildings[\"5a0546857ecc773753327266\"]\nb1.plotly_data = []\nb1.display_shops()\nb1.display_waypoints()\nb1.visualize_bssids()\nb1.show()","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"def get_building_id(path): \n    with open(path) as f:\n        next(f) # first line can be skipped\n        return re.findall(r\"SiteID:(\\w*)\", next(f))[0]\n    \ndef extract_trajectory(trajectory_path):\n    trajectory_id = os.path.basename(trajectory_path)[:-4]\n    wifi_logs = []\n    with open(trajectory_path) as f:\n        line = f.readline()\n        while line:\n            wifi_match = re.findall(r\"(\\d{13})\\tTYPE_WIFI\\t(\\w{40})\\t(\\w{40})\\t(-\\d+)\\t(\\d+)\\t\\d+\", line)\n            if wifi_match:\n                wifi_logs.append((trajectory_id, \n                                  int(wifi_match[0][0]), \n                                  wifi_match[0][2], \n                                  int(wifi_match[0][3])))\n            line = f.readline()\n    df_wifi = pd.DataFrame(wifi_logs, columns=(\"trajectory_id\", \"t\", \"bssid\", \"rssi\"))\n    return df_wifi","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"BATCH_SIZE = 100\ndef get_positions_for_trajectory(building_wifi, wifi, prefix=\"\"):\n    bssids = list(building_wifi.columns)\n    all_trajectory_ids = wifi.trajectory_id.unique()\n    readings = sorted(wifi.groupby([\"trajectory_id\", \"t\"]))\n    \n    def get_building_cube(bs):\n        # building_wifi.values  np.array of (#points, #bssids)\n        building_cube_ = np.array([building_wifi.values for _ in range(bs)])\n        building_cube_[building_cube_ >= -20] = np.NaN\n        building_cube_is_ = ~np.isnan(building_cube_)\n\n        building_cube40_ = building_cube_.copy()\n        building_cube40_[building_cube40_ >= -40] = np.NaN\n        building_cube40_is_ = ~np.isnan(building_cube40_)\n        return building_cube_, building_cube_is_, building_cube40_, building_cube40_is_\n    \n    building_cube, building_cube_is, building_cube40, building_cube40_is = get_building_cube(BATCH_SIZE)\n\n    building_positions = list(building_wifi.index)\n    touched_trajectories = set()\n    results = {}\n    for i in range(0, len(readings), BATCH_SIZE):        \n        if is_interactive() and i > BATCH_SIZE * 3:\n            break\n        readings_batch = readings[i:i + BATCH_SIZE]\n        touched_trajectories.update([trajectory_id for (trajectory_id, _), _ in readings_batch])\n        \n        if len(readings_batch) == BATCH_SIZE:\n            print(f\"{prefix} - {i+BATCH_SIZE}/{len(readings)} ({len(touched_trajectories)}/ {len(all_trajectory_ids)})\")\n\n        else:\n            print(f\"{prefix} - pad remaining {len(readings)}\")\n            building_cube, building_cube_is, building_cube40, building_cube40_is = get_building_cube(len(readings_batch))\n\n        wifi_cube = np.empty((len(readings_batch), len(building_wifi.index), len(bssids)))\n        wifi_cube[:] = np.NaN\n        for nn, ((building_id, t), group) in enumerate(readings_batch):\n            for mm, row in group.iterrows():\n                if row[\"bssid\"] in bssids and row[\"rssi\"] < -20:\n                    wifi_cube[nn, :, bssids.index(row[\"bssid\"])] = row[\"rssi\"]\n        wifi_cube40 = wifi_cube.copy()\n        wifi_cube40[wifi_cube40 >= -40] = np.NaN\n        wifi_cube_is = ~(np.isnan(wifi_cube).astype(bool))\n        wifi_cube40_is = ~(np.isnan(wifi_cube40).astype(bool))\n\n        diff_both = np.nansum(abs(building_cube - wifi_cube), axis=2)\n        cnt_both = (~np.isnan(building_cube - wifi_cube)).astype(int).sum(axis=2)\n        cnt_both_nan = cnt_both.copy().astype(float)\n        cnt_both_nan[cnt_both_nan == 0] = np.NaN\n        p_diff_both_ = 30-(diff_both / cnt_both_nan)\n        p_cnt_both = cnt_both / len(bssids)\n        \n        only_reading_is = np.clip(wifi_cube_is.astype(int) - building_cube_is.astype(int), 0, 1).astype(bool)\n        only_reading_ = wifi_cube.copy()\n        only_reading_[~only_reading_is] = 0\n        only_reading = abs(only_reading_).sum(axis=2)\n        cnt_only_reading40 = np.clip(wifi_cube40_is.astype(int) - building_cube40_is.astype(int), 0, 1).sum(axis=2)\n        \n        cnt_only_both_reading40_nan = (cnt_both + cnt_only_reading40).astype(float)\n        cnt_only_both_reading40_nan[cnt_only_both_reading40_nan == 0] = np.NaN\n        p_only_reading_ = only_reading / len(bssids)\n        p_cnt_only_reading40 = cnt_only_reading40 / len(bssids)\n        p_both_in_reading40 = cnt_both / cnt_only_both_reading40_nan\n\n        only_known_is = np.clip(building_cube_is.astype(int) - wifi_cube_is.astype(int), 0, 1).astype(bool)\n        only_known = building_cube.copy()\n        only_known[~only_known_is] = 0\n        only_known = abs(only_known).sum(axis=2)\n        cnt_only_known40 = np.clip(building_cube40_is.astype(int) - wifi_cube40_is.astype(int), 0, 1).sum(axis=2)\n        p_only_known = only_known / len(bssids)\n        p_cnt_only_known40 = cnt_only_known40 / len(bssids)\n\n        cnt_both_only_known40_nan = (cnt_both + cnt_only_known40).astype(float)\n        cnt_both_only_known40_nan[cnt_both_only_known40_nan == 0] = np.NaN\n        p_both_in_known40 = np.nan_to_num(cnt_both / cnt_both_only_known40_nan)\n        cnt_neither = ((~wifi_cube_is) & (~building_cube_is)).astype(int).sum(axis=2)\n        p_cnt_neither = cnt_neither / len(bssids)\n\n        p_diff_both = np.clip(p_diff_both_, 0, 30) / 30\n        p_only_reading = np.clip(10 - p_only_reading_, 0, 10) / 10\n        p_only_known = np.clip(30 - p_only_known, 0, 30) / 30\n\n        scores = np.nansum([\n            .2 * p_diff_both,\n            .2 * p_both_in_reading40,\n            .2 * p_both_in_known40,\n            .15 * p_only_reading,\n            .05 * p_only_known,\n            .2 * p_cnt_neither,\n        ], axis=0)\n                \n        for mm, t_score in enumerate(scores):\n            trajectory_id, t = readings_batch[mm][0]\n            if trajectory_id not in results:\n                results[trajectory_id] = {}\n            results[trajectory_id][t] = {\n                building_positions[nn]: b_score\n                for nn, b_score in enumerate(t_score)}\n    return results","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"# this is the required trajectories needed for the output\nresult_timestamps_out = {}\nresult_timestamps_out_list = []\nfor site_path_timestamp in list(pd.read_csv(\"../input/indoor-location-navigation/sample_submission.csv\")[\"site_path_timestamp\"]):\n    building_id, trajectory, timestamp = site_path_timestamp.split(\"_\")\n    if building_id not in result_timestamps_out:\n        result_timestamps_out[building_id] = {}\n    if trajectory not in result_timestamps_out[building_id]:\n        result_timestamps_out[building_id][trajectory] = []\n    result_timestamps_out[building_id][trajectory].append(int(timestamp))\n    result_timestamps_out_list.append((building_id, trajectory, int(timestamp)))\nlen(result_timestamps_out_list)  # the output has 10133 lines","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"scores_all_positions = {}\npositions_of_best_score = {}\nbest_score_for_selected = {}\noutput_positions = {}\noutput = []\n\nfor tp, (building_id, trajectories) in enumerate(result_timestamps_out.items()):\n    if is_interactive() and building_id != \"5a0546857ecc773753327266\": continue\n    building = all_buildings[building_id]\n    print(f\"{tp}/{len(result_timestamps_out)} = {building_id}\")\n    stacked_wifi_positision_from_test = pd.concat([extract_trajectory(f\"../input/indoor-location-navigation/test/{trajectory_id}.txt\")\n                                                   for trajectory_id in trajectories.keys()])\n    all_scores = get_positions_for_trajectory(building.wifi, stacked_wifi_positision_from_test, f\"{tp}/{len(result_timestamps_out)}\")\n    # format: [trajectory_id][timestamp][position_id] = score\n    \n    \n    for ti, (trajectory_id, positions_data) in enumerate(all_scores.items()):\n        this_best_positions_regardless_of_floor = {t: max(positions_data[t].items(), key=lambda obj: obj[1])[0]\n                                                   for t in positions_data.keys()}\n        best_floor = Counter([r[0] for r in this_best_positions_regardless_of_floor.values()]).most_common(1)[0]\n        this_best_positions_on_floor = {t: max([(k, v) for (k, v) in positions_data[t].items() if k[0] == best_floor[0]], \n                                               key=lambda obj: obj[1])[0]\n                                        for t in positions_data.keys()}\n\n        if is_interactive() or trajectory_id == \"046cfa46be49fc10834815c6\":\n            if building_id not in scores_all_positions:\n                scores_all_positions[building_id] = {}\n                positions_of_best_score[building_id] = {}\n\n            scores_all_positions[building_id][trajectory_id] = positions_data\n            positions_of_best_score[building_id][trajectory_id] = this_best_positions_on_floor\n\n        resulted_timestamps = sorted(this_best_positions_on_floor.keys())\n        output_ts = {}\n        c = 0\n        try:\n            timestamps = result_timestamps_out[building_id][trajectory_id]\n        except KeyError:\n            print(f\"Could not find {building_id}{trajectory_id}\")\n            continue\n        for timestamp in timestamps:\n            # it always holds: c-pointer is always larger than current timestamp\n            while c < len(resulted_timestamps) - 1 and timestamp > resulted_timestamps[c]:\n                c += 1\n            point1 = this_best_positions_on_floor[resulted_timestamps[c]]\n\n            if c == 0 or timestamp >= resulted_timestamps[c]:  # before first result or after last result\n                output_ts[timestamp] = point1\n                continue\n            point0 = this_best_positions_on_floor[resulted_timestamps[c-1]]         \n            output_ts[timestamp] = (best_floor[0], (point0[1] + point1[1])/2, (point0[2] + point1[2])/2)\n\n        if building_id not in output_positions:\n            output_positions[building_id] = {}\n        output_positions[building_id][trajectory_id] = output_ts\n\n        for t in sorted(output_ts.keys()):\n            best_fit = output_ts[t]\n            output.append({\n                \"site_path_timestamp\": f\"{building_id}_{trajectory_id}_{t:013d}\",\n                \"floor\": FLOOR_MAP[best_fit[0]],\n                \"x\": best_fit[1],\n                \"y\": best_fit[2],\n            })\n    pd.DataFrame(output).to_csv(f\"submission-{tp}.csv\", index=False)\npd.DataFrame(output).to_csv(\"submission.csv\", index=False)\nif is_interactive():\n    display(pd.DataFrame(output))","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"!head submission.csv","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"summary = {}\nfor building_id in BUILDING_IDS:\n    floors = get_folders(f'/kaggle/input/indoor-location-navigation/metadata/{building_id}/*')\n    invalid_floors = [floor for floor in floors if floor not in FLOOR_MAP]\n    train_trajectories = glob.glob(f\"/kaggle/input/indoor-location-navigation/train/{building_id}/*/*.txt\")\n    with open(train_trajectories[0]) as f:\n        next(f)\n        building_name = re.findall(r\"SiteName:(\\w*)\", next(f))[0]\n    \n    summary[building_id] = {\"floors\": floors, \"floors_no\": len(floors), \"invalid_floors\": invalid_floors,\n                            \"no_train\": len(train_trajectories), \"no_test\": 0, \"building_name\": building_name}\n    \nfor path in glob.glob(f\"/kaggle/input/indoor-location-navigation/test/*.txt\"):\n    with open(path) as f:\n        next(f) # first line\n        building_id = re.findall(r\"SiteID:(\\w*)\", next(f))[0]\n    summary[building_id][\"no_test\"] += 1\n\npd.set_option('display.max_rows', None)\npd.set_option('display.max_columns', 20)\n\nsummary = pd.DataFrame(summary).T.sort_values(\"no_test\", ascending=False)\nsummary.to_csv(\"summary.csv\")\n\nRELEVANT_BUILDINGS = list(summary.loc[summary[\"no_test\"] > 0].index)\n\n@interact\ndef show_articles_more_than(column=['no_test', 'floors_no', 'no_train'], x=2):\n    return summary.loc[summary[column] >= x]","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"traj_id = \"046cfa46be49fc10834815c6\"\nb1 = all_buildings[\"5a0546857ecc773753327266\"]\nb1.plotly_data = []\nb1.display_shops()\nb1.show_position(scores_all_positions[\"5a0546857ecc773753327266\"][traj_id])\nb1.show_trajectory(positions_of_best_score[\"5a0546857ecc773753327266\"][traj_id], traj_id)\nb1.show()","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"traj_id = \"05d052dde78384b0c543d89c\"\nb1 = all_buildings[\"5a0546857ecc773753327266\"]\nb1.plotly_data = []\nb1.display_shops()\nb1.show_position(scores_all_positions[\"5a0546857ecc773753327266\"][traj_id])\nb1.show_trajectory(positions_of_best_score[\"5a0546857ecc773753327266\"][traj_id], traj_id)\nb1.show()","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"traj_id = \"0c06cc9f21d172618d74c6c8\"\nb1 = all_buildings[\"5a0546857ecc773753327266\"]\nb1.plotly_data = []\nb1.display_shops()\nb1.show_position(scores_all_positions[\"5a0546857ecc773753327266\"][traj_id])\nb1.show_trajectory(positions_of_best_score[\"5a0546857ecc773753327266\"][traj_id], traj_id)\nb1.show()","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"traj_id = \"146035943a1482883ed98570\"\nb1 = all_buildings[\"5a0546857ecc773753327266\"]\nb1.plotly_data = []\nb1.display_shops()\nb1.show_position(scores_all_positions[\"5a0546857ecc773753327266\"][traj_id])\nb1.show_trajectory(positions_of_best_score[\"5a0546857ecc773753327266\"][traj_id], traj_id)\nb1.show()","execution_count":null,"outputs":[]}],"metadata":{"kernelspec":{"language":"python","display_name":"Python 3","name":"python3"},"language_info":{"pygments_lexer":"ipython3","nbconvert_exporter":"python","version":"3.6.4","file_extension":".py","codemirror_mode":{"name":"ipython","version":3},"name":"python","mimetype":"text/x-python"}},"nbformat":4,"nbformat_minor":4}