Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,11 @@ set(SOURCES
./qubitverse/simulator/lexer/lexer.cc
./qubitverse/simulator/parser/parser.cc
./qubitverse/simulator/gates/gates.cc
./qubitverse/simulator/gates/advanced_gates.cc
)

# Add test executable
add_executable(grover_test ./qubitverse/simulator/grover_test.cc)

# Create the executable target
add_executable(${PROJECT_NAME} ${SOURCES})
95 changes: 73 additions & 22 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,14 +11,13 @@ The simulator allows you to **store and apply various quantum gates** to qubit s
This project is divided into two main parts:

### 🔹 Quantum Gate Simulator (C++)
- Implements basic quantum mechanics concepts such as **qubit state representation** and **quantum gate operations**.
- Provides a set of common quantum gates:
- Identity
- Pauli-X, Pauli-Y, Pauli-Z
- Hadamard
- Phase (S)
- T-Gate
- Uses **manual matrix operations** (without external libraries like Eigen) to evolve quantum states.
- Implements basic quantum mechanics concepts such as **qubit state representation** and **quantum gate operations**.
- Provides a comprehensive set of quantum gates:
- **Single-qubit gates**: Identity, Pauli-X/Y/Z, Hadamard, Phase (S), T-Gate, Rotation gates (Rx, Ry, Rz)
- **Two-qubit gates**: CNOT, CZ, SWAP
- **Advanced multi-qubit gates**: Toffoli (CCX), Fredkin (CSWAP), Multi-controlled X/Z, Quantum Fourier Transform (QFT)
- Uses **manual matrix operations** (without external libraries like Eigen) to evolve quantum states.
- Includes **validation tests** for advanced algorithms like Grover's search.

### 🔹 GUI Visualizer (Node.js)
- A **frontend interface** that communicates with the C++ simulator.
Expand All @@ -31,11 +30,13 @@ This project is divided into two main parts:

## ✨ Features

- **Quantum Gate Storage** – Manage and apply common gates easily.
- **State Evolution** – Apply operations on qubits and observe transformations.
- **Extensible Backend** – Future support for **multi-qubit systems** and advanced gates (like CNOT).
- **Interactive GUI** – User-friendly Node.js frontend with drag-and-drop interface.
- **Separation of Concerns** – C++ handles computation, Node.js handles visualization.
- **Quantum Gate Storage** – Manage and apply common gates easily.
- **State Evolution** – Apply operations on qubits and observe transformations.
- **Advanced Multi-Qubit Gates** – Full support for Toffoli, Fredkin, multi-controlled gates, and QFT.
- **Algorithm Implementation** – Grover's search algorithm validation and testing.
- **Interactive GUI** – User-friendly Node.js frontend with drag-and-drop interface.
- **Separation of Concerns** – C++ handles computation, Node.js handles visualization.
- **High Precision** – Numerical accuracy with < 1e-12 error tolerance.

---

Expand Down Expand Up @@ -82,9 +83,56 @@ The frontend will connect with the backend to visualize quantum gate operations.
4. Drag and drop gates onto qubits, then visualize state changes.

Example workflow:
- Initialize a |0⟩ qubit
- Apply a Hadamard gate → get a superposition state
- Apply a Pauli-Z gate → observe phase flip on the Bloch sphere
- Initialize a |0⟩ qubit
- Apply a Hadamard gate → get a superposition state
- Apply a Pauli-Z gate → observe phase flip on the Bloch sphere

---

## 🔧 Advanced Gates API

The simulator now includes advanced multi-qubit gates essential for quantum algorithms:

### Toffoli Gate (CCX)
```cpp
apply_toffoli_gate(state, len, ctrl1, ctrl2, target);
```
Applies X gate to target qubit when both control qubits are in |1⟩ state.

### Fredkin Gate (CSWAP)
```cpp
apply_fredkin_gate(state, len, ctrl, target1, target2);
```
Swaps target1 and target2 qubits when control qubit is in |1⟩ state.

### Multi-Controlled Gates
```cpp
// Multi-controlled X
apply_multi_controlled_x(state, len, controls, target);

// Multi-controlled Z
apply_multi_controlled_z(state, len, controls, target);
```
Apply X or Z gate when all control qubits are in |1⟩ state.

### Quantum Fourier Transform
```cpp
// Full QFT
apply_qft(state, len, qubits, inverse);

// Decomposed QFT (more efficient)
apply_qft_decomposed(state, len, qubits, inverse);
```
Performs quantum Fourier transform on specified qubits.

