Skip to content
This repository has been archived by the owner on Sep 13, 2019. It is now read-only.

Commit

Permalink
Merge pull request #59 from danbev/printCircuit
Browse files Browse the repository at this point in the history
Add print circuit method
  • Loading branch information
jesusprubio authored May 3, 2019
2 parents 00cc7e7 + c74c8fa commit f9657c5
Show file tree
Hide file tree
Showing 3 changed files with 166 additions and 0 deletions.
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,10 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.
## [Unreleased]

### 🎉 Added

- `@qiskit/qiskit-sim`: Add print circuit method

## [0.8.0] - 2019-04-25

### 🎉 Added
Expand Down
90 changes: 90 additions & 0 deletions packages/qiskit-sim/lib/Circuit.js
Original file line number Diff line number Diff line change
Expand Up @@ -180,11 +180,13 @@ class Circuit {
id,
name: (gate instanceof Gate) ? gate.name : gate.toLowerCase(),
connector,
multiQubit: numConnectors > 1,
};
}
return this;
}


createTransform(U, qubits) {
const dimension = this.numAmplitudes();
this.initTransform(dimension);
Expand Down Expand Up @@ -362,6 +364,94 @@ class Circuit {
return s;
}

print(writable = process.stdout) {
const columnLen = 10;
const spaceLen = 4;
const gateLen = 4;

const connectionsMap = new Map();
for (let column = 0; column < this.gates[0].length; column += 1) {
for (let wire = 0; wire < this.nQubits; wire += 1) {
const gate = this.gates[wire][column];
if (gate && gate.multiQubit) {
const m = connectionsMap.has(column) ? connectionsMap.get(column) :
new Map();
let entry;
if (m.has(gate.id)) {
entry = m.get(gate.id);
entry.to = wire;
} else {
entry = {from: wire,
fromVisited: false,
to: null,
toVisited: false};
}
m.set(gate.id, entry);
connectionsMap.set(column, m);
}
}
}

let columnHeader = ''.padStart(columnLen);
for (let i = 0; i < this.numCols(); i += 1) {
columnHeader += `column ${i}`.padEnd(columnLen, ' ');
columnHeader += ''.padEnd(spaceLen, ' ');
}
writable.write('\n');
writable.write(columnHeader);
writable.write('\n');

for (let wire = 0; wire < this.nQubits; wire += 1) {
writable.write(`wire ${wire} `.padEnd(columnLen, '-'));
let wireOutput = '';
let connOutput = ''.padStart(columnLen, ' ');
for (let column = 0; column < this.gates[wire].length; column += 1) {
const gate = this.getGateAt(column, wire);
const connections = connectionsMap.get(column);
if (connections) {
if (gate && connections.has(gate.id)) {
const c = connections.get(gate.id);
if (c.from === wire) {
c.fromVisited = true;
}
if (c.to === wire) {
c.toVisited = true;
}

if (c.fromVisited === true && c.toVisited === true) {
connections.delete(gate.id);
if (connections.size === 0) {
connectionsMap.delete(column);
}
} else {
connOutput += ` |`;
}
} else {
connOutput += ` |`;
}
}

if (gate) {
if (gate.multiQubit && gate.connector !== 0) {
wireOutput += `[*]`.padEnd(gateLen, '-');
} else {
wireOutput += `[${gate.name}]`.padEnd(gateLen, '-');
connOutput += ''.padEnd(gateLen, ' ');
}
} else {
wireOutput += ''.padEnd(gateLen, '-');
connOutput += ''.padEnd(gateLen, ' ');
}
wireOutput += ''.padEnd(columnLen, '-');
connOutput += ''.padEnd(columnLen, ' ');
}
writable.write(wireOutput);
writable.write('\n');
writable.write(connOutput);
writable.write('\n');
}
}

static createCircuit(qubits) {
if (typeof qubits !== 'number')
throw new TypeError('The "qubits" argument must be of type number. ' +
Expand Down
72 changes: 72 additions & 0 deletions packages/qiskit-sim/test/functional/Circuit.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
'use strict';

const assert = require('assert');
const { Writable } = require('stream');

const { Circuit, Gate } = require('../..');

Expand Down Expand Up @@ -150,3 +151,74 @@ describe('sim:Circuit:createCircuit', () => {
});
});
});

describe('sim:Circuit:print', () => {
let result = '';
const writable = new Writable({
write(chunk, encoding, callback) {
result += chunk.toString();
callback();
}
});

function stripWhitespace(str) {
return str.replace(/\s+/g, '');
}

afterEach( () => { result = ''; } )

it('should print circuit with single hadamard gate', () => {
const expected = `
column 0
wire 0 ---[h]-----------`;

Circuit.createCircuit(1).addGate(Gate.h, 0, 0).print(writable);
assert.strictEqual(stripWhitespace(result), stripWhitespace(expected));
});

it('should print circuit with multiple gates', () => {
const expected = `
column 0
wire 0 ---[h]-----------
wire 1 ---[h]-----------`;

Circuit.createCircuit(2).addGate(Gate.h, 0, 0)
.addGate(Gate.h, 0, 1)
.print(writable);
assert.strictEqual(stripWhitespace(result), stripWhitespace(expected));
});

it('should print circuit with connections', () => {
const expected = `
column 0 column 1
wire 0 ---[x]-----------[cx]----------
|
wire 1 -----------------[*]-----------`;
// Note that the star in this case represents the target qubit
// and the control qubit will be qubit 0.

Circuit.createCircuit(2).addGate(Gate.x, 0, 0)
.addGate(Gate.cx, 1, [0, 1])
.print(writable);
assert.strictEqual(stripWhitespace(result), stripWhitespace(expected));
});

it('should print circuit with connections over mutiple wires', () => {
const expected = `
column 0 column 1
wire 0 ---[x]-----------[cx]----------
|
wire 1 -------------------------------
|
wire 2 -----------------[*]-----------
wire 3 -------------------------------`;

Circuit.createCircuit(4).addGate(Gate.x, 0, 0)
.addGate(Gate.cx, 1, [0, 2])
.print(writable);
assert.strictEqual(stripWhitespace(result), stripWhitespace(expected));
});

});

0 comments on commit f9657c5

Please sign in to comment.