2. gyakorlat – Kvantum véletlenszerű számgenerátor létrehozása
Ebben az egységben valósítja meg a kvantum véletlenszám-generátor második részét. Több véletlenszerű bit kombinálásával nagyobb véletlenszerű számot hozhat létre. Ez a rész az előző leckében már létrehozott véletlenszerű bitgenerátorra épül.
Több véletlenszerű bit egyesítése nagyobb szám létrehozásához
Az előző leckében létrehozott egy véletlenszerű bitgenerátort, amely egy qubitet szuperpozíciós állapotba helyez, majd a qubitet 0 vagy 1 véletlenszerű bitérték létrehozására méri, mindegyik 50% valószínűséggel. Ennek a bitnek az értéke valóban véletlenszerű, nem lehet előre tudni, hogy mi lesz a mérési eredmény. De hogyan használhatja ezt a viselkedést nagyobb véletlenszerű számok létrehozására?
Ha négyszer ismétli meg a folyamatot, akkor létrehozhatja a bináris számjegyek sorozatát:
$${0, 1, 1, 0}$$
Ha ezeket a biteket egy bitsztringbe egyesíti, akkor nagyobb számot is létrehozhat. Ebben a példában a bináris ${0110}$ bitütemezése megegyezik a decimális 6-os számmal.
$${0110_{\ binary} \equiv 6_{\ decimális}}$$
Tetszőlegesen nagy véletlenszerű szám létrehozásához egyszerűen ismételje meg ezt a folyamatot többször. Ezután egyesítse az összes bitet bináris számmá, és konvertálja a bináris számot decimális számmá.
A véletlenszám-generáló logikájának meghatározása
A Q#-kód megírása előtt vázoljuk fel a logikát egy véletlenszerű szám létrehozásához:
- Adja meg
maxa létrehozni kívánt tizedesjegyek maximális számát. - Határozza meg a létrehozáshoz
nBitsszükséges véletlenszerű bitekmaxszámát. - Generáljunk egy
nBitshosszúságú véletlenszerű bitsztringet. - Ha a bitsztring nagyobb számot
maxjelöl, térjen vissza az előző lépéshez. - Ellenkező esetben a folyamat befejeződött. A generált számot decimális egész számként adja vissza.
Definiáljuk például a max értékét 12-nek. Vagyis a 12 a legnagyobb szám, amelyet a véletlenszerű számgenerátornak ki kell termelnie.
A következő egyenlet segítségével határozza meg a 12-es szám binárisban való megjelenítéséhez szükséges bitek számát:
$${\lfloor ln(12) / ln(2) + 1 \rfloor}$$
Az egyenlet szerint 4 bitre van szükség a 0 és 12 közötti szám megjelenítéséhez.
Tegyük fel például, hogy négyszer generál véletlenszerű bitet, és az eredmény a ${1101_{\ binary}}$ bitsztring lesz. Ez a bináris érték decimálisan 13-nak felel meg. Mivel a 13 nagyobb mint 12, megismételjük a folyamatot.
Ezután létrehozza a ${0110_{\ binary}}$ bitsztringet, ami megegyezik a ${6_{\ decimális rendszer}}$ értékkel. Mivel a 6 kisebb mint 12, a folyamat befejeződött.
A kvantum véletlenszerű számgenerátor a 6-os számot adja vissza.
Teljes véletlenszerű számgenerátor létrehozása a Q-ban#
Itt bővíti az előző leckéből származó Main.qs fájlt a véletlenszám-generátor létrehozásához.
Importálja a szükséges könyvtárakat
Először importálja a névtereket a Q#standard kódtárból, amely tartalmazza a program írásához szükséges függvényeket és műveleteket. A Q#-fordító számos gyakori függvényt és műveletet automatikusan betölt. A kvantum véletlenszerű számgenerátorhoz azonban további függvényekre és műveletekre van szükség két Q#-névtérből: Std.Math és Std.Convert.
Másolja és illessze be a következő import irányelveket a Main.qs fájl elején:
import Std.Convert.*;
import Std.Math.*;
Nevezze át a Main műveletet GenerateRandomBit-re
A véletlenszerű számgenerátor program az Main előző leckében írt műveletet használja véletlenszerű bit létrehozásához. Nevezze át a Main műveletet GenerateRandomBit úgy, hogy a műveletnek leíróbb neve legyen, és ne legyen a program belépési pontja.
Másolja és illessze be a következő kódot a következőbe Main.qs:
import Std.Convert.*;
import Std.Math.*;
operation GenerateRandomBit() : Result {
// Allocate a qubit.
use q = Qubit();
// Set the qubit into superposition of 0 and 1 using the Hadamard
H(q);
// Measure the qubit and store the result.
let result = M(q);
// Reset qubit to the |0〉 state.
Reset(q);
// Return the result of the measurement.
return result;
}
A véletlenszerű számgenerátor műveletének meghatározása
Hozzon létre egy új, úgynevezett GenerateRandomNumberInRangeműveletet. Ez a művelet többször meghívja a GenerateRandomBit műveletet a bitek sztringjének létrehozásához.
Másolja ki a következő kódot, és helyezze közvetlenül a GenerateRandomBit művelet elé a Main.qs fájlban:
/// Generates a random number between 0 and `max`.
operation GenerateRandomNumberInRange(max : Int) : Int {
// Determine the number of bits needed to represent `max` and store it
// in the `nBits` variable. Then generate `nBits` random bits which will
// represent the generated random number.
mutable bits = [];
let nBits = BitSizeI(max);
for idxBit in 1..nBits {
set bits += [GenerateRandomBit()];
}
let sample = ResultArrayAsInt(bits);
// Return random number if it's within the requested range.
// Generate it again if it's outside the range.
return sample > max ? GenerateRandomNumberInRange(max) | sample;
}
Íme a kód áttekintése a következőben: GenerateRandomNumberInRange.
- Hívja meg a
BitSizeIfüggvényt aStd.Mathkódtárból a tároltmaxegész szám megjelenítéséhez szükséges bitek számának kiszámításához. - Használjon egy
forhurkot, hogy véletlenszerű biteket generáljon, amelyek száma egyenlőnBits-tel. Hívja meg aGenerateRandomBitműveletet a véletlenszerű bitek létrehozásához. - A
forcikluson belül használja azsetutasítást abitsváltozó frissítésére minden új véletlenszerű bitnél. A változóbitsegy módosítható változó, ami azt jelenti, hogy a számítás során az értékbitsváltozhat. - Hívja meg a
ResultArrayAsIntfüggvényt aStd.Convertkódtárból, hogy a bitekbitstömbje a benne tároltsamplepozitív egész számmá alakuljon. - Az
returnutasításban ellenőrizze, hogysamplenagyobb-e, mintmax. Hasamplenagyobb, mintmax, akkor hívjaGenerateRandomNumberInRangeújra, és kezdje újra. Ellenkező esetben adja vissza a megadott helyen tároltsamplevéletlenszerű számot.
Belépési pont hozzáadása
Végül adjon hozzá egy belépésipont-műveletet a kódhoz, hogy a fordító futtathassa a programot. Alapértelmezés szerint a Q#-fordító egy Main műveletet keres, és belépési pontként használja Main , függetlenül attól, hogy hol Main található a fájlban. Itt a Main művelet beállít egy értéket max , és meghívja a GenerateRandomNumberInRange műveletet, hogy véletlenszerű számot hozzon létre 0 és max0 között.
Ha például 0 és 100 közötti véletlenszerű számot szeretne létrehozni, másolja a következő kódot a Main.qs fájlba:
operation Main() : Int {
let max = 100;
Message($"Generating a random number between 0 and {max}: ");
// Generate random number in the 0..max range.
return GenerateRandomNumberInRange(max);
}
Végleges program
A program teljes Q#-kódja a következő helyen található Main.qs:
import Std.Convert.*;
import Std.Math.*;
operation Main() : Int {
let max = 100;
Message($"Generating a random number between 0 and {max}: ");
// Generate random number in the 0..max range.
return GenerateRandomNumberInRange(max);
}
/// Generates a random number between 0 and `max`.
operation GenerateRandomNumberInRange(max : Int) : Int {
// Determine the number of bits needed to represent `max` and store it
// in the `nBits` variable. Then generate `nBits` random bits which will
// represent the generated random number.
mutable bits = [];
let nBits = BitSizeI(max);
for idxBit in 1..nBits {
set bits += [GenerateRandomBit()];
}
let sample = ResultArrayAsInt(bits);
// Return random number if it's within the requested range.
// Generate it again if it's outside the range.
return sample > max ? GenerateRandomNumberInRange(max) | sample;
}
operation GenerateRandomBit() : Result {
// Allocate a qubit.
use q = Qubit();
// Set the qubit into superposition of 0 and 1 using the Hadamard operation
H(q);
// Measure the qubit value using the `M` operation, and store the
// measurement value in the `result` variable.
let result = M(q);
// Reset qubit to the |0〉 state.
Reset(q);
// Return the result of the measurement.
return result;
}
A program futtatása
Próbálja ki az új kvantum véletlenszerű számgenerátort!
A program futtatásához válassza a Kódlencse futtatása lehetőséget a művelet fölötti Main parancsok listájából. Vagy nyomja le a Ctrl + F5 billentyűkombinációt. A kimenet megjelenik a hibakeresési konzolon. Futtassa többször a programot, és figyelje meg, hogyan változik az eredmény.
Gratulálunk! Létrehozott egy igazán véletlenszerű kvantumszámgenerátort a Q#-ban.
Bónusz gyakorlat
Próbálja meg úgy módosítani a programot, hogy a generált véletlenszerű szám is nagyobb legyen, mint egy minimális pozitív szám, minnulla helyett.