def test_add_ctx_normal(self): experiments_path = os.path.dirname(os.getcwd()) + "/experiments/" A = buildOTA(experiments_path + 'example3.json', 's') AA = buildAssistantOTA(A, 's') sigma = AA.sigma max_time_value = AA.max_time_value() H = buildOTA(experiments_path + 'example3_1.json', 'q') HH = buildAssistantOTA(H, 'q') # AA.show() # print("------------------------------") # HH.show() # print("------------------------------") # H.show() flag, ctx = equivalence_query_normal(max_time_value, AA, HH) # print("-------------ctx-----------------") # print(ctx.tws) ctxs = guess_ctx_reset(ctx.tws, AA) # print(len(ctxs)) # for rtws in ctxs: # print(rtws) # print("-------------local tws-----------------") for ctx in ctxs: local_tws = dRTWs_to_lRTWs(ctx) normalize(local_tws) # #if check_guessed_reset(local_tws, table) == True: # print(ctx) # print(local_tws) # pref = prefixes(local_tws) # for tws in pref: # print(tws) # print("-------------------") T1_tables = init_table_normal(sigma, AA) T1_table_0 = T1_tables[0] test_E = [[Timedword('b', 2), Timedword('a', 4)], [Timedword('a', 5)]] T1_table_0.E = test_E # T1_table_0.show() # print("----------------------------------------") # tables = add_ctx_normal(ctx, T1_table_0, AA) #self.assertEqual(len(tables),65536) # tables[0].show() # tables[1].show() # tables[2].show() # tables[100].show() # tables[4095].show() # for table in tables: # table.show() # print("---------------------") T1_tables = init_table_normal(sigma, AA) T1_table_0 = T1_tables[0] test_E = [[Timedword('b', 2), Timedword('a', 4)]] T1_table_0.E = test_E # T1_table_0.show() # print("----------------------------------------") tables = add_ctx_normal(ctx, T1_table_0, AA) self.assertEqual(len(tables), 128)
def rec(current_table): """If solution is found, return target. Else, return None.""" nonlocal t_number t_number += 1 cur_depth = current_table.effective_len() if t_number % 10 == 0: print(t_number, cur_depth) if cur_depth > depth: return None # First check if the table is closed flag_closed, new_S, new_R, move = current_table.is_closed() if not flag_closed: temp_tables = make_closed(new_S, new_R, move, current_table, sigma, AA) for table in temp_tables: target = rec(table) if target is not None: return target return None # If is closed, check if the table is consistent flag_consistent, new_a, new_e_index, reset_index_i, reset_index_j, reset_i, reset_j = current_table.is_consistent() if not flag_consistent: temp_tables = make_consistent(new_a, new_e_index, reset_index_i, reset_index_j, reset_i, reset_j, current_table, sigma, AA) for table in temp_tables: target = rec(table) if target is not None: return target return None # If prepared, check conversion to FA fa_flag, fa, sink_name = to_fa(current_table, t_number) if not fa_flag: return None # Can convert to FA: convert to OTA and test equivalence h = fa_to_ota(fa, sink_name, sigma, t_number) equivalent, ctx = equivalence_query_normal(max_time_value, AA, h, prev_ctx) # Add counterexample to prev list if not equivalent and ctx not in prev_ctx: prev_ctx.append(ctx) if not equivalent: temp_tables = add_ctx_normal(ctx.tws, current_table, AA) for table in temp_tables: target = rec(table) if target is not None: return target return None else: target = copy.deepcopy(h) return target
def single_search(): """Single path search: at each step, pick a random successor.""" nonlocal round_num init_tables = init_table_normal(sigma, AA) current_table = random.choice(init_tables) # Current hypothesis cur_h = None while True: round_num += 1 current_table = random_steps(current_table, 15, cur_h, comparator=False) if current_table == 'failed': return None if current_table.effective_len() >= 15: return None print('ctx test:', current_table.effective_len()) # If prepared, check conversion to FA fa_flag, fa, sink_name = to_fa(current_table, t_number) if not fa_flag: return None # Can convert to FA: convert to OTA and test equivalence cur_h = fa_to_ota(fa, sink_name, sigma, t_number) # equivalent, ctx = equivalence_query_normal(max_time_value, AA, cur_h, prev_ctx) equivalent, ctx, _ = pac_equivalence_query(A, max_time_value, AA, cur_h, round_num, 0.001, 0.001) if ctx: print(ctx.tws) # Add counterexample to prev list if not equivalent and ctx not in prev_ctx: prev_ctx.append(ctx) if not equivalent: temp_tables = add_ctx_normal(ctx.tws, current_table, AA) if len(temp_tables) > 0: current_table = random.choice(temp_tables) else: return None else: return current_table, cur_h
def random_steps(current_table, max_len, cur_h, comparator=True): """Execute random_one_step until reaching a candidate. Here a candidate means a prepared table that agrees with teacher on all existing counterexamples. """ nonlocal t_number while current_table.effective_len() < max_len: res = random_one_step(current_table) if res == 'failed': return 'failed' elif res == 'candidate': # Find shortest difference if cur_h is None or not comparator: return current_table else: t_number += 1 fa_flag, fa, sink_name = to_fa(current_table, t_number) if not fa_flag: return 'failed' h = fa_to_ota(fa, sink_name, sigma, t_number) equivalent, ctx = equivalence_query_normal( max_time_value, cur_h, h, None) assert not equivalent realValue = AA.is_accepted_delay(ctx.tws) value = h.is_accepted_delay(ctx.tws) if (realValue == 1 and value != 1) or (realValue != 1 and value == 1): temp_tables = add_ctx_normal(ctx.tws, current_table, AA) if len(temp_tables) > 0: current_table = random.choice(temp_tables) else: return 'failed' else: return current_table else: current_table = res return 'failed'
def random_one_step(current_table): """Find a random successor of the current table. Here a successor is defined to be the table after executing one make_closed, one make_consistent, or one add_ctx_normal on existing counterexamples. """ nonlocal t_number # First check if the table is closed flag_closed, new_S, new_R, move = current_table.is_closed() if not flag_closed: if debug_flag: print( "------------------make closed--------------------------") temp_tables = make_closed(new_S, new_R, move, current_table, sigma, AA) if len(temp_tables) > 0: return random.choice(temp_tables) else: return 'failed' # If is closed, check if the table is consistent flag_consistent, new_a, new_e_index, reset_index_i, reset_index_j, reset_i, reset_j = current_table.is_consistent( ) if not flag_consistent: if debug_flag: print( "------------------make consistent--------------------------" ) temp_tables = make_consistent(new_a, new_e_index, reset_index_i, reset_index_j, reset_i, reset_j, current_table, sigma, AA) if len(temp_tables) > 0: return random.choice(temp_tables) else: return 'failed' # If prepared, check conversion to FA t_number += 1 fa_flag, fa, sink_name = to_fa(current_table, t_number) if not fa_flag: return 'failed' # Can convert to FA: convert to OTA and test equivalence h = fa_to_ota(fa, sink_name, sigma, t_number) equivalent, ctx = True, None if prev_ctx is not None: for ctx in prev_ctx: teacher_res = AA.is_accepted_delay(ctx.tws) hypothesis_res = h.is_accepted_delay(ctx.tws) if teacher_res != hypothesis_res and hypothesis_res != -2: equivalent, ctx = False, ctx if equivalent: # If equivalent, the current table is a candidate return 'candidate' else: # Otherwise, add counterexample temp_tables = add_ctx_normal(ctx.tws, current_table, AA) if len(temp_tables) > 0: return random.choice(temp_tables) else: return 'failed'
def parallel_search(): """Parallel search. Maintain a list of current tables (of size width). At each iteration, pick a number of random successors (of size expand_factor) to form the new list of tables. Sort the new list and pick the best 'width' tables for the next iteration. """ nonlocal round_num, t_number init_tables = init_table_normal(sigma, AA) width = 15 expand_factor = 2 tables = [] for i in range(width): tables.append(random.choice(init_tables)) while round_num < 10: round_num += 1 print(round_num) new_tables = [] for i in range(min(len(tables), width)): for j in range(expand_factor): if round_num == 1: current_table, cur_h = tables[i], None else: current_table, cur_h, ctx = tables[i] temp_tables = add_ctx_normal(ctx.tws, current_table, AA) if len(temp_tables) > 0: current_table = random.choice(temp_tables) else: continue current_table = random_steps(current_table, 20, cur_h, comparator=False) if current_table == 'failed': continue if current_table.effective_len() >= 20: continue # If prepared, check conversion to FA t_number += 1 fa_flag, fa, sink_name = to_fa(current_table, t_number) if not fa_flag: continue # Can convert to FA: convert to OTA and test equivalence cur_h = fa_to_ota(fa, sink_name, sigma, t_number) equivalent, ctx, sc = pac_equivalence_query( A, max_time_value, AA, cur_h, round_num, 0.001, 0.001) if not equivalent: new_tables.append( (sc, current_table, copy.deepcopy(cur_h), ctx)) else: return current_table, cur_h new_tables = sorted(new_tables, reverse=True) tables = [] for sc, table, cur_h, ctx in new_tables: print(sc, table.effective_len()) tables.append((table, cur_h, ctx)) if len(tables) >= width: break return None
def learn_ota(paras, debug_flag): A = buildOTA(paras, 's') AA = buildAssistantOTA(A, 's') max_time_value = A.max_time_value() print("**************Start to learn ...*******************") print("---------------initial table-------------------") sigma = AA.sigma need_to_explore = queue.PriorityQueue() for table in init_table_normal(sigma, AA): need_to_explore.put((table.effective_len(), table)) # List of existing counterexamples prev_ctx = [] # Current number of tables t_number = 0 start = time.time() eq_total_time = 0 eq_number = 0 target = None while True: if need_to_explore.qsize() == 0: break depth, current_table = need_to_explore.get() t_number = t_number + 1 if t_number % 1 == 0: print(t_number, need_to_explore.qsize(), current_table.effective_len()) if debug_flag: print("Table " + str(t_number) + " is as follow, %s has parent %s by %s" % (current_table.id, current_table.parent, current_table.reason)) current_table.show() print("--------------------------------------------------") # First check if the table is closed flag_closed, new_S, new_R, move = current_table.is_closed() if not flag_closed: if debug_flag: print("------------------make closed--------------------------") temp_tables = make_closed(new_S, new_R, move, current_table, sigma, AA) if len(temp_tables) > 0: for table in temp_tables: need_to_explore.put((table.effective_len(), table)) continue # If is closed, check if the table is consistent flag_consistent, new_a, new_e_index, reset_index_i, reset_index_j, reset_i, reset_j = current_table.is_consistent() if not flag_consistent: if debug_flag: print("------------------make consistent--------------------------") temp_tables = make_consistent(new_a, new_e_index, reset_index_i, reset_index_j, reset_i, reset_j, current_table, sigma, AA) if len(temp_tables) > 0: for table in temp_tables: need_to_explore.put((table.effective_len(), table)) continue # If prepared, check conversion to FA fa_flag, fa, sink_name = to_fa(current_table, t_number) if not fa_flag: continue # Can convert to FA: convert to OTA and test equivalence h = fa_to_ota(fa, sink_name, sigma, t_number) eq_start = time.time() # equivalent, ctx = equivalence_query_normal(max_time_value, AA, h, prev_ctx) equivalent, ctx = True, None if prev_ctx is not None: for ctx in prev_ctx: teacher_res = AA.is_accepted_delay(ctx.tws) hypothesis_res = h.is_accepted_delay(ctx.tws) if teacher_res != hypothesis_res and hypothesis_res != -2: equivalent, ctx = False, ctx ctx = minimizeCounterexample(AA, h, ctx) if equivalent: AA.equiv_query_num += 1 equivalent, ctx, _ = pac_equivalence_query(A, max_time_value, AA, h, AA.equiv_query_num, 0.001, 0.001) if not equivalent: # remove_sinklocation(copy.deepcopy(h)).show() print(ctx.tws) # print(ratio) # Add counterexample to prev list if not equivalent and ctx not in prev_ctx: prev_ctx.append(ctx) eq_end = time.time() eq_total_time = eq_total_time + eq_end - eq_start eq_number = eq_number + 1 if not equivalent: temp_tables = add_ctx_normal(ctx.tws, current_table, AA) if len(temp_tables) > 0: for table in temp_tables: need_to_explore.put((table.effective_len(), table)) else: target = copy.deepcopy(h) break end_learning = time.time() if target is None: print("---------------------------------------------------") print("Error! Learning Failed.") print("*******************Failed.***********************") return False else: print("---------------------------------------------------") print("Succeed! The learned OTA is as follows.") print("-------------Final table instance------------------") current_table.show() print("---------------Learned OTA-------------------------") target.show() print("---------------------------------------------------") print("Removing the sink location...") print() print("The learned One-clock Timed Automtaton: ") print() target_without_sink = remove_sinklocation(target) end_removesink = time.time() target_without_sink.show() print("---------------------------------------------------") print("Number of transitions in teacher: " + str(len(A.trans))) print("Total number of membership query: " + str(len(AA.membership_query))) # print("Total number of membership query (no-cache): " + str(AA.mem_query_num)) # print("Total number of equivalence query: " + str(len(prev_ctx) + 1)) print("Total number of equivalence query (no-cache): " + str(AA.equiv_query_num)) print("Total number of tests: " + str(AA.test_query_num)) print("Total number of tables explored: " + str(t_number)) # print("Total number of tables to explore: " + str(need_to_explore.qsize())) print("Number of locations in learned table: " + str(len(target_without_sink.locations))) print("Total time of learning: " + str(end_learning-start)) return target_without_sink