Example #1
0
    def test_no_contraction_if_each_edge_is_different(self):
        g = self.create_graph(number_nodes=6)

        g.add_edge(
            Edge(s=0, t=1, forward=True, backward=True, data=self.edge_data(name="a"))
        )
        g.add_edge(
            Edge(
                s=1,
                t=2,
                forward=True,
                backward=True,
                data=self.edge_data(name="a", highway="b"),
            )
        )
        g.add_edge(
            Edge(
                s=2,
                t=3,
                forward=True,
                backward=False,
                data=self.edge_data(name="a", highway="b"),
            )
        )
        g.add_edge(
            Edge(
                s=3,
                t=4,
                forward=True,
                backward=True,
                data=self.edge_data(name="a", highway="b"),
            )
        )
        g.add_edge(
            Edge(
                s=4,
                t=5,
                forward=True,
                backward=True,
                data=self.edge_data(name="a", highway="b", max_v=123),
            )
        )

        contracted_graph = ContractGraph(g).contract()

        self.assertEqual(len(contracted_graph.vertices), 6)
        self.assertEqual(len(contracted_graph.edges), 5)

        result_edge_data = [e.data for e in contracted_graph.edges]
        expected_edge_data = [
            self.edge_data(name="a"),
            self.edge_data(name="a", highway="b"),
            self.edge_data(name="a", highway="b"),
            self.edge_data(name="a", highway="b"),
            self.edge_data(name="a", highway="b", max_v=123),
        ]
        self.assertCountEqual(result_edge_data, expected_edge_data)
Example #2
0
    def test_contract_a_path_to_two_nodes_and_one_edge(self):
        g = self.create_graph(number_nodes=3)

        g.add_edge(Edge(s=0, t=1, forward=True, backward=True, data=self.edge_data()))
        g.add_edge(Edge(s=1, t=2, forward=True, backward=True, data=self.edge_data()))

        contracted_graph = ContractGraph(g).contract()

        self.assertEqual(len(contracted_graph.vertices), 2)
        self.assertEqual(len(contracted_graph.edges), 1)
 def test_three_vertex_should_three_edges_test(self):
     v1 = Vertex(23, VertexData(1, 1))
     v2 = Vertex(24, VertexData(2, 1))
     v3 = Vertex(1, VertexData(5, 6))
     e1 = Edge(v1.id, v2.id, True, True, EdgeData(123, "", 50, ""))
     e2 = Edge(v2.id, v3.id, True, True, EdgeData(123, "", 50, ""))
     e3 = Edge(v1.id, v3.id, True, True, EdgeData(123, "", 50, ""))
     g = gf.build_graph_from_vertices_edges([v1, v2, v3], [e1, e2, e3])
     self.assertTrue(len(g.vertices) == 3)
     self.assertTrue(len(g.edges) == 3)
Example #4
0
    def test_add_edges_correct_in_out_neighbors_test(self):
        g = Graph()

        v1, v2, v3, v4 = (
            self._get_vertex(0),
            self._get_vertex(1),
            self._get_vertex(2),
            self._get_vertex(3),
        )
        e_forward = Edge(v1.id, v2.id, True, False, EdgeData(1, " ", 100, "Test"))
        e_backward = Edge(v2.id, v3.id, False, True, EdgeData(1, " ", 100, "Test"))
        e_nothing = Edge(v3.id, v4.id, False, False, EdgeData(1, " ", 100, "Test"))
        e_both = Edge(v4.id, v1.id, True, True, EdgeData(1, " ", 100, "Test"))

        g.add_node(v1)
        g.add_node(v2)
        g.add_node(v3)
        g.add_node(v4)

        g.add_edge(e_forward)
        g.add_edge(e_backward)
        g.add_edge(e_nothing)
        g.add_edge(e_both)

        self.assertEqual(len(g.edges), 4)
        self.assertEqual(g.edges[0], e_forward)
        self.assertEqual(g.edges[1], e_backward)
        self.assertEqual(g.edges[2], e_nothing)
        self.assertEqual(g.edges[3], e_both)

        self.assertIn(e_forward.s, g.inneighbors[e_forward.t])
        self.assertIn(e_forward.t, g.outneighbors[e_forward.s])
        self.assertNotIn(e_forward.s, g.outneighbors[e_forward.t])
        self.assertNotIn(e_forward.t, g.inneighbors[e_forward.s])

        self.assertNotIn(e_backward.s, g.inneighbors[e_backward.t])
        self.assertNotIn(e_backward.t, g.outneighbors[e_backward.s])
        self.assertIn(e_backward.s, g.outneighbors[e_backward.t])
        self.assertIn(e_backward.t, g.inneighbors[e_backward.s])

        self.assertNotIn(e_nothing.s, g.inneighbors[e_nothing.t])
        self.assertNotIn(e_nothing.t, g.outneighbors[e_nothing.s])
        self.assertNotIn(e_nothing.s, g.outneighbors[e_nothing.t])
        self.assertNotIn(e_nothing.t, g.inneighbors[e_nothing.s])

        self.assertIn(e_both.s, g.inneighbors[e_both.t])
        self.assertIn(e_both.t, g.outneighbors[e_both.s])
        self.assertIn(e_both.s, g.outneighbors[e_both.t])
        self.assertIn(e_both.t, g.inneighbors[e_both.s])
