From f444e78c743d7d7b417cd8f00be474611b130632 Mon Sep 17 00:00:00 2001 From: miha-q <> Date: Tue, 30 Jul 2024 19:57:55 -0400 Subject: [PATCH] Tue Jul 30 07:57:55 PM EDT 2024 --- Makefile | 3 +- build.sh | 7 +- examples/chsh_inequality_c.txt | 3 +- examples/chsh_oneshot.txt | 42 ++++++ examples/ghz.txt | 21 +++ examples/teleportation.txt | 1 + src/bytecode.c | 12 +- src/gui.html | 226 +++++++++++++++++++++++++++------ src/imports/istina-editor.js | 2 + 9 files changed, 265 insertions(+), 52 deletions(-) create mode 100644 examples/chsh_oneshot.txt create mode 100644 examples/ghz.txt diff --git a/Makefile b/Makefile index 53867c5..a12183e 100644 --- a/Makefile +++ b/Makefile @@ -1,5 +1,6 @@ all: - echo "Please use build.sh script." + bash build.sh +# echo "Please use build.sh script." commit: git add src/ examples/ Makefile build.sh diff --git a/build.sh b/build.sh index 56d1474..898e2ea 100644 --- a/build.sh +++ b/build.sh @@ -56,11 +56,12 @@ else cflags="-std=gnu99 -I/usr/include/SDL2 -D__PTHREAD__ -D__SDL2__ -D__OPENCL__ -I/usr/include/SDL2 -D_REENTRANT" fi +rm -r bin 2>/dev/null +rm -r obj 2>/dev/null +mkdir bin 2>/dev/null +mkdir obj 2>/dev/null cd src/ -rm -r ../obj 2>/dev/null -mkdir ../obj 2>/dev/null - fcmd="gcc -o ../bin/QAnsel" for i in complex context display hardware bytecode openqasm main kernel_cpu do diff --git a/examples/chsh_inequality_c.txt b/examples/chsh_inequality_c.txt index 8218c24..5a3ee68 100644 --- a/examples/chsh_inequality_c.txt +++ b/examples/chsh_inequality_c.txt @@ -53,4 +53,5 @@ barrier q; //Sample results measure q[1] -> c[0]; -sample c[0]; \ No newline at end of file +sample c[0]; + diff --git a/examples/chsh_oneshot.txt b/examples/chsh_oneshot.txt new file mode 100644 index 0000000..4eb4c92 --- /dev/null +++ b/examples/chsh_oneshot.txt @@ -0,0 +1,42 @@ +//CHSH Inequality Bell Test +qreg q[8]; +creg c[8]; + +//Two players are also provided +// an entangled qubit. +h q[0]; +cx q[0], q[1]; +h q[2]; +cx q[2], q[3]; +h q[4]; +cx q[4], q[5]; +h q[6]; +cx q[6], q[7]; + +//00 +//do nothing +ry(pi/4) q[1]; + +//01 +ry(pi/2) q[2]; +ry(pi/4) q[3]; + +//10 +//do nothing +ry(-pi/4) q[5]; + +//11 +ry(pi/2) q[6]; +ry(-pi/4) q[7]; + +//Transfer to host +measure q[0] -> c[0]; +measure q[1] -> c[1]; +measure q[2] -> c[2]; +measure q[3] -> c[3]; +measure q[4] -> c[4]; +measure q[5] -> c[5]; +measure q[6] -> c[6]; +measure q[7] -> c[7]; + +sample c; diff --git a/examples/ghz.txt b/examples/ghz.txt new file mode 100644 index 0000000..d988daa --- /dev/null +++ b/examples/ghz.txt @@ -0,0 +1,21 @@ +qreg q[3]; +creg c[3]; + +//Prepare GHZ state +h q[0]; +cx q[0], q[1]; +cx q[0], q[2]; + +h q[0]; +measure q[0] -> c[0]; + +sdg q[1]; +h q[1]; +measure q[1] -> c[1]; + +sdg q[2]; +h q[2]; +measure q[2] -> c[2]; + +sample c; + diff --git a/examples/teleportation.txt b/examples/teleportation.txt index 68ea158..94e04bf 100644 --- a/examples/teleportation.txt +++ b/examples/teleportation.txt @@ -29,3 +29,4 @@ if(c==3) z q[2]; reset q[0]; reset q[1]; print q[2]; + diff --git a/src/bytecode.c b/src/bytecode.c index b171016..f694362 100644 --- a/src/bytecode.c +++ b/src/bytecode.c @@ -699,7 +699,7 @@ void qansel_born(cpx_mtx_t* stateVector, int PC, int qubitCount, unsigned char q } cpx_t n; cpx_mtx_get(stateVector, 0, j, &n); - printf(": %.1f%%\n", cpx_magsqr(&n) * 100); + printf("\t%.1f%%\n", cpx_magsqr(&n) * 100); } } else if (q0 <= QANSEL_QBOUND_UPPER) @@ -714,8 +714,8 @@ void qansel_born(cpx_mtx_t* stateVector, int PC, int qubitCount, unsigned char q prob += cpx_magsqr(&n); } } - printf("0: %.1f%%\n", (1 - prob) * 100.0); - printf("1: %.1f%%\n", prob * 100.0); + printf("0\t%.1f%%\n", (1 - prob) * 100.0); + printf("1\t%.1f%%\n", prob * 100.0); } } @@ -1538,14 +1538,14 @@ int qanselExecuteBytecode(unsigned char* buff, int sizeofbuff, QAnselContext* ct } if ((ctx->sampling_bit) == QANSEL_ALL) { - printf(": %.1f%%\n", ((float)stats[i] / (float)shots) * (float)100); + printf("\t%i\t%.1f%%\n", stats[i], ((float)stats[i] / (float)shots) * (float)100); } } if ((ctx->sampling_bit) != QANSEL_ALL) { float prob = ((float)count / (float)shots) * (float)100; - printf("0: %.1f%%\n", ((float)100)-prob); - printf("1: %.1f%%\n", prob); + printf("0\t%i\t%.1f%%\n", shots-count, ((float)100)-prob); + printf("1\t%i\t%.1f%%\n", count, prob); } } else diff --git a/src/gui.html b/src/gui.html index 7822732..bbc6648 100644 --- a/src/gui.html +++ b/src/gui.html @@ -5,7 +5,25 @@ -
-    -    - - -    -
  
