@@ -66,11 +66,13 @@ badjlist = [[1,2,5,6],[3,4,6]]
66
66
bg = BipartiteGraph(7, fadjlist, badjlist)
67
67
```
68
68
"""
69
- mutable struct BipartiteGraph{I<: Integer } <: LightGraphs.AbstractGraph{I}
69
+ mutable struct BipartiteGraph{I<: Integer ,M } <: LightGraphs.AbstractGraph{I}
70
70
ne:: Int
71
71
fadjlist:: Vector{Vector{I}} # `fadjlist[src] => dsts`
72
72
badjlist:: Vector{Vector{I}} # `badjlist[dst] => srcs`
73
+ metadata:: M
73
74
end
75
+ BipartiteGraph (ne:: Integer , fadj:: AbstractVector , badj:: AbstractVector ) = BipartiteGraph (ne, fadj, badj, nothing )
74
76
75
77
"""
76
78
```julia
@@ -91,10 +93,22 @@ $(SIGNATURES)
91
93
92
94
Build an empty `BipartiteGraph` with `nsrcs` sources and `ndsts` destinations.
93
95
"""
94
- BipartiteGraph (nsrcs:: T , ndsts:: T ) where T = BipartiteGraph (0 , map (_-> T[], 1 : nsrcs), map (_-> T[], 1 : ndsts))
96
+ function BipartiteGraph (nsrcs:: T , ndsts:: T ; metadata= nothing ) where T
97
+ fadjlist = map (_-> T[], 1 : nsrcs)
98
+ badjlist = map (_-> T[], 1 : ndsts)
99
+ BipartiteGraph (0 , fadjlist, badjlist, metadata)
100
+ end
95
101
96
- Base. eltype (:: Type{BipartiteGraph{I}} ) where I = I
97
- Base. empty! (g:: BipartiteGraph ) = (foreach (empty!, g. fadjlist); foreach (empty!, g. badjlist); g. ne = 0 ; g)
102
+ Base. eltype (:: Type{<:BipartiteGraph{I}} ) where I = I
103
+ function Base. empty! (g:: BipartiteGraph )
104
+ foreach (empty!, g. fadjlist)
105
+ foreach (empty!, g. badjlist)
106
+ g. ne = 0
107
+ if g. metadata != = nothing
108
+ foreach (empty!, g. metadata)
109
+ end
110
+ g
111
+ end
98
112
Base. length (:: BipartiteGraph ) = error (" length is not well defined! Use `ne` or `nv`." )
99
113
100
114
if isdefined (LightGraphs, :has_contiguous_vertices )
@@ -106,8 +120,8 @@ LightGraphs.vertices(g::BipartiteGraph) = (𝑠vertices(g), 𝑑vertices(g))
106
120
𝑑vertices (g:: BipartiteGraph ) = axes (g. badjlist, 1 )
107
121
has_𝑠vertex (g:: BipartiteGraph , v:: Integer ) = v in 𝑠vertices (g)
108
122
has_𝑑vertex (g:: BipartiteGraph , v:: Integer ) = v in 𝑑vertices (g)
109
- 𝑠neighbors (g:: BipartiteGraph , i:: Integer ) = g. fadjlist[i]
110
- 𝑑neighbors (g:: BipartiteGraph , i :: Integer ) = g. badjlist[i ]
123
+ 𝑠neighbors (g:: BipartiteGraph , i:: Integer , with_metadata :: Val{M} = Val ( false )) where M = M ? zip (g . fadjlist[i], g . metadata[i]) : g. fadjlist[i]
124
+ 𝑑neighbors (g:: BipartiteGraph , j :: Integer , with_metadata :: Val{M} = Val ( false )) where M = M ? zip ( g. badjlist[j], (g . metadata[i][j] for i in g . badjlist[j])) : g . badjlist[j ]
111
125
LightGraphs. ne (g:: BipartiteGraph ) = g. ne
112
126
LightGraphs. nv (g:: BipartiteGraph ) = sum (length, vertices (g))
113
127
LightGraphs. edgetype (g:: BipartiteGraph{I} ) where I = BipartiteEdge{I}
124
138
# ##
125
139
# ## Populate
126
140
# ##
127
- LightGraphs. add_edge! (g:: BipartiteGraph , i:: Integer , j:: Integer ) = add_edge! (g, BipartiteEdge (i, j))
128
- function LightGraphs. add_edge! (g:: BipartiteGraph , edge:: BipartiteEdge )
141
+ struct NoMetadata
142
+ end
143
+ const NO_METADATA = NoMetadata ()
144
+
145
+ LightGraphs. add_edge! (g:: BipartiteGraph , i:: Integer , j:: Integer , md= NO_METADATA) = add_edge! (g, BipartiteEdge (i, j), md)
146
+ function LightGraphs. add_edge! (g:: BipartiteGraph , edge:: BipartiteEdge , md= NO_METADATA)
129
147
@unpack fadjlist, badjlist = g
130
148
verts = vertices (g)
131
149
s, d = src (edge), dst (edge)
@@ -134,6 +152,9 @@ function LightGraphs.add_edge!(g::BipartiteGraph, edge::BipartiteEdge)
134
152
index = searchsortedfirst (list, d)
135
153
@inbounds (index <= length (list) && list[index] == d) && return false # edge already in graph
136
154
insert! (list, index, d)
155
+ if md != = NO_METADATA
156
+ insert! (g. metadata[s], index, md)
157
+ end
137
158
138
159
g. ne += 1
139
160
@inbounds list = badjlist[d]
@@ -170,7 +191,7 @@ Base.length(it::BipartiteEdgeIter{ALL}) = 2ne(it.g)
170
191
171
192
Base. eltype (it:: BipartiteEdgeIter ) = edgetype (it. g)
172
193
173
- function Base. iterate (it:: BipartiteEdgeIter{SRC,BipartiteGraph{T}} , state= (1 , 1 , SRC)) where T
194
+ function Base. iterate (it:: BipartiteEdgeIter{SRC,<: BipartiteGraph{T}} , state= (1 , 1 , SRC)) where T
174
195
@unpack g = it
175
196
neqs = nsrcs (g)
176
197
neqs == 0 && return nothing
@@ -191,7 +212,7 @@ function Base.iterate(it::BipartiteEdgeIter{SRC,BipartiteGraph{T}}, state=(1, 1,
191
212
return nothing
192
213
end
193
214
194
- function Base. iterate (it:: BipartiteEdgeIter{DST,BipartiteGraph{T}} , state= (1 , 1 , DST)) where T
215
+ function Base. iterate (it:: BipartiteEdgeIter{DST,<: BipartiteGraph{T}} , state= (1 , 1 , DST)) where T
195
216
@unpack g = it
196
217
nvars = ndsts (g)
197
218
nvars == 0 && return nothing
0 commit comments