# Program reading diffusion_times results and transforming it for each transmission starting time into a cumulative distribution, on a single file.

import sys
import gzip
import operator

if len(sys.argv)!=6:
    sys.stdout.write("Invalid number of arguments, it should be used as follow :\npython %s MaxContactTime Output_file_path Inputs_file_path_root NB_of_Nodes Node_removed\n"%sys.argv[0])
    sys.exit(0)

MaxTime=int(sys.argv[1])
out=gzip.open(sys.argv[2],'w')
NB_Imotes=int(sys.argv[4])
Imote_suppr=int(sys.argv[5])
inputs=[None]*NB_Imotes

# Open all time files, there is one for all nodes as results are distributed by senders
for i in range(NB_Imotes):
    if i!=Imote_suppr-1:
        inputs[i]=gzip.open(sys.argv[3]+str(i+1)+".dat",'r')

# Initialize distribution structure
distribs = [None]*(MaxTime+1)
for i in range(MaxTime+1):
    distribs[i] = {}

# Process all input files sequentially in order to internally construct the distribution, it remains a result writing file.
for k in range(NB_Imotes):
    count = MaxTime/1000
    if (k+1!=Imote_suppr):
        old_t=MaxTime+1
        max_value = 0
        values=["*"]
        
        # Computes sequentially all input lines (one line correspond a starting node and starting time.
        for l in inputs[k]:
            l=l.split()
            t=int(l[0])

            # Add jumped starting time, it occurs when nodes are isolated. Values can easily be deduced from last read line (saving I/O exectution time).
            for j in range(old_t-t-1):
                distribs[old_t-j-1][0]=distribs[old_t-j-1].get(0,0)+1
                for i in range(max_value+j+2):
                    delta=values.count(i-j-1)
                    if (i-j-1)==0:
                        delta-=1
                    if delta>0:
                        distribs[old_t-j-1][i]=distribs[old_t-j-1].get(i,0)+delta

            # Parsing a line to add the distrib structure
            values=map(int,filter(lambda x: x!="*",l[2:]))
            max_value = reduce(max,values,0)
            for i in range(max_value+1):
                delta=values.count(i)
                if delta>0:
                    distribs[t][i]=distribs[t].get(i,0)+delta
        
            old_t=t

        # Extending the results for times befor first contact.
        for j in range(old_t):
            distribs[old_t-j-1][0]=distribs[old_t-j-1].get(0,0)+1
            for i in range(max_value+j+2):
                delta=values.count(i-j-1)
                if (i-j-1)==0:
                    delta-=1
                if delta>0:
                    distribs[old_t-j-1][i]=distribs[old_t-j-1].get(i,0)+delta

    
# Sort the distributions by times and write on the given output file
for t in xrange(MaxTime,-1,-1):
    distribs[t] = distribs[t].items()
    distribs[t].sort()
    sum = reduce(operator.add,map(lambda (a,b): b ,distribs[t]),0)
    cum = 0
    for (i,n) in distribs[t]:
        cum+=n
        out.write("%d\t%f\n"%(i,float(cum)/float(sum)))
    out.write("\n")
