Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Remove specific edge from MultiDiGraph #4478

Closed
vymao opened this issue Dec 20, 2020 · 3 comments
Closed

Remove specific edge from MultiDiGraph #4478

vymao opened this issue Dec 20, 2020 · 3 comments
Labels
Question A question about NetworkX or network science in general

Comments

@vymao
Copy link

vymao commented Dec 20, 2020

Hi,

I am using MultiDiGraph and would like to remove a particular edge with particular class from node u to v. That is, for example, for a graph as such:

>>> G.edges(data = "class")
OutMultiEdgeDataView([(1, 2, 12), (1, 2, 14), (1, 3, 53), (1, 3, 50), (1, 4, 12), (4, 5, 53), (5, 6, 12), (5, 7, 53)])

I would like to remove the edge (1, 2, {"class": 12}) while leaving the other edge from 1 to 2 unchanged.

Is it possible to do this? I looked at remove_edge but that seems to require that the edge attributes have different classification names, and that if I put multiple edges under the same classification name, it would remove them all.

I have edges with weights, and ideally I would be able to assign these attributes without a particular class label but so far I don't seem to be able to do that.

@dschult
Copy link
Member

dschult commented Dec 21, 2020

For MultiGraph, the remove_edge docs say that you should use the "edge key" to identify specific edges. It is likely that is the role your edge "class" is playing for your code. To be sure, ask whether there can ever be two edges between a pair of nodes with the same class. If not, then use the "class" value as the edge key.

How do you do that? Creating the edge key has to happen when you create the edge. By default the edge keys are integers starting at 0 and incrementing for each edge between that pair of nodes.
MG.add_edge(u, v, edge_key) is a reasonable approach: MG.add_edge(u, v, class) in your case.
MG.add_edges_from([(u1, v1, edge_key1), (u2, v2, edge_key2), ...]) is another approach.

If you don't know the class for the edge when you construct the multigraph, you can convert one MultiGraph with edge attribute "class" to a MultiGraph with both edge attribute class, and identical edge key as follows:

MH = nx.MultiGraph((u, v, c, {"class": c, "old_key": k}) for u, v, k, c in MG.edges(keys=True, data="class"))

(actually, you don't need the keys=True or old_key parts if you don't need the old keys.)

If your "class" attribute is not unique within a pair of nodes, you can't use that value as an edge key.
Then the best way to remove the edge is something like:

MG.remove_edges_from((u, v, k) for u, v, k, c in MG.edges(keys=True, data="class") if c == 12)

That might remove more than one edge -- or no edges depending on which have attribute class==12.

@rossbar
Copy link
Contributor

rossbar commented Dec 21, 2020

The remove_edge method supports removing edges by key for multigraphs. You can see the keys by adding keys=True to the G.edges call.

@rossbar rossbar added the Question A question about NetworkX or network science in general label Dec 21, 2020
@rossbar
Copy link
Contributor

rossbar commented Jun 8, 2022

I think this one has been sufficiently answered and the relevant info is in the docstring. This should be further bolstered by #5699. I'm going to close this but if the issue persists please feel free to reopen.

@rossbar rossbar closed this as not planned Won't fix, can't repro, duplicate, stale Jun 8, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Question A question about NetworkX or network science in general
Development

No branches or pull requests

3 participants