Skip to content

Commit a4d766a

Browse files
committed
Add more tests
1 parent 54d40e6 commit a4d766a

File tree

8 files changed

+119
-95
lines changed

8 files changed

+119
-95
lines changed

src/MetaGraphsNext.jl

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,8 @@ using Graphs
55
using SimpleTraits
66

77
export MetaGraph
8-
export label_for, code_for, set_data!
8+
export label_for, code_for, labels
9+
export set_data!
910
export weighttype, default_weight, get_weight_function
1011
export MGFormat, DOTFormat
1112

src/graphs.jl

Lines changed: 0 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -47,30 +47,6 @@ function Base.issubset(meta_graph::MetaGraph, h::MetaGraph)
4747
return issubset(meta_graph.graph, h.graph)
4848
end
4949

50-
## Link between graph codes and metagraph labels
51-
52-
"""
53-
code_for(meta_graph::MetaGraph, label)
54-
55-
Find the vertex code (or index) associated with label `label`.
56-
57-
This can be useful to pass to methods inherited from `Graphs`. Note, however, that vertex codes can be reassigned after vertex deletion.
58-
"""
59-
function code_for(meta_graph::MetaGraph, label)
60-
return meta_graph.vertex_properties[label][1]
61-
end
62-
63-
"""
64-
label_for(meta_graph::MetaGraph, code)
65-
66-
Find the label associated with code `code`.
67-
68-
This can be useful to interpret the results of methods inherited from `Graphs`. Note, however, that vertex codes can be reassigned after vertex deletion.
69-
"""
70-
function label_for(meta_graph::MetaGraph, code::Integer)
71-
return meta_graph.vertex_labels[code]
72-
end
73-
7450
## Set vertex and edge data
7551

7652
"""

src/metagraph.jl

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,8 @@ struct MetaGraph{
4343
default_weight::Weight
4444
end
4545

46+
## Constructors
47+
4648
"""
4749
MetaGraph(
4850
graph,
@@ -175,6 +177,8 @@ function MetaGraph(
175177
)
176178
end
177179

180+
## Base extensions
181+
178182
function Base.show(
179183
io::IO, meta_graph::MetaGraph{<:Any,<:Any,Label,VertexData,EdgeData}
180184
) where {Label,VertexData,EdgeData}
@@ -199,3 +203,36 @@ function Base.:(==)(meta_graph_1::MetaGraph, meta_graph_2::MetaGraph)
199203
(meta_graph_1.default_weight == meta_graph_2.default_weight)
200204
)
201205
end
206+
207+
## Link between graph codes and metagraph labels
208+
209+
"""
210+
code_for(meta_graph::MetaGraph, label)
211+
212+
Find the vertex code (or index) associated with label `label`.
213+
214+
This can be useful to pass to methods inherited from `Graphs`. Note, however, that vertex codes can be reassigned after vertex deletion.
215+
"""
216+
function code_for(meta_graph::MetaGraph, label)
217+
return meta_graph.vertex_properties[label][1]
218+
end
219+
220+
"""
221+
label_for(meta_graph::MetaGraph, code)
222+
223+
Find the label associated with code `code`.
224+
225+
This can be useful to interpret the results of methods inherited from `Graphs`. Note, however, that vertex codes can be reassigned after vertex deletion.
226+
"""
227+
function label_for(meta_graph::MetaGraph, code::Integer)
228+
return meta_graph.vertex_labels[code]
229+
end
230+
231+
"""
232+
labels(meta_graph::MetaGraph)
233+
234+
List all vertex labels, *not necessarily in the same order as the codes!*
235+
"""
236+
function labels(meta_graph::MetaGraph)
237+
return values(meta_graph.vertex_labels)
238+
end

