コード例 #1
0
def vertex_branching(graph: nx.Graph, budget: int):
    #print("in branching start:", graph.number_of_nodes(), graph.number_of_edges(), "budget", budget, file=sys.stderr)
    flag, graph, vc, folded_verts = reduction.rrhandler(graph, budget)
    #print("in branching vc:", vc, "fold_verts:", folded_verts, "new graph", graph.number_of_nodes(), file=sys.stderr)
    if not flag:  # NO instance
        return False, set()
    budget -= len(vc) + len(folded_verts)
    num_edges = graph.number_of_edges()
    if budget < 0:
        return False, set()
    if budget <= 0 and num_edges > 0:
        return False, set()
    elif num_edges == 0:
        return True, utils.unfold(vc, folded_verts)
    else:  # budget > 0 and num_edges > 0
        cur_node, max_degree = max(graph.degree_iter(), key=itemgetter(1))
        # print("branching on vertex ", cur_node, "of degree", max_degree, file=sys.stderr)
        nbrs = set(graph.neighbors_iter(cur_node))
        flip = random.random() < 0.5  # flip coin to decide branch order
        if flip:
            branches = [(nbrs, len(nbrs)), (set(), 1)]
        else:
            branches = [(set(), 1), (nbrs, len(nbrs))]
        nodes = set(graph.nodes_iter())
        for branch, budget_change in branches:
            if budget_change > budget: continue
            res, vc_new = vertex_branching(
                graph.subgraph(nodes - {cur_node} - branch),
                budget - budget_change)
            if res:
                final_vc = vc | vc_new | (branch or {cur_node})
                return True, utils.unfold(final_vc, folded_verts)
        return False, set()
コード例 #2
0
ファイル: reduction.py プロジェクト: aditya95sriram/python-vc
def degreeone(graph: nx.Graph, k: int = -1):
    """
    Degree 1 vertices (RR2)

    :param graph: graph to reduce
    :param k: parameter k
    :return: 4-tuple (flag, changed, new_graph, vc)
    where flag=false denotes that this is a NO-instance and vice-versa,
    changed indicates if the reduction rule caused any change,
    new_graph is the reduced subgraph,
    vc is the partial vc constructed while applying reduction rules
    """
    deg_one = set()
    for v, deg in graph.degree_iter():
        if deg == 1:
            deg_one.add(v)

    if len(deg_one) == 0:  # no degree 1 vertices found, so no change
        return True, False, graph, set()

    vc = set()
    to_delete = set()
    while deg_one:
        v = deg_one.pop()
        if v in vc:
            continue
        neigh = utils.first(graph.neighbors_iter(v))
        to_delete.add(v)
        vc.add(neigh)
        if len(vc) > k:  # NO-instance
            return False, False, graph, set()
    nodes = set(graph.nodes_iter())
    new_graph = graph.subgraph(nodes - vc - to_delete)
    return True, True, new_graph, vc
コード例 #3
0
 def __init__(self, graph: nx.Graph):
     self.graph = graph.copy()
     self.degrees = []
     self.entry_finder = dict()
     for v, d in graph.degree_iter():
         entry = [-d, v]
         self.degrees.append(entry)
         self.entry_finder[v] = entry
     heapq.heapify(self.degrees)
コード例 #4
0
ファイル: reduction.py プロジェクト: aditya95sriram/python-vc
def degree_k(graph: nx.Graph, budget: int):
    """
    Delete high-degree (degre > budget) vertices

    :param graph: copy of graph to reduce
    :param budget: parameter k
    :return: (new_graph, vc)
    """
    vc = set()
    for v, d in graph.degree_iter():
        if d > budget:
            vc.add(v)
    graph.remove_nodes_from(vc)
    return graph, vc
コード例 #5
0
ファイル: reduction.py プロジェクト: aditya95sriram/python-vc
def degreedel(graph: nx.Graph, k: int):
    """
    Degree 0 and degree greater than k vertices (RR1)

    :param graph: graph to reduce
    :param k: parameter k
    :return: 4-tuple (flag, changed, new_graph, vc)
    where flag=false denotes that this is a NO-instance and vice-versa,
    changed indicates if the reduction rule caused any change,
    new_graph is the reduced subgraph,
    vc is the partial vc constructed while applying reduction rules
    """
    n = graph.number_of_nodes()
    # print('n:', n)
    # print('V',v)
    degree_dir = graph.degree_iter()
    # print('degree_dir', degree_dir)

    to_delete = set()  # delete degree 0
    vc = set()  # add degree>k to vc

    for v, deg in degree_dir:
        if deg == 0:
            to_delete.add(v)
        if deg > k:
            vc.add(v)

    # handling high degree vertices
    len_vc = len(vc)
    #graph.remove_nodes_from(deg_large)
    if len_vc > k:  # more than k high-degree => NO-instance
        return False, False, graph, set()

    # print('VC-del:', vc)

    # repeatedly applying reduction rules
    if len_vc + len(to_delete) == 0:  # no improvement in this case
        return True, False, graph, vc
    else:
        nodes = set(graph.nodes_iter())
        new_graph = graph.subgraph(nodes - vc - to_delete)
        #graph_new, vc_small, k, flag = degreedel(graph, k)
        # print('vc_small, vc_new', vc_small,  vc_new)
        #c = vc.union(vc_small)

        # print('c', c)
        #graph = graph_new
        return True, True, new_graph, vc
コード例 #6
0
def degree_hist(graph: nx.Graph):
    hist = {}
    for v, d in graph.degree_iter():
        hist[d] = hist.get(d, 0) + 1
    return hist
コード例 #7
0
ファイル: graph_analysis.py プロジェクト: linzhp/Codevo3
from os import path
import numpy as np
from networkx import Graph, transitivity, clustering, average_shortest_path_length, connected_component_subgraphs
from networkx.readwrite import json_graph


if __name__ == '__main__':
    with open(sys.argv[1]) as g_file:
        data = json.load(g_file)
        g = Graph(json_graph.node_link_graph(data))
    print('Number of nodes:', g.number_of_nodes())
    print('Average degree:', 2 * g.number_of_edges()/g.number_of_nodes())
    print('Transitivity:', transitivity(g))
    cc = clustering(g)
    print('Average clustering coefficient:', np.mean(list(cc.values())))
    for subgraph in connected_component_subgraphs(g):
        if subgraph.number_of_nodes() > 1:
            print('Average shortest path length for subgraph of', subgraph.number_of_nodes(), ':',
                  average_shortest_path_length(subgraph))
    # Calculating average clustering coefficient for different degrees
    degree_cc = {}
    for node, degree in g.degree_iter():
        if degree not in degree_cc:
            degree_cc[degree] = []
        degree_cc[degree].append(cc[node])

    with open(path.join(path.dirname(sys.argv[1]), 'clustering.csv'), 'w', newline='') as cc_file:
        writer = csv.DictWriter(cc_file, ['degree', 'average_cc'])
        writer.writeheader()
        for degree in degree_cc:
            writer.writerow({'degree': degree, 'average_cc': np.mean(degree_cc[degree])})
コード例 #8
0
def get_degree_heap(graph: nx.Graph):
    degrees = [(-d, v) for (v, d) in graph.degree_iter()]
    heapq.heapify(degrees)
    return degrees