- -
- + @@ -69,7 +90,7 @@
-
-
+
+    +    + + +    +
  
+ +  
-
+
+
+
+
+
+
- +
@@ -88,11 +109,11 @@ case "01": return "CX"; break; } break; - case "SWAP": + case "SW": switch (pos) { - case "10": return "SWAP"; break; - case "01": return "SWAP"; break; + case "10": return "SW"; break; + case "01": return "SW"; break; } break; case "CCX": @@ -103,12 +124,12 @@ case "001": return "CCX"; break; } break; - case "CSWAP": + case "CSW": switch (pos) { - case "100": return "CSWAP"; break; - case "010": return "CSWAP"; break; - case "001": return "CSWAP"; break; + case "100": return "CSW"; break; + case "010": return "CSW"; break; + case "001": return "CSW"; break; } break; } @@ -126,8 +147,13 @@ "T", "CX", "CCX", - "SWAP", - "CSWAP", + "SW", + "CSW", + "Rx", + "Ry", + "Rz", + "U", + "RST", "🔍", "|1⟩", "|0⟩", @@ -137,6 +163,108 @@ SCALE: 64, STATE: [ [], [], [], [], [], [], [], [], [], [], [], [], [], [], [] ], DRAG: "", + decode: () => + { + var width = 0; + for (var i = 0; i < ProgramTrack.STATE.length - 1; i++) + { + if (ProgramTrack.STATE[i].length > width) + { + width = ProgramTrack.STATE[i].length; + } + } + var ret = ""; + var maxQ = -1; + var maxC = -1; + for (var i = 0; i < width; i++) + { + var ifblk = ProgramTrack.STATE[ProgramTrack.STATE.length - 1][i].trim(); + if (ifblk.length > 0) + { + var a = ifblk.split("")[0].includes("0") ? 0 : 1; + var b = parseInt(ifblk.split("")[1].split("<")[0]); + ifblk = "if(c[" + b + "]==" + a + ") "; + if (b > maxC) maxC = b; + } + var cx = [0, -1, -1]; + var sw = [0, -1, -1]; + var ccx = [0, -1, -1, -1]; + var csw = [0, -1, -1, -1]; + for (var j = 0; j < ProgramTrack.STATE.length - 1; j++) + { + var instr = ProgramTrack.STATE[j][i].trim(); + if (instr.length == 0) continue; + console.log(instr); + if (j > maxQ) maxQ = j; + switch (instr) + { + case "X": ret += ifblk + "x q[" + j + "];\n"; break; + case "Y": ret += ifblk + "y q[" + j + "];\n"; break; + case "Z": ret += ifblk + "z q[" + j + "];\n"; break; + case "H": ret += ifblk + "h q[" + j + "];\n"; break; + case "S": ret += ifblk + "s q[" + j + "];\n"; break; + case "T": ret += ifblk + "t q[" + j + "];\n"; break; + case "S†": ret += ifblk + "sdg q[" + j + "];\n"; break; + case "T†": ret += ifblk + "tdg q[" + j + "];\n"; break; + default: + if (instr.includes("🔍")) + { + var num = parseInt(instr.split(">")[1].split("<")[0]); + if (num > maxC) maxC = num; + ret += ifblk + "measure q[" + j + "] -> c[" + num + "];\n"; + } + } + if (instr == overline("CX", "10")) { if (cx[1] != -1) { cx[0] = 1; } cx[1] = j; } + if (instr == overline("CX", "01")) { if (cx[2] != -1) { cx[0] = 1; } cx[2] = j; } + if (instr == overline("SW", "10")) { if (sw[1] != -1) { sw[0] = 1; } sw[1] = j; } + if (instr == overline("SW", "01")) { if (sw[2] != -1) { sw[0] = 1; } sw[2] = j; } + + if (instr == overline("CCX", "100")) { if (ccx[1] != -1) { ccx[0] = 1; } ccx[1] = j; } + if (instr == overline("CCX", "010")) { if (ccx[2] != -1) { ccx[0] = 1; } ccx[2] = j; } + if (instr == overline("CCX", "001")) { if (ccx[3] != -1) { ccx[0] = 1; } ccx[3] = j; } + if (instr == overline("CSW", "100")) { if (csw[1] != -1) { csw[0] = 1; } csw[1] = j; } + if (instr == overline("CSW", "010")) { if (csw[2] != -1) { csw[0] = 1; } csw[2] = j; } + if (instr == overline("CSW", "001")) { if (csw[3] != -1) { csw[0] = 1; } csw[3] = j; } + } + + if (cx[0]) { ret = "Duplicate `CX` at column " + (i + 1) + "."; break; } + if (cx[1] != -1 && cx[2] != -1) { ret += ifblk + "cx q[" + cx[1] + "], q[" + cx[2] + "];\n"; } + else if (cx[1] != -1 || cx[2] != -1) { ret = "Incomplete `CX` at column " + (i + 1) + "."; break; } + + if (sw[0]) { ret = "Duplicate `SW` at column " + (i + 1) + "."; break; } + if (sw[1] != -1 && sw[2] != -1) { ret += ifblk + "swap q[" + sw[1] + "], q[" + sw[2] + "];\n"; } + else if (sw[1] != -1 || sw[2] != -1) { ret = "Incomplete `SW` at column " + (i + 1) + "."; break; } + + if (ccx[0]) { ret = "Duplicate `CCX` at column " + (i + 1) + "."; break; } + if (ccx[1] != -1 && ccx[2] != -1 && ccx[3] != -1) { ret += ifblk + "ccx q[" + ccx[1] + "], q[" + ccx[2] + "], q[" + ccx[3] + "];\n"; } + else if (ccx[1] != -1 || ccx[2] != -1 || ccx[3] != -1) { ret = "Incomplete `CCX` at column " + (i + 1) + "."; break; } + + if (csw[0]) { ret = "Duplicate `CSW` at column " + (i + 1) + "."; break; } + if (csw[1] != -1 && csw[2] != -1 && csw[3] != -1) { ret += ifblk + "cswap q[" + csw[1] + "], q[" + csw[2] + "], q[" + csw[3] + "];\n"; } + else if (csw[1] != -1 || csw[2] != -1 || csw[3] != -1) { ret = "Incomplete `CSW` at column " + (i + 1) + "."; break; } + } + if (!ret.includes("Duplicate") && !ret.includes("Incomplete")) + { + if (maxC >= 0) + { + ret = "creg c[" + (maxC + 1) + "];\n" + ret; + } + if (maxQ >= 0) + { + ret = "qreg q[" + (maxQ + 1) + "];\n" + ret; + if (maxC >= 0) + { + ret += "sample c;\n"; + } + else + { + ret += "born q;\n"; + } + } + + } + return ret; + }, drag: (e, erase, evt) => { if (e.innerHTML.includes("Q") || e.innerHTML.includes("IF") || e.innerHTML.includes("...")) @@ -154,14 +282,14 @@ { case overline("CX", "10"): ProgramTrack.STATE[s[0]][s[1]] = overline("CX", "01"); break; case overline("CX", "01"): ProgramTrack.STATE[s[0]][s[1]] = overline("CX", "10"); break; - case overline("SWAP", "10"): ProgramTrack.STATE[s[0]][s[1]] = overline("SWAP", "01"); break; - case overline("SWAP", "01"): ProgramTrack.STATE[s[0]][s[1]] = overline("SWAP", "10"); break; + case overline("SW", "10"): ProgramTrack.STATE[s[0]][s[1]] = overline("SW", "01"); break; + case overline("SW", "01"): ProgramTrack.STATE[s[0]][s[1]] = overline("SW", "10"); break; case overline("CCX", "100"): ProgramTrack.STATE[s[0]][s[1]] = overline("CCX", "010"); break; case overline("CCX", "010"): ProgramTrack.STATE[s[0]][s[1]] = overline("CCX", "001"); break; case overline("CCX", "001"): ProgramTrack.STATE[s[0]][s[1]] = overline("CCX", "100"); break; - case overline("CSWAP", "100"): ProgramTrack.STATE[s[0]][s[1]] = overline("CSWAP", "010"); break; - case overline("CSWAP", "010"): ProgramTrack.STATE[s[0]][s[1]] = overline("CSWAP", "001"); break; - case overline("CSWAP", "001"): ProgramTrack.STATE[s[0]][s[1]] = overline("CSWAP", "100"); break; + case overline("CSW", "100"): ProgramTrack.STATE[s[0]][s[1]] = overline("CSW", "010"); break; + case overline("CSW", "010"): ProgramTrack.STATE[s[0]][s[1]] = overline("CSW", "001"); break; + case overline("CSW", "001"): ProgramTrack.STATE[s[0]][s[1]] = overline("CSW", "100"); break; } var instr = ProgramTrack.STATE[s[0]][s[1]].split("<")[0]; switch (instr) @@ -188,8 +316,8 @@ { case "CX": case "CCX": - case "SWAP": - case "CSWAP": + case "SW": + case "CSW": break; default: h = e.innerHTML; } @@ -211,7 +339,7 @@ var drag_event = "onmousedown='ProgramTrack.drag(this, true, event);'"; var px = ProgramTrack.SCALE + "px"; var tr = ""; - var td = ""; itr++; - if (itr > /*8*/ 100) + if (itr > 4 && i != INSTRUCTIONS.length - 1) { html += "" + tr; itr = 0; @@ -257,13 +385,15 @@ } html += ""; $(".program-instr")[0].innerHTML = html; - + IstinaEditor.setText(ProgramTrack.decode()); } }; window.onload = function() { ProgramTrack.draw(); + $(".program-track")[0].parentNode.style.height = Math.round($(".program-instr")[0].getBoundingClientRect().height) + "px"; + $(".program-track")[0].parentNode.style.width = Math.round($(".program-instr")[0].getBoundingClientRect().width) + "px"; }; document.body.addEventListener("mousemove", e => @@ -277,6 +407,7 @@ }); document.body.addEventListener("mouseup", e => { + ProgramTrack.draw(); if ($(".program-drag")[0].style.visibility == "hidden") { return; @@ -291,7 +422,7 @@ attr[1] = parseInt(attr[1]); var html = $(".program-drag td")[0].innerHTML; var qubit = parseInt(elem.getAttribute("qubit")); - console.log(html); + console.log(elem.innerHTML); switch (html) { case "|1⟩": case "|0⟩": @@ -303,9 +434,9 @@ switch (html) { case "CX": html = overline("CX", "10"); break; - case "SWAP": html = overline("SWAP", "10"); break; + case "SW": html = overline("SW", "10"); break; case "CCX": html = overline("CCX", "100"); break; - case "CSWAP": html = overline("CSWAP", "100"); break; + case "CSW": html = overline("CSW", "100"); break; case "🔍": html = "🔍0"; break; case "|1⟩": html = "|1⟩0"; break; case "|0⟩": html = "|0⟩0"; break; @@ -328,17 +459,19 @@ } } ProgramTrack.draw(); + if (elem.innerHTML.trim() == "...") + { + $(".program-track-container")[0].scrollLeft = $(".program-track-container")[0].scrollLeftMax; + } }); //Chart - const ctx = document.getElementById('myChart'); - - new Chart(ctx, { + var resultsChart = new Chart(document.getElementById("resultsChart"), { type: 'bar', data: { labels: ['000', '001', '010', '011', '100', '101', '110', '111'], datasets: [{ label: '# of |1⟩', - data: [12, 19, 3, 5, 2, 3, 5, 2], + data: [], borderWidth: 1 }] }, @@ -350,6 +483,17 @@ } } }); + function displayResults(results) + { + var bitCount = Math.ceil(Math.log2(results.length)); + resultsChart.data.datasets[0].data = results; + resultsChart.data.labels = []; + for (var i = 0; i < results.length; i++) + { + resultsChart.data.labels[resultsChart.data.labels.length] = i.toString(2).padStart(bitCount, "0"); + } + resultsChart.update(); + } diff --git a/src/imports/istina-editor.js b/src/imports/istina-editor.js index 1b5d90f..7cebdc7 100644 --- a/src/imports/istina-editor.js +++ b/src/imports/istina-editor.js @@ -231,6 +231,8 @@ IstinaEditor.highlightForQAnsel = function(txt) "z", "t", "s", + "tdg", + "sdg", "cx", "swap", "cswap", -- 2.39.5