def rec(state, depth, stack_size):
        if clock() - start > time_limit:
            return
        
        s = state.get_score_abort()
        
        if depth <= 0 or stack_size <= 0:
            check(s)
            return

        preprocessed = preprocess_world(state)
        
        if upper_bound(preprocessed)-state.time <= best.score:
            return
        
        aggressive_preprocess(preprocessed)

        frozen_state = preprocessed.get_hash()
        old_score = visited.get(frozen_state)
        if old_score is not None and s <= old_score:
            return
        
        visited[frozen_state] = s
        
        check(s)
        
        zzz = 'LRUDW'
        num_commands = len(commands)
        next_steps = set()
        
        greedy = path_to_nearest_lambda_or_lift(state)
        if greedy is not None:
            greedy = [greedy[1]]
        else:
            greedy = []
            
        #greedy = []
        
        for cmds in chain(greedy, product(zzz, zzz)):
            new_state = state
            for cmd in cmds:
                if new_state.final_score is None:
                    new_state = new_state.apply_command(cmd)
                commands.append(cmd)
            
            if new_state.final_score is None:
                h = new_state.get_hash()
                if h not in next_steps:
                    next_steps.add(h)
                    if cmds in greedy:
                        new_depth = depth
                    else:
                        new_depth = depth-1
                    rec(new_state, new_depth, stack_size-1)
            else:
                check(new_state.final_score)
                
            for _ in cmds:
                commands.pop()
        assert num_commands == len(commands)
示例#2
0
    def get_ub_and_cache_entry(self, world):
        '''
        return upper bound and CacheEntry;
        
        given world is raw (not even preprocessed);
        calls are cached
        '''
        assert not world.terminated
        
        raw_hash = world.get_hash()
        result = self.ub_ce_cache.get(raw_hash)
        if result is not None:
            self.stats['ub ce hit'] += 1
            ub, cache_entry = result
            return ub-world.time, cache_entry

        self.check_stop()

        preprocessed = preprocess_world(world)
        self.stats['preprocess'] += 1
        
        ub = upper_bound(preprocessed)
        
        aggressive_preprocess(preprocessed) #inplace
        
        key = preprocessed.get_hash()
        cache_entry = self.cache.get(key)
        if cache_entry is None:
            cache_entry = self.cache[key] = CacheEntry()
            cache_entry.time = 100000000
            cache_entry.command = None
            
        self.ub_ce_cache[raw_hash] = ub, cache_entry
        return ub-world.time, cache_entry