How can get the adjacent matrix that only cantain k-hop neighbors?
Closed this issue · 12 comments
From now on, we recommend using our discussion forum (https://github.com/rusty1s/pytorch_geometric/discussions) for general questions.
❓ Questions & Help
Thank you for your work!
Please, I want to know hot to get the adjacent matrix that only cantain k-hop neighbors?
For example, cora
dataset, the edge_index
is the complete adjacent matrix. If I want to get the adjacent matrix, which is only contain 2-hop neighbors but not contain 1-hop and x-hop x>2
, how can I do?
I m looking forward to your answer! Thank you!
If it is applicable, you could use dense adjacency matrices to achieve that:
adj = torch.zeros(N, N, dtype=torch.long)
adj[edge_index[0], edge_index[1]] = 1
new_adj = (adj @ adj)
new_adj = ((new_adj > 0).to(torch.long) + adj) == 1
If it is applicable, you could use dense adjacency matrices to achieve that:
adj = torch.zeros(N, N, dtype=torch.long) adj[edge_index[0], edge_index[1]] = 1 new_adj = (adj @ adj) new_adj = ((new_adj > 0).to(torch.long) + adj) == 1
Thank you for your answer!
Is any sparse approach?
You could use np.isin
to filter out the edges that appear in both adj
and adj @ adj
. That should work for sparse adjacencies.
You could use
np.isin
to filter out the edges that appear in bothadj
andadj @ adj
. That should work for sparse adjacencies.
I'm sorry for my slowness. Could you be more specific?
Sure. It might look like the following code (note that I didn't test it):
edge_index = ...
edge_index2 = spspmm(...)
idx = edge_index[0] * num_nodes + edge_index[1]
idx2 = edge_index2[0] * num_nodes + edge_index2[1]
mask = torch.from_numpy(np.isin(idx2.numpy(), idx.numpy()))
mask = ~mask # Invert mask to only contain the elements not in `idx`
edge_index2 = edge_index2[:, mask]
Sure. It might look like the following code (note that I didn't test it):
edge_index = ... edge_index2 = spspmm(...) idx = edge_index[0] * num_nodes + edge_index[1] idx2 = edge_index2[0] * num_nodes + edge_index2[1] mask = torch.from_numpy(np.isin(idx2.numpy(), idx.numpy())) mask = ~mask # Invert mask to only contain the elements not in `idx` edge_index2 = edge_index2[:, mask]
I m sorry that there is a problem.
All computation is finished on cuda
. So it seems that converting to numpy
is not feasible.
:)Do you have any approches implement it on cuda
?
The goal of obtain the k-hop edge_index
is to make messege passing only in k-hop neighbor.
For example, I only want implement GraphConv
layers on 2-hop neighbor but no 1-hop and other k-hop neighbor.
Do you have other mrthods? Thank you!
As far as I know, there is no isin
functionality implemented in PyTorch, but you can transfer your tensors to CPU first before calling numpy()
.
Yes, I didn't do it because transfer to CPU and transfer to GPU can cause problem of speed.
Is there any approaches that can make messege passing only in k-hop neighbor but no other neighbor?
Thank you!
I don't know of any. I also do not think that speed is a deciding factor, as you can usually simply pre-process the 2-hop graph, and therefore only have to do it once.
U 're right. I have to implement it first.
Thanks again for your reply from the other side of the ocean
Hi, I check the code and write it as follow:
x, edge_index = data.x, data.edge_index
N = x.size(0)
row, col = edge_index
edge_index2 = torch_sparse.spspmm(edge_index, torch.ones([col.size(0)], device='cuda'),
edge_index, torch.ones([col.size(0)], device='cuda'),
N, N, N)
idx = edge_index[0] * N + edge_index[1]
idx2 = edge_index2[0] * N + edge_index2[1]
mask = torch.from_numpy(np.isin(idx2.cpu().numpy(), idx.cpu().numpy()))
mask = ~mask # Invert mask to only contain the elements not in `idx`
edge_index2 = edge_index2[:, mask]
But it reported the error:
File "k-hop.py", line 53, in <module>
edge_index2 = edge_index2[:, mask]
TypeError: tuple indices must be integers or slices, not tuple
How can I fix this error? Thank you!
Hi, I check the code and write it as follow:
x, edge_index = data.x, data.edge_index N = x.size(0) row, col = edge_index edge_index2 = torch_sparse.spspmm(edge_index, torch.ones([col.size(0)], device='cuda'), edge_index, torch.ones([col.size(0)], device='cuda'), N, N, N) idx = edge_index[0] * N + edge_index[1] idx2 = edge_index2[0] * N + edge_index2[1] mask = torch.from_numpy(np.isin(idx2.cpu().numpy(), idx.cpu().numpy())) mask = ~mask # Invert mask to only contain the elements not in `idx` edge_index2 = edge_index2[:, mask]
But it reported the error:
File "k-hop.py", line 53, in <module> edge_index2 = edge_index2[:, mask] TypeError: tuple indices must be integers or slices, not tuple
How can I fix this error? Thank you!
I found it just need to add an _
in spspmm
and fix this error.
And how can I check it and insure it dose get k-hop neighbor?