Example #5
0
    def test_contract_loop_to_nothing(self):
        g = self.create_graph(number_nodes=4)

        # loop
        g.add_edge(Edge(s=0, t=1, forward=True, backward=True, data=self.edge_data()))
        g.add_edge(Edge(s=1, t=2, forward=True, backward=True, data=self.edge_data()))
        g.add_edge(Edge(s=2, t=0, forward=True, backward=True, data=self.edge_data()))

        # connection (otherwise no intersections will be found)
        g.add_edge(Edge(s=0, t=3, forward=True, backward=True, data=self.edge_data()))

        contracted_graph = ContractGraph(g).contract()

        self.assertEqual(len(contracted_graph.vertices), 2)
        self.assertEqual(len(contracted_graph.edges), 1)
 def test_two_vertex_should_fail_test(self):
     v1 = Vertex(23, VertexData(1, 1))
     v2 = Vertex(24, VertexData(2, 1))
     e = Edge(21, 24, True, True, EdgeData(123, "", 50, ""))
     g = gf.build_graph_from_vertices_edges([v1, v2], [e])
     self.assertTrue(len(g.vertices) == 2)
     self.assertTrue(len(g.edges) == 0)
    def test_if_data_is_converted(self):
        g = self.create_graph(number_nodes=2)

        edge_data = self.edge_data()
        g.add_edge(Edge(s=0, t=1, forward=True, backward=True, data=edge_data))

        nx_graph = convert_to_networkx(g)

        self.assertEqual(len(nx_graph.nodes), 2)
        self.assertEqual(len(nx_graph.edges), 2)

        nx_edges = nx_graph.edges(data=True)
        e0, e1 = nx_edges
        self.assertCountEqual([(e0[0], e0[1]), (e1[0], e1[1])], [(0, 1),
                                                                 (1, 0)])
        self.assertDictEqual(
            e0[2],
            {
                "highway": edge_data.highway,
                "length": edge_data.length,
                "max_v": edge_data.max_v,
                "name": edge_data.name,
            },
        )
        self.assertDictEqual(
            e1[2],
            {
                "highway": edge_data.highway,
                "length": edge_data.length,
                "max_v": edge_data.max_v,
                "name": edge_data.name,
            },
        )
 def test_two_vertex_should_be_one_edge_test(self):
     v1 = Vertex(23, VertexData(1, 1))
     v2 = Vertex(24, VertexData(2, 1))
     e = Edge(23, 24, True, True, EdgeData(123, "", 50, ""))
     g = gf.build_graph_from_vertices_edges([v1, v2], [e])
     self.assertTrue(len(g.vertices) == 2)
     self.assertTrue(len(g.edges) == 1)
     self.assertEqual(g.edges[0].data.length, 123)
Example #9
0
    def add_edges_correct_in_out_neighbors_test(self):
        g = Graph()

        v1, v2, v3, v4 = self.get_vertex(0), self.get_vertex(
            1), self.get_vertex(2), self.get_vertex(3)
        e_forward = Edge(v1.id, v2.id, 1, " ", 100, True, False, "Test")
        e_backward = Edge(v2.id, v3.id, 1, " ", 100, False, True, "Test")
        e_nothing = Edge(v3.id, v4.id, 1, " ", 100, False, False, "Test")
        e_both = Edge(v4.id, v1.id, 1, " ", 100, True, True, "Test")

        g.add_node(v1)
        g.add_node(v2)
        g.add_node(v3)
        g.add_node(v4)

        g.add_edge(e_forward)
        g.add_edge(e_backward)
        g.add_edge(e_nothing)
        g.add_edge(e_both)

        self.assertEqual(len(g.edges), 4)
        self.assertEqual(g.edges[0], e_forward)
        self.assertEqual(g.edges[1], e_backward)
        self.assertEqual(g.edges[2], e_nothing)
        self.assertEqual(g.edges[3], e_both)

        self.assertTrue(e_forward.s in g.inneighbors[e_forward.t])
        self.assertTrue(e_forward.t in g.outneighbors[e_forward.s])
        self.assertTrue(e_forward.s not in g.outneighbors[e_forward.t])
        self.assertTrue(e_forward.t not in g.inneighbors[e_forward.s])

        self.assertTrue(e_backward.s not in g.inneighbors[e_backward.t])
        self.assertTrue(e_backward.t not in g.outneighbors[e_backward.s])
        self.assertTrue(e_backward.s in g.outneighbors[e_backward.t])
        self.assertTrue(e_backward.t in g.inneighbors[e_backward.s])

        self.assertTrue(e_nothing.s not in g.inneighbors[e_nothing.t])
        self.assertTrue(e_nothing.t not in g.outneighbors[e_nothing.s])
        self.assertTrue(e_nothing.s not in g.outneighbors[e_nothing.t])
        self.assertTrue(e_nothing.t not in g.inneighbors[e_nothing.s])

        self.assertTrue(e_both.s in g.inneighbors[e_both.t])
        self.assertTrue(e_both.t in g.outneighbors[e_both.s])
        self.assertTrue(e_both.s in g.outneighbors[e_both.t])
        self.assertTrue(e_both.t in g.inneighbors[e_both.s])
