AncestralBase#

class pgmpy.base.AncestralBase(*args, backend=None, **kwargs)[source]#

Bases: Graph, _GraphRolesMixin

add_edge(u, v, u_mark, v_mark)[source]#

Add an edge with specified marks.

Parameters:
uHashable

One endpoint of the edge.

vHashable

The other endpoint of the edge.

u_markstr

Mark at node u for edge (u, v). Must be one of {“>”, “-”, “o”}.

v_markstr

Mark at node v for edge (u, v). Must be one of {“>”, “-”, “o”}.

Returns:
None

Adds the edge to the graph in-place

Examples

>>> from pgmpy.base import AncestralBase
>>> g = AncestralBase()

# Directed edge A → B >>> g.add_edge(“A”, “B”, “-”, “>”) >>> g[“A”][“B”][“marks”] {‘A’: ‘-’, ‘B’: ‘>’}

# Bidirected edge A ↔ D >>> g.add_edge(“A”, “D”, “>”, “>”) >>> g[“A”][“D”][“marks”] {‘A’: ‘>’, ‘D’: ‘>’}

# Undirected edge C — E >>> g.add_edge(“C”, “E”, “-”, “-“) >>> g[“C”][“E”][“marks”] {‘C’: ‘-’, ‘E’: ‘-‘}

add_edges_from(ebunch)[source]#

Add multiple edges from an iterable of (u, v, marks) tuples.

Parameters:
ebunchIterable[tuple]

Each tuple should be of the form (u, v, u_mark, v_mark).

Returns:
None

Adds the edges to the graph in-place.

Examples

>>> from pgmpy.base import AncestralBase
>>> g = AncestralBase()
>>> edges = [("A", "B", "-", ">"), ("B", "C", ">", "-"), ("C", "D", "o", "o")]
>>> g.add_edges_from(edges)
>>> list(g.edges(data=True))
[('A', 'B', {'marks': {'A': '-', 'B': '>'}}),
 ('B', 'C', {'marks': {'B': '>', 'C': '-'}}),
 ('C', 'D', {'marks': {'C': 'o', 'D': 'o'}})]
property adjacency_matrix#

Return adjacency matrix with edge marks and node-to-index mapping.

Returns:
Mnp.ndarray

A square matrix of shape (n_nodes, n_nodes) where M[i, j] is the mark at node j for edge (i, j).

node_indexdict

Mapping from node label to row/col index.

Examples

>>> from pgmpy.base import AncestralBase
>>> edges = [("A", "B", "-", ">"), ("B", "C", ">", "-")]
>>> graph = AncestralBase(ebunch=edges)
>>> M, node_index = graph.adjacency_matrix
>>> print(M)
[[0 '>' 0]
 ['-' 0 '-']
 [0 '>' 0]]
>>> print(node_index)
{'A': 0, 'B': 1, 'C': 2}
copy()[source]#

Return a copy of the graph, preserving nodes, edges, marks, latents, and roles.

Returns:
AncestralBase

A new instance of the same class as self with all properties copied.

classmethod from_dagitty(string: str = None, filename: str = None)[source]#

Populate the MAG from a Dagitty string representation.

Parameters:
stringstr

A string in dagitty format representing the MAG.

filenamestr, optional

Path to file containing Dagitty format string.

Returns:
MAG

A new MAG instance created from the Dagitty representation.

Examples

>>> from pgmpy.base import MAG
>>> dag_str = '''dag {
... L -> A
... B -> C
... L [latents]
... B [outcome]
... A [exposure]
... }'''
>>> mag = MAG.from_dagitty(dag_str)
get_ancestors(node)[source]#

Get all ancestor nodes of the given node.

Parameters:
nodeHashable

The node whose ancestors are to be found.

Returns:
ancestorsset

Set of ancestor nodes including the starting node.

Examples

>>> from pgmpy.base import AncestralBase
>>> edges = [
...     ("A", "B", "-", ">"),
...     ("B", "C", "-", ">"),
...     ("C", "D", "-", ">"),
...     ("E", "C", "-", ">"),
... ]
>>> graph = AncestralBase(ebunch=edges)
>>> print(graph.get_ancestors("D"))
{'A', 'B', 'C', 'D', 'E'}
>>> print(graph.get_ancestors("C"))
{'A', 'B', 'C', 'E'}
>>> print(graph.get_ancestors("A"))
{'A'}
get_children(node)[source]#

Get nodes that this node points to with ‘>’

Parameters:
nodeHashable

The node whose children are to be found.

Returns:
childrenset

Set of child nodes.

Examples

>>> from pgmpy.base import AncestralBase
>>> edges = [("A", "B", "-", ">"), ("A", "C", "-", ">"), ("B", "D", "-", ">")]
>>> graph = AncestralBase(ebunch=edges)
>>> print(graph.get_children("A"))
{'B', 'C'}
>>> print(graph.get_children("B"))
{'D'}
>>> print(graph.get_children("D"))
set()
get_descendants(node)[source]#

Get all descendant nodes (children, grandchildren, etc.)

Parameters:
nodeHashable

