def observe(self): obs_arr = [] # load on each server for server in self.servers: # queuing work load = sum(j.size for j in server.queue) if server.curr_job is not None: # remaining work currently being processed load += server.curr_job.finish_time - self.wall_time.curr_time # if the load is larger than observation threshold # report a warning if load > self.obs_high[server.server_id]: logger.warn('Server ' + str(server.server_id) + ' at time ' + str(self.wall_time.curr_time) + ' has load ' + str(load) + ' larger than obs_high ' + str(self.obs_high[server.server_id])) load = self.obs_high[server.server_id] obs_arr.append(load) # incoming job size if self.incoming_job is None: obs_arr.append(0) else: if self.incoming_job.size > self.obs_high[-1]: logger.warn('Incoming job at time ' + str(self.wall_time.curr_time) + ' has size ' + str(self.incoming_job.size) + ' larger than obs_high ' + str(self.obs_high[-1])) obs_arr.append(self.obs_high[-1]) else: obs_arr.append(self.incoming_job.size) obs_arr = np.array(obs_arr) assert self.observation_space.contains(obs_arr) return obs_arr
def step(self, action): # action is a permutation of identity matrix assert self.action_space.contains(action) # action corresponding to one of the permutation port_mapping = self.all_mappings[action] # assign packet to the output port for (i, p) in enumerate(port_mapping): self.queue_occupancy[i, p] = max(self.queue_occupancy[i, p] - 1, 0) # reamining total queue length reward = -np.sum(self.queue_occupancy) # never ending environment done = False # sample new traffic incoming_traffic = self.sample_from_bistochastic_matrix() self.queue_occupancy += incoming_traffic # cap the observation if np.any(self.queue_occupancy > config.ss_state_max_queue): obs_queue = np.minimum(self.queue_occupancy, config.ss_state_max_queue) logger.warn( 'Queue occupancy is clipped since it exceeds max queue value ' + str(config.ss_state_max_queue)) else: obs_queue = self.queue_occupancy # current queue occupancy in the observation space assert self.observation_space.contains(obs_queue) return obs_queue, reward, done, {}
def __init__(self, low=None, high=None, struct=None, shape=None, dtype=None): """ Two kinds of valid input: Box(low=-1.0, high=1.0, shape=(3,4)) # low and high are scalars, and shape is provided Box(low=np.array([-1.0,-2.0]), high=np.array([2.0,4.0])) # low and high are arrays of the same shape """ if shape is None: assert low.shape == high.shape shape = low.shape else: assert np.isscalar(low) and np.isscalar(high) low = low + np.zeros(shape) high = high + np.zeros(shape) if dtype is None: # Autodetect type if (high == 255).all(): dtype = np.uint8 else: dtype = np.float32 logger.warn( "park.spaces.Box autodetected dtype as {}. Please provide explicit dtype." .format(dtype)) self.low = low.astype(dtype) self.high = high.astype(dtype) #core.Space.__init__(self, struct, shape, dtype) space.Box.__init__(self, low, high, shape, dtype)
def clip_obs(obs, obs_low, obs_high): # TODO: this supports 1D only, need to add a iterator in each space type assert len(obs.shape) == 1 # fit in observation space for i in range(obs.shape[0]): if obs[i] > obs_high[i]: logger.warn('Observation at index ' + str(i) + ' has value ' + str(obs_arr[i]) + ', which is larger than obs_high ' + str(obs_high[i])) obs[i] = obs_high[i] if obs[i] < obs_low[i]: logger.warn('Observation at index ' + str(i) + ' has value ' + str(obs_arr[i]) + ', which is lower than obs_low ' + str(obs_low[i])) obs[i] = obs_low[i]
def observe(self): if self.chunk_idx < self.total_num_chunks: valid_chunk_idx = self.chunk_idx else: valid_chunk_idx = 0 if self.past_action is not None: valid_past_action = self.past_action else: valid_past_action = 0 # network throughput of past chunk, past chunk download time, # current buffer, number of chunks left and the last bitrate choice obs_arr = [self.past_chunk_throughputs[-1], self.past_chunk_download_times[-1], self.buffer_size, self.total_num_chunks - self.chunk_idx, valid_past_action] # current chunk size of different bitrates obs_arr.extend(self.chunk_sizes[i][valid_chunk_idx] for i in range(6)) # fit in observation space for i in range(len(obs_arr)): if obs_arr[i] > self.obs_high[i]: logger.warn('Observation at index ' + str(i) + ' at chunk index ' + str(self.chunk_idx) + ' has value ' + str(obs_arr[i]) + ', which is larger than obs_high ' + str(self.obs_high[i])) obs_arr[i] = self.obs_high[i] obs_arr = np.array(obs_arr) assert self.observation_space.contains(obs_arr) return obs_arr
def seed(self, seed=None): """ Sets the seed for this env's random number generator(s). """ logger.warn('Could not seed environment ' + self.metadata['env.name']) return