Running germ selection on multiple processors

The code below should be put into a script and run using mpiexec. It's primary function is to pass a MPI Comm object to pygsti.algorithms.germselection.build_up_breadth.

In [1]:
from __future__ import print_function
import time

import pygsti
import pygsti.construction as pc
from pygsti.construction import std2Q_XYICNOT
from pygsti.algorithms import germselection as germsel

from mpi4py import MPI
comm = MPI.COMM_WORLD

def do_greedy_germsel(gs_target, forced_germs, candidate_counts,
                      seedStart, outFilename, comm):
    #candidate_counts is a dict of keys = germ lengths, values = # of germs at that length                                                            

    tStart = time.time()

    candidate_germs = []
    for i,(germLength, count) in enumerate(candidate_counts.items()):
        if count == "all upto":
            candidate_germs.extend( pc.list_all_gatestrings_without_powers_and_cycles(
                    gs_target.gates.keys(), maxLength=germLength) )
        else:
            candidate_germs.extend( pc.list_random_gatestrings_onelen(
                    gs_target.gates.keys(), germLength, count, seed=seedStart+i))

    available_germs = pygsti.tools.remove_duplicates( forced_germs + candidate_germs )
    print("%d available germs" % len(available_germs))
    germs = germsel.build_up_breadth(gs_target, available_germs,
                     randomizationStrength=1e-3, numCopies=3, seed=1234,
                     gatePenalty=10.0, scoreFunc='all', tol=1e-6, threshold=1e5,
                     pretest=False, force=forced_germs, verbosity=5, comm=comm, memLimit=0.5*(1024**3))

    if comm is None or comm.Get_rank() == 0:
        print("Germs (%d) = \n" % len(germs), "\n".join(map(str,germs)))
        print("Total time = %gs" % (time.time()-tStart))
        pickle.dump(germs,open(outFilename,"wb"))
    return germs
                                                                                                                                         
#2Q case                                                                                                                                              
gs_target = std2Q_XYICNOT.gs_target
forced_germs = pygsti.construction.gatestring_list([(gl,) for gl in gs_target.gates.keys()]) #singletons                                                                                      
candidate_counts = { 3:"all upto", 4:30, 5:20, 6:20, 7:20, 8:20} # germLength:num_candidates                                                          
seedStart = 4
do_greedy_germsel(gs_target, forced_germs, candidate_counts,
                  seedStart, "germs_EXAMPLE.pkl", comm)
201 available germs
Starting germ set optimization. Lower score is better.
Memory estimate of 13.6 GB (0.5 GB limit) for all-Jac mode.
Memory estimate of 0.2 GB (0.5 GB limit) for single-Jac mode.
    Initial germ set computation Iter 1 of 6 Gii: 
    Initial germ set computation Iter 2 of 6 Gix: 
    Initial germ set computation Iter 3 of 6 Giy: 
    Initial germ set computation Iter 4 of 6 Gxi: 
    Initial germ set computation Iter 5 of 6 Gyi: 
    Initial germ set computation Iter 6 of 6 Gcnot: 
  Outer iteration: 1 of 1282 amplified, 6 germs
    Inner iter over candidate germs Iter 001 of 195 GiiGix: 
      Score: major=-114.0 minor=275.75502325607516, N: 194
    Inner iter over candidate germs Iter 002 of 195 GiiGiy: 
      Score: major=-114.0 minor=275.7522442827053, N: 194
    Inner iter over candidate germs Iter 003 of 195 GiiGxi: 
      Score: major=-114.0 minor=303.1298571245524, N: 194
    Inner iter over candidate germs Iter 004 of 195 GiiGyi: 
      Score: major=-114.0 minor=359.3300959231139, N: 194
    Inner iter over candidate germs Iter 005 of 195 GiiGcnot: 
      Score: major=-114.0 minor=276.2687268384213, N: 194
    Inner iter over candidate germs Iter 006 of 195 GixGiy: 
      Score: major=-114.0 minor=257.4426897879868, N: 194
    Inner iter over candidate germs Iter 007 of 195 GixGxi: 
      Score: major=-114.0 minor=341.56964685981245, N: 194
    Inner iter over candidate germs Iter 008 of 195 GixGyi: 
      Score: major=-114.0 minor=282.3386744924068, N: 194
    Inner iter over candidate germs Iter 009 of 195 GixGcnot: 
      Score: major=-114.0 minor=577.5866443200778, N: 194
    Inner iter over candidate germs Iter 010 of 195 GiyGxi: 
      Score: major=-114.0 minor=294.80873540346374, N: 194
    Inner iter over candidate germs Iter 011 of 195 GiyGyi: 
      Score: major=-114.0 minor=274.01388120453817, N: 194
    Inner iter over candidate germs Iter 012 of 195 GiyGcnot: 
      Score: major=-114.0 minor=292.41877705095874, N: 194
    Inner iter over candidate germs Iter 013 of 195 GxiGyi: 
      Score: major=-114.0 minor=257.14469808616434, N: 194
    Inner iter over candidate germs Iter 014 of 195 GxiGcnot: 
      Score: major=-114.0 minor=295.1901473400719, N: 194
    Inner iter over candidate germs Iter 015 of 195 GyiGcnot: 
      Score: major=-114.0 minor=262.2444012232528, N: 194
    Inner iter over candidate germs Iter 016 of 195 GiiGiiGix: 
      Score: major=-104.0 minor=245.73088449107456, N: 194
    Inner iter over candidate germs Iter 017 of 195 GiiGiiGiy: 
      Score: major=-104.0 minor=236.1043493154918, N: 194
    Inner iter over candidate germs Iter 018 of 195 GiiGiiGxi: 
      Score: major=-104.0 minor=257.48113898508547, N: 194
    Inner iter over candidate germs Iter 019 of 195 GiiGiiGyi: 
      Score: major=-104.0 minor=295.3201744814378, N: 194
    Inner iter over candidate germs Iter 020 of 195 GiiGiiGcnot: 
      Score: major=-104.0 minor=274.60740870875316, N: 194
    Inner iter over candidate germs Iter 021 of 195 GiiGixGix: 
      Score: major=-104.0 minor=453.2493918611676, N: 194
    Inner iter over candidate germs Iter 022 of 195 GiiGixGiy: 
      Score: major=-104.0 minor=275.15640639818946, N: 194
    Inner iter over candidate germs Iter 023 of 195 GiiGixGxi: 
      Score: major=-104.0 minor=304.4741877376942, N: 194
    Inner iter over candidate germs Iter 024 of 195 GiiGixGyi: 
      Score: major=-104.0 minor=278.44120228187865, N: 194
    Inner iter over candidate germs Iter 025 of 195 GiiGixGcnot: 