src/weights.jl

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -64,12 +64,11 @@ function Base.getindex(meta_weights::MetaWeights, code_1::Integer, code_2::Integ
6464
if has_edge(meta_graph, code_1, code_2)
6565
labels = meta_graph.vertex_labels
6666
weight_function = get_weight_function(meta_graph)
67-
weight_function(
68-
meta_graph[arrange(
69-
meta_graph, labels[code_1], labels[code_2], code_1, code_2
70-
)...],
67+
arranged_label_1, arranged_label_2 = arrange(
68+
meta_graph, labels[code_1], labels[code_2], code_1, code_2
7169
)
70+
return weight_function(meta_graph[arranged_label_1, arranged_label_2])
7271
else
73-
default_weight(meta_graph)
72+
return default_weight(meta_graph)
7473
end
7574
end

test/labels_codes_directedness.jl

Lines changed: 0 additions & 42 deletions
This file was deleted.

test/runtests.jl

Lines changed: 2 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -10,10 +10,10 @@ using Test
1010
@testset verbose = true "Code quality (Aqua.jl)" begin
1111
Aqua.test_all(MetaGraphsNext; ambiguities=false)
1212
end
13-
@testset verbose = true "Code formatting (JuliaFormatter.jl)" begin
13+
@testset verbose = false "Code formatting (JuliaFormatter.jl)" begin
1414
@test format(MetaGraphsNext; verbose=false, overwrite=false)
1515
end
16-
@testset verbose = true "Doctests (Documenter.jl)" begin
16+
@testset verbose = false "Doctests (Documenter.jl)" begin
1717
doctest(MetaGraphsNext)
1818
end
1919
@testset verbose = true "Tutorial" begin
@@ -27,7 +27,4 @@ using Test
2727
include(joinpath("tutorial", "3_files.jl"))
2828
end
2929
end
30-
@testset verbose = true "Labels, codes, directedness" begin
31-
include("labels_codes_directedness.jl")
32-
end
3330
end

test/tutorial/1_basics.jl

Lines changed: 70 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -16,9 +16,33 @@ colors = MetaGraph(
1616
graph_data="additive colors", # tag for the whole graph
1717
)
1818

19+
@test_throws ErrorException @inferred MetaGraph( #src
20+
Graph(); #src
21+
label_type=Symbol, #src
22+
vertex_data_type=NTuple{3,Int}, #src
23+
edge_data_type=String, #src
24+
graph_data="additive colors", #src
25+
) #src
26+
1927
# The `label_type` argument defines how vertices will be referred to, it can be anything but an integer type (to avoid confusion with codes, see below). The `vertex_data_type` and `edge_data_type` type determine what kind of data will be associated with each vertex and edge. Finally, `graph_data` can contain an arbitrary object associated with the graph as a whole.
2028

21-
# However, since this constructor receives types as keyword arguments, it is type-unstable. Casual users may not care, but if your goal is performance, you should use the following syntax instead, which relies on positional arguments.
29+
# However, since this constructor receives types as keyword arguments, it is type-unstable. Casual users may not care, but if your goal is performance, you should use either of the following alternatives:
30+
# 1. Wrap the constructor in a function
31+
# 2. Switch to positional arguments (be careful with the order!)
32+
33+
function colors_constructor()
34+
return MetaGraph(
35+
Graph();
36+
label_type=Symbol,
37+
vertex_data_type=NTuple{3,Int},
38+
edge_data_type=String,
39+
graph_data="additive colors",
40+
)
41+
end
42+
43+
@test @inferred colors_constructor() == colors #src
44+
45+
#-
2246

2347
colors_stable = MetaGraph(Graph(), Symbol, NTuple{3,Int}, String, "additive colors")
2448

@@ -28,9 +52,7 @@ colors_stable = MetaGraph(Graph(), Symbol, NTuple{3,Int}, String, "additive colo
2852
NTuple{3,Int}, #src
2953
String, #src
3054
"additive colors", #src
31-
) == colors_stable #src
32-
33-
# Be careful with the order!
55+
) == colors #src
3456

3557
# ## Modifying the graph
3658

@@ -103,39 +125,69 @@ label_for(colors, 1)
103125
label_for(colors, 3)
104126
@test label_for(colors, 3) == :blue #src
105127

106-
# ## Adding weights
128+
# Test coherence #src
107129

108-
# The most simple way to add edge weights is to speficy a default weight for all of them.
130+
for label in labels(colors) #src
131+
@test label_for(colors, code_for(colors, label)) == label #src
132+
end #src
109133

110-
weighted_default = MetaGraph(Graph(); label_type=Symbol, default_weight=2);
111-
#-
112-
default_weight(weighted_default)
113-
@test @inferred default_weight(weighted_default) == 2 #src
114-
#-
115-
weighttype(weighted_default)
116-
@test @inferred weighttype(weighted_default) == Int #src
134+
for code in vertices(colors) #src
135+
@test code_for(colors, label_for(colors, code)) == code #src
136+
end #src
137+
138+
# Delete vertex in a copy and test again #src
117139

118-
# You can use the `weight_function` keyword to specify a function which will transform edge metadata into a weight. This weight must always be the same type as the `default_weight`.
140+
colors_copy = copy(colors) #src
141+
rem_vertex!(colors_copy, 1) #src
142+
143+
for label in labels(colors_copy) #src
144+
@test label_for(colors_copy, code_for(colors_copy, label)) == label #src
145+
end #src
146+
147+
for code in vertices(colors_copy) #src
148+
@test code_for(colors_copy, label_for(colors_copy, code)) == code #src
149+
end #src
150+
151+
# ## Handling weights
152+
153+
# You can use the `weight_function` field to specify a function which will transform edge metadata into a weight. This weight must always have the same type as the `default_weight`, which is the value returned in case an edge does not exist.
119154

120155
weighted = MetaGraph(
121-
Graph(); label_type=Symbol, edge_data_type=Float64, weight_function=ed -> ed^2
156+
Graph();
157+
label_type=Symbol,
158+
edge_data_type=Float64,
159+
weight_function=ed -> ed^2,
160+
default_weight=Inf,
122161
);
123162

124163
weighted[:alice] = nothing;
125164
weighted[:bob] = nothing;
165+
weighted[:charlie] = nothing;
166+
126167
weighted[:alice, :bob] = 2.0;
168+
weighted[:bob, :charlie] = 3.0;
127169
#-
128170
weight_matrix = Graphs.weights(weighted)
129171
@test @inferred Graphs.weights(weighted) == weight_matrix
130172
#-
173+
default_weight(weighted)
174+
@test @inferred default_weight(weighted) Inf #src
175+
#-
131176
size(weight_matrix)
132-
@test size(weight_matrix) == (2, 2) #src
177+
@test size(weight_matrix) == (3, 3) #src
133178
#-
134179
weight_matrix[1, 2]
135180
@test @inferred weight_matrix[1, 2] 4.0 #src
136181
#-
182+
weight_matrix[2, 3]
183+
@test @inferred weight_matrix[2, 3] 9.0 #src
184+
#-
185+
weight_matrix[1, 3]
186+
@test @inferred weight_matrix[1, 3] Inf #src
187+
#-
137188
wf = get_weight_function(weighted)
138-
wf(3)
139-
@test @inferred wf(3) == 9 #src
189+
@test @inferred get_weight_function(weighted) == wf
190+
wf(4.0)
191+
@test @inferred wf(4.0) 16.0 #src
140192

141193
# You can then use all functions from Graphs.jl that require weighted graphs (see the rest of the tutorial).

test/tutorial/2_graphs.jl

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,8 @@ cities[:Paris, :Berlin] = 878;
3333

3434
is_directed(cities)
3535
@test @inferred !is_directed(cities) #src
36+
@test !istrait(IsDirected{typeof(cities)}) #src
37+
@test MetaGraphsNext.arrange(cities, :London, :Paris) == (:Paris, :London)
3638
#-
3739
eltype(cities)
3840
@test @inferred eltype(cities) == Int #src
@@ -119,6 +121,8 @@ rock_paper_scissors[:paper, :rock] = "paper beats rock";
119121

120122
is_directed(rock_paper_scissors)
121123
@test @inferred is_directed(rock_paper_scissors) #src
124+
@test istrait(IsDirected{typeof(rock_paper_scissors)}) #src
125+
@test MetaGraphsNext.arrange(rock_paper_scissors, :paper, :rock) == (:paper, :rock) #src
122126

123127
# Directed graphs can be reversed:
124128

0 commit comments

Comments
 (0)