# tn-lens

`tn-lens` is an interactive visualizer that bridges the gap between quantum circuit geometry and tensor network contraction paths.

It maps abstract tensor math back to physical quantum operations, providing a split-screen interactive UI.

## Features

* A RAM slider filters the contraction tree, instantly highlighting intermediate tensors that exceed your hardware limits.
* Clicking an overgrown tensor highlights the exact causal cone of quantum gates in the circuit that generated it.
* Natively parses OpenQASM 2.0/3.0 strings, as well as `qiskit.QuantumCircuit`, `cirq.Circuit`, and `pennylane.QuantumTape` objects.
* Automatically handles mid-circuit measurements (wire re-initialization) and safely wraps custom/exotic gates into generic multi-qubit bounding boxes.

## Installation

Install the base package via pip:

```bash
pip install tn-lens
```

To use advanced hypergraph optimizers (highly recommended for circuits > 20 qubits), install the `optimizers` extra, which pulls in `cotengra`:

```bash
pip install tn-lens[optimizers]
```

## Usage

`tn-lens` can be used directly from the terminal or imported as a Python library.

### Command Line Interface (CLI)

You can analyze any standard OpenQASM file directly from your terminal:

```bash
tn-lens my_circuit.qasm --optimizer greedy --memory 16.0
```

**CLI Arguments:**
* `input_file`: Path to the `.qasm` file.
* `-o`, `--output`: Path to save the HTML visualization (default: `tensor_network.html`).
* `-O`, `--optimizer`: Contraction path optimizer (`greedy`, `optimal`, `auto`).
* `-m`, `--memory`: Initial RAM threshold in MB for the UI slider.
* `--no-browser`: Prevents the browser from opening automatically.

### Python API

You can inject `tn-lens` directly into your existing quantum workflows. The library uses duck-typing to automatically translate Qiskit, Cirq, or PennyLane objects.

```python
from qiskit import QuantumCircuit
from tn_lens.circuit import QASMParser
from tn_lens.analyzer import analyze_tensors
from tn_lens.renderer import render_graph

# 1. Define your circuit in your preferred framework
qc = QuantumCircuit(10)
for i in range(10):
    qc.h(i)
for i in range(9):
    qc.cx(i, i+1)

# 2. Parse into tensor inputs
parser = QASMParser()
inputs, output, shapes, gate_info = parser.parse(qc)
circuit_svg = parser.generate_svg(gate_info)

# 3. Analyze contraction path
nodes, edges, path, info = analyze_tensors(
    inputs, output, shapes, optimizer='auto'
)

# 4. Render the interactive UI
render_graph(
    nodes, edges, 
    circuit_svg=circuit_svg, 
    memory_limit_mb=10.0, 
    output_html="analysis.html"
)
```
