to_d2_graph.py 3.01 KB
Newer Older
Yoann Dufresne's avatar
Yoann Dufresne committed
1 2 3 4 5 6
#!/usr/bin/env python3

import networkx as nx
import argparse
import sys

7
from deconvolution.d2graph import d2_graph as d2
Yoann Dufresne's avatar
Yoann Dufresne committed
8 9 10 11 12


def parse_arguments():
    parser = argparse.ArgumentParser(description='Transform a 10X barcode graph into a d2 graph. The program dig for the d-graphs and then merge them into a d2-graph.')
    parser.add_argument('barcode_graph', help='The barcode graph file. Must be a gefx formated file.')
13
    parser.add_argument('--output_prefix', '-o', default="d2_graph",  help="Output file prefix.")
14
    parser.add_argument('--threads',       '-t', default=8, type=int, help='Number of thread to use for dgraph computation')
15
    parser.add_argument('--debug',         '-d', action='store_true', help="Debug")
Yoann Dufresne's avatar
Yoann Dufresne committed
16
    parser.add_argument('--verbose',         '-v', action='store_true', help="Verbose")
Yoann Dufresne's avatar
Yoann Dufresne committed
17
    parser.add_argument('--edge_divergence_threshold', '-dt', default=0.25, type=float, help='Divergence threshold value to link two udgs in the d2-graph')
18
    parser.add_argument('--maxclq',        '-c', action='store_true', help="Enable max clique community detection (default behaviour)")
19 20
    parser.add_argument('--louvain',       '-l', action='store_true', help="Enable Louvain community detection instead of all max-cliques")
    parser.add_argument('--comtest',       '-k', action='store_true', help="Enable [placeholder] community detection algorithm instead of max-cliques")
Yoann Dufresne's avatar
Yoann Dufresne committed
21 22 23 24 25 26 27

    args = parser.parse_args()
    return args

def main():
    # Parsing the input file
    args = parse_arguments()
28
    
29
    # debug = args.debug
Yoann Dufresne's avatar
Yoann Dufresne committed
30
    filename = args.barcode_graph
31 32 33 34
   
    def dprint(s):
        from datetime import datetime
        t = datetime.now().strftime('%Y-%m-%d %H:%M:%S')
Yoann Dufresne's avatar
verbose  
Yoann Dufresne committed
35
        print(t, s)
36 37 38 39 40 41 42 43

    dprint("loading barcode graph")
    if filename.endswith('.gexf'):
        G = nx.read_gexf(filename)
    elif filename.endswith('.graphml'):
        G = nx.read_graphml(filename)
    else:
        print("Input file must be gexf or graphml formatted", file=sys.stderr)
44
        exit(1)
45
    dprint("barcode graph loaded")
46

47 48 49 50 51 52 53
    if args.louvain:
        clique_mode = "louvain"
    elif args.comtest:
        clique_mode = "testing"
    else:
        clique_mode = None

54 55 56 57 58 59
    # Debug config
    debug = False
    debug_path = "/dev/null"
    if args.debug:
        debug = True
        debug_path = f"{args.output_prefix}_debug"
60
        import os, shutil
61
        if os.path.isdir(debug_path):
62
            shutil.rmtree(debug_path)
63 64
        os.mkdir(debug_path)

Yoann Dufresne's avatar
Yoann Dufresne committed
65
    # Index size must be changed for general purpose. 8 is good for d=5
66
    dprint("creating D2graph object")
67
    d2g = d2.D2Graph(G, debug=debug, debug_path=debug_path)
68 69
    dprint("D2 graph object created")
    dprint("constructing d2 graph from barcode graph")
Yoann Dufresne's avatar
verbose  
Yoann Dufresne committed
70
    d2g.construct_from_barcodes(neighbor_threshold=args.edge_divergence_threshold, clique_mode=clique_mode, threads=args.threads, verbose=args.verbose)
71
    dprint("[debug] d2 graph constructed")
Yoann Dufresne's avatar
Yoann Dufresne committed
72
    
73
    # d2g.save(f"{args.output_prefix}.tsv")
74
    nx.write_gexf(d2g, f"{args.output_prefix}.gexf")
Yoann Dufresne's avatar
Yoann Dufresne committed
75 76 77 78


if __name__ == "__main__":
    main()