---------------------------------------------------------------------------
KeyboardInterrupt                         Traceback (most recent call last)
<ipython-input-1-3129db9f05b2> in <module>()
     44 seedStart = 4
     45 do_greedy_germsel(gs_target, forced_germs, candidate_counts,
---> 46                   seedStart, "germs_EXAMPLE.pkl", comm)

<ipython-input-1-3129db9f05b2> in do_greedy_germsel(gs_target, forced_germs, candidate_counts, seedStart, outFilename, comm)
     30                      randomizationStrength=1e-3, numCopies=3, seed=1234,
     31                      gatePenalty=10.0, scoreFunc='all', tol=1e-6, threshold=1e5,
---> 32                      pretest=False, force=forced_germs, verbosity=5, comm=comm, memLimit=0.5*(1024**3))
     33 
     34     if comm is None or comm.Get_rank() == 0:

/Users/enielse/research/pyGSTi/packages/pygsti/algorithms/germselection.py in build_up_breadth(gatesetList, germsList, randomize, randomizationStrength, numCopies, seed, gatePenalty, scoreFunc, tol, threshold, check, force, pretest, memLimit, comm, profiler, verbosity)
   1307                     worstScore = max( worstScore, compute_composite_germ_score(
   1308                         partialDerivDaggerDeriv=testDDD[None,:,:], initN=initN,
-> 1309                         **nonAC_kwargs))
   1310                     testDDDs.append(testDDD) #save in case this is a keeper
   1311 

/Users/enielse/research/pyGSTi/packages/pygsti/algorithms/germselection.py in compute_composite_germ_score(scoreFn, thresholdAC, initN, partialDerivDaggerDeriv, gateset, partialGermsList, eps, numGaugeParams, gatePenalty, germLengths, l1Penalty)
    429 
    430     combinedDDD = _np.sum(partialDerivDaggerDeriv, axis=0)
--> 431     sortedEigenvals = _np.sort(_np.real(_nla.eigvalsh(combinedDDD)))
    432     observableEigenvals = sortedEigenvals[numGaugeParams:]
    433     N_AC = 0

/Library/Frameworks/Python.framework/Versions/3.5/lib/python3.5/site-packages/numpy/linalg/linalg.py in eigvalsh(a, UPLO)
   1007     t, result_t = _commonType(a)
   1008     signature = 'D->d' if isComplexType(t) else 'd->d'
-> 1009     w = gufunc(a, signature=signature, extobj=extobj)
   1010     return w.astype(_realType(result_t), copy=False)
   1011 

KeyboardInterrupt: 

Above is keyboard-interrupted on purpose, as this output was produced with a single processor and it would have taken a very long time.

In [ ]: