Kitaplar / Yöntem ile Programlamaya Giriş / Bölüm 15 — Kuantum programlama
Bölüm 15 — Kuantum programlama
Klasik bir bit ya 0 ya 1’dir. Bir kübit ise ölçülene kadar 0 ile 1’in bir süperpozisyonunda bulunabilir. Ölçtüğünüzde belirli olasılıklarla 0 ya da 1 olur. Yöntem’in Kuantum birimi, bilgisayarınızda en çok 20 kübitlik kuantum devreleri kurup simüle etmenizi sağlar.
İlk kübit
program İlkKübit
kullan Kuantum
değişken
d: herhangi
i, birler: tamsayı
başla
KuantumTohum(5)
d := Devre(1) // bir kübit, |0⟩ durumunda
yaz('Başlangıç : ' + d.Durum, 1)
d.X(0) // NOT kapısı: |0⟩ -> |1⟩
yaz('X sonrası : ' + d.Durum, 1)
d.H(0) // Hadamard: süperpozisyon
yaz('H sonrası : ' + d.Durum, 1)
yaz('Olasılıklar: ' + d.Olasılıklar, 2)
// 100 kez hazırla ve ölç
birler := 0
1'den 100'e kadar her i için
başla
d := Devre(1)
d.H(0)
birler += d.Ölç(0)
bitir
yaz('100 ölçümde 1 çıkma sayısı: ' + birler, 1)
bitir.Başlangıç : 1|0⟩
X sonrası : 1|1⟩
H sonrası : 0.7071|0⟩ - 0.7071|1⟩
Olasılıklar: ['0': 0.5, '1': 0.5]
100 ölçümde 1 çıkma sayısı: 50|0⟩ ve |1⟩ (“ket sıfır”, “ket bir”) kübitin temel durumlarıdır. Hadamard kapısından sonra kübit ikisinin karışımı oldu. Genliklerin karesi olasılığı verir: 0.7071² ≈ 0.5. Eksi işareti olasılığı değiştirmez ama girişimde (interference) önemlidir. Ölç durumu çökertir ve 0 ya da 1 döndürür; 100 denemenin yarısı 1 çıktı.
Dolanıklık
İki kübit dolanık hale getirildiğinde, birini ölçmek diğerinin sonucunu da belirler.
program Dolanıklık
kullan Kuantum
değişken
d: herhangi
a, b, i: tamsayı
başla
KuantumTohum(3)
d := Devre(2)
d.H(0)
d.CX(0, 1) // q0 1 ise q1'i çevir
yaz(d.Çiz, 1)
yaz('Durum: ' + d.Durum, 1)
yaz('1000 atış: ' + d.Çalıştır(1000), 2)
1'den 5'e kadar her i için
başla
d := Devre(2)
d.H(0); d.CX(0, 1)
a := d.Ölç(0)
b := d.Ölç(1)
yaz('q0 = ' + a + ', q1 = ' + b, 1)
bitir
bitir.q0: ─H──●──
q1: ────X──
Durum: 0.7071|00⟩ + 0.7071|11⟩
1000 atış: ['00': 509, '11': 491]
q0 = 1, q1 = 1
q0 = 0, q1 = 0
q0 = 0, q1 = 0
q0 = 1, q1 = 1
q0 = 0, q1 = 0Bu, ünlü Bell durumudur. Sonuçların her biri tek başına rastgeledir, ama iki kübit her zaman aynı değeri verir; 01 ya da 10 hiç çıkmaz. Çiz devreyi metin olarak gösterir: ● kontrol kübiti, X hedeftir. Çalıştır(1000) devreyi 1000 kez çalıştırıp sonuçları sayar.
Bit sırası: Yöntem’de bit dizilerinde q0 en soldadır. '10', q0 = 1 ve q1 = 0 demektir.
Temel kapılar
| Kapı | Yöntem | Etkisi |
|---|---|---|
| X (NOT) | d.X(q) |
0 ↔︎ 1 |
| Hadamard | d.H(q) |
Eşit süperpozisyon oluşturur |
| Z, S, T | d.Z(q), d.S(q), d.T(q) |
Fazı değiştirir; olasılıklar aynı kalır |
| Dönmeler | d.Rx(q, θ), d.Ry(q, θ), d.Rz(q, θ) |
Kübiti bir eksen etrafında θ kadar döndürür |
| CNOT | d.CX(k, h) |
Kontrol 1 ise hedefi çevirir |
| Toffoli | d.CCX(k1, k2, h) |
İki kontrol de 1 ise hedefi çevirir |
| Takas | d.Takas(a, b) |
İki kübiti yer değiştirir |
| Ölçüm | d.Ölç(q) |
0 ya da 1 döndürür, durum çöker |
Kuantum araması: Grover algoritması
Sırasız bir listede bir elemanı bulmak için klasik bir bilgisayar ortalama N/2 deneme yapar. Grover algoritması bunu yaklaşık √N adımda yapar. KuantumAlgoritmaları birimi algoritmayı hazır sunar.
program GroverArama
kullan Kuantum, KuantumAlgoritmaları
değişken
d: herhangi
sayım: sözlük
başla
KuantumTohum(11)
// 3 kübit = 8 olasılık. Aranan: '110'
d := Grover('110')
sayım := d.Çalıştır(200)
yaz('Sonuçlar: ' + sayım, 1)
yaz(Biçimle('Doğru cevabın olasılığı: %{:.1}', d.Olasılık('110') * 100), 1)
bitir.Sonuçlar: ['000': 1, '001': 1, '010': 3, '011': 2, '100': 2, '101': 1, '110': 186, '111': 4]
Doğru cevabın olasılığı: %94.5Algoritma iki adımı tekrarlar. Kehanet aranan durumun genliğinin işaretini çevirir. Yayılım tüm genlikleri ortalamaları etrafında yansıtır. Her turda doğru cevabın genliği büyür, ötekiler küçülür. Bu iki adımın Yöntem kodunu kutuphane/KuantumAlgoritmalari.y dosyasında okuyabilirsiniz.
Kuantum ve yapay zekâ buluşuyor: değişimsel devreler
Parametreli kapılar (örneğin Ry(q, θ)) bir sinir ağının ağırlıkları gibi ayarlanabilir. ParametreKaydırma, bir devrenin çıktısının parametrelere göre gradyanını hesaplar. Ardından Bölüm 12’deki gradyan inişi aynen uygulanır.
program DeğişimselDevre
kullan Kuantum, Matematik
değişken
açı: liste
grad: liste
i: tamsayı
// Ry(θ) uygulanmış bir kübitin ⟨Z⟩ değeri = cos θ. En küçük değer θ = π'de: -1
fonksiyon Enerji(p: liste): ondalık
değişken
d: herhangi
başla
d := Devre(1)
d.Ry(0, p[0])
dön d.BeklenenDeğer('Z')
bitir
başla
açı := [0.3]
1'den 30'a kadar her i için
başla
grad := ParametreKaydırma(@Enerji, açı)
açı := [açı[0] - 0.4 * grad[0]]
eğer i mod 10 = 0 ise
yaz(Biçimle('adım {:2}: θ = {:.4} enerji = {:.4}', i, açı[0], Enerji(açı)), 1)
bitir
yaz(Biçimle('π = {:.4}', pi), 1)
bitir.adım 10: θ = 2.9135 enerji = -0.9741
adım 20: θ = 3.1402 enerji = -1.0000
adım 30: θ = 3.1416 enerji = -1.0000
π = 3.1416Devre, enerjiyi en aza indiren açıyı kendi kendine buldu: θ = π. Moleküllerin taban durum enerjisini hesaplayan VQE ve kuantum makine öğrenmesi modelleri bu fikrin büyütülmüş halleridir. İki kübitli tam bir VQE örneği, kuantum ışınlama ve QFT için ornekler/kuantum.y dosyasına bakabilirsiniz. @Enerji, fonksiyonu çağırmadan değer olarak verir (Bölüm 8).
Alıştırmalar
- Üç kübitlik bir GHZ durumu (
0.7071|000⟩ + 0.7071|111⟩) kuran bir devreyiHveCXkapılarıyla kendiniz yazınız. SonraGHZ(3)ile karşılaştırınız. Groverfonksiyonunu 4 kübitle (örneğin'1011') çalıştırınız.tekrarparametresini 1, 2, 3, 4 yapıp doğru cevabın olasılığının nasıl değiştiğini gözlemleyiniz.Enerjifonksiyonunud.Ry(0, p[0]); d.Rz(0, p[1]);veBeklenenDeğer('X')olacak şekilde değiştiriniz ve iki parametreyi birlikte eğitiniz.