def sample_valid_questions(self, iterations=50): """Sample valid questions for the current scene content.""" current_graph = self.scene_graph all_q = [] for _ in range(iterations): new_graph = gs.randomly_perturb_objects(self.scene_struct, current_graph) self.scene_struct['objects'] = new_graph self.scene_struct['relationships'] = gs.compute_relationship( self.scene_struct) self._update_description() all_q += self.full_descriptions for q in all_q: for node in q['program']: if '_output' in node: del node['_output'] # get question that are unique and can be satisfied unique_and_feasible = {} for q in all_q: q_is_unique = repr(q['program']) not in unique_and_feasible if q['answer'] is True and q_is_unique: unique_and_feasible[repr(q['program'])] = q valid_q = [] for q in unique_and_feasible: valid_q.append((unique_and_feasible[q]['question'], unique_and_feasible[q]['program'])) self.scene_struct['objects'] = current_graph self.scene_struct['relationships'] = gs.compute_relationship( self.scene_struct) return valid_q
def _update_scene(self): """Update the scene description of the current scene.""" self.previous_scene_graph = self.scene_graph for i, name in enumerate(self.obj_name): self.scene_graph[i]['3d_coords'] = tuple(self.get_body_com(name)) self.scene_struct['objects'] = self.scene_graph self.scene_struct['relationships'] = gs.compute_relationship( self.scene_struct, use_polar=self.use_polar)
def reset(self, new_scene_content=True): """Reset with a random configuration.""" if new_scene_content or not self.variable_scene_content: # sample a random scene and struct self.scene_graph, self.scene_struct = self.sample_random_scene() else: # randomly perturb existing objects in the scene new_graph = gs.randomly_perturb_objects(self.scene_struct, self.scene_graph) self.scene_graph = new_graph self.scene_struct['objects'] = self.scene_graph self.scene_struct['relationships'] = gs.compute_relationship( self.scene_struct) # Generate initial set of description from the scene graph. self.descriptions, self.full_descriptions = None, None self._update_description() self.curr_step = 0 if not self.random_start: curr_scene_xml = convert_scene_to_xml( self.scene_graph, agent=self.agent_type, checker_board=self.checker_board) else: random_loc = '{} {} -0.2'.format(random.uniform(-0.6, 0.6), random.uniform(-0.3, 0.5)) curr_scene_xml = convert_scene_to_xml( self.scene_graph, agent=self.agent_type, agent_start_loc=random_loc, checker_board=self.checker_board) self.load_xml_string(curr_scene_xml) if self.variable_scene_content and self.cache_valid_questions and new_scene_content: self.valid_questions = self.sample_valid_questions(100) if len(self.valid_questions) < 5: print('rerunning reset because valid question count is small') return self.reset(True) self.current_goal_text, self.current_goal = self.sample_goal() self._update_object_description() return self.get_obs()