DEV Community

Cover image for Polynomial-Time Algorithm for MDS (P = NP)
Frank Vega
Frank Vega

Posted on

Polynomial-Time Algorithm for MDS (P = NP)

Problem Overview

The Minimum Dominating Set (MDS) problem is a classic challenge in graph theory and computer science. Given an undirected graph G=(V,E)G = (V, E) , the goal is to find a subset of vertices SVS \subseteq V of minimum size such that every vertex in VV is either in SS or adjacent to at least one vertex in SS . This subset SS is called a dominating set, and the MDS seeks the smallest possible such set.

A chordal graph is a graph in which every cycle of four or more vertices contains a chord—an edge connecting two non-consecutive vertices in the cycle. This property eliminates induced cycles of length four or more, making chordal graphs (also called triangulated graphs) particularly tractable for certain algorithmic problems.

Algorithm Description

The provided algorithm, implemented in Python using NetworkX, computes the MDS for a general undirected graph by transforming it into a chordal graph, where the MDS can be solved in linear time.

Minimum Dominating Set Algorithm

Below is the Python implementation of the find_dominating_set algorithm using NetworkX. This algorithm computes the minimum dominating set of an undirected graph by transforming it into a chordal graph and leveraging a linear-time solution for chordal graphs.

import networkx as nx

def find_dominating_set(graph):
    if not isinstance(graph, nx.Graph):
        raise ValueError("Input must be an undirected NetworkX Graph.")
    if graph.number_of_nodes() == 0 or graph.number_of_edges() == 0:
        return set()
    optimal_dominating_set = set(nx.isolates(graph))
    graph.remove_nodes_from(optimal_dominating_set)
    if graph.number_of_nodes() == 0:
        return optimal_dominating_set

    dominance = {i: frozenset(list(graph.neighbors(i)) + [i]) for i in graph.nodes()}
    chordal_graph = nx.Graph()
    for i in graph.nodes():
        chordal_graph.add_edge((i, i), (i, dominance[i]))
        for j in graph.neighbors(i):
            if i < j:
                chordal_graph.add_edge((j, j), (i, dominance[i]))
                chordal_graph.add_edge((i, i), (j, dominance[j]))

    for i in graph.nodes():
        for j in graph.nodes():
            if i < j:
                chordal_graph.add_edge((i, i), (j, j))

    tuple_nodes = minimum_dominating_set_in_chordal_graph(chordal_graph)
    optimal_dominating_set.update({tuple_node[0] for tuple_node in tuple_nodes})

    return optimal_dominating_set

Enter fullscreen mode Exit fullscreen mode

Here’s a step-by-step description:

  1. Input Validation:

    • Checks if the input is a valid nx.Graph. Raises a ValueError if not.
  2. Handle Special Cases:

    • Returns an empty set if the graph has no nodes or no edges.
    • Identifies isolated nodes (vertices with degree 0) using nx.isolates(graph), adds them to the dominating set SS , and removes them from the graph. If the graph becomes empty, returns SS .
  3. Graph Transformation:

    • Optimize by precomputing the dominance dictionary: Calculate the closed neighborhood N[i]={i}{j(i,j)E}N[i] = \{i\} \cup \{j \mid (i, j) \in E\} for each vertex ii once and store it in a dictionary. This avoids redundant calculations in each iteration, improving efficiency.
    • Constructs a new graph chordal_graph (assumed to be chordal) with tuple nodes:
      • For each vertex iVi \in V , creates nodes (i,i)(i, i) and (i,dominance[i])(i, dominance[i]) , where dominance[i]=N[i]={i}{j(i,j)E}dominance[i] = N[i] = \{i\} \cup \{j \mid (i, j) \in E\} (the closed neighborhood).
    • Adds edges:
      • (i,i)(i, i) to (i,dominance[i])(i, dominance[i]) for each ii .
      • For each edge (i,j)E(i, j) \in E with i<ji < j :
      • (j,j)(j, j) to (i,dominance[i])(i, dominance[i]) .
      • (i,i)(i, i) to (j,dominance[j])(j, dominance[j]) .
      • (i,i)(i, i) to (j,j)(j, j) for all i<ji < j , forming a clique among (i,i)(i, i) nodes.
  4. Compute MDS in Chordal Graph:

    • Calls minimum_dominating_set_in_chordal_graph(chordal_graph) (assumed to run in linear time) to find the MDS in the transformed graph, returning a set of tuple nodes DD .
  5. Map Back to Original Graph:

    • Extracts the first component of each tuple in DD (i.e., {tuple_node[0]tuple_nodeD}\{tuple\_node[0] \mid tuple\_node \in D\} ) and adds them to SS , which already includes isolated nodes.
    • Returns SS as the MDS of GG .

Correctness Analysis

The algorithm’s correctness hinges on two claims:

  1. The transformed graph is chordal, allowing an efficient MDS computation.
  2. The MDS of the chordal graph corresponds to the MDS of the original graph.

