2021년 7월 14일 수요일

Qiskit tutorial - 5. Operators

작성중입니다.

이 글은 Qiskit 공식 홈페이지에서 제공하는 튜토리얼을 직접 해보고 요약하거나 덧붙이거나 교정한 글입니다. 원문은 [1]이며, Anaconda 의 Jupyter notebook 을 사용하는 원문과 달리 순수 Python 으로 실행가능하도록 소스코드를 수정하고, 중간마다 양자 상태를 시각화하는 코드 등이 추가되어 코드도 원문과 차이가 있습니다. 제가 작성한 코드는 [2]에 공개합니다.

기본 import 들은 다음과 같다.

코드5.1. 기본 import 문

5.1. Operator 클래스

Qiskit의 Operator 클래스는 양자 시스템에 작용하는 행렬 연산자를 나타내는 데 사용된다. 이 클래스는 텐서곱을 이용한 다중 결합 연산자를 만들거나 연산자를 작성하는데 필요한 다양한 매서드를 포함한다.

5.1.1. Operator 생성

Operator 객체를 만드는 가장 쉬운 방법은 리스트나 Numpy 배열로 주어진 행렬로 연산자를 초기화하는 것이다. 예를 들면 두 큐비트 Pauli-XX 연산자는 다음과 같이 만들 수 있다.

코드5.2. XX-게이트 연산자 구현

코드 15번의 출력은 다음과 같다.

Operator([[0.+0.j, 0.+0.j, 0.+0.j, 1.+0.j],
          [0.+0.j, 0.+0.j, 1.+0.j, 0.+0.j],
          [0.+0.j, 1.+0.j, 0.+0.j, 0.+0.j],
          [1.+0.j, 0.+0.j, 0.+0.j, 0.+0.j]],
         input_dims=(2, 2), output_dims=(2, 2))

5.1.2. Operator의 속성

Operator 객체는 행렬과 서브시스템들의 입력 및 출력 차원을 포함한다.

  • data: 기반이 되는 Numpy 배열에 접근할 때 사용한다. 
  • dims: 연산자의 전체 입력과 출력의 차원을 반환할 때 사용한다. 이 출력은 (input_dim, output_dim)의 튜플을 반환한다.(주의. 기반 행렬의 모양과 순서가 반대다.)

코드는 다음과 같다.

코드5.3. 행렬과 차원의 출력

코드 18번 라인의 출력은 다음과 같다. 

[[0.+0.j 0.+0.j 0.+0.j 1.+0.j]
 [0.+0.j 0.+0.j 1.+0.j 0.+0.j]
 [0.+0.j 1.+0.j 0.+0.j 0.+0.j]
 [1.+0.j 0.+0.j 0.+0.j 0.+0.j]]

코드 21번 라인의 출력은 다음과 같다.

4 4

5.1.3. 입력과 출력의 차원

Operator 클래스는 서브시스템의 차원을 추적하기 때문에 다중결합 연산자를 작성하는 데 사용할 수 있다. 이 값은 input_dims 와 output_dims 함수를 이용하여 접근할 수 있다.

연산자의 행이 2N개이고, 열이 2M개이면 입력과 출력 차원이 자동으로 M-큐비트와 N-큐비트로 가정된다.

코드5.4. 차원 출력

코드 25~26번 라인의 출력은 다음과 같다.

Input dimensions :  (2, 2)
Output dimensions :  (2,)

입력된 행렬을 서브시스템으로 나눌 수 없는 경우 단일 연산자로 지정된다. 예를 들어 입력된 행렬이 6 x 6 행렬이면 다음과 같이 입력과 출력 행렬은 모두 6행이다.

코드5.5. 6 x 6 행렬 연산자의 입력 출력 차원

코드 29~30번 라인의 출력은 다음과 같다.

Input dimensions:  (6,)
Output dimensions:  (6,)

입력과 출력의 차원은 새 연산자를 초기화할 때 수동으로 명시할 수 있다.

코드5.6. 연산자의 입력 출력 차원 명시

코드 34, 35번 라인과 39, 40번 라인의 출력은 다음과 같다.

Input dimensions:  (4,)
Output dimensions:  (2,)
Input dimensions:  (2, 3)
Output dimensions:  (2, 3)

또한 input_dims() 와 output_dims() 를 사용하여 일부 서브시스템의 입력 혹은 출력의 차원만 추출할 수 있다.

코드5.7. 서브시스템의 차원 출력

코드 42, 43번 라인의 출력은 다음과 같다.

Dimension of input system 0: (2,)
Dimension of input system 1: (3,)

5.2. 클래스를 연산자로 변환

