L'equivalente "Hello World" nel mondo D-Wave è l'esempio della scacchiera 2D. In questo esempio, viene fornito il seguente grafico quadrato con 4 nodi:
Definiamo che vertice nero se e bianco se . L'obiettivo è creare un motivo a scacchiera con i quattro vertici nel grafico. Esistono vari modi per definire
e per ottenere questo risultato. Innanzitutto, ci sono due possibili soluzioni a questo problema:σioσio= - 1σio= + 1hJ
La ricottura quantistica D-Wave minimizza la Hamiltoning Ising che definiamo ed è importante comprendere l'effetto delle diverse impostazioni dell'accoppiatore. Consideriamo ad esempio l' accoppiatore :J0 , 1
Se lo impostiamo su , l'hamiltoniano viene ridotto a icona se entrambi i qubit assumono lo stesso valore. Diciamo che gli accoppiatori negativi sono correlati . Mentre se lo impostiamo su , l'Hamiltoniano è ridotto al minimo se i due qubit assumono valori opposti. Pertanto, gli accoppiatori positivi sono anti-correlati .J0 , 1= - 1J0 , 1= + 1
Nell'esempio a scacchiera, vogliamo anti-correlare ogni coppia di qubit vicini che danno origine al seguente hamiltoniano:
H= σ0σ1+ σ0σ2+ σ1σ3+ σ2σ3
Per motivi di dimostrazione, aggiungiamo anche un termine di bias sul qubit modo tale da ottenere solo la soluzione n. 1. Questa soluzione richiede e quindi impostiamo il suo orientamento . L'Hamiltoniano finale è ora:0σ0= - 1h0= 1
H= σ0+ σ0σ1+ σ0σ2+ σ1σ3+ σ2σ3
Quindi codifichiamolo!
NOTA: AVETE BISOGNO dell'accesso al servizio cloud di D-Wave perché tutto funzioni.
Prima di tutto, assicurati di avere installato il pacchetto Python dwave_sapi2
( https://cloud.dwavesys.com/qubist/downloads/ ). Tutto sarà Python 2.7 poiché D-Wave al momento non supporta versioni di Python superiori. Detto questo, importiamo gli elementi essenziali:
from dwave_sapi2.core import solve_ising
from dwave_sapi2.embedding import find_embedding, embed_problem, unembed_answer
from dwave_sapi2.util import get_hardware_adjacency
from dwave_sapi2.remote import RemoteConnection
Per connettersi all'API Risolutore D-Wave è necessario un token API valido per il loro solutore SAPI, l'URL SAPI e sarà necessario decidere quale processore quantico si desidera utilizzare:
DWAVE_SAPI_URL = 'https://cloud.dwavesys.com/sapi'
DWAVE_TOKEN = [your D-Wave API token]
DWAVE_SOLVER = 'DW_2000Q_VFYC_1'
Consiglio di usare la Chimera D-Wave 2000Q Virtual Full Yield (VFYC) che è un chip perfettamente funzionante senza qubit morti! Ecco il layout del chip Chimera:
A questo punto sto dividendo il tutorial in due pezzi distinti. Nella prima sezione, stiamo incorporando manualmente il problema nel grafico hardware Chimera e nella seconda sezione stiamo usando l'euristica di incorporamento di D-Wave per trovare un incorporamento hardware.
Incorporamento manuale
La cella unitaria nell'angolo in alto a sinistra sul layout del chip D-Wave 2000Q sopra appare così:
010 → 01 → 42 → 73 → 3hJ
J = {(0,4): 1, (4,3): 1, (3,7): 1, (7,0): 1}
h = [-1,0,0,0,0,0,0,0,0]
h
connection = RemoteConnection(DWAVE_SAPI_URL, DWAVE_TOKEN)
solver = connection.get_solver(DWAVE_SOLVER)
Ora, possiamo definire il numero di letture e scegliere answer_mode
di essere "istogramma" che ordina già i risultati in base al numero di occorrenze per noi. Ora siamo pronti a risolvere l'istanza di Ising con la ricottura quantistica D-Wave:
params = {"answer_mode": 'histogram', "num_reads": 10000}
results = solve_ising(solver, h, J, **params)
print results
Dovresti ottenere il seguente risultato:
{
'timing': {
'total_real_time': 1655206,
'anneal_time_per_run': 20,
'post_processing_overhead_time': 13588,
'qpu_sampling_time': 1640000,
'readout_time_per_run': 123,
'qpu_delay_time_per_sample': 21,
'qpu_anneal_time_per_sample': 20,
'total_post_processing_time': 97081,
'qpu_programming_time': 8748,
'run_time_chip': 1640000,
'qpu_access_time': 1655206,
'qpu_readout_time_per_sample': 123
},
'energies': [-5.0],
'num_occurrences': [10000],
'solutions': [
[1, 3, 3, 1, -1, 3, 3, -1, {
lots of 3 's that I am omitting}]]}
energies
- 5.030 → 04 → 17 → 23 → 3[ 1 , - 1 , - 1 , 1 ]
Incorporamento euristico
Jh
J = {(0,1): 1, (0,2): 1, (1,3): 1, (2,3): 1}
h = [-1,0,0,0]
Stabiliamo nuovamente la connessione remota e otteniamo l'istanza del solutore D-Wave 2000Q VFYC:
connection = RemoteConnection(DWAVE_SAPI_URL, DWAVE_TOKEN)
solver = connection.get_solver(DWAVE_SOLVER)
Per trovare un incorporamento del nostro problema, dobbiamo prima ottenere la matrice di adiacenza del grafico hardware corrente:
adjacency = get_hardware_adjacency(solver)
Ora proviamo a trovare un incorporamento del nostro problema:
embedding = find_embedding(J.keys(), adjacency)
Se hai a che fare con istanze di Ising di grandi dimensioni potresti voler cercare incorporamenti in più thread (parallelizzati su più CPU) e quindi selezionare l'incorporamento con la lunghezza della catena più piccola! Una catena è quando più qubit sono costretti ad agire come un singolo qubit al fine di aumentare il grado di connettività. Tuttavia, più lunga è la catena, maggiore è la probabilità che si spezzi. E le catene rotte danno risultati cattivi!
Ora siamo pronti per incorporare il nostro problema nel grafico:
[h, j0, jc, embeddings] = embed_problem(h, J, embedding, adjacency)
j0
jc
J
J = j0.copy()
J.update(jc)
Ora siamo pronti a risolvere il problema incorporato:
params = {"answer_mode": 'histogram', "num_reads": 10000}
raw_results = solve_ising(solver, h, J, **params)
print 'Lowest energy found: {}'.format(raw_results['energies'])
print 'Number of occurences: {}'.format(raw_results['num_occurrences'])
Non raw_results
avrà senso per noi a meno che non abbiamo risolto il problema. Nel caso in cui alcune catene si siano rotte, le stiamo risolvendo con un voto a maggioranza come definito dall'argomento facoltativo broken_chains
:
unembedded_results = unembed_answer(raw_results['solutions'],
embedding, broken_chains='vote')
print 'Solution string: {}'.format(unembedded_results)
Se lo esegui, dovresti ottenere il risultato corretto in tutte le letture:
Lowest energy found: [-5.0]
Number of occurences: [10000]
Solution string: [[1, -1, -1, 1]]
Spero che questo abbia risposto alla tua domanda e ti consiglio vivamente di controllare tutti i parametri aggiuntivi che puoi passare alla solve_ising
funzione per migliorare la qualità delle tue soluzioni come num_spin_reversal_transforms
o postprocess
.