english

Quantum Computer Simulator


Language C++
Tested environment SunOS g++2.8.1

このプログラムが量子コンピュータ開発の何らかの役に立てることを期待して, 以下に同意される方に公開します.
ダウンロードされるときは tokunaga@is.s.u-tokyo.ac.jp 宛てに 同意の意思をメールしてください.

1.利用者がこのプログラムを利用して得た研究成果などを公表するときには, 利用したことを明記する.また製作者まで連絡する.
2.利用者がこのプログラムを改良したときは速やかに製作者に 連絡し,速やかに公開をする.
3.利用者がバグを見つけたら,そのバグが現われる入力データを添えて製作者まで 連絡する.
4.製作者は,このプログラムの使用によって発生したどのような問題に対しても責任をとらない.

source download
programmed by Ayumu NAGAI and Yuuki TOKUNAGA

製作者連絡先:
徳永裕己 (Tokunaga Yuuki)
東京大学大学院理学系研究科情報科学専攻
〒113-0033 東京都文京区本郷7-3-1
TEL: 03-5841-4102 FAX: 03-5800-6933
E-mail: tokunaga@is.s.u-tokyo.ac.jp


Usage


まず,QCS.tar.gz を解凍してください.

libqm/   基本ライブラリ.ここは変更する必要はありません.
sample/ ここに自分で書いたプログラムを置いてください.
基本的な説明です. 細部はプログラム例を参考にしてください. 例えば test2.cc というプログラムを書いたら, Makefile.in のファイルの EXECFILES と OBJS を以下のように書きたしてください. プログラムが増えるたびに OBJS は OBJS3,OBJS4, ... のように増やしてください. -------- EXECFILES = test test2 OBJS2 = test2.o SOURCES = $(OBJS2:.o=.cc) ARCHIVES = $(LIBDIR)/libqm.a test2: $(FRC) $(OBJS2) $(ARCHIVES) $(CCLINK) $(LDFLAGS) -o $@ $(OBJS2) $(LINKMATH) $(LINKAR) -------- そして,以下のようにコンパイルします. cd libqm
make Makefiles -f Makefile.in
make
cd ../sample
make Makefiles -f Makefile.in
make
操作するのは QMachine 型のベクトルです.これは n qubit のとき 2^n 個の振幅を保存するベクトルです. 操作は量子回路を意識してできます. U,(1qubit に対する 2x2行列をかける操作) controlled-U, WH, FFT, AND, OR, NOT, cNOT, SWAP, をかけることができます. (* FFT は量子回路の記述による DFT より早いですが,bit 数が大きくなると 多少誤差がでます.正確に行うときは量子回路の記述通りにプログラムしてください) 細かい仕様は libqm の中のヘッダファイルを読んでください.

Example

------------------------------
#include < iostream.h >
#include < stdlib.h >
#include < math.h >
#include < qmachine.h >
#include < time-device.h >

int
main()
{
    double seed = dgettime();// ランダム関数の種  観測に用いる
    srandom((int)((seed-(int)seed) * 1000000));   
    
    int bits = 3;            // 使用 qubit 数
    int states = 1 << bits;
    QMachine qm( states );   // qm  宣言

    qm.Init();               // qm 初期化 |00...0> の振幅を1に他を0にする
    cout << qm << endl;      // qm の状態を出力 2^n 個の振幅を出力する

    NOT(0)*qm;               // NOT    0ビット目の NOT をとる
    cout << qm << endl; 


    OR(2,1,0)*qm;            // OR     0,1 ビット目 の OR をとり 
    cout << qm << endl;      //        2 ビット目に出力するゲート


    cNOT(1,0)*qm;            // cNOT   標的ビットを1ビット目,制御ビットを
    cout << qm << endl;      //        0ビット目とする制御NOTゲート

    cNOT cn(1,0);            // 制御が2つ以上かかるときはまずゲートを宣言して
    cn.control(trans(2,0));  // から制御ビットをこのように指定する
    cn*qm;                   // この場合2ビット目と0ビット目が制御ビット  
    cout << qm << endl;        

    U(1,0,0,exp(Complex(0, M_PI/6.0)),0)*qm;
                             // Uゲート  U_{00} = 1, U_{01} = 0, 
                             //          U_{10} = 0, U_{11} = exp(i \pi / 6)
                             //          の2x2行列を1ビット目にかけるゲート 
    cout << qm << endl; 


    cU(1,0,0,exp(Complex(0, M_PI/6.0)),2,0)*qm;
                             // Controlled-Uゲート  上と同じ2x2行列を
                             // 標的ビットを2ビット目,制御ビットを0ビット目
                             // としてかける
    cout << qm << endl; 

    cU cu(1,0,0,exp(Complex(0, M_PI/6.0)),2,0);
    cu.control(trans(0,1));  // cUゲートの制御が2つ以上かかるときは
    cu*qm;                   // このようにゲートを宣言してから制御
    cout << qm << endl;      // ビットを0と1に変更する
    

    WH(2,0)*qm;              // WH 変換を0から2ビット目にかける
    cout << qm << endl; 

    FFT(2,1)*qm;             // FFT を1から2ビットにかける
    cout << qm << endl; 

    cout << "answer = " << qm.Measure( bits-1, 0 ) << endl; 
    // 0ビット目から最後のビットまでの観測をして出力.状態は収縮する.
    // qm.Measure( bits-1, 0, NO_SHRINK ) とすると収縮しないようにもできる

    cout << qm << endl;     
    
    return 0;
}


