def create_searchers(specs): # unpack from specs g = specs.graph capture_range = specs.capture_range zeta = specs.zeta m = specs.size_team if specs.start_searcher_v is None: # if initial position was not defined by user v_list = placement_list(specs, 's') if specs.searcher_together: v_list = searchers_start_together(m, v_list) # len(v0) = m v0 = v_list specs.set_start_searchers(v0) else: # if it was, use that v0 = specs.start_searcher_v # get graph vertices V, n = ext.get_set_vertices(g) if any(v0) not in V: print("Vertex out of range, V = {1, 2...n}") return None searchers = create_dict_searchers(g, v0, capture_range, zeta) return searchers
def __init__(self, horizon, deadline, theta, my_graph, solver_type='central', timeout=30*60): """ initialize after solver is first called :param number_searchers: """ # objective function value for each time the solver runs self.obj_value = {} # solving time for each time the solver runs self.solve_time = {} # gap for each time the solver runs self.gap = {} self.x_s = {} self.belief = {} # horizon can be mutable in future experiments self.horizon = dict() self.horizon[0] = horizon # input parameters (immutable) self.g = None self.g = my_graph self.V, self.n = ext.get_set_vertices(my_graph) self.theta = theta self.deadline = deadline self.solver_type = solver_type self.timeout = timeout self.threads = {} self.gamma = 0.99
def create_team(specs): # TODO move this to team class later # unpack from specs g = specs.graph capture_range = specs.capture_range zeta = specs.zeta m = specs.size_team alpha = specs.alpha kappa = specs.kappa if specs.start_searcher_v is None: # if initial position was not defined by user v_list = cp.placement_list(specs, 's') if specs.searcher_together: v_list = cp.searchers_start_together(m, v_list) # len(v0) = m v0 = v_list specs.set_start_searchers(v0) else: # if it was, use that v0 = specs.start_searcher_v # get graph vertices V, n = ext.get_set_vertices(g) if any(v0) not in V: print("Vertex out of range, V = {1, 2...n}") return None team = MyTeam2(m) team.create_dict_searchers(g, v0, kappa, alpha, capture_range, zeta) team.set_danger_perception(specs.perception) return team
def set_initial_belief(g_or_n, v_list: list, type_distribution='uniform'): """ Make initial belief vector (assign probabilities to list of vertices) based on :param g_or_n : graph or n, to obtain number of total vertices (n) :param v_list : list of vertices # [1, 3...] to be assigned non zero probability :param type_distribution : type of distribution, default is uniform """ n = ext.get_set_vertices(g_or_n)[1] # create belief vector of zeros b_0 = np.zeros(n + 1) # get number of possible initial vertices q = len(v_list) # if the initial_prob is not a list with pre-determined initial probabilities # for each possible initial vertex # just consider equal probability between possible vertices if type_distribution is 'uniform': prob_init = 1 / q else: prob_init = type_distribution # initial target belief (vertices in v_list will change value, others remain zero) # b[0] = 0 b_0[v_list] = prob_init return list(b_0)
def draw_v_random(g_or_n, q=1, my_seed=None): """Choose possible random vertices for the starting point of the target positions are given in model indexing (1,2...) :param g_or_n : graph :param q : number of possible vertices :param my_seed : random seed generator (optional) return: v_target --> possible initial vertices of the target v_left: target from the graph that are 'free' """ # get set of vertices V, n = ext.get_set_vertices(g_or_n) v_target = [] if my_seed is None: v_left = V # randomly pick vertices for pos in range(0, q): my_v = int(random.choice(v_left)) v_target.append(my_v) # take out that vertex from list of possible vertices v_left.remove(my_v) else: v_target = pick_pseudo_random(V, my_seed, q) v_left = ext.get_v_left(n, v_target) return v_target, v_left
def list_to_dict(data: list): n = len(data) V = ext.get_set_vertices(n)[0] data_dict = {} for v in V: vidx = ext.get_python_idx(v) data_dict[v] = data[vidx] return data_dict
def test_fov(): rooms = bf.compartments_ss2() my_list = [] for name in rooms.keys(): for v in rooms[name]: my_list.append(v) my_list.sort() V = ext.get_set_vertices(46)[0] assert my_list == V
def define_capture_matrix(self, g): V, n = ext.get_set_vertices(g) # size of capture matrix nu = n + 1 my_aux = {} for v in V: # loop through vertices to get capture matrices C = self.rule_intercept(v, nu, self.capture_range, self.zeta, g) my_aux[v] = C C_all = my_aux return C_all
def placement_list(specs, op='s'): """Call only when the initial position is random (no list defined by user) Make sure belief and searchers' start vertices are far away (out of reach) so that b_c(0) = 0 :param specs : inputs :param op : 's' to place searchers, 't' to get list of vertices for belief """ g = specs.graph # placing searchers or belief? if op == 's': v_input = specs.start_target_v_list my_seed = specs.searcher_seed # check if searchers are starting together if specs.searcher_together: q = 1 else: q = specs.size_team else: v_input = specs.start_searcher_v # quantity of possible nodes (probability > 0) q = specs.qty_possible_nodes # seed my_seed = specs.target_seed if v_input is None: # draw q random nodes v_list, v_left = draw_v_random(g, q, my_seed) else: # check if it's out of reach at t = 0 v_taken = v_input v_list = [] out_of_reach = False # keep drawing until is out of reach while out_of_reach is False: v_list = draw_v_random(g, q, my_seed)[0] specs.change_seed(my_seed, 't') out_of_reach = check_reachability(g, specs.capture_range, v_list, v_taken) my_seed += 500 # check for bug (not a vertex in graph) V = ext.get_set_vertices(g)[0] if any(v_list) not in V: print("Vertex out of range, V = {1, 2...n}") exit() return v_list
def structure(self, g, deadline): V, n = ext.get_set_vertices(g) self.n = n self.V = V self.g_name = g["name"] self.g = g T = ext.get_set_time(deadline) T_ext = ext.get_set_time_u_0(deadline) self.tau = deadline self.T = T self.T_ext = T_ext # create dicts for eta, eta_level self.create_empty_dicts()
def structure(self, g, deadline): V, n = ext.get_set_vertices(g) self.n = n self.V = V self.g_name = g["name"] self.g = g T = ext.get_set_time(deadline) T_ext = ext.get_set_time_u_0(deadline) self.tau = deadline self.T = T self.T_ext = T_ext # get connectivity matrix (list form) self.E = ext.get_connectivity_matrix(g) # init 0 populated or empty dictionaries: z, xi, lbda self.create_empty_dicts()
def create_graph(n: int, edges: list, base_name: str): """Create iGraph based on :param n : number of vertices :param edges : list of connections, python index: [(0, 1), (1,2)...] :param base_name : """ # create new graph g = Graph(directed=False) g.add_vertices(n) # make sure it's indexed right v1 = [e[0] for e in edges] v2 = [e[1] for e in edges] if min(v1) > 0 or min(v2) > 0: edges = [(e[0] - 1, e[1] - 1) for e in edges] g.add_edges(edges) V = ext.get_set_vertices(g)[0] # label starting at 1 g.vs["label"] = V # find shortest path length between any two vertices short_paths = g.shortest_paths_dijkstra() g["path_len"] = short_paths # find neighbors to each vertex for v in V: vidx = ext.get_python_idx(v) nei = g.neighbors(vidx) g.vs[vidx]["neighbors"] = nei # name graph g["name"] = base_name return g
def my_graph(number_vertex: int, ref: str, graph_opt=1, w=None, h=None): """Function to create graph according to user inputs""" # Graph representing environment # create new graph g = Graph(directed=False) g.add_vertices(number_vertex) if graph_opt == 1: g.add_edges([(0, 1), (0, 2), (1, 3), (1, 4), (2, 4), (4, 5), (5, 6)]) elif graph_opt == 2: g.add_edges([(0, 1), (1, 2)]) elif graph_opt == 3: g.add_edges([(0, 1), (0, 2), (1, 3), (1, 4), (2, 4), (4, 5), (5, 6), (6, 7)]) elif graph_opt == 4: # create graph from Hollinger 2009 - MUSEUM g.add_edges( [ (0, 55), (1, 55), (2, 55), (3, 55), (55, 56), (55, 54), (55, 34), (55, 33), (55, 35), (54, 32), (54, 31), (54, 30), (54, 53), (53, 29), (53, 28), (53, 27), (53, 26), (53, 39), (53, 52), (53, 38), (53, 37), (53, 36), (52, 57), (52, 25), (52, 50), (50, 51), (50, 49), (25, 24), (24, 43), (57, 56), (57, 4), (57, 5), (57, 6), (57, 40), (57, 41), (57, 43), (49, 48), (48, 43), (48, 59), (43, 42), (43, 44), (43, 22), (44, 7), (44, 8), (44, 9), (44, 21), (44, 23), (44, 45), (21, 45), (21, 22), (46, 45), (45, 10), (46, 11), (46, 12), (46, 13), (46, 47), (46, 20), (47, 14), (58, 47), (58, 15), (58, 59), (58, 18), (58, 19), (59, 17), (59, 16) ]) elif graph_opt == 5: g = add_edge_grid(g, w, h) elif graph_opt == 7: # create graph from Hollinger 2009 - OFFICE edges = [(1, 2), (1, 5), (1, 9), (1, 7), (2, 1), (2, 3), (2, 4), (3, 2), (4, 2), (5, 1), (6, 7), (7, 6), (7, 8), (7, 1), (8, 7), (9, 1), (9, 10), (10, 9), (10, 11), (10, 12), (10, 13), (10, 18), (10, 19), (10, 20), (10, 27), (11, 10), (11, 14), (11, 28), (12, 10), (12, 15), (12, 16), (13, 10), (13, 17), (14, 11), (14, 15), (15, 14), (15, 12), (16, 12), (16, 17), (17, 16), (17, 13), (18, 10), (18, 19), (18, 26), (18, 70), (19, 10), (19, 18), (19, 20), (19, 25), (19, 26), (20, 10), (20, 19), (20, 21), (20, 24), (21, 20), (21, 22), (22, 21), (22, 23), (23, 22), (23, 24), (24, 23), (24, 20), (24, 25), (25, 24), (25, 19), (25, 26), (26, 25), (26, 19), (26, 18), (27, 10), (27, 49), (28, 11), (28, 29), (29, 28), (29, 34), (30, 31), (30, 33), (31, 30), (31, 32), (32, 33), (32, 31), (32, 37), (33, 32), (33, 36), (34, 29), (34, 35), (35, 34), (35, 36), (35, 40), (35, 49), (36, 35), (36, 33), (36, 39), (36, 37), (37, 36), (37, 32), (37, 38), (38, 37), (38, 42), (39, 36), (39, 40), (39, 41), (40, 35), (40, 39), (40, 43), (41, 39), (41, 42), (42, 41), (42, 38), (43, 40), (43, 44), (43, 47), (44, 43), (44, 45), (45, 44), (45, 46), (46, 45), (46, 47), (47, 43), (47, 46), (47, 48), (48, 47), (48, 50), (49, 35), (49, 27), (49, 58), (49, 50), (50, 48), (50, 49), (50, 51), (50, 52), (51, 50), (52, 50), (52, 56), (52, 53), (53, 52), (53, 54), (53, 55), (53, 56), (54, 53), (54, 55), (55, 54), (55, 53), (56, 52), (56, 53), (56, 64), (57, 58), (57, 63), (58, 49), (58, 57), (58, 59), (58, 62), (59, 60), (59, 61), (59, 58), (60, 70), (60, 61), (60, 59), (61, 60), (61, 59), (61, 69), (61, 68), (62, 58), (62, 67), (63, 57), (63, 66), (63, 64), (64, 63), (64, 56), (64, 65), (65, 64), (65, 66), (66, 65), (66, 67), (66, 63), (67, 62), (67, 66), (67, 68), (68, 61), (68, 67), (68, 69), (69, 61), (69, 68), (70, 18), (70, 60)] edges = map(lambda x: (x[0] - 1, x[1] - 1), edges) g.add_edges(edges) g.simplify(multiple=True, loops=False) V_, n = ext.get_idx_vertices(g) V = ext.get_set_vertices(g)[0] # label starting at 1 g.vs["label"] = V # find shortest path length between any two vertices short_paths = g.shortest_paths_dijkstra() g["path_len"] = short_paths # find neighbors to each vertex for v in V_: nei = g.neighbors(v) g.vs[v]["neighbors"] = nei # name graph g["name"] = ref return g
def __init__(self, g): """ :param g : graph """ # --------------------- # pre defined parameters # --------------------- # danger levels self.levels, self.n_levels, self.level_label, self.level_color = self.define_danger_levels( ) self.options = self.define_options() # ------------------------ # Default settings # ------------------------ # apply danger constraints self.constraints = True # apply kill probability self.kill = True # a priori knowledge self.true_priori = False self.uniform_priori = True # estimation knowledge self.true_estimate = False self.mva_conservative = True # z true always gonna be mean, for now estimate also going to be mean (so it doesn't get stuck) self.z_true_op = 1 self.z_est_op = 1 # z for priori is gonna be conservative (op = 4) self.z_pri_op = 4 self.use_fov = True # point or prob (default: point) self.perception = self.options[0] # ----------- # input parameters (graph, immutable) # ----------- # vertices self.V, self.n = ext.get_set_vertices(g) self.fov = None # ---------- # team of searchers (get rid of this to avoid issues when searcher is dead?) # ---------- self.S, self.m = [], 0 # danger threshold for the searchers self.kappa = list() self.alpha = list() self.k_mva = None self.v0 = [1] # ------------------------- # ground truth # ------------------------- # eta[v_idx] = [eta_l1, ... eta_l5] self.eta = [] # z[v_idx] = argmax eta_l \in {1,..5} self.z = [] # H[v_idx] = [cumulative for each level] - probabilistic approach self.H = [] # probability kill self.prob_kill = None # ------------ # estimation # ------------ # a priori knowledge of danger # eta0_0[v] = [eta0_0_l1,... eta0_0_l5] self.eta0_0 = [] # z0_0[v] = level, level in {1,...5} self.z0_0 = [] self.H0_0 = [] # estimates at each time step # eta_hat[v_idx] = [l1,...l5] self.eta_hat = [] # probable danger level, zhat self.z_hat = [] # for each level, H[l-1] = [H_l1, H_l2...H_l5] (estimate) self.H_hat = [] # for each searcher threshold self.Hs_hat = [] # to make getting the values easier # look up of estimated danger (when robots sees available images in that vertex) # etahat[v_idx] = [eta_hat_l1, ... eta_hat_l5] self.lookup_eta_hat = [] # H_hat[vidx] = [l1...l5] self.lookup_H_hat = [] # z[v_idx] = argmax eta_l \in {1,..5} self.lookup_z_hat = [] # matching scores xi[v] = [[i1_1...i1_5], [i2_1,...i2_5]] self.xi = dict() # ------------- # storage # ------------- # probability of each danger level: eta_hat[v,t] = [prob l1, ...l5] self.stored_eta_hat = {0: list()} # probable danger level, argmax eta: eta_hat[v,t] = level self.stored_z_hat = {0: list()} # cumulative danger, from eta_hat self.stored_H_hat = {0: list()} # name of folder for this sim: eg smoke_G9V_grid_date#_run# self.folder_name = "" # whole path + /name_folder f_name = 'exp_data' if self.perception == 'prob': f_name = 'exp_data_prob' self.path_exp_data = self.get_folder_path(f_name) # ----------------------- # danger data from files # ----------------------- # true distributions self.true_file_name = '' self.true_file_path = '' self.true_raw = None # estimated offline (% images) self.estimated_file_name = '' self.estimated_file_path = '' self.percentage_im = None self.estimated_raw = None # path to files and extension self.extension = 'pkl' self.folder_path = self.get_folder_path()
def update_n(self): self.n = ext.get_set_vertices(self.graph)[1]