From 78f7c4b26a857918dbd9a468d6e4430dfec452a3 Mon Sep 17 00:00:00 2001 From: govin08 Date: Thu, 1 Aug 2024 10:09:20 +0900 Subject: [PATCH] tested throughly for twos scripts. --- .../generate_signals.cpython-312.pyc | Bin 69079 -> 70636 bytes Scripts/generate_signals.py | 78 ++- analysis/0725_main_test/6_use_class_gs.ipynb | 513 +++++++++++++++--- test_0731/results/issues_generate_signals.txt | 0 test_0731/results/sn_1722384300.add.xml | 36 +- 5 files changed, 520 insertions(+), 107 deletions(-) create mode 100644 test_0731/results/issues_generate_signals.txt diff --git a/Scripts/__pycache__/generate_signals.cpython-312.pyc b/Scripts/__pycache__/generate_signals.cpython-312.pyc index 1e39633eb689ac0afa90aca493eae09174728d1f..ac5155c952b1bac8190a28733bf79302ab6066a3 100644 GIT binary patch delta 5346 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 B;KTp` diff --git a/Scripts/generate_signals.py b/Scripts/generate_signals.py index ca2e85833..b9a26a25c 100644 --- a/Scripts/generate_signals.py +++ b/Scripts/generate_signals.py @@ -52,6 +52,7 @@ class SignalGenerator(): self.uturn_ids = ids['uturn_ids'] self.coord_ids = ids['coord_ids'] + # 1. 데이터 준비 def prepare_data(self): print("1. 데이터를 준비합니다.") @@ -66,11 +67,13 @@ class SignalGenerator(): self.prepare_auxiliaries() self.time15 = datetime.now() + # 1-1. 네트워크 불러오기 def load_networks(self): self.net = sumolib.net.readNet(os.path.join(self.path_networks, 'sn.net.xml')) print("1-1. 네트워크가 로드되었습니다.") + # 1-2. 테이블 불러오기 def load_tables(self): if self.config_name == 'draft': @@ -197,6 +200,7 @@ class SignalGenerator(): self.plan.at[i, f'dura_A{j}'] = row[f'dura_B{j}'] print("1-2. 테이블들이 로드되었습니다.") + # 1-3. 네트워크 무결성 검사 def check_networks(self): # https://sumo.dlr.de/docs/Netedit/neteditUsageExamples.html#simplify_tls_program_state_after_changing_connections @@ -218,6 +222,7 @@ class SignalGenerator(): traci.close() print("1-3. 네트워크의 모든 clean state requirement들을 체크했습니다.") + # 1-4. 테이블 무결성 검사 def check_tables(self): self.check_history() @@ -226,6 +231,7 @@ class SignalGenerator(): # self.check_moves() # 이동류번호에 대한 무결성검사 필요하나 아직 작성하지 않음. (24. 2. 5 화) print("1-4. 테이블들의 무결성 검사를 완료했습니다.") + # 1-4-1. 신호이력(history) 검사 def check_history(self): # 1-4-1-1. inter_no 검사 @@ -252,6 +258,7 @@ class SignalGenerator(): if invalid_inter_nos: msg = f"1-4-1-3. 음수이거나 200보다 큰 현시시간이 존재합니다. : {invalid_inter_nos}" + # 1-5. 보조 딕셔너리, 데이터프레임, 리스트 등 만들기 def prepare_auxiliaries(self): # inter2node : a dictionary that maps inter_no to the node_id @@ -346,7 +353,8 @@ class SignalGenerator(): self.time22 = datetime.now() self.make_hrhists() self.time23 = datetime.now() - + + # 2-1. rhistory def make_rhistory(self): # 1. 조회시점의 유닉스 타임 이전의 신호이력 수집 @@ -398,6 +406,7 @@ class SignalGenerator(): self.rhistory['start_unix'] = self.rhistory['start_unix'].astype(int) self.rhistory = self.rhistory[['inter_no', 'start_unix'] + [f'dura_{alph}{j}' for alph in ['A', 'B'] for j in range(1,9)] + ['cycle']] + def load_prow(self, inter_no, time): ''' load the planned row @@ -418,6 +427,7 @@ class SignalGenerator(): return program_start, prow + # 2-2. rhists def make_rhists(self): self.rhists = [] @@ -516,6 +526,7 @@ class SignalGenerator(): self.rhists = pd.concat(self.rhists)#.sort_values(by=['start_unix','inter_no']) self.rhists = self.rhists[self.rhists.start_unix >= self.present_time - self.subtractor // 2] + def calculate_DS(self, rhist, curr_unix): # program_starts = np.array(self.timetable.start_seconds) # idx = (program_starts <= self.present_time).sum() - 1 @@ -543,6 +554,7 @@ class SignalGenerator(): S_n = S_n_durs.values.sum() // 2 return D_n, S_n + # 2-3. hrhists def make_hrhists(self): # 계층화된 형태로 변환 @@ -578,6 +590,7 @@ class SignalGenerator(): self.hrhists['start_unix'] = self.hrhists['start_unix'].astype(int) # self.hrhists = self.hrhists.sort_values(by = ['start_unix', 'inter_no', 'phas_A', 'phas_B']).reset_index(drop=True) + # 3. 이동류정보 전처리 def process_movement(self): print("3. 이동류정보 테이블을 변환합니다.") @@ -586,6 +599,7 @@ class SignalGenerator(): self.update_movement() self.time32 = datetime.now() + # 3-1. movement def make_movement(self): if self.config_name == 'draft' or self.config_name == 'test_0721': @@ -628,21 +642,56 @@ class SignalGenerator(): self.movement = movement elif self.config_name == 'test_0731': - self.movement = pd.read_csv(os.path.join(self.path_tables, 'TL_IF_SIGL.csv')) - self.movement = self.movement.drop(columns=['FRST_REG_DT', 'RINGA_FLOW', 'RINGB_FLOW']) - self.movement = self.movement.rename(columns={ + phases = pd.read_csv(os.path.join(self.path_tables, 'TL_IF_SIGL.csv')) + phases = phases.drop(columns=['FRST_REG_DT', 'RINGA_FLOW', 'RINGB_FLOW']) + phases = phases.rename(columns={ 'PHASE_DT':'start_unix','CRSRD_ID':'inter_no', 'RINGA_PHASE':'phas_A', 'RINGB_PHASE':'phas_B', 'MAP_MODE':'STOS_NO' }) isp2move_A = self.isp2move['A'] isp2move_B = self.isp2move['B'] - self.movement['move_A'] = self.movement.apply( + phases['move_A'] = phases.apply( lambda row: int(isp2move_A.get((row.inter_no, row.STOS_NO, row.phas_A), -1)), axis=1) - self.movement['move_B'] = self.movement.apply( + phases['move_B'] = phases.apply( lambda row: int(isp2move_B.get((row.inter_no, row.STOS_NO, row.phas_B), -1)), axis=1) - self.movement['start_unix'] = pd.to_datetime(self.movement['start_unix']) - self.movement['start_unix'] = self.movement['start_unix'].apply(lambda x: int(x.timestamp())) + phases['start_unix'] = phases['start_unix'].apply(lambda x:int(datetime.strptime(x, '%Y-%m-%d %H:%M:%S').timestamp())) + + for fsec in range(self.present_time - self.sim_timespan, self.present_time + 1, 5): + # 1. 상태 테이블 조회해서 전체 데이터중 필요데이터(교차로번호, A링 현시번호, A링 이동류번호, B링 현시번호, B링 이동류번호)만 수집 : A + moves = [group.iloc[-1:] for _, group in phases[phases.start_unix < fsec].groupby('inter_no')] + if not moves: + move = pd.DataFrame({ + 'start_unix':[], 'inter_no':[], 'phas_A':[], 'phas_B':[], + 'STOS_NO':[], 'move_A':[], 'move_B':[]}) + else: + move = pd.concat(moves) + move = move.drop(columns='start_unix') + # 2. 이력 테이블 조회해서 교차로별로 유닉스시간 최대인 데이터(교차로번호, 종료유닉스타임)만 수집 : B + recent_histories = [group.iloc[-1:] for _, group in self.history[self.history['end_unix'] < fsec].groupby('inter_no')] # 교차로별로 유닉스시간이 최대인 행들 + + if not recent_histories: + rhistory = pd.DataFrame({'inter_no':[], 'end_unix':[]}) # recent history + else: + rhistory = pd.concat(recent_histories) + recent_unix = rhistory[['inter_no', 'end_unix']] + # 3. 상태 테이블 조회정보(A)와 이력 테이블 조회정보(B) 조인(키값 : 교차로번호) : C + move = pd.merge(move, recent_unix, how='left', on='inter_no') + move['end_unix'] = move['end_unix'].fillna(0).astype(int) + # # 4. C데이터 프레임에 신규 컬럼(시작 유닉스타임) 생성 후 종료유닉스 타임 값 입력, 종료 유닉스 타임 컬럼 제거 + move = move.rename(columns = {'end_unix':'start_unix'}) + # 5. 이동류 이력정보 READ + # - CSV 파일로 서버에 저장된 이동류정보를 읽어옴(파일이 없는 경우에는 데이터가 없는 프레임 D 생성) + try: # movement가 존재할 경우 그걸 그대로 씀. + self.movement + except AttributeError: # movement가 존재하지 않는 경우 생성 + self.movement = pd.DataFrame() + # 6. 이동류 이력정보 데이터테이블(D)에 C데이터 add + self.movement = pd.concat([self.movement, move]) + # 7. D데이터 프레임에서 중복데이터 제거(교차로번호, 시작 유닉스타임, A링 현시번호, B링 현시번호 같은 행은 제거) + self.movement = self.movement.drop_duplicates(['inter_no','phas_A','phas_B','start_unix']) + # 8. D데이터 보관 시간 기준시간을 시작 유닉스 타임의 최대값 - self.subtractor // 2을 값으로 산출하고, 보관 시간 기준시간보다 작은 시작 유닉스 타임을 가진 행은 모두 제거(1시간 데이터만 보관) + self.movement = self.movement[self.movement.start_unix > fsec - self.subtractor // 2] # 3-2. movement_updated @@ -670,6 +719,7 @@ class SignalGenerator(): else: self.movement_updated = self.movement + # 4. 통합테이블 생성 def make_histids(self): print("4. 통합 테이블을 생성합니다.") @@ -680,11 +730,13 @@ class SignalGenerator(): self.attach_children() self.time43 = datetime.now() + # 4-1. movedur : movements and durations def merge_dfs(self): self.movedur = pd.merge(self.hrhists, self.movement_updated, how='inner', on=['inter_no', 'start_unix', 'phas_A', 'phas_B']) self.movedur = self.movedur[['inter_no', 'start_unix', 'phas_A', 'phas_B', 'move_A', 'move_B', 'duration']] + # 4-2. histid def assign_signals(self): self.histid = self.movedur.copy() @@ -695,7 +747,6 @@ class SignalGenerator(): mapping_dict = self.matching.set_index(['node_id', 'move_no'])['state'].to_dict() # matching : 가능한 모든 (노드id, 이동류번호)에 대한 신호 * 시차제와 연관 有 - for i, row in self.histid.iterrows(): node_id = row.node_id move_A = row.move_A @@ -715,6 +766,7 @@ class SignalGenerator(): state_B = ''.join(self.node2init[node_id]) self.histid.at[i, 'state_B'] = state_B + # 4-3. histids def attach_children(self): new_histids = [] @@ -745,6 +797,7 @@ class SignalGenerator(): self.histids = self.histids.sort_values(by=['start_unix', 'node_id', 'phas_A', 'phas_B']).reset_index(drop=True) self.histids = self.histids[['inter_no', 'node_id', 'start_unix', 'phas_A', 'phas_B', 'move_A', 'move_B', 'duration', 'state_A', 'state_B']] + # 5. 신호 생성 def get_signals(self): print("5. 신호를 생성합니다.") @@ -755,6 +808,7 @@ class SignalGenerator(): self.make_tl_file() self.time53 = datetime.now() + # 5-1. 신호 파일의 시작 및 종료시각 설정 def set_timepoints(self): self.offsets = {} @@ -783,6 +837,7 @@ class SignalGenerator(): self.sigtable = pd.concat(self.sigtable).reset_index(drop=True) self.sigtable['phase_sumo'] = self.sigtable.groupby(['node_id', 'start_unix']).cumcount() + # 5-2. 적색 및 황색신호 부여 def assign_red_yellow(self): ''' @@ -847,6 +902,7 @@ class SignalGenerator(): self.SIGTABLE.append(SIG) self.SIGTABLE = pd.concat(self.SIGTABLE) + # 5-2-1 helper function of 5-2 def get_red(self, pre_state:str, cur_state:str): assert len(pre_state) == len(cur_state), "cur_state, nex_state의 길이가 서로 다릅니다." @@ -862,6 +918,7 @@ class SignalGenerator(): raise ValueError(f"예상치 못한 신호조합: previous={p}, current={c}") return state_r + # 5-2-2 helper function of 5-2 def get_yellow(self, cur_state:str, nex_state:str): assert len(cur_state) == len(nex_state), "cur_state, nex_state의 길이가 서로 다릅니다." @@ -879,6 +936,7 @@ class SignalGenerator(): raise ValueError(f"예상치 못한 신호조합: current={c}, next={n}") return state_y + # 5-2-3 helper function of 5-2 def cumulate(self, sig, alph): @@ -950,6 +1008,7 @@ class SignalGenerator(): csig = pd.concat(csig).reset_index(drop=True) return csig + # 5-3. 신호파일 생성 def make_tl_file(self): strings = ['\n'] @@ -967,6 +1026,7 @@ class SignalGenerator(): with open(self.path_output, 'w') as f: f.write(strings) + # 6. 이슈사항 저장 def write_issues(self): print('6. 이슈사항을 저장합니다.') diff --git a/analysis/0725_main_test/6_use_class_gs.ipynb b/analysis/0725_main_test/6_use_class_gs.ipynb index b61028cd2..8e9c84b07 100644 --- a/analysis/0725_main_test/6_use_class_gs.ipynb +++ b/analysis/0725_main_test/6_use_class_gs.ipynb @@ -53,6 +53,27 @@ "self.process_history()" ] }, + { + "cell_type": "code", + "execution_count": 4, + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "3. 이동류정보 테이블을 변환합니다.\n", + "4. 통합 테이블을 생성합니다.\n", + "5. 신호를 생성합니다.\n" + ] + } + ], + "source": [ + "self.process_movement()\n", + "self.make_histids()\n", + "self.get_signals()" + ] + }, { "cell_type": "code", "execution_count": 4, @@ -244,15 +265,6 @@ "phases" ] }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "self.history['end_unix'] = self.history['end_unix'].apply(lambda x:int(datetime.strptime(x, '%Y-%m-%d %H:%M:%S').timestamp()))\n" - ] - }, { "cell_type": "code", "execution_count": 5, @@ -264,7 +276,7 @@ }, { "cell_type": "code", - "execution_count": 26, + "execution_count": 6, "metadata": {}, "outputs": [ { @@ -287,70 +299,443 @@ "print(fsecs[-1])" ] }, - { - "cell_type": "code", - "execution_count": 6, - "metadata": {}, - "outputs": [], - "source": [ - "fsecs = list(range(self.present_time - self.sim_timespan, self.present_time + 1, 5))" - ] - }, { "cell_type": "code", "execution_count": 7, "metadata": {}, "outputs": [ { - "ename": "ValueError", - "evalue": "Cannot merge a Series without a name", - "output_type": "error", - "traceback": [ - "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m", - "\u001b[1;31mValueError\u001b[0m Traceback (most recent call last)", - "Cell \u001b[1;32mIn[7], line 20\u001b[0m\n\u001b[0;32m 18\u001b[0m recent_unix \u001b[38;5;241m=\u001b[39m rhistory[[\u001b[38;5;124m'\u001b[39m\u001b[38;5;124minter_no\u001b[39m\u001b[38;5;124m'\u001b[39m, \u001b[38;5;124m'\u001b[39m\u001b[38;5;124mend_unix\u001b[39m\u001b[38;5;124m'\u001b[39m]]\n\u001b[0;32m 19\u001b[0m \u001b[38;5;66;03m# 3. 상태 테이블 조회정보(A)와 이력 테이블 조회정보(B) 조인(키값 : 교차로번호) : C\u001b[39;00m\n\u001b[1;32m---> 20\u001b[0m move \u001b[38;5;241m=\u001b[39m \u001b[43mpd\u001b[49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43mmerge\u001b[49m\u001b[43m(\u001b[49m\u001b[43mmove\u001b[49m\u001b[43m,\u001b[49m\u001b[43m \u001b[49m\u001b[43mrecent_unix\u001b[49m\u001b[43m,\u001b[49m\u001b[43m \u001b[49m\u001b[43mhow\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[38;5;124;43m'\u001b[39;49m\u001b[38;5;124;43mleft\u001b[39;49m\u001b[38;5;124;43m'\u001b[39;49m\u001b[43m,\u001b[49m\u001b[43m \u001b[49m\u001b[43mon\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[38;5;124;43m'\u001b[39;49m\u001b[38;5;124;43minter_no\u001b[39;49m\u001b[38;5;124;43m'\u001b[39;49m\u001b[43m)\u001b[49m\n\u001b[0;32m 21\u001b[0m move[\u001b[38;5;124m'\u001b[39m\u001b[38;5;124mend_unix\u001b[39m\u001b[38;5;124m'\u001b[39m] \u001b[38;5;241m=\u001b[39m move[\u001b[38;5;124m'\u001b[39m\u001b[38;5;124mend_unix\u001b[39m\u001b[38;5;124m'\u001b[39m]\u001b[38;5;241m.\u001b[39mfillna(\u001b[38;5;241m0\u001b[39m)\u001b[38;5;241m.\u001b[39mastype(\u001b[38;5;28mint\u001b[39m)\n\u001b[0;32m 22\u001b[0m \u001b[38;5;66;03m# # 4. C데이터 프레임에 신규 컬럼(시작 유닉스타임) 생성 후 종료유닉스 타임 값 입력, 종료 유닉스 타임 컬럼 제거\u001b[39;00m\n", - "File \u001b[1;32mc:\\github\\siggen\\siggen_env\\Lib\\site-packages\\pandas\\core\\reshape\\merge.py:152\u001b[0m, in \u001b[0;36mmerge\u001b[1;34m(left, right, how, on, left_on, right_on, left_index, right_index, sort, suffixes, copy, indicator, validate)\u001b[0m\n\u001b[0;32m 135\u001b[0m \u001b[38;5;129m@Substitution\u001b[39m(\u001b[38;5;124m\"\u001b[39m\u001b[38;5;130;01m\\n\u001b[39;00m\u001b[38;5;124mleft : DataFrame or named Series\u001b[39m\u001b[38;5;124m\"\u001b[39m)\n\u001b[0;32m 136\u001b[0m \u001b[38;5;129m@Appender\u001b[39m(_merge_doc, indents\u001b[38;5;241m=\u001b[39m\u001b[38;5;241m0\u001b[39m)\n\u001b[0;32m 137\u001b[0m \u001b[38;5;28;01mdef\u001b[39;00m \u001b[38;5;21mmerge\u001b[39m(\n\u001b[1;32m (...)\u001b[0m\n\u001b[0;32m 150\u001b[0m validate: \u001b[38;5;28mstr\u001b[39m \u001b[38;5;241m|\u001b[39m \u001b[38;5;28;01mNone\u001b[39;00m \u001b[38;5;241m=\u001b[39m \u001b[38;5;28;01mNone\u001b[39;00m,\n\u001b[0;32m 151\u001b[0m ) \u001b[38;5;241m-\u001b[39m\u001b[38;5;241m>\u001b[39m DataFrame:\n\u001b[1;32m--> 152\u001b[0m left_df \u001b[38;5;241m=\u001b[39m \u001b[43m_validate_operand\u001b[49m\u001b[43m(\u001b[49m\u001b[43mleft\u001b[49m\u001b[43m)\u001b[49m\n\u001b[0;32m 153\u001b[0m right_df \u001b[38;5;241m=\u001b[39m _validate_operand(right)\n\u001b[0;32m 154\u001b[0m \u001b[38;5;28;01mif\u001b[39;00m how \u001b[38;5;241m==\u001b[39m \u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mcross\u001b[39m\u001b[38;5;124m\"\u001b[39m:\n", - "File \u001b[1;32mc:\\github\\siggen\\siggen_env\\Lib\\site-packages\\pandas\\core\\reshape\\merge.py:2689\u001b[0m, in \u001b[0;36m_validate_operand\u001b[1;34m(obj)\u001b[0m\n\u001b[0;32m 2687\u001b[0m \u001b[38;5;28;01melif\u001b[39;00m \u001b[38;5;28misinstance\u001b[39m(obj, ABCSeries):\n\u001b[0;32m 2688\u001b[0m \u001b[38;5;28;01mif\u001b[39;00m obj\u001b[38;5;241m.\u001b[39mname \u001b[38;5;129;01mis\u001b[39;00m \u001b[38;5;28;01mNone\u001b[39;00m:\n\u001b[1;32m-> 2689\u001b[0m \u001b[38;5;28;01mraise\u001b[39;00m \u001b[38;5;167;01mValueError\u001b[39;00m(\u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mCannot merge a Series without a name\u001b[39m\u001b[38;5;124m\"\u001b[39m)\n\u001b[0;32m 2690\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m obj\u001b[38;5;241m.\u001b[39mto_frame()\n\u001b[0;32m 2691\u001b[0m \u001b[38;5;28;01melse\u001b[39;00m:\n", - "\u001b[1;31mValueError\u001b[0m: Cannot merge a Series without a name" - ] + "data": { + "text/html": [ + "
\n", + "\n", + "\n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + " \n", + "
inter_nophas_Aphas_BSTOS_NOmove_Amove_Bstart_unix
6455110621722383976
7456220621722383967
1437110621722384007
74563307-11722383967
745644017-11722383967
6455220-1-11722383976
8457110621722384053
7456110521722383967
1437220511722384007
3442110611722384098
8457220511722384053
4443110621722384102
1437330831722384007
845733017171722384053
3442220621722384098
1437440741722384007
3442330521722384098
8457440831722384053
3442440741722384098
8457550741722384053
1437110621722384207
4443220521722384102
8457110621722384232
0436110521722384236
3442550831722384098
44433307181722384102
8457220511722384232
1437220511722384207
3442660831722384098
0436220831722384236
3442110611722384297
845733017171722384232
\n", + "
" + ], + "text/plain": [ + " inter_no phas_A phas_B STOS_NO move_A move_B start_unix\n", + "6 455 1 1 0 6 2 1722383976\n", + "7 456 2 2 0 6 2 1722383967\n", + "1 437 1 1 0 6 2 1722384007\n", + "7 456 3 3 0 7 -1 1722383967\n", + "7 456 4 4 0 17 -1 1722383967\n", + "6 455 2 2 0 -1 -1 1722383976\n", + "8 457 1 1 0 6 2 1722384053\n", + "7 456 1 1 0 5 2 1722383967\n", + "1 437 2 2 0 5 1 1722384007\n", + "3 442 1 1 0 6 1 1722384098\n", + "8 457 2 2 0 5 1 1722384053\n", + "4 443 1 1 0 6 2 1722384102\n", + "1 437 3 3 0 8 3 1722384007\n", + "8 457 3 3 0 17 17 1722384053\n", + "3 442 2 2 0 6 2 1722384098\n", + "1 437 4 4 0 7 4 1722384007\n", + "3 442 3 3 0 5 2 1722384098\n", + "8 457 4 4 0 8 3 1722384053\n", + "3 442 4 4 0 7 4 1722384098\n", + "8 457 5 5 0 7 4 1722384053\n", + "1 437 1 1 0 6 2 1722384207\n", + "4 443 2 2 0 5 2 1722384102\n", + "8 457 1 1 0 6 2 1722384232\n", + "0 436 1 1 0 5 2 1722384236\n", + "3 442 5 5 0 8 3 1722384098\n", + "4 443 3 3 0 7 18 1722384102\n", + "8 457 2 2 0 5 1 1722384232\n", + "1 437 2 2 0 5 1 1722384207\n", + "3 442 6 6 0 8 3 1722384098\n", + "0 436 2 2 0 8 3 1722384236\n", + "3 442 1 1 0 6 1 1722384297\n", + "8 457 3 3 0 17 17 1722384232" + ] + }, + "execution_count": 7, + "metadata": {}, + "output_type": "execute_result" } ], "source": [ - "fsec = fsecs[5]\n", - "# 1. 상태 테이블 조회해서 전체 데이터중 필요데이터(교차로번호, A링 현시번호, A링 이동류번호, B링 현시번호, B링 이동류번호)만 수집 : A\n", - "moves = [group.iloc[-1] for _, group in phases[phases.start_unix < fsec].groupby('inter_no')]\n", - "if not moves:\n", - " move = pd.DataFrame({\n", - " 'start_unix':[], 'inter_no':[], 'phas_A':[], 'phas_B':[],\n", - " 'STOS_NO':[], 'move_A':[], 'move_B':[]})\n", - "else:\n", - " move = pd.concat(moves)\n", - "move = move.drop(columns='start_unix')\n", - "# 2. 이력 테이블 조회해서 교차로별로 유닉스시간 최대인 데이터(교차로번호, 종료유닉스타임)만 수집 : B\n", - "recent_histories = [group.iloc[-1:] for _, group in self.history[self.history['end_unix'] < fsec].groupby('inter_no')] # 교차로별로 유닉스시간이 최대인 행들\n", + "for fsec in range(self.present_time - self.sim_timespan, self.present_time + 1, 5):\n", + " # 1. 상태 테이블 조회해서 전체 데이터중 필요데이터(교차로번호, A링 현시번호, A링 이동류번호, B링 현시번호, B링 이동류번호)만 수집 : A\n", + " moves = [group.iloc[-1:] for _, group in phases[phases.start_unix < fsec].groupby('inter_no')]\n", + " if not moves:\n", + " move = pd.DataFrame({\n", + " 'start_unix':[], 'inter_no':[], 'phas_A':[], 'phas_B':[],\n", + " 'STOS_NO':[], 'move_A':[], 'move_B':[]})\n", + " else:\n", + " move = pd.concat(moves)\n", + " move = move.drop(columns='start_unix')\n", + " # 2. 이력 테이블 조회해서 교차로별로 유닉스시간 최대인 데이터(교차로번호, 종료유닉스타임)만 수집 : B\n", + " recent_histories = [group.iloc[-1:] for _, group in self.history[self.history['end_unix'] < fsec].groupby('inter_no')] # 교차로별로 유닉스시간이 최대인 행들\n", "\n", - "if not recent_histories:\n", - " rhistory = pd.DataFrame({'inter_no':[], 'end_unix':[]}) # recent history\n", - "else:\n", - " rhistory = pd.concat(recent_histories)\n", - "recent_unix = rhistory[['inter_no', 'end_unix']]\n", - "# 3. 상태 테이블 조회정보(A)와 이력 테이블 조회정보(B) 조인(키값 : 교차로번호) : C\n", - "move = pd.merge(move, recent_unix, how='left', on='inter_no')\n", - "move['end_unix'] = move['end_unix'].fillna(0).astype(int)\n", - "# # 4. C데이터 프레임에 신규 컬럼(시작 유닉스타임) 생성 후 종료유닉스 타임 값 입력, 종료 유닉스 타임 컬럼 제거\n", - "move = move.rename(columns = {'end_unix':'start_unix'})\n", - "# 5. 이동류 이력정보 READ\n", - "# - CSV 파일로 서버에 저장된 이동류정보를 읽어옴(파일이 없는 경우에는 데이터가 없는 프레임 D 생성)\n", - "try:\n", - " movement # movement가 존재할 경우 그걸 그대로 씀.\n", - "except NameError: # movement가 존재하지 않는 경우 생성\n", - " movement = pd.DataFrame()\n", - "# 6. 이동류 이력정보 데이터테이블(D)에 C데이터 add\n", - "movement = pd.concat([movement, move])\n", - "# 7. D데이터 프레임에서 중복데이터 제거(교차로번호, 시작 유닉스타임, A링 현시번호, B링 현시번호 같은 행은 제거)\n", - "movement = movement.drop_duplicates(['inter_no','phas_A','phas_B','start_unix'])\n", - "# 8. D데이터 보관 시간 기준시간을 시작 유닉스 타임의 최대값 - self.subtractor // 2을 값으로 산출하고, 보관 시간 기준시간보다 작은 시작 유닉스 타임을 가진 행은 모두 제거(1시간 데이터만 보관)\n", - "movement = movement[movement.start_unix > fsec - self.subtractor // 2]\n", + " if not recent_histories:\n", + " rhistory = pd.DataFrame({'inter_no':[], 'end_unix':[]}) # recent history\n", + " else:\n", + " rhistory = pd.concat(recent_histories)\n", + " recent_unix = rhistory[['inter_no', 'end_unix']]\n", + " # 3. 상태 테이블 조회정보(A)와 이력 테이블 조회정보(B) 조인(키값 : 교차로번호) : C\n", + " move = pd.merge(move, recent_unix, how='left', on='inter_no')\n", + " move['end_unix'] = move['end_unix'].fillna(0).astype(int)\n", + " # # 4. C데이터 프레임에 신규 컬럼(시작 유닉스타임) 생성 후 종료유닉스 타임 값 입력, 종료 유닉스 타임 컬럼 제거\n", + " move = move.rename(columns = {'end_unix':'start_unix'})\n", + " # 5. 이동류 이력정보 READ\n", + " # - CSV 파일로 서버에 저장된 이동류정보를 읽어옴(파일이 없는 경우에는 데이터가 없는 프레임 D 생성)\n", + " try:\n", + " movement # movement가 존재할 경우 그걸 그대로 씀.\n", + " except NameError: # movement가 존재하지 않는 경우 생성\n", + " movement = pd.DataFrame()\n", + " # 6. 이동류 이력정보 데이터테이블(D)에 C데이터 add\n", + " movement = pd.concat([movement, move])\n", + " # 7. D데이터 프레임에서 중복데이터 제거(교차로번호, 시작 유닉스타임, A링 현시번호, B링 현시번호 같은 행은 제거)\n", + " movement = movement.drop_duplicates(['inter_no','phas_A','phas_B','start_unix'])\n", + " # 8. D데이터 보관 시간 기준시간을 시작 유닉스 타임의 최대값 - self.subtractor // 2을 값으로 산출하고, 보관 시간 기준시간보다 작은 시작 유닉스 타임을 가진 행은 모두 제거(1시간 데이터만 보관)\n", + " movement = movement[movement.start_unix > fsec - self.subtractor // 2]\n", "movement\n" ] }, diff --git a/test_0731/results/issues_generate_signals.txt b/test_0731/results/issues_generate_signals.txt new file mode 100644 index 000000000..e69de29bb diff --git a/test_0731/results/sn_1722384300.add.xml b/test_0731/results/sn_1722384300.add.xml index 3130f9cb6..48b05fc06 100644 --- a/test_0731/results/sn_1722384300.add.xml +++ b/test_0731/results/sn_1722384300.add.xml @@ -62,10 +62,6 @@ - - - - @@ -91,16 +87,6 @@ - - - - - - - - - - @@ -197,10 +183,6 @@ - - - - @@ -226,10 +208,6 @@ - - - - @@ -276,10 +254,6 @@ - - - - @@ -288,14 +262,8 @@ - - - - - - - - + +