The starting node.

Returns:
descendantsset

Set of descendant nodes including the starting node.

Examples

>>> from pgmpy.base import AncestralBase
>>> edges = [
...     ("A", "B", "-", ">"),
...     ("B", "C", "-", ">"),
...     ("C", "D", "-", ">"),
...     ("B", "E", "-", ">"),
... ]
>>> graph = AncestralBase(ebunch=edges)
>>> print(graph.get_descendants("A"))
{'A', 'B', 'C', 'D', 'E'}
>>> print(graph.get_descendants("B"))
{'B', 'C', 'D', 'E'}
>>> print(graph.get_descendants("D"))
{'D'}
get_neighbors(node, u_type=None, v_type=None)[source]#

Get neighbors of a node with optional edge mark constraints.

Parameters:
nodeHashable

The node whose neighbors are to be found.

u_typeOptional[str]

Required mark at the given node for the edge.

v_typeOptional[str]

Required mark at the neighbor node for the edge.

Returns:
neighborsset

Set of neighboring nodes satisfying the mark constraints.

Examples

>>> from pgmpy.base import AncestralBase
>>> edges = [("A", "B", "-", ">"), ("B", "C", ">", "-"), ("C", "D", "o", "o")]
>>> graph = AncestralBase(ebunch=edges)
>>> print(graph.get_neighbors("B"))
{'A', 'C'}
>>> print(graph.get_neighbors("B", u_type=">"))
{'C', 'A'}
>>> print(graph.get_neighbors("B", v_type="-"))
{'A', 'C'}
>>> print(graph.get_neighbors("B", u_type=">", v_type="-"))
{'C', 'A'}
get_parents(node)[source]#

Get nodes that point to this node with ‘>’

Parameters:
nodeHashable

The node whose parents are to be found.

Returns:
parentsset

Set of parent nodes.

Examples

>>> from pgmpy.base import AncestralBase
>>> edges = [("A", "B", "-", ">"), ("C", "B", "-", ">"), ("B", "D", "-", ">")]
>>> graph = AncestralBase(ebunch=edges)
>>> print(graph.get_parents("B"))
{'A', 'C'}
>>> print(graph.get_parents("D"))
{'B'}
>>> print(graph.get_parents("A"))
set()
get_reachable_nodes(node, u_type=None, v_type=None)[source]#

Get all nodes reachable from the given node following edges with specified marks.

Parameters:
nodeHashable

The starting node.

u_typeOptional[str]

Required mark at the current node for traversal.

v_typeOptional[str]

Required mark at the neighbor node for traversal.

Returns:
reachableset

Set of reachable nodes including the starting node.

Examples

>>> from pgmpy.base import AncestralBase
>>> edges = [
...     ("A", "B", "-", ">"),
...     ("B", "C", "-", ">"),
...     ("A", "D", "o", "o"),
...     ("D", "E", "o", "o"),
... ]
>>> graph = AncestralBase(ebunch=edges)
>>> print(graph.get_reachable_nodes("A", v_type=">"))
{'A', 'B', 'C'}
>>> print(graph.get_reachable_nodes("A", u_type="o", v_type="o"))
{'A', 'D', 'E'}
get_spouses(node)[source]#

Get nodes connected by bidirectional ‘>’ edges (spouses).

Parameters:
nodeHashable

The node whose spouses are to be found.

Returns:
spousesset

Set of spouse nodes.

Examples

>>> from pgmpy.base import AncestralBase
>>> edges = [("A", "B", ">", ">"), ("A", "C", "-", ">"), ("C", "D", ">", ">")]
>>> graph = AncestralBase(ebunch=edges)
>>> print(graph.get_spouses("A"))
{'B'}
>>> print(graph.get_spouses("C"))
{'D'}
>>> print(graph.get_spouses("B"))
{'A'}
to_dagitty() str[source]#

Convert the MAG to a Dagitty string representation.

Returns:
str

A string in Dagitty format representing the MAG.

References

dagitty syntax: https://cran.r-project.org/web/packages/dagitty/dagitty.pdf

Examples

>>> from pgmpy.base import MAG
>>> mag = MAG()
>>> mag.add_edge("X", "Y", "-", ">")
>>> mag.add_edge("Z", "Y", "-", ">")
>>> print(mag.to_dagitty())
mag {
X -> Y
Z -> Y
}
>>> mag2 = MAG()
>>> mag2.add_edge("A", "B", ">", ">")
>>> mag2.add_edge("C", "D", "-", "-")
>>> print(mag2.to_dagitty())
mag {
A <-> B
C -- D
}
>>> # MAG with latent variables and roles
>>> mag3 = MAG()
>>> mag3.add_edge("L", "X", "-", ">")
>>> mag3.add_edge("X", "Y", "-", ">")
>>> mag3.latents = {"L"}
>>> mag3 = mag3.with_role("exposures", "X")
>>> mag3 = mag3.with_role("outcomes", "Y")
>>> print(mag3.to_dagitty())
mag {
L -> X
X -> Y
L [latents]
Y [outcome]
X [exposure]
}