def _walk(self, actions: Dict, prod_score_dic: Dict, world: WikiTablesVariableFreeWorld) -> List: """ search in the action space without data selection operations like lookup. the operations used reflect the semantics of a question, it is more abstract and the space would be much smaller """ # Buffer of NTs to expand, previous actions incomplete_paths = [([str(type_)], [f"{START_SYMBOL} -> {type_}"], prod_score_dic[f"{START_SYMBOL} -> {type_}"]) for type_ in world.get_valid_starting_types()] _completed_paths = [] multi_match_substitutions = world.get_multi_match_mapping() while incomplete_paths: next_paths = [] for nonterminal_buffer, history, cur_score in incomplete_paths: # Taking the last non-terminal added to the buffer. We're going depth-first. nonterminal = nonterminal_buffer.pop() next_actions = [] if nonterminal in multi_match_substitutions: for current_nonterminal in [ nonterminal ] + multi_match_substitutions[nonterminal]: if current_nonterminal in actions: next_actions.extend(actions[current_nonterminal]) elif nonterminal not in actions: continue else: next_actions.extend(actions[nonterminal]) # Iterating over all possible next actions. for action in next_actions: if action not in [ "e -> mul_row_select", "r -> one_row_select" ] and action in history: continue new_history = history + [action] new_nonterminal_buffer = nonterminal_buffer[:] # Since we expand the last action added to the buffer, the left child should be # added after the right child. for right_side_part in reversed( self._get_right_side_parts(action)): if types.is_nonterminal(right_side_part): new_nonterminal_buffer.append(right_side_part) new_prod_score = prod_score_dic[action] + cur_score next_paths.append( (new_nonterminal_buffer, new_history, new_prod_score)) incomplete_paths = [] for nonterminal_buffer, path, score in next_paths: # An empty buffer means that we've completed this path. if not nonterminal_buffer: # if path only has two operations, it is start->string: if len(path) > 2: _completed_paths.append((path, score)) elif len(path) < self._max_path_length: incomplete_paths.append((nonterminal_buffer, path, score)) return _completed_paths
def _walk(self, non_terminal: str, actions: List, prod_score_dic: Dict, world: WikiTablesVariableFreeWorld) -> None: incomplete_paths = [([non_terminal], [f"#S# -> {non_terminal}"], None)] _completed_paths = [] multi_match_substitutions = world.get_multi_match_mapping() while incomplete_paths: next_paths = [] for nonterminal_buffer, history, cur_score in incomplete_paths: # Taking the last non-terminal added to the buffer. We're going depth-first. nonterminal = nonterminal_buffer.pop() next_actions = [] if nonterminal in multi_match_substitutions: for current_nonterminal in [ nonterminal ] + multi_match_substitutions[nonterminal]: if current_nonterminal in actions: next_actions.extend(actions[current_nonterminal]) elif nonterminal not in actions: continue else: next_actions.extend(actions[nonterminal]) # Iterating over all possible next actions. for action in next_actions: if action in history: continue new_history = history + [action] new_nonterminal_buffer = nonterminal_buffer[:] # Since we expand the last action added to the buffer, the left child should be # added after the right child. for right_side_part in reversed( self._get_right_side_parts(action)): if types.is_nonterminal(right_side_part): new_nonterminal_buffer.append(right_side_part) if cur_score is None: new_prod_score = prod_score_dic[action] else: new_prod_score = prod_score_dic[action] + cur_score next_paths.append( (new_nonterminal_buffer, new_history, new_prod_score)) incomplete_paths = [] for nonterminal_buffer, path, score in next_paths: # An empty buffer means that we've completed this path. if not nonterminal_buffer: _completed_paths.append((path, score)) elif len(path) < 6: #TODO: set this incomplete_paths.append((nonterminal_buffer, path, score)) strip_path = [] for path, score in _completed_paths: strip_path.append((path[1:], score)) # the first node is faked return strip_path