키스킷에서 사용하는 다음 클래스들은 연산자 초기화 메소드를 이용하여 Operator 객체로 바로 변환 가능하다. 

  • Pauli 객체
  • Gate 와 Instruction 객체
  • QuantumCircuits 객체

마지막 객체는 시뮬레이터 백엔드를 호출하지 않고 양자 회로에 대한 최종 유니타리 행렬을 계산하기 위해 Operator 클래스를 유니타리 시뮬레이터로 사용할 수 있다는 것을 의미한다. 회로에 지원되지 않는 연산이 포함되어 있으면 예외가 발생한다. 지원되지 않는 연산들은 측정, 재설정, 조건부 연산, 또는 '게이트를 행렬로 정의할 때 행렬 정의나 분해가 존재하지 않는 게이트'들이다. 구현은 다음과 같다.

코드5.8. 클래스를 Operator 객체로 변환 구현

코드 49번 라인의 출력은 다음과 같다.

Operator([[0.+0.j, 0.+0.j, 0.+0.j, 1.+0.j],
          [0.+0.j, 0.+0.j, 1.+0.j, 0.+0.j],
          [0.+0.j, 1.+0.j, 0.+0.j, 0.+0.j],
          [1.+0.j, 0.+0.j, 0.+0.j, 0.+0.j]],
         input_dims=(2, 2), output_dims=(2, 2))

코드 52번 라인의 출력은 다음과 같다.

Operator([[1.+0.j, 0.+0.j, 0.+0.j, 0.+0.j],
          [0.+0.j, 0.+0.j, 0.+0.j, 1.+0.j],
          [0.+0.j, 0.+0.j, 1.+0.j, 0.+0.j],
          [0.+0.j, 1.+0.j, 0.+0.j, 0.+0.j]],
         input_dims=(2, 2), output_dims=(2, 2))

코드 64번 라인의 출력은 다음과 같다.

Operator([[ 0.70710678+0.j,  0.70710678+0.j,  0.        +0.j, ...,
            0.        +0.j,  0.        +0.j,  0.        +0.j],
          [ 0.        +0.j,  0.        +0.j,  0.70710678+0.j, ...,
            0.        +0.j,  0.        +0.j,  0.        +0.j],
          [ 0.        +0.j,  0.        +0.j,  0.        +0.j, ...,
            0.        +0.j,  0.        +0.j,  0.        +0.j],
          ...,
          [ 0.        +0.j,  0.        +0.j,  0.        +0.j, ...,
            0.        +0.j,  0.        +0.j,  0.        +0.j],
          [ 0.        +0.j,  0.        +0.j,  0.70710678+0.j, ...,
            0.        +0.j,  0.        +0.j,  0.        +0.j],
          [ 0.70710678+0.j, -0.70710678+0.j,  0.        +0.j, ...,
            0.        +0.j,  0.        +0.j,  0.        +0.j]],
         input_dims=(2, 2, 2, 2, 2, 2, 2, 2, 2, 2), output_dims=(2, 2, 2, 2, 2, 2, 2, 2, 2, 2))

5.3. 회로에서 연산자 사용

유니타리인 Operator 객체는 QuantumCircuit.append() 를 이용하여 QuantumCircuit 객체에 바로 넣을 수 있다. 이는 Operator 객체를 회로에 추가할 수 있는 UnitaryGate 객체로 바꿔준다. 만약 연산자가 유니타리가 아니면 예외처리된다. 객체의 유니타리 여부는 Operator.is_unitary() 를 사용하여 확인할 수 있다. 만약 연산자가 유니타리이면 True, 아니면 False 를 반환한다. 구현은 다음과 같다.

코드5.9. 회로에서 연산자 사용 구현

코드 76번 라인의 출력은 다음과 같다.

그림5.1. Operator 객체를 이용한 회로 도식

5.4. 연산자 결합

연산자들은 다양한 방법으로 결합될 수 있다.

5.4.1. 텐서곱




댓글 2개:

  1. New Jersey - Casino - The JTM Hub
    Casino New Jersey offers the newest casino in the state. 포천 출장안마 Get a $10 no deposit bonus 양산 출장샵 and get 통영 출장마사지 a $1000 free chip. Check 경상북도 출장안마 the 창원 출장안마 casino NJ bonus code here!

    답글삭제
  2. The King Casino and Resort
    The king nba매니아 casino casinosites.one and resort features a modern casino with everything you'd 토토 expect from a classic Vegas Strip casino. The resort features 50000 square feet of Funding: casino-roll.com $250 millionDesign: Inspired DesignMasters: ventureberg.com/ Ivan Karaszko

    답글삭제