Class: NetworkX::Graph
- Inherits:
-
Object
- Object
- NetworkX::Graph
- Defined in:
- lib/networkx/graph.rb,
lib/networkx/others/reads.rb,
lib/networkx/traversals/bfs.rb,
lib/networkx/traversals/dfs.rb,
lib/networkx/others/generators.rb,
lib/networkx/traversals/edge_dfs.rb
Overview
Describes the class for making Undirected Graphs
Direct Known Subclasses
Instance Attribute Summary collapse
-
#adj ⇒ Hash{ Object => Hash{ Object => Hash{ Object => Object } } }
readonly
Stores the edges and their attributes in an adjencency list form.
-
#graph ⇒ Hash{ Object => Object }
readonly
Stores the attributes of the graph.
Class Method Summary collapse
- .balanced_tree(r, h) ⇒ Object
- .barbell_graph(m1, m2) ⇒ Object
- .bull_graph ⇒ Object
- .circular_ladder_graph(n) ⇒ Object
-
.complete_edges(n) ⇒ Object
private class method.
- .complete_graph(n) ⇒ Object
- .cubical_graph ⇒ Object
- .cycle_graph(n) ⇒ Object
- .diamond_graph ⇒ Object
-
.dodecahedral_graph ⇒ Object
12.
- .empty_graph(number_of_nodes) ⇒ Object
- .heawood_graph ⇒ Object
- .house_graph ⇒ Object
- .house_x_graph ⇒ Object
- .ladder_graph(n) ⇒ Object
- .lollipop_graph(m, n) ⇒ Object
- .moebius_kantor_graph ⇒ Object
- .null_graph ⇒ Object
-
.octahedral_graph ⇒ Object
8: 6 nodes, 12 edges.
- .path_graph(n) ⇒ Object
- .read_edgelist(path, comment: '#', delimiter: nil) ⇒ Object (also: read_edges)
- .read_weighted_edgelist(path, comment: '#', delimiter: nil) ⇒ Object (also: read_weighted_edges)
- .star_graph(n) ⇒ Object
- .tetrahedral_graph ⇒ Object
- .trivial_graph ⇒ Object
- .wheel_graph(n) ⇒ Object
Instance Method Summary collapse
-
#add_edge(node1, node2, **edge_attrs) ⇒ Object
Adds the respective edges.
-
#add_edges(edges) ⇒ Object
Adds multiple edges from an array.
- #add_edges_from(rng) ⇒ Object
-
#add_node(node, **node_attrs) ⇒ Object
Adds a node and its attributes to the graph.
-
#add_nodes(nodes) ⇒ Object
Adds multiple nodes to the graph.
-
#add_nodes_from(nodes_for_adding) ⇒ Object
[TODO][EXPERIMENTAL].
- #add_path(paths) ⇒ Object
-
#add_weighted_edge(node1, node2, weight) ⇒ Object
Adds weighted edge.
-
#add_weighted_edges(edges, weights) ⇒ Object
Adds multiple weighted edges.
-
#add_weighted_edges_from(edges, weight: :weight) ⇒ Object
[TODO][EXPERIMENTAL].
-
#bfs_edges(node) ⇒ Object
[EXPERIMENTAL].
- #bfs_nodes(root) ⇒ Object
-
#clear ⇒ Object
Clears the graph.
-
#degree(nodes = nil) ⇒ Object
[EXPERIMENTAL].
- #dfs_edges(node) ⇒ Object
-
#dfs_postorder_nodes(root, used = {root => true}) ⇒ Array[Object]
[EXPERIMENTAL].
-
#dfs_preorder_nodes(root) ⇒ Array[Object]
[EXPERIMENTAL].
- #directed? ⇒ Boolean
-
#each_bfs_edge(node) ⇒ Object
[EXPERIMENTAL].
- #each_bfs_node(root) ⇒ Object
- #each_dfs_edge(node) ⇒ Object
- #each_dfs_postorder_node(root, &block) ⇒ Object
-
#each_dfs_preorder_node(root) ⇒ Object
[EXPERIMENTAL].
-
#each_edge(data: false) ⇒ Object
[TODO][EXPERIMENTAL].
- #each_node(data: false, &block) ⇒ Object
-
#edge?(node1, node2) ⇒ Boolean
(also: #has_edge?)
Checks if the the edge consisting of two nodes is present in the graph.
-
#edge_subgraph(edges) ⇒ Object
Returns subgraph conisting of given edges.
-
#edges(data: false) ⇒ Array[[Object, Object]]
[TODO][EXPERIMENTAL].
-
#get_edge_data(node1, node2) ⇒ Object
Gets the edge data.
-
#get_node_data(node) ⇒ Object
Gets the node data.
- #info ⇒ Object
-
#initialize(**graph_attrs) ⇒ Graph
constructor
Constructor for initializing graph.
- #multigraph? ⇒ Boolean
-
#neighbours(node) ⇒ Object
Retus a hash of neighbours of a node.
-
#node?(node) ⇒ Boolean
(also: #has_node?)
Checks if a node is present in the graph.
-
#nodes(data: false) ⇒ Hash | Array
Return nodes of graph.
-
#number_of_edges ⇒ Object
Returns number of edges.
-
#number_of_nodes ⇒ Object
Returns number of nodes.
-
#put_graph_x2 ⇒ Object
Experimental For debug.
-
#remove_edge(node1, node2) ⇒ Object
Removes edge from the graph.
-
#remove_edges(edges) ⇒ Object
(also: #remove_edges_from)
Removes multiple edges from the graph.
-
#remove_node(node) ⇒ Object
Removes node from the graph.
-
#remove_nodes(nodes) ⇒ Object
(also: #remove_nodes_from)
Removes multiple nodes from the graph.
-
#size(is_weighted = false) ⇒ Object
Returns the size of the graph.
-
#subgraph(nodes) ⇒ Object
Returns subgraph consisting of given array of nodes.
Constructor Details
#initialize(**graph_attrs) ⇒ Graph
Constructor for initializing graph
16 17 18 19 20 |
# File 'lib/networkx/graph.rb', line 16 def initialize(**graph_attrs) @nodes = {} @adj = {} @graph = graph_attrs end |
Instance Attribute Details
#adj ⇒ Hash{ Object => Hash{ Object => Hash{ Object => Object } } } (readonly)
Stores the edges and their attributes in an adjencency list form
7 8 9 |
# File 'lib/networkx/graph.rb', line 7 def adj @adj end |
#graph ⇒ Hash{ Object => Object } (readonly)
Stores the attributes of the graph
7 8 9 |
# File 'lib/networkx/graph.rb', line 7 def graph @graph end |
Class Method Details
.balanced_tree(r, h) ⇒ Object
18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 |
# File 'lib/networkx/others/generators.rb', line 18 def self.balanced_tree(r, h) edges = [] q = [0] i = 0 h.times do t = q.dup q.clear t.each do |v| r.times do i += 1 edges << [v, i] q << i end end end graph = new(name: "balanced_tree(#{r}, #{h})") graph.add_edges(edges) graph end |
.barbell_graph(m1, m2) ⇒ Object
38 39 40 41 42 43 44 45 46 |
# File 'lib/networkx/others/generators.rb', line 38 def self.(m1, m2) edges = complete_edges(m1) edges.concat((m1..m2 + m1).map { |k| [k - 1, k] }) edges.concat complete_edges(m1 + m2...m1 + m2 + m1) graph = new(name: "barbell_graph(#{m1}, #{m2})") graph.add_edges(edges) graph end |
.bull_graph ⇒ Object
145 146 147 148 149 150 |
# File 'lib/networkx/others/generators.rb', line 145 def self.bull_graph edges = [[0, 1], [1, 2], [2, 0], [1, 3], [2, 4]] graph = new(name: 'bull_graph') graph.add_edges(edges) graph end |
.circular_ladder_graph(n) ⇒ Object
63 64 65 66 67 68 69 70 71 72 73 |
# File 'lib/networkx/others/generators.rb', line 63 def self.circular_ladder_graph(n) edges = (0...n - 1).map { |v| [v, v + 1] } edges << [n - 1, 0] edges.concat((n...2 * n - 1).map { |v| [v, v + 1] }) edges << [2 * n - 1, n] edges.concat((0...n).map { |v| [v, v + n] }) graph = new(name: "circular_ladder_graph(#{n})") graph.add_edges(edges) graph end |
.complete_edges(n) ⇒ Object
private class method
6 7 8 9 10 11 12 13 14 15 16 |
# File 'lib/networkx/others/generators.rb', line 6 def self.complete_edges(n) n = (0...n) if n.is_a?(Integer) edges = [] n.each do |i| n.each do |j| edges << [i, j] if i < j end end edges end |
.complete_graph(n) ⇒ Object
48 49 50 51 52 53 54 55 56 57 58 59 60 61 |
# File 'lib/networkx/others/generators.rb', line 48 def self.complete_graph(n) n = (0...n) if n.is_a?(Integer) edges = [] n.each do |i| n.each do |j| edges << [i, j] if i < j end end graph = new(name: "complete_graph(#{n})") graph.add_edges(edges) graph end |
.cubical_graph ⇒ Object
152 153 154 155 156 |
# File 'lib/networkx/others/generators.rb', line 152 def self.cubical_graph graph = circular_ladder_graph(4) graph.graph[:name] = 'cubical_graph' graph end |
.cycle_graph(n) ⇒ Object
75 76 77 78 79 80 81 82 |
# File 'lib/networkx/others/generators.rb', line 75 def self.cycle_graph(n) edges = (0...n - 1).map { |v| [v, v + 1] } edges << [n - 1, 0] graph = new(name: "cycle_graph(#{n})") graph.add_edges(edges) graph end |
.diamond_graph ⇒ Object
158 159 160 161 162 163 |
# File 'lib/networkx/others/generators.rb', line 158 def self.diamond_graph edges = [[0, 1], [0, 2], [1, 2], [1, 3], [2, 3]] graph = new(name: 'diamond_graph') graph.add_edges(edges) graph end |
.dodecahedral_graph ⇒ Object
12
166 167 168 169 170 171 172 |
# File 'lib/networkx/others/generators.rb', line 166 def self.dodecahedral_graph edges = (0...19).map { |k| [k, k + 1] } edges.concat [[0, 19], [0, 10], [1, 8], [2, 6], [3, 19], [4, 17], [5, 15], [7, 14], [9, 13], [11, 18], [12, 16]] graph = new(name: 'dodecahedral_graph') graph.add_edges(edges) graph end |
.empty_graph(number_of_nodes) ⇒ Object
84 85 86 87 88 |
# File 'lib/networkx/others/generators.rb', line 84 def self.empty_graph(number_of_nodes) empty_graph = new(name: "empty_graph#{number_of_nodes}") empty_graph.add_nodes_from(0...number_of_nodes) empty_graph end |
.heawood_graph ⇒ Object
174 175 176 177 178 179 180 181 |
# File 'lib/networkx/others/generators.rb', line 174 def self.heawood_graph edges = (0...13).map { |k| [k, k + 1] } edges << [13, 0] edges.concat [[0, 5], [1, 10], [2, 7], [3, 12], [4, 9], [6, 11], [8, 13]] graph = new(name: 'heawood_graph') graph.add_edges(edges) graph end |
.house_graph ⇒ Object
183 184 185 186 187 188 |
# File 'lib/networkx/others/generators.rb', line 183 def self.house_graph edges = [[0, 1], [0, 2], [1, 3], [2, 3], [2, 4], [3, 4]] graph = new(name: 'house_graph') graph.add_edges(edges) graph end |
.house_x_graph ⇒ Object
190 191 192 193 194 195 196 |
# File 'lib/networkx/others/generators.rb', line 190 def self.house_x_graph edges = (0...4).map { |k| [k, k + 1] } edges.concat [[0, 2], [0, 3], [1, 3], [2, 4], [3, 4]] graph = new(name: 'house_x_graph') graph.add_edges(edges) graph end |
.ladder_graph(n) ⇒ Object
90 91 92 93 94 95 96 97 98 |
# File 'lib/networkx/others/generators.rb', line 90 def self.ladder_graph(n) edges = (0...n - 1).map { |k| [k, k + 1] } edges.concat((n...2 * n - 1).map { |k| [k, k + 1] }) edges.concat((0...n).map { |k| [k, k + n] }) graph = new(name: "ladder_graph(#{n})") graph.add_edges(edges) graph end |
.lollipop_graph(m, n) ⇒ Object
100 101 102 103 104 105 106 107 |
# File 'lib/networkx/others/generators.rb', line 100 def self.lollipop_graph(m, n) edges = complete_edges(m) edges.concat((m - 1...m - 1 + n).map { |v| [v, v + 1] }) graph = new(name: "lollipop_graph(#{m}, #{n})") graph.add_edges(edges) graph end |
.moebius_kantor_graph ⇒ Object
198 199 200 201 202 203 204 205 |
# File 'lib/networkx/others/generators.rb', line 198 def self.moebius_kantor_graph edges = (0...15).map { |k| [k, k + 1] } edges << [15, 0] edges.concat [[0, 5], [1, 12], [2, 7], [4, 9], [3, 14], [6, 11], [8, 13], [10, 15]] graph = new(name: 'moebius_kantor_graph') graph.add_edges(edges) graph end |
.null_graph ⇒ Object
109 110 111 |
# File 'lib/networkx/others/generators.rb', line 109 def self.null_graph new(name: 'null_graph') end |
.octahedral_graph ⇒ Object
8: 6 nodes, 12 edges
208 209 210 211 212 213 214 215 216 217 218 |
# File 'lib/networkx/others/generators.rb', line 208 def self.octahedral_graph edges = [] 6.times do |i| 6.times do |j| edges << [i, j] if i != j && i + j != 5 end end graph = new(name: 'octahedral_graph') graph.add_edges(edges) graph end |
.path_graph(n) ⇒ Object
113 114 115 116 117 118 119 |
# File 'lib/networkx/others/generators.rb', line 113 def self.path_graph(n) edges = (0...n - 1).map { |v| [v, v + 1] } graph = new(name: "path_graph(#{n})") graph.add_edges(edges) graph end |
.read_edgelist(path, comment: '#', delimiter: nil) ⇒ Object Also known as: read_edges
6 7 8 9 10 11 12 13 14 15 16 17 |
# File 'lib/networkx/others/reads.rb', line 6 def read_edgelist(path, comment: '#', delimiter: nil) edges = File.readlines(path).filter_map do |line| line.sub!(/#{comment}.+/, '') line.strip.split(delimiter) if line.strip.size > 0 end edges.each{|edge| edge.map!{|node| NetworkX.to_number_if_possible(node) } } graph = new graph.add_edges(edges) graph end |
.read_weighted_edgelist(path, comment: '#', delimiter: nil) ⇒ Object Also known as: read_weighted_edges
20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 |
# File 'lib/networkx/others/reads.rb', line 20 def read_weighted_edgelist(path, comment: '#', delimiter: nil) edges = File.readlines(path).filter_map do |line| line.sub!(/#{comment}.+/, '') line.strip.split(delimiter) if line.strip.size > 0 end edges.map! do |x, y, weight| [ NetworkX.to_number_if_possible(x), NetworkX.to_number_if_possible(y), {weight: NetworkX.to_number_if_possible(weight)} ] end graph = new graph.add_edges(edges) graph end |
.star_graph(n) ⇒ Object
121 122 123 124 125 126 127 |
# File 'lib/networkx/others/generators.rb', line 121 def self.star_graph(n) edges = (1..n).map { |i| [0, i] } graph = new(name: "star_graph(#{n})") graph.add_edges(edges) graph end |
.tetrahedral_graph ⇒ Object
220 221 222 223 224 |
# File 'lib/networkx/others/generators.rb', line 220 def self.tetrahedral_graph graph = complete_graph(4) graph.graph[:name] = 'tetrahedral_graph' graph end |
.trivial_graph ⇒ Object
129 130 131 132 133 |
# File 'lib/networkx/others/generators.rb', line 129 def self.trivial_graph trivial_graph = new(name: 'trivial_grpph') trivial_graph.add_node(0) trivial_graph end |
.wheel_graph(n) ⇒ Object
135 136 137 138 139 140 141 142 143 |
# File 'lib/networkx/others/generators.rb', line 135 def self.wheel_graph(n) edges = (1..n - 1).map { |i| [0, i] } edges.concat((1...n - 1).map { |i| [i, i + 1] }) edges << [1, n - 1] graph = new(name: "wheel_graph(#{n})") graph.add_edges(edges) graph end |
Instance Method Details
#add_edge(node1, node2, **edge_attrs) ⇒ Object
Adds the respective edges
33 34 35 36 37 38 39 40 |
# File 'lib/networkx/graph.rb', line 33 def add_edge(node1, node2, **edge_attrs) add_node(node1) add_node(node2) edge_attrs = (@adj[node1][node2] || {}).merge(edge_attrs) @adj[node1][node2] = edge_attrs @adj[node2][node1] = edge_attrs end |
#add_edges(edges) ⇒ Object
Adds multiple edges from an array
47 48 49 50 51 52 53 54 55 |
# File 'lib/networkx/graph.rb', line 47 def add_edges(edges) case edges when Array edges.each { |node1, node2, attrs| add_edge(node1, node2, **(attrs || {})) } else raise ArgumentError, 'Expected argument to be an Array of edges, ' \ "received #{edges.class.name} instead." end end |
#add_edges_from(rng) ⇒ Object
57 58 59 |
# File 'lib/networkx/graph.rb', line 57 def add_edges_from(rng) rng.each { |node| add_edge(*node) } end |
#add_node(node, **node_attrs) ⇒ Object
Adds a node and its attributes to the graph
68 69 70 71 72 73 74 75 |
# File 'lib/networkx/graph.rb', line 68 def add_node(node, **node_attrs) if @nodes.has_key?(node) @nodes[node].merge!(node_attrs) else @adj[node] = {} @nodes[node] = node_attrs end end |
#add_nodes(nodes) ⇒ Object
Adds multiple nodes to the graph
83 84 85 86 87 88 89 90 91 92 93 |
# File 'lib/networkx/graph.rb', line 83 def add_nodes(nodes) case nodes when Set, Array nodes.each { |node, node_attrs| add_node(node, **(node_attrs || {})) } when Range nodes.each { |node| add_node(node) } else raise ArgumentError, 'Expected argument to be an Array/Set/Range of nodes, ' \ "received #{nodes.class.name} instead." end end |
#add_nodes_from(nodes_for_adding) ⇒ Object
[TODO][EXPERIMENTAL]
98 99 100 101 102 103 104 105 |
# File 'lib/networkx/graph.rb', line 98 def add_nodes_from(nodes_for_adding) case nodes_for_adding when String nodes_for_adding.each_char { |node| add_node(node) } else nodes_for_adding.each { |node| add_node(node) } end end |
#add_path(paths) ⇒ Object
107 108 109 |
# File 'lib/networkx/graph.rb', line 107 def add_path(paths) paths.each_cons(2){|x, y| add_edge(x, y) } end |
#add_weighted_edge(node1, node2, weight) ⇒ Object
Adds weighted edge
183 184 185 |
# File 'lib/networkx/graph.rb', line 183 def add_weighted_edge(node1, node2, weight) add_edge(node1, node2, weight: weight) end |
#add_weighted_edges(edges, weights) ⇒ Object
Adds multiple weighted edges
195 196 197 198 199 200 201 202 203 204 |
# File 'lib/networkx/graph.rb', line 195 def add_weighted_edges(edges, weights) raise ArgumentError, 'edges and weights array must have equal number of elements.' \ unless edges.size == weights.size raise ArgumentError, 'edges and weight must be given in an Array.' \ unless edges.is_a?(Array) && weights.is_a?(Array) (edges.transpose << weights).transpose.each do |node1, node2, weight| add_weighted_edge(node1, node2, weight) end end |
#add_weighted_edges_from(edges, weight: :weight) ⇒ Object
[TODO][EXPERIMENTAL]
210 211 212 213 214 |
# File 'lib/networkx/graph.rb', line 210 def add_weighted_edges_from(edges, weight: :weight) edges.each do |s, t, w| add_edge(s, t, **{weight => w}) end end |
#bfs_edges(node) ⇒ Object
[EXPERIMENTAL]
84 85 86 |
# File 'lib/networkx/traversals/bfs.rb', line 84 def bfs_edges(node) each_bfs_edge(node).to_a end |
#bfs_nodes(root) ⇒ Object
60 61 62 |
# File 'lib/networkx/traversals/bfs.rb', line 60 def bfs_nodes(root) each_bfs_node(root).to_a end |
#clear ⇒ Object
Clears the graph
270 271 272 273 274 |
# File 'lib/networkx/graph.rb', line 270 def clear @adj.clear @nodes.clear @graph.clear end |
#degree(nodes = nil) ⇒ Object
[EXPERIMENTAL]
421 422 423 424 425 426 427 428 429 |
# File 'lib/networkx/graph.rb', line 421 def degree(nodes = nil) if nodes.nil? @adj.transform_values(&:size) else res = {} nodes.each { |node| res[node] = @adj[node].size } res end end |
#dfs_edges(node) ⇒ Object
89 90 91 |
# File 'lib/networkx/traversals/edge_dfs.rb', line 89 def dfs_edges(node) each_dfs_edge(node).to_a end |
#dfs_postorder_nodes(root, used = {root => true}) ⇒ Array[Object]
[EXPERIMENTAL]
115 116 117 118 119 120 121 122 123 124 125 126 |
# File 'lib/networkx/traversals/dfs.rb', line 115 def dfs_postorder_nodes(root, used = {root => true}) res = [] @adj[root].each do |v, _data| next if used[v] used[v] = true res.concat dfs_postorder_nodes(v, used) end res << root res end |
#dfs_preorder_nodes(root) ⇒ Array[Object]
[EXPERIMENTAL]
86 87 88 |
# File 'lib/networkx/traversals/dfs.rb', line 86 def dfs_preorder_nodes(root) each_dfs_preorder_node(root).to_a end |
#directed? ⇒ Boolean
443 444 445 |
# File 'lib/networkx/graph.rb', line 443 def directed? ['NetworkX::DiGraph', 'NetworkX::MultiDiGraph'].include?(self.class.name) end |
#each_bfs_edge(node) ⇒ Object
[EXPERIMENTAL]
91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 |
# File 'lib/networkx/traversals/bfs.rb', line 91 def each_bfs_edge(node) return enum_for(:each_bfs_edge, node) unless block_given? que = [node] used = {node => true} while que[0] node = que.shift @adj[node].each do |v, _data| next if used[v] used[v] = true yield(node, v) que << v end end end |
#each_bfs_node(root) ⇒ Object
64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 |
# File 'lib/networkx/traversals/bfs.rb', line 64 def each_bfs_node(root) return enum_for(:each_bfs_node, root) unless block_given? queue = [root] dist = {root => 0} while (v = queue.shift) yield v d = dist[v] @adj[v].each do |u, _data| next if dist[u] dist[u] = d + 1 queue << u end end end |
#each_dfs_edge(node) ⇒ Object
93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 |
# File 'lib/networkx/traversals/edge_dfs.rb', line 93 def each_dfs_edge(node) return enum_for(:each_dfs_edge, node) unless block_given? st = [node] used = {} parents = {} while st[-1] node = st.pop yield(parents[node], node) if parents[node] used[node] = true @adj[node].reverse_each do |v, _data| next if used[v] parents[v] = node st << v unless used[v] end end end |
#each_dfs_postorder_node(root, &block) ⇒ Object
129 130 131 132 133 |
# File 'lib/networkx/traversals/dfs.rb', line 129 def each_dfs_postorder_node(root, &block) return enum_for(:each_dfs_postorder_node, root) unless block_given? dfs_postorder_nodes(root).each(&block) end |
#each_dfs_preorder_node(root) ⇒ Object
[EXPERIMENTAL]
93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 |
# File 'lib/networkx/traversals/dfs.rb', line 93 def each_dfs_preorder_node(root) return enum_for(:each_dfs_preorder_node, root) unless block_given? st = [root] used = {root => true} while st[-1] node = st.pop yield(node) @adj[node].reverse_each do |v, _data| next if used[v] used[v] = node st << v end end end |
#each_edge(data: false) ⇒ Object
[TODO][EXPERIMENTAL]
248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 |
# File 'lib/networkx/graph.rb', line 248 def each_edge(data: false) return enum_for(:each_edge, data: data) unless block_given? h = {} @adj.each do |v, ws| ws.each do |w, info| next if v > w h[[v, w, info]] = true end end if data h.each { |(v, w, info), _true| yield(v, w, info) } else h.each { |(v, w, _info), _true| yield(v, w) } end end |
#each_node(data: false, &block) ⇒ Object
230 231 232 233 234 |
# File 'lib/networkx/graph.rb', line 230 def each_node(data: false, &block) return enum_for(:each_node, data: data) unless block_given? data ? @nodes.each(&block) : @nodes.each_key(&block) end |
#edge?(node1, node2) ⇒ Boolean Also known as: has_edge?
Checks if the the edge consisting of two nodes is present in the graph
294 295 296 |
# File 'lib/networkx/graph.rb', line 294 def edge?(node1, node2) node?(node1) && @adj[node1].has_key?(node2) end |
#edge_subgraph(edges) ⇒ Object
Returns subgraph conisting of given edges
401 402 403 404 405 406 407 408 409 410 411 412 413 414 415 416 417 418 |
# File 'lib/networkx/graph.rb', line 401 def edge_subgraph(edges) case edges when Array, Set sub_graph = NetworkX::Graph.new(**@graph) edges.each do |u, v| raise KeyError, "Edge between #{u} and #{v} does not exist in the graph!" unless @nodes.has_key?(u) \ && @adj[u].has_key?(v) sub_graph.add_node(u, **@nodes[u]) sub_graph.add_node(v, **@nodes[v]) sub_graph.add_edge(u, v, **@adj[u][v]) end sub_graph else raise ArgumentError, 'Expected Argument to be Array or Set of edges, ' \ "received #{edges.class.name} instead." end end |
#edges(data: false) ⇒ Array[[Object, Object]]
[TODO][EXPERIMENTAL]
241 242 243 |
# File 'lib/networkx/graph.rb', line 241 def edges(data: false) each_edge(data: data).to_a end |
#get_edge_data(node1, node2) ⇒ Object
Gets the edge data
318 319 320 321 322 |
# File 'lib/networkx/graph.rb', line 318 def get_edge_data(node1, node2) raise KeyError, 'No such edge exists!' unless node?(node1) && node?(node2) @adj[node1][node2] end |
#get_node_data(node) ⇒ Object
Gets the node data
305 306 307 308 309 |
# File 'lib/networkx/graph.rb', line 305 def get_node_data(node) raise ArgumentError, 'No such node exists!' unless node?(node) @nodes[node] end |
#info ⇒ Object
431 432 433 434 435 436 437 |
# File 'lib/networkx/graph.rb', line 431 def info info = '' info << "Type: #{self.class}\n" info << "Number of nodes: #{number_of_nodes}\n" info << "Number of edges: #{number_of_edges}\n" info end |
#multigraph? ⇒ Boolean
439 440 441 |
# File 'lib/networkx/graph.rb', line 439 def multigraph? ['NetworkX::MultiGraph', 'NetworkX::MultiDiGraph'].include?(self.class.name) end |
#neighbours(node) ⇒ Object
Retus a hash of neighbours of a node
330 331 332 333 334 |
# File 'lib/networkx/graph.rb', line 330 def neighbours(node) raise KeyError, 'No such node exists!' unless node?(node) @adj[node] end |
#node?(node) ⇒ Boolean Also known as: has_node?
Checks if a node is present in the graph
282 283 284 |
# File 'lib/networkx/graph.rb', line 282 def node?(node) @nodes.has_key?(node) end |
#nodes(data: false) ⇒ Hash | Array
Return nodes of graph
222 223 224 225 226 227 228 |
# File 'lib/networkx/graph.rb', line 222 def nodes(data: false) if data @nodes else @nodes.keys end end |
#number_of_edges ⇒ Object
Returns number of edges
348 349 350 |
# File 'lib/networkx/graph.rb', line 348 def number_of_edges @adj.values.map(&:length).sum / 2 end |
#number_of_nodes ⇒ Object
Returns number of nodes
340 341 342 |
# File 'lib/networkx/graph.rb', line 340 def number_of_nodes @nodes.length end |
#put_graph_x2 ⇒ Object
Experimental For debug.
229 230 231 232 233 234 235 |
# File 'lib/networkx/others/generators.rb', line 229 def put_graph_x2 output = <<~"OUTPUT" #{number_of_nodes} #{number_of_edges} #{edges.map { |edge| edge.join(' ') }.join("\n")} OUTPUT puts output end |
#remove_edge(node1, node2) ⇒ Object
Removes edge from the graph
149 150 151 152 153 154 155 156 |
# File 'lib/networkx/graph.rb', line 149 def remove_edge(node1, node2) raise KeyError, "#{node1} is not a valid node." unless @nodes.has_key?(node1) raise KeyError, "#{node2} is not a valid node" unless @nodes.has_key?(node2) raise KeyError, 'The given edge is not a valid one.' unless @adj[node1].has_key?(node2) @adj[node1].delete(node2) @adj[node2].delete(node1) if node1 != node2 end |
#remove_edges(edges) ⇒ Object Also known as: remove_edges_from
Removes multiple edges from the graph
164 165 166 167 168 169 170 171 172 |
# File 'lib/networkx/graph.rb', line 164 def remove_edges(edges) case edges when Array, Set edges.each { |node1, node2| remove_edge(node1, node2) } else raise ArgumentError, 'Expected Arguement to be Array or Set of edges, ' \ "received #{edges.class.name} instead." end end |
#remove_node(node) ⇒ Object
Removes node from the graph
117 118 119 120 121 122 123 |
# File 'lib/networkx/graph.rb', line 117 def remove_node(node) raise KeyError, "Error in deleting node #{node} from Graph." unless @nodes.has_key?(node) @adj[node].each_key { |k| @adj[k].delete(node) } @adj.delete(node) @nodes.delete(node) end |
#remove_nodes(nodes) ⇒ Object Also known as: remove_nodes_from
Removes multiple nodes from the graph
131 132 133 134 135 136 137 138 139 |
# File 'lib/networkx/graph.rb', line 131 def remove_nodes(nodes) case nodes when Set, Array nodes.each { |node| remove_node(node) } else raise ArgumentError, 'Expected argument to be an Array or Set of nodes, ' \ "received #{nodes.class.name} instead." end end |
#size(is_weighted = false) ⇒ Object
Returns the size of the graph
359 360 361 362 363 364 365 366 367 368 |
# File 'lib/networkx/graph.rb', line 359 def size(is_weighted = false) if is_weighted graph_size = 0 @adj.each do |_, hash_val| hash_val.each { |_, v| graph_size += v[:weight] if v.has_key?(:weight) } end return graph_size / 2 end number_of_edges end |
#subgraph(nodes) ⇒ Object
Returns subgraph consisting of given array of nodes
376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 |
# File 'lib/networkx/graph.rb', line 376 def subgraph(nodes) case nodes when Array, Set sub_graph = NetworkX::Graph.new(**@graph) nodes.each do |u, _| raise KeyError, "#{u} does not exist in the current graph!" unless @nodes.has_key?(u) sub_graph.add_node(u, **@nodes[u]) @adj[u].each do |v, edge_val| sub_graph.add_edge(u, v, **edge_val) if @adj[u].has_key?(v) && nodes.include?(v) end end sub_graph else raise ArgumentError, 'Expected Argument to be Array or Set of nodes, ' \ "received #{nodes.class.name} instead." end end |