(kill(all), load(graphs), 0);
0;

/* a helper macro to capture output to a string ("print to string") */
(p2s([L])::=buildq([L, f: gensym()],
    block([f: make_string_output_stream()],
      with_stdout(f, splice(L)),
      get_output_stream_string(f))), 'done);
'done$

p2s(print_graph(create_graph([1,2,3], [[1,2], [2,3], [1,3]])));
"
Graph on 3 vertices with 3 edges.
Adjacencies:
  1 :  3  2
  2 :  3  1
  3 :  1  2
"$

p2s(print_graph(create_graph(
                  [1,2,3,4],
                  [
                   [1,3], [1,4],
                   [2,3], [2,4]
                  ],
                  'directed = true)));
"
Digraph on 4 vertices with 4 arcs.
Adjacencies:
  1 :  4  3
  2 :  4  3
  3 :
  4 :
"$

p2s(print_graph(circulant_graph(10, [1, 3])));
"
Graph on 10 vertices with 20 edges.
Adjacencies:
  9 :  2  6  0  8
  8 :  1  5  9  7
  7 :  0  4  8  6
  6 :  9  3  7  5
  5 :  8  2  6  4
  4 :  7  1  5  3
  3 :  6  0  4  2
  2 :  9  5  3  1
  1 :  8  4  2  0
  0 :  7  3  9  1
"$

(g:create_graph([1,2,3,4,5],[[1,2],[2,3],[1,3],[4,5]]), 0);
0;

vertices(g);
[1,2,3,4,5];

edges(g);
[[4,5],[1,3],[2,3],[1,2]];

neighbors(4,g);
[5];

neighbors(1,g);
[3,2];

is_connected(g);
false;

connected_components(g);
[[5,4],[3,2,1]];

vertex_distance(1,5,g);
inf;

(g:create_graph([1,2,3,4,5],[[1,2],[2,3],[1,3],[3,4],[4,5]]), 0);
0;

is_connected(g);
true;

is_biconnected(g);
false;

biconnected_components(g);
[[1,2,3],[3,4],[4,5]];

vertex_distance(1,5,g);
3;

shortest_path(1,5,g);
[1,3,4,5];

is_connected(empty_graph(1));
true;

is_connected(empty_graph(0));
true;

is_connected(complete_graph(4));
true;

max_clique(complete_graph(5));
[0,1,2,3,4];

max_clique(empty_graph(5));
[0];

max_clique(empty_graph(0));
[];

is_bipartite(flower_snark(4));
true;

chromatic_number(flower_snark(4));
2;

chromatic_index(flower_snark(4));
3;

is_bipartite(flower_snark(5));
false;

chromatic_number(flower_snark(5));
3;

chromatic_index(flower_snark(5));
4;

is_bipartite(empty_graph(1));
true;

is_bipartite(empty_graph(0));
true;

is_bipartite(complete_graph(0));
true;

chromatic_number(empty_graph(0));
0;

chromatic_number(empty_graph(1));
1;

chromatic_number(empty_graph(2));
1;

chromatic_number(complete_graph(2));
2;

chromatic_index(empty_graph(3));
0;

chromatic_index(cycle_graph(3));
3;

chromatic_index(cycle_graph(4));
2;

girth(flower_snark(4));
4;

girth(flower_snark(5));
5;

girth(flower_snark(6));
6;

girth(flower_snark(7));
6;

odd_girth(flower_snark(4));
inf;

odd_girth(flower_snark(5));
5;

odd_girth(flower_snark(6));
inf;

odd_girth(flower_snark(7));
7;

is_isomorphic(empty_graph(0), empty_graph(0));
true;

is_isomorphic(empty_digraph(0), empty_digraph(0));
true;

is_isomorphic(empty_graph(1), empty_graph(1));
true;

is_isomorphic(graph_product(path_graph(3), path_graph(5)), graph_product(path_graph(5), path_graph(3)));
true;

is_isomorphic(graph_union(cycle_graph(3), cycle_graph(3)), cycle_graph(6));
false;

is_isomorphic(petersen_graph(), complement_graph(line_graph(complete_graph(5))));
true;

is_planar(empty_graph(0));
true;

is_planar(empty_graph(2));
true;

is_planar(dodecahedron_graph());
true;

is_planar(flower_snark(5));
false;

is_planar(complete_graph(4));
true;

is_planar(complete_graph(5));
false;

is_planar(complete_graph(6));
false;

is_planar(complete_bipartite_graph(3,3));
false;

is_planar(complete_bipartite_graph(2,4));
true;

is_tree(empty_graph(0));
false;

is_tree(empty_graph(1));
true;

is_tree(empty_graph(2));
false;

is_tree(path_graph(4));
true;

is_tree(cycle_graph(4));
false;

(g:graph_union(cycle_graph(3), cycle_graph(4)), 0);
0;

vertex_connectivity(g);
0;

edge_connectivity(g);
0;

(add_edge([0,3], g), 0);
0;

vertex_connectivity(g);
1;

edge_connectivity(g);
1;

min_edge_cut(g);
[[0,3]];

(add_edge([0,4], g), 0);
0;

vertex_connectivity(g);
1;

min_vertex_cut(g);
[0];

edge_connectivity(g);
2;

(g: graph_union(complete_graph(5), complete_graph(5)), connect_vertices([5,6],[2,3,4], g), 0);
0;

vertex_connectivity(g);
2;

vertex_connectivity(path_graph(2));
inf;

edge_connectivity(path_graph(2));
1;

vertex_connectivity(empty_graph(1));
inf;

edge_connectivity(empty_graph(1));
inf;

(g:graph6_decode("H|twgsN"),0);
0;

is_planar(g);
true;

vertex_connectivity(g);
3;

edge_connectivity(g);
4;

min_vertex_cut(g);
[3,4,5];

(g:create_graph(
  [1,2,3,4,5],
  [
   [1,2], [2,5],
   [5,3],
   [5,4], [3,4], [1,3]
  ],              
  directed=true),
0);
0;

topological_sort(g);
[1,2,5,3,4];

topological_sort(path_digraph(3));
[0,1,2];

topological_sort(cycle_digraph(3));
[];

/* Check for edge weight copying on digraphs (Bug 2541) */
block([dg: cycle_digraph(3), dg2],
      set_edge_weight([0,1], 100, dg),
      dg2: copy_graph(dg),
      is (get_edge_weight([0,1], dg2) = get_edge_weight([0,1], dg)));
true;

edge_coloring(cycle_graph(4));
[2,[[[0,1],2],[[1,2],1],[[2,3],2],[[0,3],1]]]$

edge_coloring(petersen_graph());
[4,
 [[[0,5],3],[[5,7],1],[[0,1],1],[[1,6],2],[[6,8],1],[[1,2],3],[[2,7],4],
  [[7,9],2],[[2,3],2],[[3,8],3],[[5,8],2],[[3,4],1],[[4,9],4],[[6,9],3],
  [[0,4],2]]]$

/* larger example which triggers ADJUST-ARRAY
 * this example is to ensure that result of shortest_weighted_path doesn't change
 */
block ([g200_20 : petersen_graph(200, 20)],
       for e in edges(g200_20) do set_edge_weight(e, e[1]+e[2], g200_20),
       shortest_weighted_path(0, 100, g200_20));
[3100, [0, 200, 220, 240, 260, 280, 300, 100]];

/* test vertex labels */

(vv: [[17, "foo"], [29, "foo"], [1729, "bar"], 2, 4, 6, 8],
 G: create_graph (vv, []),
 get_unique_vertex_by_label ("bar", G));
1729;

get_unique_vertex_by_label ("baz", G);
false;

errcatch (get_unique_vertex_by_label ("foo", G));
[];

get_all_vertices_by_label ("foo", G);
[17, 29];

(for v in [2, 17, 29, 4, 6] do set_vertex_label (v, "baz", G),
 get_all_vertices_by_label ("baz", G));
[2, 4, 6, 17, 29];

makelist (get_vertex_label (v, G), v, [8, 2, 4, 6, 1729, 17, 29]);
[false, "baz", "baz", "baz", "bar", "baz", "baz"];