Key Points:

  • Isolated Nodes: Correctly included in SS since they must be dominated and have no neighbors.
  • Chordal Property: The new constructed graph chordal_graph is chordal (every cycle of length 4 or more has a chord), enabling efficient computation of the Minimum Dominating Set (MDS). The clique of Type 1 nodes (e.g., (i,i)(i, i) ) and structured Type 2 connections (e.g., (i,dominance[i])(i, dominance[i]) ) ensure this. The Type 1 nodes form a clique, which is trivially chordal. Any cycle involving Type 2 nodes (i,dominance[i])(i, dominance[i]) must include their neighbors (i,i)(i, i) and (j,j)(j, j) . Since all Type 1 nodes are interconnected (forming a clique), every cycle longer than 3 has a chord. Thus, chordal_graph is chordal.
  • Domination in GG :
    • For a vertex vGv \in G :
    • If (v,v)(v, v) or (v,dominance[v])(v, dominance[v]) is in DD , then vSv \in S , and vv is dominated.
    • If neither is in DD , (v,v)(v, v) must be dominated in chordal_graph. Its neighbors include (j,dominance[j])(j, dominance[j]) (where jj is a neighbor of vv ) and all (j,j)(j, j) . If any such node is in DD , jSj \in S , and if jj is adjacent to vv in GG , vv is dominated.
    • The clique among (i,i)(i, i) nodes ensures connectivity, and edges to (i,dominance[i])(i, dominance[i]) preserve GG ’s structure.
  • Minimality:
    • The Minimum Dominating Set (MDS) minimizes D|D| . If the algorithm produces a dominating set SS and a smaller dominating set SS' exists in the graph, then the set D={(i,i)iS}D' = \{(i, i) | i ∈ S'\} would dominate all nodes in chordal_graph, contradicting the minimality of DD .
  • Guarantee the Appropriate Solution:
    • When deciding between selecting (i,i)(i, i) or (i,dominance[i])(i, dominance[i]) , choosing either has the same significance. This is because we extract from (i,i)(i, i) and (i,dominance[i])(i, dominance[i]) the first coordinate in the tuple, i.e., the node ii . Consequently, the transformation encodes GG ’s domination constraints such that the MDS in chordal_graph maps to a minimal set in GG .

Conclusion:

Assuming minimum_dominating_set_in_chordal_graph correctly finds the MDS, the algorithm produces a valid MDS for GG . The transformation preserves domination relationships, and the inclusion of isolated nodes.

Running Time Analysis

Let n=Vn = |V| (number of vertices) and m=Em = |E| (number of edges) in the original graph GG .

  1. Input Validation: O(1)O(1) using isinstance check.
  2. Special Cases:
    • graph.number_of_nodes() and graph.number_of_edges(): O(1)O(1) in NetworkX.
    • nx.isolates(graph): O(n)O(n) to check degrees.
    • Removing nodes: O(n)O(n) in worst case.
  3. Transformation:
    • Time complexity of precomputing the dominance dictionary: Constructing the dictionary requires O(n2)O(n^2) time, as it involves iterating over all nn nodes and, for each node, retrieving its neighbors, which can take up to O(n)O(n) time per node in the worst case.
    • Nodes: O(n)O(n) tuple nodes created (2 per vertex, but constant factor).
    • Edges:
      • (i,i)(i, i) to (i,dominance[i])(i, dominance[i]) : O(n)O(n) .
      • For each (i,j)E(i, j) \in E with i<ji < j : O(m)O(m) edges added.
      • Clique edges (i,i)(i, i) to (j,j)(j, j) : O(n2)O(n^2) for (n2)\binom{n}{2} pairs.
    • Computing dominance[i]dominance[i] : O(deg(i))O(deg(i)) , total O(m+n)O(m + n) across all ii .
    • Total for chordal_graph: O(n2)O(n^2) edges, construction time O(n2)O(n^2) .
  4. MDS in Chordal Graph:
    • Vchordal=O(n)|V_{chordal}| = O(n) , Echordal=O(n2)|E_{chordal}| = O(n^2) .
    • Assumed linear time: O(Vchordal+Echordal)=O(n+n2)=O(n2)O(|V_{chordal}| + |E_{chordal}|) = O(n + n^2) = O(n^2) .
  5. Mapping Back: O(n)O(n) to extract and update SS .

Total Running Time:

  • Dominant term: O(n2)O(n^2) from clique edges and chordal MDS computation.
  • Overall: O(n2)O(n^2) , quadratic in the number of vertices.

Notes:

  • We implement a solution for finding the minimum dominating set in chordal graphs using Mixed Integer Linear Programming (MILP) techniques, as detailed here. Although this approach has a worse time complexity compared to the well-known linear-time algorithm for this problem, it serves to validate the correctness of the algorithm for small to medium-sized graphs. The complete Python implementation is available via pip install baldor and can be found in Baldor: Minimum Dominating Set Solver.

Conclusion

This algorithm resolves MDS in O(n2)O(n^2) time, suggesting P=NPP = NP and delivering practical benefits across diverse fields, including artificial intelligence, medicine, and impact in the industries. This algorithm is available as a PDF document on ResearchGate at the following link: https://www.researchgate.net/publication/389992967_A_Quadratic-Time_Solution_to_the_Minimum_Dominating_Set_Problem_A_Breakthrough_Algorithm.

Heroku

Built for developers, by developers.

Whether you're building a simple prototype or a business-critical product, Heroku's fully-managed platform gives you the simplest path to delivering apps quickly — using the tools and languages you already love!

Learn More

Top comments (0)

The Most Contextual AI Development Assistant

Pieces.app image

Our centralized storage agent works on-device, unifying various developer tools to proactively capture and enrich useful materials, streamline collaboration, and solve complex problems through a contextual understanding of your unique workflow.

👥 Ideal for solo developers, teams, and cross-company projects

Learn more

👋 Kindness is contagious

If you found this post helpful, please leave a ❤️ or a friendly comment below!

Okay