Example #10
0
    def test_add_edges_correct_set_of_neighbors_test(self):
        g = Graph()
        v1, v2, v3 = self._get_vertex(0), self._get_vertex(1), self._get_vertex(2)
        e_forward = Edge(v1.id, v2.id, True, False, EdgeData(1, " ", 100, "Test"))
        e_backward = Edge(v2.id, v3.id, False, True, EdgeData(1, " ", 100, "Test"))
        e_both = Edge(v3.id, v1.id, True, True, EdgeData(1, " ", 100, "Test"))

        g.add_node(v1)
        g.add_node(v2)
        g.add_node(v3)

        g.add_edge(e_forward)
        g.add_edge(e_backward)
        g.add_edge(e_both)

        self.assertTrue(self._checkEqual([v2.id, v3.id], g.all_neighbors(v1.id)))
        self.assertTrue(self._checkEqual([v1.id, v3.id], g.all_neighbors(v2.id)))
        self.assertTrue(self._checkEqual([v1.id, v2.id], g.all_neighbors(v3.id)))
Example #11
0
    def add_edge_adds_one_edge_test(self):
        g = Graph()

        v1, v2 = self.get_vertex(0), self.get_vertex(1)
        e = Edge(v1.id, v2.id, 1, " ", 100, True, True, "Test")

        g.add_node(v1)
        g.add_node(v2)
        g.add_edge(e)

        self.assertEqual(len(g.edges), 1)
        self.assertEqual(g.edges[0], e)
Example #12
0
    def test_add_edge_adds_one_edge_test(self):
        g = Graph()

        v1, v2 = self._get_vertex(0), self._get_vertex(1)
        data = EdgeData(23.4, "", 100, "")
        e = Edge(v1.id, v2.id, True, True, data)

        g.add_node(v1)
        g.add_node(v2)
        g.add_edge(e)

        self.assertEqual(len(g.edges), 1)
        self.assertEqual(g.edges[0], e)
    def test_converting_K4_graph(self):
        g = self.create_graph(number_nodes=4)

        g.add_edge(
            Edge(s=0, t=1, forward=True, backward=True, data=self.edge_data()))
        g.add_edge(
            Edge(s=1, t=2, forward=True, backward=True, data=self.edge_data()))
        g.add_edge(
            Edge(s=2, t=3, forward=True, backward=True, data=self.edge_data()))
        g.add_edge(
            Edge(s=3, t=0, forward=True, backward=True, data=self.edge_data()))

        g.add_edge(
            Edge(s=1, t=3, forward=True, backward=True, data=self.edge_data()))
        g.add_edge(
            Edge(s=0, t=2, forward=True, backward=True, data=self.edge_data()))

        nx_graph = convert_to_networkx(g)

        self.assertEqual(len(nx_graph.nodes), 4)
        self.assertEqual(len(nx_graph.edges), 12)
Example #14
0
    def test_contracting_stops_at_intersections(self):
        g = self.create_graph(number_nodes=7)

        # path of 5 nodes
        g.add_edge(Edge(s=0, t=1, forward=True, backward=True, data=self.edge_data()))
        g.add_edge(Edge(s=1, t=2, forward=True, backward=True, data=self.edge_data()))
        g.add_edge(Edge(s=2, t=3, forward=True, backward=True, data=self.edge_data()))
        g.add_edge(Edge(s=3, t=4, forward=True, backward=True, data=self.edge_data()))

        # path of two nodes attached in the middle of the path above
        g.add_edge(Edge(s=2, t=5, forward=True, backward=True, data=self.edge_data()))
        g.add_edge(Edge(s=5, t=6, forward=True, backward=True, data=self.edge_data()))

        # expected outcome: 4 nodes remain, and 3 edges, one deg 3 node, all others are deg 1 nodes

        contracted_graph = ContractGraph(g).contract()

        self.assertEqual(len(contracted_graph.vertices), 4)
        self.assertEqual(len(contracted_graph.edges), 3)

        nmb_neigbors = [len(contracted_graph.all_neighbors(n_id)) for n_id in range(4)]
        self.assertCountEqual(nmb_neigbors, [3, 1, 1, 1])