### Grover's Algorithm
The included test file demonstrates Grover's search algorithm using the advanced gates:
```bash
# Build and run the test
cmake .
make grover_test
./grover_test
```

---

Expand Down Expand Up @@ -139,11 +187,14 @@ qubitverse/
---

## 📌 Roadmap
- [ ] Add **multi-qubit support**
- [ ] Implement **CNOT and controlled gates**
- [ ] Improve **visualization with real-time animations**
- [ ] Add **export/import** of circuits
- [ ] Provide a **hosted live demo**
- [x] Add **multi-qubit support**
- [x] Implement **CNOT and controlled gates**
- [x] Implement **advanced multi-qubit gates** (Toffoli, Fredkin, QFT)
- [ ] Improve **visualization with real-time animations**
- [ ] Add **export/import** of circuits**
- [ ] Provide a **hosted live demo**
- [ ] Add **quantum error correction** support
- [ ] Implement **variational quantum algorithms**

---

Expand All @@ -155,7 +206,7 @@ See the [LICENSE](https://github.com/Dark-CodeX/qubitverse/blob/main/LICENSE) fi

## 🌟 Acknowledgments
- Inspired by basic concepts of **Quantum Computing**.
- Educational references: Nielsen & Chuang *Quantum Computation and Quantum Information*.
- Educational references: Nielsen & Chuang - *Quantum Computation and Quantum Information*.
- Open-source tools and the developer community.

---
Binary file added grover_test
Binary file not shown.
195 changes: 195 additions & 0 deletions qubitverse/simulator/gates/advanced_gates.cc
Original file line number Diff line number Diff line change
@@ -0,0 +1,195 @@
/**
* @file advanced_gates.cc
* @license This file is licensed under the GNU GENERAL PUBLIC LICENSE Version 3, 29 June 2007. You may obtain a copy of this license at https://www.gnu.org/licenses/gpl-3.0.en.html.
* @author Tushar Chaurasia (Dark-CodeX)
*/

#include "./advanced_gates.hh"

namespace simulator
{
void apply_toffoli_gate(std::complex<double>*& state, const std::size_t len,
const std::size_t ctrl1, const std::size_t ctrl2, const std::size_t target)
{
if (std::log2(len) < 3.0) {
std::fprintf(stderr, "error: Toffoli gate requires a minimum of 3 qubit-system, but it was %zu qubit-system.\n", (std::size_t)std::log2(len));
std::exit(EXIT_FAILURE);
}

// Toffoli gate applies X to target only when both controls are |1⟩
for (std::size_t i = 0; i < len; ++i) {
// Check if both control qubits are in |1⟩ state
bool ctrl1_set = (i >> ctrl1) & 1;
bool ctrl2_set = (i >> ctrl2) & 1;

if (ctrl1_set && ctrl2_set) {
// Flip the target bit
std::size_t flipped_index = i ^ (1ULL << target);
// Swap amplitudes only if i < flipped_index to avoid double swapping
if (i < flipped_index) {
std::swap(state[i], state[flipped_index]);
}
}
}
}

void apply_fredkin_gate(std::complex<double>*& state, const std::size_t len,
const std::size_t ctrl, const std::size_t target1, const std::size_t target2)
{
if (std::log2(len) < 3.0) {
std::fprintf(stderr, "error: Fredkin gate requires a minimum of 3 qubit-system, but it was %zu qubit-system.\n", (std::size_t)std::log2(len));
std::exit(EXIT_FAILURE);
}

// Fredkin gate swaps target1 and target2 only when control is |1⟩
for (std::size_t i = 0; i < len; ++i) {
// Check if control qubit is in |1⟩ state
bool ctrl_set = (i >> ctrl) & 1;

if (ctrl_set) {
// Swap target1 and target2 bits
std::size_t swapped_index = i ^ (1ULL << target1) ^ (1ULL << target2);
// Swap amplitudes only if i < swapped_index to avoid double swapping
if (i < swapped_index) {
std::swap(state[i], state[swapped_index]);
}
}
}
}

void apply_multi_controlled_x(std::complex<double>*& state, const std::size_t len,
const std::vector<std::size_t>& controls, const std::size_t target)
{
std::size_t num_qubits = static_cast<std::size_t>(std::log2(len));
if (num_qubits < controls.size() + 1) {
std::fprintf(stderr, "error: Multi-controlled X gate requires at least %zu qubits, but system has %zu qubits.\n",
controls.size() + 1, num_qubits);
std::exit(EXIT_FAILURE);
}

// Apply X to target only when all controls are |1⟩
for (std::size_t i = 0; i < len; ++i) {
if (are_controls_set(i, controls)) {
// Flip the target bit
std::size_t flipped_index = i ^ (1ULL << target);
// Swap amplitudes only if i < flipped_index to avoid double swapping
if (i < flipped_index) {
std::swap(state[i], state[flipped_index]);
}
}
}
}

void apply_multi_controlled_z(std::complex<double>*& state, const std::size_t len,
const std::vector<std::size_t>& controls, const std::size_t target)
{
std::size_t num_qubits = static_cast<std::size_t>(std::log2(len));
if (num_qubits < controls.size() + 1) {
std::fprintf(stderr, "error: Multi-controlled Z gate requires at least %zu qubits, but system has %zu qubits.\n",
controls.size() + 1, num_qubits);
std::exit(EXIT_FAILURE);
}

// Apply phase of -1 when all controls are |1⟩ and target is |1⟩
for (std::size_t i = 0; i < len; ++i) {
if (are_controls_set(i, controls)) {
bool target_set = (i >> target) & 1;
if (target_set) {
state[i] *= -1.0;
}
}
}
}

void apply_qft(std::complex<double>*& state, const std::size_t len,
const std::vector<std::size_t>& qubits, bool inverse)
{
std::size_t num_qubits = static_cast<std::size_t>(std::log2(len));
std::size_t n = qubits.size();

if (n == 0) return;

// Create a copy of the state for transformation
std::vector<std::complex<double>> new_state(len, 0.0);

// QFT matrix implementation
double normalization = 1.0 / std::sqrt(static_cast<double>(1ULL << n));

for (std::size_t output = 0; output < (1ULL << n); ++output) {
for (std::size_t input = 0; input < (1ULL << n); ++input) {
std::complex<double> phase = qft_phase_factor(output, input, n);
if (inverse) {
phase = std::conj(phase);
}

// Map qubits to actual indices
std::size_t full_input = 0;
std::size_t full_output = 0;

for (std::size_t i = 0; i < num_qubits; ++i) {
bool is_in_qft = std::find(qubits.begin(), qubits.end(), i) != qubits.end();
if (is_in_qft) {
std::size_t qft_idx = std::distance(qubits.begin(),
std::find(qubits.begin(), qubits.end(), i));
bool bit = (input >> qft_idx) & 1;
if (bit) full_input |= (1ULL << i);

bit = (output >> qft_idx) & 1;
if (bit) full_output |= (1ULL << i);
}
}

new_state[full_output] += state[full_input] * phase * normalization;
}
}

// Copy back to original state
for (std::size_t i = 0; i < len; ++i) {
state[i] = new_state[i];
}
}

void apply_qft_decomposed(std::complex<double>*& state, const std::size_t len,
const std::vector<std::size_t>& qubits, bool inverse)
{
std::size_t n = qubits.size();
if (n == 0) return;

// Apply Hadamard gates and controlled phase rotations
for (std::size_t i = 0; i < n; ++i) {
// Apply Hadamard to qubit i
qubit::apply_predefined_gate_public(state, len, qubit::gate_type::HADAMARD, qubits[i]);

// Apply controlled phase rotations
for (std::size_t j = i + 1; j < n; ++j) {
double angle = (inverse ? -1.0 : 1.0) * M_PI / static_cast<double>(1ULL << (j - i));
qubit::apply_theta_gate_public(state, len, qubit::gate_type::PHASE_GENERAL_SHIFT, angle, qubits[i]);
// Note: This is a simplified implementation. In practice, controlled rotations would be needed.
}
}

// Apply SWAP gates to reverse qubit order (for standard QFT)
if (!inverse) {
for (std::size_t i = 0; i < n / 2; ++i) {
qubit::apply_2qubit_gate_public(state, len, qubit::gate_type::SWAP_GATE, qubits[i], qubits[n - 1 - i]);
}
}
}

bool are_controls_set(std::size_t index, const std::vector<std::size_t>& controls)
{
for (std::size_t ctrl : controls) {
if (((index >> ctrl) & 1) == 0) {
return false;
}
}
return true;
}

std::complex<double> qft_phase_factor(std::size_t k, std::size_t n, std::size_t N)
{
double angle = 2.0 * M_PI * static_cast<double>(k * n) / static_cast<double>(1ULL << N);
return std::complex<double>(std::cos(angle), std::sin(angle));
}

} // namespace simulator
Loading
Loading