plt.gca().set_aspect('equal', 'datalim')
    plt.scatter(X[:, 0], X[:, 1], s=10, c='b')
    plt.axis('equal')
    plt.title('Scatter plot of data points')
    pdf.savefig(fig)


# The persistent cohomology of $X$ is in the plot. As expected from the dataset, the $1$-dimensional persistent cohomology
# of $X$ has one prominent topological feature.

# In[13]:


prime = 23 #choose the prime base for the coefficient field that we use to construct the persistence cohomology.
vr = dionysus.fill_rips(X, 2, 2.) #Vietoris-Rips complex
cp = dionysus.cohomology_persistence(vr, prime, True) #Create the persistent cohomology based on the chosen parameters.
dgms = dionysus.init_diagrams(cp, vr) #Calculate the persistent diagram using␣ the designated coefficient field and complex.


# In[14]:


with PdfPages('fig_cp-cp_dataset_ph.pdf') as pdf:
    fig = plt.figure(figsize=(4,4), dpi=100)
    plt.xlim([0, 2])
    plt.yticks([])
    plt.title('Barcode(dim 1) of data points')
    dionysus.plot.plot_bars(dgms[1], show=True)
    #dionysus.plot.plot_diagram(dgms[1], show=True)
    #dionysus.plot.plot_diagram(dgms[0], show=True)
    #Plot the barcode and diagrams using matplotlib incarnation within Dionysus2. This mechanism is different in Dionysus.
예제 #2
0
    dgm_denoise_1 = bars_1
    #print(type(dgm_denoise_0))
    #dionysus.plot.plot_diagram(dgm_denoise_0, show=False)
    #dionysus.plot.plot_diagram(dgm_denoise_1, show=False)
    return ([dgm_denoise_0, dgm_denoise_1])


#Let us compute the bottle-neck distance between full dataset and k-PCA dataset. k denotes the number of principal components.
prime = 23
D = 20
#Here is the data insertion part
mean = np.repeat(0, D)
cov = np.identity(D)
dat1 = np.random.multivariate_normal(mean, cov, 100)
vr = dionysus.fill_rips(dat1, 2, 10)  #Vietoris-Rips complex
cp = dionysus.cohomology_persistence(vr, prime,
                                     True)  #Create the persistent cohomology
dgms = dionysus.init_diagrams(
    cp, vr
)  #Calculate the persistent diagram using the designated coefficient field.
#record for plottings..
A = np.array([0, 0, 1, 1])

for thres in [0, 0.025, 0.05, 0.1, 0.2]:
    #######Thresholding the features on the persistent diagrams describing persistent cohomology of VR complex(CC)
    dgms_tmp = denoise_dgm(dgms, thres)  #thresholding CC diagrams
    dgms_base_0 = dionysus._dionysus.Diagram(
    )  #take persistent points of dim 0
    dgms_base_1 = dionysus._dionysus.Diagram(
    )  #take persistent points of dim 1
    #pybind issue, need to be correct instead of succint.
    for itr in range(len(dgms_tmp[0])):
예제 #3
0
    pdf.savefig(fig)
    #                            #
    ##############################
    ##############################
    #Compute Persistence Diagrams#
    prime = 23
    maxscale = float(sys.argv[3])
    #Choose the prime base for the coefficient field that we use to construct the persistence cohomology.
    threshold = float(sys.argv[2])
    print('Base coefficient field: Z/', prime ,'Z',sep='')
    print('Maximal scale:', float(sys.argv[3]))
    print('Persistence threshold for selecting significant cocycles:',threshold)

    vr = dionysus.fill_rips(dataset, 2, float(sys.argv[3]))
    #Vietoris-Rips complex
    cp = dionysus.cohomology_persistence(vr, prime, True)
    #Create the persistent cohomology based on the chosen parameters.
    dgms = dionysus.init_diagrams(cp, vr)
    #Calculate the persistent diagram using the designated coefficient field and complex.
    now = datetime.datetime.now()
    print('>>>>>>End Time (VR-computation):',now.strftime("%Y-%m-%d %H:%M:%S"))
    ###Plot the barcode and diagrams using matplotlib incarnation within Dionysus2. This mechanism is different in Dionysus.
    #Plots of persistence barcodes of Vietoris-Rips complex for dimension 0 and 1.
    fig = plt.figure(figsize=(5,5), dpi=100)
    plt.title('Persistence Barcode for dim 0')
    dionysus.plot.plot_bars(dgms[0], show=True)
    pdf.savefig(fig)
    fig = plt.figure(figsize=(5,5), dpi=100)
    plt.title('Persistence Barcode for dim 1')
    dionysus.plot.plot_bars(dgms[1], show=True)
    pdf.savefig(fig)
