def make_torch_type_for_GCN(nodes_pos, edges_indices, edges_thickness, node_adj): # GCNの為の引数を作成 T = make_T_matrix(edges_indices) edge_adj = make_edge_adj(edges_indices, T) D_e = make_D_matrix(edge_adj) D_v = make_D_matrix(node_adj) # GCNへの変換 node = torch.from_numpy(nodes_pos).clone().double() node = node.unsqueeze(0) edge = torch.from_numpy(edges_thickness).clone().double() edge = edge.unsqueeze(0).unsqueeze(2) node_adj = torch.from_numpy(node_adj).clone().double() node_adj = node_adj.unsqueeze(0) edge_adj = torch.from_numpy(edge_adj).clone().double() edge_adj = edge_adj.unsqueeze(0) D_v = torch.from_numpy(D_v).clone().double() D_v = D_v.unsqueeze(0) D_e = torch.from_numpy(D_e).clone().double() D_e = D_e.unsqueeze(0) T = torch.from_numpy(T).clone().double() T = T.unsqueeze(0) return node, edge, node_adj, edge_adj, D_v, D_e, T
def select_action(first_node_num): nodes_pos, edges_indices, edges_thickness, node_adj = env.extract_node_edge_info( ) node_num = nodes_pos.shape[0] # ラベル作成 label = np.zeros((node_num, 1)) label[:first_node_num] = 1 nodes_pos = np.concatenate([nodes_pos, label], 1) # GCNの為の引数を作成 T = make_T_matrix(edges_indices) edge_adj = make_edge_adj(edges_indices, T) D_e = make_D_matrix(edge_adj) D_v = make_D_matrix(node_adj) # GCNへの変換 node = torch.from_numpy(nodes_pos).clone().double() node = node.unsqueeze(0) edge = torch.from_numpy(edges_thickness).clone().double() edge = edge.unsqueeze(0).unsqueeze(2) node_adj = torch.from_numpy(node_adj).clone().double() node_adj = node_adj.unsqueeze(0) edge_adj = torch.from_numpy(edge_adj).clone().double() edge_adj = edge_adj.unsqueeze(0) D_v = torch.from_numpy(D_v).clone().double() D_v = D_v.unsqueeze(0) D_e = torch.from_numpy(D_e).clone().double() D_e = D_e.unsqueeze(0) T = torch.from_numpy(T).clone().double() T = T.unsqueeze(0) # action求め emb_graph, state_value = GCN(node, edge, node_adj, edge_adj, D_v, D_e, T) # 新規ノードの座標決め coord = X_Y(emb_graph) coord_x_tdist = tdist.Normal(coord[0][0].item(), coord[0][2].item()) coord_y_tdist = tdist.Normal(coord[0][1].item(), coord[0][3].item()) coord_x_action = coord_x_tdist.sample() coord_y_action = coord_y_tdist.sample() # 0-1に収める coord_x_action = torch.clamp(coord_x_action, min=0, max=1) coord_y_action = torch.clamp(coord_y_action, min=0, max=1) # グラフ追加を止めるかどうか stop_prob = Stop(emb_graph) stop_categ = Categorical(stop_prob) stop = stop_categ.sample() # ノード1を求める node1_prob = Select_node1(emb_graph) node1_categ = Categorical(node1_prob) node1 = node1_categ.sample() # 新規ノード new_node = torch.Tensor([coord_x_action, coord_y_action, 0]).double() new_node = torch.reshape(new_node, (1, 1, 3)) node_cat = torch.cat([node, new_node], 1) # H1を除いたnode_catの作成 non_node1_node_cat = torch.cat( [node_cat[:, 0:node1, :], node_cat[:, node1 + 1:, :]], 1) # H1の情報抽出 H1 = emb_graph[0][node1] H1_cat = H1.repeat(non_node1_node_cat.shape[1], 1) H1_cat = H1_cat.unsqueeze(0) # HとH1のノード情報をconcat emb_graph_cat = torch.cat([non_node1_node_cat, H1_cat], 2) # ノード2を求める node2_prob = Select_node2(emb_graph_cat) node2_categ = Categorical(node2_prob) node2_temp = node2_categ.sample() if node2_temp >= node1: node2 = node2_temp + 1 # node1分の調整 else: node2 = node2_temp H2 = node_cat[0][node2] # node_posよりH2の特徴を抽出 # エッジの太さ決め # H1とH2のノード情報をconcat H1 = H1.unsqueeze(0) H2 = H2.unsqueeze(0) emb_graph_cat2 = torch.cat([H1, H2], 2) edge_thickness = Edge_thickness(emb_graph_cat2) edge_thickness_tdist = tdist.Normal(edge_thickness[0][0].item(), edge_thickness[0][1].item()) edge_thickness_action = edge_thickness_tdist.sample() edge_thickness_action = torch.clamp(edge_thickness_action, min=0, max=1) action = {} action["which_node"] = np.array([node1.item(), node2.item()]) action["new_node"] = np.array([[coord_x_action, coord_y_action]]) action["edge_thickness"] = np.array([edge_thickness_action]) action["end"] = stop.item() # save to action buffer GCN.saved_actions.append(Saved_Action(action, state_value)) Stop.saved_actions.append(Saved_prob_Action(stop_categ.log_prob(stop))) Select_node1.saved_actions.append( Saved_prob_Action(node1_categ.log_prob(node1))) Select_node2.saved_actions.append( Saved_prob_Action( node2_categ.log_prob(node2_temp))) # node2_tempを利用していることに注意 X_Y.saved_actions.append(Saved_mean_std_Action(coord[0][:2], coord[0][2:])) Edge_thickness.saved_actions.append( Saved_mean_std_Action(edge_thickness[0][0], edge_thickness[0][1])) GCN.node_nums.append(node_num) return action