Example #1
0
  /**
   * Returns minimum spanning tree. Method uses Kruskal's algorithm for this purpose. Working only
   * for undirected graph
   *
   * @return map represents branches of minimum-spanning-tree (key - child, value - parent)
   */
  public static Map<Integer, Integer> minTreeKruskal(Graph graph) {
    if (graph.isDirected())
      throw new UnsupportedOperationException(
          "Kruscal's algorithm works only for undirected graphs");
    Map<Integer, Integer> tree = new HashMap<>();
    // get all edges via iterator
    List<Graph.Edge> edges = new ArrayList<>();
    for (Graph.Edge edge : graph.edges()) edges.add(edge);
    // sort edges by weight
    Collections.sort(
        edges,
        new Comparator<Graph.Edge>() {
          @Override
          public int compare(Graph.Edge o1, Graph.Edge o2) {
            return o1.getWeight() - o2.getWeight();
          }
        });

    // for algorithm we use disjoint set forest data structure (a.k.a. union-find, merge-find etc.
    // see wikipedia)
    DisjointSetForest<Integer> set = new DisjointSetForest<>();
    for (Integer number : graph.vertexes()) set.makeSet(number);
    // adding edges to tree, while it can't be possible to add edge that don't creates a cycle
    for (Graph.Edge edge : edges) {
      if (set.find(edge.getIn()) != set.find(edge.getOut())) {
        if (!tree.containsKey(edge.getIn())) tree.put(edge.getIn(), edge.getOut());
        else tree.put(edge.getOut(), edge.getIn());
        set.union(edge.getIn(), edge.getOut());
      }
    }
    return tree;
  }
Example #2
0
  /**
   * Returns maximum spanning tree. Method uses Prim's algorithm for this purpose. Working only for
   * undirected graph
   *
   * @return map represents branches of maximum-spanning-tree (key - child, value - parent)
   */
  public static Map<Integer, Integer> maxTreePrim(Graph graph) {
    if (graph.isDirected())
      throw new UnsupportedOperationException("Prim's algorithm works only for undirected graphs");
    Map<Integer, Integer> tree = new HashMap<>();
    List<Graph.Edge> edges = new ArrayList<>();
    Set<Integer> labeled = new HashSet<>();
    Iterator<Integer> vertexIt = graph.vertexes().iterator();
    // continue while there are vertexes to add
    while (vertexIt.hasNext()) {
      int vertex = vertexIt.next();
      // if vertex is labeled - skip it
      if (labeled.contains(vertex)) continue;
      labeled.add(vertex);
      // Add to list all edges adjacent to vertex
      edges.addAll(graph.getAdjacentEdges(vertex));
      // While we have edges to add
      while (!edges.isEmpty()) {

        // sort all edges by weight
        Collections.sort(
            edges,
            new Comparator<Graph.Edge>() {
              @Override
              public int compare(Graph.Edge o1, Graph.Edge o2) {
                return o2.getWeight() - o1.getWeight();
              }
            });
        Iterator<Graph.Edge> it = edges.iterator();
        while (it.hasNext()) {
          Graph.Edge edge = it.next();
          if (!labeled.contains(edge.getIn())) {
            labeled.add(edge.getIn());
            edges.addAll(graph.getAdjacentEdges(edge.getIn()));
            tree.put(edge.getIn(), edge.getOut());
            break;
          }
          if (!labeled.contains(edge.getOut())) {
            labeled.add(edge.getOut());
            edges.addAll(graph.getAdjacentEdges(edge.getOut()));
            tree.put(edge.getOut(), edge.getIn());
            break;
          }
          it.remove();
        }
      }
    }
    return tree;
  }