예제 #4
0
def GCC2(dataset,threshold,maxscale,CEthreshold=1e-5,lp=1,lq=2,Nsteps=1000,lambda_coef=0.5,PLOT=True):
    sys.argv = np.asarray(['GCC2_fun.GCC2','dataset',threshold,maxscale,CEthreshold,lp,lq,Nsteps,lambda_coef])
    return_list = []
    print('Number of arguments:', str(len(sys.argv)), 'arguments.')
    if len(sys.argv)!=8 and len(sys.argv)!=9:
        print("""
        ### usage: GCC2(dataset,threshold,maxscale,CEthreshold=1e-5,lp=1,lq=2,Nsteps=1000,lambda_coef=0.5)
        ###[dataset] The dataset you want to analyze using circular coordinates in numpy array. The cols of the array are dimensions/variables; the rows of the array are samples.
        ###[threshold] The threhold on persistence which we use to select those significant cocyles from all cocycles constructed from the Vietoris-Rips complex built upon the data. If negative integer M, the 1-cocycles with the 1,2,...,M-th largest persistence will be picked. This option would override the threshold option. 
        ###[CEthreshold] The threshold that we use to determine the constant edges. When the coordinate functions' values changed below this threshold, we consider it as a constant edge and plot it.
        ###[maxscal] The maximal scale at which we shall construct the Vietoris-Rips complex for circular coordinate computation.
        ###[lp] [lq] The generalized penalty function is in form of (1-lambda_parameter)*L^[lp]+lambda_parameter*L^[lq].
        ###[Nsteps] How many iterations you want to run in the tensorflow optimizer to obtain our circular coordinates? If negative number, no optimization would be executed.
        ###[lambda] This is a float parameter, if supplied, then only that lambda in the genealized coordinate would be calculated. 

        ###Functionality of this code.
        ####Part1: Construct the Vietoris-Rips complex built upon the data and associated persistence diagrams and barcodes.
        #####Scatter plot and associated persistence diagrams and barcodes, with significant topological features selected.
        ####Part2: Output the circular coordinates with different penalty functions.
        ####Part3: Output the embeddings with different penalty functions.""")
        return return_list
    print('Argument List:', str(sys.argv),'\n')
    filenam=sys.argv[1]
    print('Data file:', filenam)


    #From Python_code/utils.py
    def coboundary_1(vr, thr):
        D = [[],[]]
        data = []
        indexing = {}
        ix = [0]*2
        for s in vr:
            if s.dimension() != 1:
                continue
            elif s.data > thr:
                #break
                continue
            indexing.setdefault(s.dimension(),{})
            indexing.setdefault(s.dimension()-1,{})
            if not s in indexing[s.dimension()]:
                indexing[s.dimension()][s] = ix[s.dimension()]
                ix[s.dimension()] += 1
            for dat, k in enumerate(s.boundary()): 
                if not k in indexing[s.dimension()-1]:
                    indexing[k.dimension()][k] = k[0]
                    ix[k.dimension()] += 1
                D[0].append(indexing[s.dimension()][s]) #rows
                D[1].append(indexing[k.dimension()][k]) #cols
                data.append(1. if dat % 2 == 0 else -1.)
        return sp.sparse.csr_matrix((data, (D[0], D[1]))), indexing


    def optimizer_inputs(vr, bars, cocycle, init_z, prime, thr):
        bdry,indexing = coboundary_1(vr,thr)
        n, m = bdry.shape # edges X nodes
        #-----------------
        l2_cocycle = [0]*len(init_z) #reorganize the coordinates so they fit with the coboundary indices
        for i, coeff in enumerate(init_z):
            l2_cocycle[i] = coeff
        l2_cocycle = np.array(l2_cocycle)
        #-----------------
        f = np.zeros((n,1)) # cocycle we need to smooth out, reorganize to fit coboundary
        for c2 in cocycle:
            if c2.element<(prime//2):
                f[indexing[1][vr[c2.index]]] += c2.element
            else:
                f[indexing[1][vr[c2.index]]] += c2.element-prime  
        return l2_cocycle,f,bdry

    #Dionysus2 only.
    #This code is composed in such way that it produces the whole thing in a single pdf file.
    #dataset = np.loadtxt(filenam)

    #from matplotlib.backends.backend_pdf import PdfPages
    
    title_str='Circular Coordinates with Generalized Penalty Functions'
    # Create the PdfPages object to which we will save the pages:
    # The with statement makes sure that the PdfPages object is closed properly at the end of the block, even if an Exception occurs.
    
    os.environ['TF_CPP_MIN_LOG_LEVEL'] = '2'
    filenam = os.path.splitext(filenam)[0]
    pdfnam = filenam+'_output.pdf'
    print('Output file:', pdfnam,'\n')

    now = datetime.datetime.now()
    print('>>>>>>Start Time(VR computation):',now.strftime("%Y-%m-%d %H:%M:%S"))

    ##############################
    #Scatter plots for datapoints#
    if PLOT:
        fig = plt.figure(figsize=(5,5), dpi=100)
        plt.xlabel('X')
        plt.ylabel('Y')
        plt.gca().set_aspect('equal', 'datalim')
        plt.scatter(dataset.T[0,:],dataset.T[1,:],s=10, c='b')
        plt.axis('equal')
        plt.title('Scatter plot of data points')
        #pdf.savefig(fig)
    #                            #
    ##############################
    ##############################
    #Compute Persistence Diagrams#
    prime = 23
    maxscale = float(sys.argv[3])
    #Choose the prime base for the coefficient field that we use to construct the persistence cohomology.
    threshold = float(sys.argv[2])
    print('Base coefficient field: Z/', prime ,'Z',sep='')
    print('Maximal scale:', float(sys.argv[3]))
    print('Persistence threshold for selecting significant cocyles:',threshold)

    vr = dionysus.fill_rips(dataset, 2, float(sys.argv[3]))
    #Vietoris-Rips complex
    cp = dionysus.cohomology_persistence(vr, prime, True)
    #Create the persistent cohomology based on the chosen parameters.
    dgms = dionysus.init_diagrams(cp, vr)
    #Calculate the persistent diagram using the designated coefficient field and complex.
    now = datetime.datetime.now()
    print('>>>>>>End Time (VR-computation):',now.strftime("%Y-%m-%d %H:%M:%S"))
    ###Plot the barcode and diagrams using matplotlib incarnation within Dionysus2. This mechanism is different in Dionysus.
    if PLOT:
        #Plots of persistence barcodes of Vietoris-Rips complex for dimension 0 and 1.
        fig = plt.figure(figsize=(5,5), dpi=100)
        plt.title('Persistence Barcode for dim 0')
        dionysus.plot.plot_bars(dgms[0], show=True)
        #pdf.savefig(fig)
        fig = plt.figure(figsize=(5,5), dpi=100)
        plt.title('Persistence Barcode for dim 1')
        dionysus.plot.plot_bars(dgms[1], show=True)
        #pdf.savefig(fig)
        plt.show()

        #Plots of persistence diagrams of Vietoris-Rips complex for dimension 0 and 1.
        fig = plt.figure(figsize=(5,5), dpi=100)
        plt.title('Persistence Diagram for dim 0')
        dionysus.plot.plot_diagram(dgms[0], show=True)
        #pdf.savefig(fig)
        fig = plt.figure(figsize=(5,5), dpi=100)
        plt.title('Persistence Diagram for dim 1')
        dionysus.plot.plot_diagram(dgms[1], show=True)
        #pdf.savefig(fig)
        plt.show()


    ######Select and highlight the features selected.
    bars = [bar for bar in dgms[1] ]
    #Choose cocycle that persist at least threshold we choose.
    cocycles = [cp.cocycle(bar.data) for bar in bars]
    #Sort the list 'cocycles' by the persistence corresponding to each bar
    cocycles_persistence = [bar.death-bar.birth for bar in bars]
    #print(cocycles_persistence)
    cocycles_ind = np.argsort(-np.asarray(cocycles_persistence), axis=-1, kind=None, order=None) 
    cocycles = [cocycles[i] for i in cocycles_ind]
    bars = [bars[i] for i in cocycles_ind]
    if threshold<0:
        leadings = int(np.abs(threshold))
        #Override threshold option
        threshold = 0 
        print('\n>>>>>>Threshold overridden, the 1-cocyles with the ',leadings,' largest persistence would be selected for computation.')
        cocycles = cocycles[0:leadings]
        bars = bars[0:leadings]
    else:
        bars = [bar for bar in dgms[1] if bar.death-bar.birth > threshold and bar.death-bar.birth < float(sys.argv[3]) ]
        cocycles = [cp.cocycle(bar.data) for bar in bars]
    print('>>>>>>Selected significant features:')
    for B_Lt in bars:
        print(B_Lt,'\tpersistence = ',B_Lt.death-B_Lt.birth)
    ####################
    #PersistenceBarcode#
    if PLOT:
        #Red highlight ***ALL*** cocyles that persist more than threshold value on barcode, when more than one cocyles have persisted over threshold values, this plots the first one.
        fig = plt.figure(figsize=(5,5), dpi=100)
        dionysus.plot.plot_bars(dgms[1], show=False)
        Lt1 = [[bar.birth,bar.death] for bar in bars]
        #Lt1 stores the bars with persistence greater than the [threshold].
        Lt1_tmp = [[bar.birth,bar.death] for bar in dgms[1] ]
        for Lt in Lt1:
            loc=0
            target=Lt
            for g in range(len(Lt1_tmp)):
                if Lt1_tmp[g][0] == target[0] and Lt1_tmp[g][1] == target[1]:
                    loc=g
            #Searching correct term
            plt.plot([Lt[0],Lt[1]],[loc,loc],'r-')
            #print(Lt)

        plt.title('Selected cocycles on barcodes (red bars)')
        #pdf.savefig(fig)
        plt.show()
    #                  #
    ####################
    ####################
    #PersistenceDiagram#
    if PLOT:
        #Red highlight ***ALL*** cocyles that persist more than threshold value on diagram.
        fig = plt.figure(figsize=(5,5), dpi=100)
        dionysus.plot.plot_diagram(dgms[1], show=False)
        Lt2 = [[point.birth,point.death] for point in bars ]
        #Lt2 stores the (multi-)points with persistence greater than the [threshold].
        for Lt in Lt2:
            plt.plot(Lt[0],Lt[1],'ro')
        plt.title('Selected cocycles on diagram (red points)')
        plt.figure(figsize=(5,5), dpi=100)
        #pdf.savefig(fig)
        plt.show()
    #                  #
    ####################

    #                            #
    ##############################
    ##############################
    #    Visualization of GCC    #
    overall_coords = np.zeros(dataset.shape[0], dtype = float)
    #from Python_code import utils
    toll = float(sys.argv[4])#tolerance for constant edges.
    print('\nConstant edges, with coordinates difference <',toll)
    print('Optimizer maximal iteration steps=',int(sys.argv[7]))

    lp=int(sys.argv[5])
    lq=int(sys.argv[6])
    now = datetime.datetime.now()
    print('>>>>>> Start Time (GCC computation):',now.strftime("%Y-%m-%d %H:%M:%S"))
    if len(sys.argv)>=9:
        lambda_list = [float(sys.argv[8])]
    else:
        lambda_list = [0,0.5,1]
    for lambda_parameter in lambda_list:
        print('>>>>>> lambda = ',lambda_parameter,'. => Analysis of Circular coordinates \n (mod {} - {}*L{} + {}*L{})'.format(prime,1-lambda_parameter,lp,lambda_parameter,lq))
        embedding = []
        if PLOT:
            fig = plt.figure(figsize=(5,5), dpi=100)
            plt.text(0.3,0.5,'Analysis of Circular coordinates \n (mod {} - {}*L{} + {}*L{})'.format(prime,1-lambda_parameter,lp,lambda_parameter,lq),transform=plt.gca().transAxes)
            #pdf.savefig(fig)
            plt.show()
        print('Penalty function =>',(1-lambda_parameter),'*L^',lp,"+",lambda_parameter,"*L^",lq,sep='')
        for g in range(len(cocycles)):
            chosen_cocycle = cocycles[g]
            chosen_bar = bars[g]
            #print(chosen_cocycle,chosen_bar)
            NEW_THRESHOLD = max([vr[c2.index].data for c2 in chosen_cocycle]) 
            vr_L2 = dionysus.Filtration([s for s in vr if s.data <=NEW_THRESHOLD])
            coords = dionysus.smooth(vr_L2, chosen_cocycle, prime)
            l2_cocycle,f,bdry = optimizer_inputs(vr, bars, chosen_cocycle, coords, prime, NEW_THRESHOLD)
            l2_cocycle = l2_cocycle.reshape(-1, 1)
            ##It does not seem to work to have double invokes here...
            B_mat = bdry.todense()         
            z_init = l2_cocycle
            z = tf.Variable(z_init, name='z', trainable=True, dtype=tf.float64)
            trainable_variables = [z]
            def loss_function():
                cost_z = (1-lambda_parameter)*tf.math.pow( tf.math.reduce_sum( tf.math.pow( tf.abs(f - tf.linalg.matmul(B_mat,z) ),lp ) ), 1/lp) + lambda_parameter*tf.math.pow( tf.math.reduce_sum( tf.math.pow( tf.math.abs(f - tf.linalg.matmul(B_mat,z) ),lq ) ), 1/lq)
                return cost_z
            #print(B_mat.shape)
            #l2_cocycle=np.zeros((B_mat.shape[1],1))
            tf.random.set_seed(1)
            optimizer = tf.optimizers.Adam(learning_rate=1e-4, beta_1=0.9, beta_2=0.999, epsilon=1e-7, amsgrad=False)
            #optimizer = tf.keras.optimizers.SGD(learning_rate=1e-4) #Not recommended if you are not using tensorflow-gpu, may result a different result sometimes.
            B_mat = tf.Variable(B_mat, name="B_mat", trainable=False, dtype=tf.float64)
            f = tf.Variable(f, name="f", trainable=False, dtype=tf.float64)
            if int(sys.argv[7])>0:
                print('Before optim cost:',loss_function().numpy())
                for i in range(int(sys.argv[7])):
                    train = optimizer.minimize(loss_function, var_list=trainable_variables)
                    #err = np.sum(np.abs(z.numpy() - z_init))
                    #print('>>> step',train.numpy(),' err=',err)
                print('After  optim cost:',loss_function().numpy(),' in ',train.numpy(),' steps')
                res_tf=z.numpy()
            else:
                print('Non-optimized cost:',loss_function().numpy())
                res_tf=z_init
            #print("Absolute differentiation =>",np.sum(np.abs(res_tf-np.asarray(coords) )))
            overall_coords=overall_coords+res_tf.T[0,:]
            color = np.mod(res_tf.T[0,:],1)
            #print(color)
            return_list.append(color)
            if PLOT:
                fig = plt.figure(figsize=(5,5), dpi=100)
                plt.scatter(dataset.T[0,:],dataset.T[1,:],s=10, c=color, cmap="hsv",zorder=10)
                plt.clim(0,1)
                plt.colorbar()
                plt.axis('equal')
                plt.title('Circular coordinates {}-th cocyle (mod {} - {}*L{} + {}*L{})'.format(g+1,prime,1-lambda_parameter,lp,lambda_parameter,lq))
                plt.show()
            edges_constant = []
            thr = chosen_bar.birth
            #####Constatn edges
            #Want to check constant edges in all edges that were there when the cycle was created
            for s in vr:
                if s.dimension() != 1:
                    continue
                elif s.data > thr:
                    break
                if abs(color[s[0]]-color[s[1]]) <= toll:
                    edges_constant.append([dataset[s[0],:],dataset[s[1],:]])
            edges_constant = np.array(edges_constant)
            #pdf.savefig(fig)
            
            #print('Loop End Time:',now.strftime("%Y-%m-%d %H:%M:%S"))
            if PLOT:
                fig = plt.figure(figsize=(5,5), dpi=100)
                if edges_constant.T!=[]:
                  plt.plot(edges_constant.T[0,:],edges_constant.T[1,:], c='k', alpha=.5)
                plt.scatter(dataset.T[0,:],dataset.T[1,:],s=10, c=color, cmap="hsv",zorder=10)
                plt.clim(0,1)
                plt.colorbar()
                plt.axis('equal')
                plt.title('Circular coordinates/constant edges, \n {}-th cocyle (mod {} - {}*L{} + {}*L{})'.format(g+1,prime,1-lambda_parameter,lp,lambda_parameter,lq))
                #pdf.savefig(fig)
                plt.show()
            color_filenam = filenam+'_CircularCoordinates_'+str(lambda_parameter)+'_'+str(g)+'.txt'
            np.savetxt(color_filenam,color)
            print('Penalty function =>',(1-lambda_parameter),'*L^',lp,"+",lambda_parameter,"*L^",lq,' Coordinates=>',color_filenam,sep='')
            
            if PLOT:
                fig = plt.figure(figsize=(5,5), dpi=100)
                angle = np.arctan(dataset.T[0,:]/dataset.T[1,:])
                plt.scatter(angle,color,s=10, c='b',zorder=10)
                plt.ylim([0,1])
                plt.xlim([-np.pi/2,np.pi/2])
                plt.title('Correlation plot against angle, \n {}-th cocyle (mod {} - {}*L{} + {}*L{})'.format(g+1,prime,1-lambda_parameter,lp,lambda_parameter,lq))
                #pdf.savefig(fig)
                plt.show()
            embedding.extend([[np.sin(a) for a in 2*np.pi*color], [np.cos(a) for a in 2*np.pi*color]])
            if PLOT:
                fig = plt.figure(figsize=(5,5), dpi=100)
                dist2 = np.sqrt(np.power(dataset.T[0,:],2)+np.power(dataset.T[1,:],2))
                plt.scatter(dist2,color,s=10, c='b',zorder=10)
                plt.ylim([0,1])
                plt.xlim([0,maxscale])
                plt.title('Correlation plot aginst distance, \n {}-th cocyle (mod {} - {}*L{} + {}*L{})'.format(g+1,prime,1-lambda_parameter,lp,lambda_parameter,lq))
                #pdf.savefig(fig)
                plt.show()
            

        emb_filenam = filenam+'_Embedding_'+str(lambda_parameter)+'.txt'
        np.savetxt(emb_filenam, np.array(embedding))
        print('Penalty function =>',(1-lambda_parameter),'*L^',lp,"+",lambda_parameter,"*L^",lq,' Embeddings=>',emb_filenam,sep='')
        #We plot the final circular coordinates with all co-cycles combined.
        overall_edges_constant = []
        overall_thr = float(sys.argv[2]) #For the combined coordinates, we choose the global threshold.
        for s in vr:
            if s.dimension() != 1:
                continue
            elif s.data > overall_thr:
                break
            if abs(overall_coords[s[0]]-overall_coords[s[1]]) <= toll:
                overall_edges_constant.append([dataset[s[0],:],dataset[s[1],:]])
        overall_edges_constant = np.array(overall_edges_constant)
        if PLOT:
            #fig = plt.figure(figsize=(5,5), dpi=100)
            #if overall_edges_constant.T!=[]:
            #  plt.plot(overall_edges_constant.T[0,:],overall_edges_constant.T[1,:], c='k', alpha=.5)
            #plt.scatter(dataset.T[0,:],dataset.T[1,:],s=10, c=overall_coords, cmap="hsv",zorder=10)
            #plt.clim(0,1)
            #plt.colorbar()
            #plt.axis('equal')
            #plt.title('Combined circular coordinates/constant edges \n (mod {} - {}*L{} + {}*L{})'.format(prime,1-lambda_parameter,lp,lambda_parameter,lq))
            #pdf.savefig(fig)
            #plt.show()

            fig = plt.figure(figsize=(5,5), dpi=100)
            angle = np.arctan(dataset.T[0,:]/dataset.T[1,:])
            plt.scatter(angle,overall_coords,s=10, c='b',zorder=10)
            plt.ylim([0,1])
            plt.xlim([-np.pi/2,np.pi/2])
            plt.title('Correlation plot \n (mod {} - {}*L{} + {}*L{})'.format(prime,1-lambda_parameter,lp,lambda_parameter,lq))
            #pdf.savefig(fig)
            plt.show()

            fig = plt.figure(figsize=(5,5), dpi=100)
            dist2 = np.sqrt(np.power(dataset.T[0,:],2)+np.power(dataset.T[1,:],2))
            #print(color)
            plt.scatter(dist2,color,s=10, c='b',zorder=10)
            plt.ylim([0,1])
            plt.xlim([0,maxscale])
            plt.title('Correlation plot aginst distance, \n {}-th cocyle (mod {} - {}*L{} + {}*L{})'.format(g+1,prime,1-lambda_parameter,lp,lambda_parameter,lq))
            #pdf.savefig(fig)
            plt.show()

    now = datetime.datetime.now()
    print('>>>>>> End Time (GCC computation):',now.strftime("%Y-%m-%d %H:%M:%S"))
    return return_list