------------------------
実行結果

lager:/home/users/tokunaga/QCS/sample>./example
[ (1,0), (0,0), (0,0), (0,0), (0,0), (0,0), (0,0), (0,0) ]
[ (0,0), (1,0), (0,0), (0,0), (0,0), (0,0), (0,0), (0,0) ]
[ (0,0), (0,0), (0,0), (0,0), (0,0), (1,0), (0,0), (0,0) ]
[ (0,0), (0,0), (0,0), (0,0), (0,0), (0,0), (0,0), (1,0) ]
[ (0,0), (0,0), (0,0), (0,0), (0,0), (1,0), (0,0), (0,0) ]
[ (0,0), (0,0), (0,0), (0,0), (0,0), (0.866025,0.5), (0,0), (0,0) ]
[ (0,0), (0,0), (0,0), (0,0), (0,0), (0.5,0.866025), (0,0), (0,0) ]
[ (0,0), (0,0), (0,0), (0,0), (0,0), (0.5,0.866025), (0,0), (0,0) ]
[ (0.176777,0.306186), (-0.176777,-0.306186), (0.176777,0.306186), (-0.176777,-0.306186), (-0.176777,-0.306186), (0.176777,0.306186), (-0.176777,-0.306186), (0.176777,0.306186) ]
[ (0,0), (0,0), (-0.12941,0.482963), (0.12941,-0.482963), (0,0), (0,0), (0.482963,0.12941), (-0.482963,-0.12941) ]
answer = 2
[ (0,0), (0,0), (-0.258819,0.965926), (0,0), (0,0), (0,0), (0,0), (0,0) ]

以上が簡単なゲートの使い方の例です.
記述の仕方は他にも色々と融通がきくようになっています.
計算時間を減らすために途中で qubit を増やす,減らすなどもできます.
細かい仕様は libqm/ のヘッダファイル qmachine.h, matrix.h をみてください.


素因数分解 実行例

lager:/home/users/tokunaga/QCS/sample>./factor -n 221
n= 221        
x= 49
r= 149
x= 144
r= 2
13(Shor)
17(sosuu) 
iter = 2
=========== Message from class Time ===========
 Time[  1] =  2.289 [sec.]   2.289 [sec.]  (by gettimeofday)
===============================================

tiger:/home/users/tokunaga/QCS/sample>./factor -n 1147
n= 1147
x= 251
r= 9
x= 746
r= 2
x= 1122
r= 12
31(Shor)
37(sosuu) 
iter = 3
=========== Message from class Time ===========
 Time[  1] =  83.93 [sec.]   83.93 [sec.]  (by gettimeofday)
===============================================

lager:/home/users/tokunaga/QCS/sample>./factor -n 5183
n= 5183
x= 3249
r= 45
x= 3300
r= 168
71(Shor)
73(sosuu) 
iter = 2
=========== Message from class Time ===========
 Time[  1] =   1241 [sec.]    1241 [sec.]  (by gettimeofday)
===============================================


問題点,不明な点がありましたら tokunaga@is.s.u-tokyo.ac.jp までお願いします.
tokunaga@is.s.u-tokyo.ac.jp / last modified 2000.7.4