Example #3
0
  @After
  public void validateGraphState() {
    new EqualsTester()
        .addEqualityGroup(network, Graphs.copyOf(network), ImmutableNetwork.copyOf(network))
        .testEquals();

    String networkString = network.toString();
    assertThat(networkString).contains("isDirected: " + network.isDirected());
    assertThat(networkString).contains("allowsParallelEdges: " + network.allowsParallelEdges());
    assertThat(networkString).contains("allowsSelfLoops: " + network.allowsSelfLoops());

    int nodeStart = networkString.indexOf("nodes:");
    int edgeStart = networkString.indexOf("edges:");
    String nodeString = networkString.substring(nodeStart, edgeStart);
    String edgeString = networkString.substring(edgeStart);

    Graph<Integer> asGraph = network.asGraph();
    assertThat(network.nodes()).isEqualTo(asGraph.nodes());
    assertThat(network.nodeOrder()).isEqualTo(asGraph.nodeOrder());
    assertThat(network.isDirected()).isEqualTo(asGraph.isDirected());
    assertThat(network.allowsSelfLoops()).isEqualTo(asGraph.allowsSelfLoops());

    for (String edge : network.edges()) {
      // TODO(b/27817069): Consider verifying the edge's incident nodes in the string.
      assertThat(edgeString).contains(edge);

      Iterator<Integer> endpointsIterator = network.incidentNodes(edge).iterator();
      Integer nodeA = endpointsIterator.next();
      Integer nodeB = endpointsIterator.next();
      assertThat(network.edgesConnecting(nodeA, nodeB)).contains(edge);
      assertThat(network.successors(nodeA)).contains(nodeB);
      assertThat(network.adjacentNodes(nodeA)).contains(nodeB);
      assertThat(network.outEdges(nodeA)).contains(edge);
      assertThat(network.incidentEdges(nodeA)).contains(edge);
      assertThat(network.predecessors(nodeB)).contains(nodeA);
      assertThat(network.adjacentNodes(nodeB)).contains(nodeA);
      assertThat(network.inEdges(nodeB)).contains(edge);
      assertThat(network.incidentEdges(nodeB)).contains(edge);

      for (Integer incidentNode : network.incidentNodes(edge)) {
        assertThat(network.nodes()).contains(incidentNode);
        for (String adjacentEdge : network.incidentEdges(incidentNode)) {
          assertTrue(
              edge.equals(adjacentEdge) || network.adjacentEdges(edge).contains(adjacentEdge));
        }
      }
    }

    for (Integer node : network.nodes()) {
      assertThat(nodeString).contains(node.toString());

      assertThat(network.adjacentNodes(node)).isEqualTo(asGraph.adjacentNodes(node));
      assertThat(network.predecessors(node)).isEqualTo(asGraph.predecessors(node));
      assertThat(network.successors(node)).isEqualTo(asGraph.successors(node));

      for (Integer otherNode : network.nodes()) {
        Set<String> edgesConnecting = network.edgesConnecting(node, otherNode);
        boolean isSelfLoop = node.equals(otherNode);
        if (network.isDirected() || !isSelfLoop) {
          assertThat(edgesConnecting)
              .isEqualTo(Sets.intersection(network.outEdges(node), network.inEdges(otherNode)));
        }
        if (!network.allowsParallelEdges()) {
          assertThat(edgesConnecting.size()).isAtMost(1);
        }
        if (!network.allowsSelfLoops() && isSelfLoop) {
          assertThat(edgesConnecting).isEmpty();
        }
        for (String edge : edgesConnecting) {
          assertThat(network.incidentNodes(edge)).isEqualTo(Endpoints.of(network, node, otherNode));
        }
      }

      for (String incidentEdge : network.incidentEdges(node)) {
        assertTrue(
            network.inEdges(node).contains(incidentEdge)
                || network.outEdges(node).contains(incidentEdge));
        assertThat(network.edges()).contains(incidentEdge);
        assertThat(network.incidentNodes(incidentEdge)).contains(node);
      }

      for (String inEdge : network.inEdges(node)) {
        assertThat(network.incidentEdges(node)).contains(inEdge);
        assertThat(network.outEdges(network.incidentNodes(inEdge).adjacentNode(node)))
            .contains(inEdge);
      }

      for (String outEdge : network.outEdges(node)) {
        assertThat(network.incidentEdges(node)).contains(outEdge);
        assertThat(network.inEdges(network.incidentNodes(outEdge).adjacentNode(node)))
            .contains(outEdge);
      }

      for (Integer adjacentNode : network.adjacentNodes(node)) {
        assertTrue(
            network.predecessors(node).contains(adjacentNode)
                || network.successors(node).contains(adjacentNode));
        assertTrue(
            !network.edgesConnecting(node, adjacentNode).isEmpty()
                || !network.edgesConnecting(adjacentNode, node).isEmpty());
      }

      for (Integer predecessor : network.predecessors(node)) {
        assertThat(network.successors(predecessor)).contains(node);
        assertThat(network.edgesConnecting(predecessor, node)).isNotEmpty();
      }

      for (Integer successor : network.successors(node)) {
        assertThat(network.predecessors(successor)).contains(node);
        assertThat(network.edgesConnecting(node, successor)).isNotEmpty();
      }
    }
  }
 @Override
 public boolean init(Graph graph) {
   return !(graph.getNodeCount() == 0 || !(graph.isDirected()));
 }
 @Override
 public final boolean isDirected() {
   return g.isDirected();
 }