Example #15
0
    def test_contracting_stops_if_edge_is_different(self):
        g = self.create_graph(number_nodes=10)

        g.add_edge(
            Edge(
                s=0,
                t=1,
                forward=True,
                backward=True,
                data=self.edge_data(length=2, name="abc"),
            )
        )
        g.add_edge(
            Edge(
                s=1,
                t=2,
                forward=True,
                backward=True,
                data=self.edge_data(length=3, name="abc"),
            )
        )
        g.add_edge(
            Edge(
                s=2,
                t=3,
                forward=True,
                backward=True,
                data=self.edge_data(length=5, name="def"),
            )
        )
        g.add_edge(
            Edge(
                s=3,
                t=4,
                forward=True,
                backward=True,
                data=self.edge_data(length=7, name="def"),
            )
        )
        g.add_edge(
            Edge(
                s=4,
                t=5,
                forward=True,
                backward=True,
                data=self.edge_data(length=11, name="ghi"),
            )
        )
        g.add_edge(
            Edge(
                s=5,
                t=6,
                forward=True,
                backward=True,
                data=self.edge_data(length=13, name="ghi"),
            )
        )
        g.add_edge(
            Edge(
                s=6,
                t=7,
                forward=True,
                backward=True,
                data=self.edge_data(length=17, name="jkl"),
            )
        )
        g.add_edge(
            Edge(
                s=7,
                t=8,
                forward=True,
                backward=True,
                data=self.edge_data(length=23, name="mno"),
            )
        )
        g.add_edge(
            Edge(
                s=8,
                t=9,
                forward=True,
                backward=True,
                data=self.edge_data(length=29, name="mno"),
            )
        )
        # input: 0-1-2-3-4-5-6-7-8-9
        # expected outcome: 0-2-4-6-7-9

        contracted_graph = ContractGraph(g).contract()

        self.assertEqual(len(contracted_graph.vertices), 6)
        self.assertEqual(len(contracted_graph.edges), 5)

        result_edge_data = [e.data for e in contracted_graph.edges]
        expected_edge_data = [
            self.edge_data(length=5, name="abc"),
            self.edge_data(length=12, name="def"),
            self.edge_data(length=24, name="ghi"),
            self.edge_data(length=17, name="jkl"),
            self.edge_data(length=52, name="mno"),
        ]
        self.assertCountEqual(result_edge_data, expected_edge_data)
Example #16
0
    def _find_new_edges(self) -> Set[Edge]:
        #  maintain a list L of nodes from which we want to start searches to find new contracted edges
        #  initialize L with all intersection nodes (i.e., all nodes with degree != 2)
        #   for each node n in L
        #     for each of n's neighbor
        #       search until:
        #           - an intersection node is found or edge is found
        #           - the next edge is different in it's structure (e.g., different highway type, different max speed, ...)
        self.start_nodes = self._find_all_intersections()
        self.seen_start_nodes = set(self.start_nodes)
        new_edges = set()
        bidirectional_edges: Set[Tuple[int, int]] = set()

        out_edges_per_node = self._get_out_edges()
        while len(self.start_nodes) > 0:
            node_id = self.start_nodes.popleft()

            out_edges = out_edges_per_node[node_id]
            for first_out_edge in out_edges:
                start_node_id = node_id

                edges_to_merge, final_node_id = self._find_edges_to_merge(
                    start_node_id, first_out_edge
                )

                if len(edges_to_merge) == 0:
                    continue

                sum_edge_lengths = sum([e.data.length for e in edges_to_merge])
                data = replace(edges_to_merge[0].data, length=sum_edge_lengths)

                if edges_to_merge[0].backward:
                    #  deduplication measure; if not for this for bidirectional edges, that are
                    #  removed between intersections, 2 new edges would be created
                    smaller_node_id = (
                        start_node_id
                        if start_node_id < final_node_id
                        else final_node_id
                    )
                    bigger_node_id = (
                        start_node_id
                        if start_node_id > final_node_id
                        else final_node_id
                    )
                    if (smaller_node_id, bigger_node_id) in bidirectional_edges:
                        # already added this edge skip it
                        continue
                    bidirectional_edges.add((smaller_node_id, bigger_node_id))
                    merged_edge = Edge(
                        smaller_node_id,
                        bigger_node_id,
                        True,
                        edges_to_merge[0].backward,
                        data,
                    )
                else:
                    merged_edge = Edge(
                        start_node_id,
                        final_node_id,
                        True,
                        edges_to_merge[0].backward,
                        data,
                    )
                new_edges.add(merged_edge)
        return new_edges