Bengali
Languages
English
Bengali
French
German
Japanese
Korean
Portuguese
Spanish
Tamil
  • Qiskit documentation >
  • Tutorials >
  • ম্যাট্রিক্স গুণফলের অবস্থা সিমুলেশন পদ্ধতি

নোট

এই পৃষ্ঠাটি tutorials/simulators/7_matrix_product_state_method.ipynb -থেকে বানানো হয়েছে।

ম্যাট্রিক্স গুণফলের অবস্থা সিমুলেশন পদ্ধতি

সিমুলেশন(মহড়া) পদ্ধতি সমূহ

AerSimulator -এ অনেক সিমুলেশন পদ্ধতি আছে, যেমন - statevector, stabilizer, extended_stabilizermatrix_product_state। এদের প্রত্যেকটা কোয়ান্টাম বর্তনীর (সার্কিট) অভ্যন্তরীন গঠন এবং কোয়ান্টাম ক্রিয়াসমূহর সমাধানপদ্ধতি নির্ধারণ করে। প্রত্যেকের কিছু সুবিধা-অসুবিধা আছে এবং কাজের জন্য কোনটা ভালো সেটা খুঁজে নিতে হয়। এই পাঠসমূহে (টিউটোরিয়াল) আমরা ম্যাট্রিক্স গুনফল অবস্থা সিমুলেশন পদ্ধতি ব্যাপারে আলোচনা করবো।

ম্যাট্রিক্স গুণফলের অবস্থা সিমুলেশন পদ্ধতি

এই সিমুলেশন ম্যাট্রিক্স গুনফল অবস্থা ধারণার উপর ভিত্তি করে বানানো। এই কাঠামো প্রথম আলোচনা হয়েছিল Efficient classical simulation of slightly entangled quantum computations by Vidal in https://arxiv.org/abs/quant-ph/0301063। বিশদে জানার জন্য আরো গবেষণাপত্র আছে, যেমন - The density-matrix renormalization group in the age of matrix product states by Schollwoeck https://arxiv.org/abs/1008.3477

একটা বিশুদ্ধ কোয়ান্টাম অবস্থা একটা অবস্থা নির্ণায়ক দিকরাশি (স্টেট ভেক্টর) দিয়ে সূচিত হয়। এর গাণিতিক রূপ হলো \(|\psi\rangle = \sum_{i_1=0}^1 {\ldots} \sum_{i_n=0}^1 c_{i_1 \ldots i_n} |i_i\rangle {\otimes} {\ldots} {\otimes} |i_n\rangle\)

অবস্থা নির্ণায়ক দিকরাশি (স্টেট ভেক্টর) উপস্থাপনা একটা বড় আকারের উপস্থাপনা বোঝায় যা আসল বর্তনীর (সার্কিট) আকারের উপর নির্ভরশীল নয়। এই উপস্থাপনার প্রত্যেক কোয়ান্টাম যুক্তিবর্তনী (গেইট) গণনাকালীন প্রচুর সময় ও মেমরি নেয়।

ম্যাট্রিক্স গুনফল অবস্থা (এমপিএস) নিম্নলিখিত রূপে একটা স্থানীয় উপস্থাপনা দেয়: \(\Gamma^{[1]} \lambda^{[1]} \Gamma^{[2]} \lambda^{[2]}\ldots \Gamma^{[1]} \lambda^{[n-1]} \Gamma^{[n]}\), যাতে \(c_{i_1 \ldots i_n}\) -এর মধ্যে থাকা সব তথ্য এমপিএস উপস্থাপনা থেকে পাওয়া যায়।

প্রত্যেক \(\Gamma^{[i]}\) হলো জটিল রাশির দিকরাশি (টেন্সর) যেটা একটা কিউবিট \(i\) কে চিহ্নিত করে। প্রত্যেক \(\lambda^{[i]}\) হলো বাস্তব সংখ্যার ম্যাট্রিক্স যার সাহায্যে \(i\)\(i+1\) কিউবিটের বিস্তার শমিত করা যায়। একক কিউবিট যুক্তিবর্তনী (গেট) কেবল প্রাসঙ্গিক দিকরাশির (টেন্সর) উপর কাজ করে:

২-কিউবিট যুক্তিবর্তনী (গেইট) পরপর কিউবিটের \(i\) এবং \(i+1\) উপর কাজ করে। এর মধ্যে \(\lambda^{[i-1]}\), \(\Gamma^{[i-1]}\), \(\lambda^{[i]}\), \(\Gamma^{[i+1]}\)\(\lambda^{[i+1]}\) -এর উপর একটা টেন্সর-কন্ট্রাক্ট ক্রিয়াকলাপ (অপারেশন) হয় যেটা একটা দিকরাশি (টেন্সর) বানায়। আমরা যুক্তিবর্তনীকে (গেইট) এই দিকরাশির (টেন্সর) উপর প্রায় করি এবং তারপর প্রাথমিক কাঠামোয় ভেঙে যায়। এর ক্রিয়াকলাপ (অপারেশন) দিকরাশির (টেন্সর) আকার বাড়াতে পারে। যেসব যুক্তিবর্তনীতে (গেট) দুটো কিউবিট পরপর না তাদের ক্ষেত্রে কিছু সোয়াপ যুক্তিবর্তনী (গেইট) ব্যবহার করে কিউবিটগুলো প্রথমে পরপর আনা হয় এবং কাজের পর বিপরীত সোয়াপ যুক্তিবর্তনী (গেইট) ব্যবহার করতে হয়।

সবচেয়ে খারাপ ক্ষেত্রে, দিকরাশিগুলো (টেন্সর) ঘাতের হারে বৃদ্ধি পেতে পারে। কিন্তু যেসব বর্তনীতে (সার্কিট) ‘বেশি’ ২-কিউবিট যুক্তিবর্তনী (গেইট) থাকে না সেক্ষেত্রে সামগ্রিক কাঠামো ‘ছোট’ ই হয়। এর ফলে যেসব বর্তনীতে (সার্কিট) আপেক্ষিকভাবে ‘কম’ এনট্যাঙ্গেলমেন্ট থাকে তাদের ক্ষেত্রে দ্রুততর ক্রিয়াকলাপ (অপারেশন) হয়। কখন এই পদ্ধতি কাজে লাগানো উচিত সেটা এখনো পরীক্ষাধীন।

ম্যাট্রিক্স গুণফলের অবস্থা সিমুলেশন পদ্ধতির ব্যবহার

ম্যাট্রিক্স গুণফল অবস্থা সিমুলেশন পদ্ধতি চালু করতে হলে AerSimulator -এ সিমুলেশন পদ্ধতি নির্বাচন করতে হবে। এছাড়া বাকি সব ক্রিয়াকলাপ (অপারেশন) AerSimulator নিজে নিয়ন্ত্রণ করে। নিচের উদাহরণে ব্যাপারটা দেখা যাক:

[1]:
import numpy as np

# Import Qiskit
from qiskit import QuantumCircuit, transpile
from qiskit.providers.aer import AerSimulator

# Construct quantum circuit
circ = QuantumCircuit(2, 2)
circ.h(0)
circ.cx(0, 1)
circ.measure([0,1], [0,1])

# Select the AerSimulator from the Aer provider
simulator = AerSimulator(method='matrix_product_state')

# Run and get counts, using the matrix_product_state method
tcirc = transpile(circ, simulator)
result = simulator.run(tcirc).result()
counts = result.get_counts(0)
counts
[1]:
{'11': 515, '00': 509}

বর্তনীর (সার্কিট) অভ্যন্তরীন অবস্থা নির্ণায়ক দিকরাশি (স্টেট ভেক্টর) দেখতে হলে save_statevector নির্দেশনা কাজে লাগাতে হবে। সম্পূর্ণ অভ্যন্তরীন এমপিএস গঠন পাওয়ার জন্য আমরা save_matrix_product_state নির্দেশনা ব্যবহার করতে পারি।

[2]:
circ = QuantumCircuit(2, 2)
circ.h(0)
circ.cx(0, 1)

# Define a snapshot that shows the current state vector
circ.save_statevector(label='my_sv')
circ.save_matrix_product_state(label='my_mps')
circ.measure([0,1], [0,1])

# Execute and get saved data
tcirc = transpile(circ, simulator)
result = simulator.run(tcirc).result()
data = result.data(0)

#print the result data
data
[2]:
{'counts': {'0x0': 494, '0x3': 530},
 'my_sv': array([0.70710678+0.j, 0.        +0.j, 0.        +0.j, 0.70710678+0.j]),
 'my_mps': ([(array([[1.-0.j, 0.-0.j]]), array([[0.-0.j, 1.-0.j]])),
   (array([[1.-0.j],
           [0.-0.j]]),
    array([[0.-0.j],
           [1.-0.j]]))],
  [array([0.70710678, 0.70710678])])}

অন্য পদ্ধতির তুলনায় ম্যাট্রিক্স গুণফল অবস্থা সিমুলেশন পদ্ধতিতে বর্তনী (সার্কিট) দ্রুত চালানো যায়। কিন্তু যদি আমরা গণনা চলাকালীন অবস্থা নির্ণায়ক দিকরাশি (স্টেট ভেক্টর) বানাই তাহলে এই পরিবর্তনের জন্য প্রচুর সময় ও মেমরি লাগবে এবং এই পদ্ধতি তখন অর্থহীন হয়ে যাবে। যেসব ক্রিয়াকলাপে (অপারেশন) পুরো অবস্থা নির্ণায়ক দিকরাশি (স্টেট ভেক্টর) দেখার প্রয়োজন নেই আমরা কেবল সেসব ক্রিয়াকলাপ (অপারেশন) এই পদ্ধতিতে করতে পারি। উদাহরণরূপে, যদি আমরা একটা বর্তনী (সার্কিট) চালাই ও পরিমাপ করি। নিচের বর্তনীতে (সার্কিট) ২০০টি কিউবিট আছে। আমরা সমস্ত কিউবিট নিয়ে একটা EPR state বানাতে পারি। যদিও এই অবস্থা খুবই পরিসাংখ্যিক বিজড়িত, ম্যাট্রিক্স গুনফল অবস্থা পদ্ধতি সহজেই এটা সামলাতে পারবে কারণ কার্যকরভাবে এটা কেবল ২টি অবস্থা।

আমরা এর থেকেও অধিক কিউবিট সামলে নিতে পারি, কিন্তু এক্সেকিউট বা সম্পাদন হতে মিনিট খানেক সময় নিতে পারে। একই বর্তনী (সার্কিট) আপনি ৫০০টি কিউবিট দিয়ে চালানোর চেষ্টা করে দেখুন! অথবা হতে পারে 1000(অপেক্ষা করবার সময় আপনি এক কাপ কফি নিয়ে আসতে পারেন)।

[3]:
num_qubits = 50
circ = QuantumCircuit(num_qubits, num_qubits)

# Create EPR state
circ.h(0)
for i in range (0, num_qubits-1):
    circ.cx(i, i+1)

# Measure
circ.measure(range(num_qubits), range(num_qubits))

tcirc = transpile(circ, simulator)
result = simulator.run(tcirc).result()
print("Time taken: {} sec".format(result.time_taken))
result.get_counts()
Time taken: 0.31022214889526367 sec
[3]:
{'11111111111111111111111111111111111111111111111111': 548,
 '00000000000000000000000000000000000000000000000000': 476}
[4]:
import qiskit.tools.jupyter
%qiskit_version_table
%qiskit_copyright

Version Information

Qiskit SoftwareVersion
Qiskit0.25.0
Terra0.17.0
Aer0.8.0
Ignis0.6.0
Aqua0.9.0
IBM Q Provider0.12.2
System information
Python3.8.8 | packaged by conda-forge | (default, Feb 20 2021, 16:22:27) [GCC 9.3.0]
OSLinux
CPUs8
Memory (Gb)31.38858413696289
Tue Apr 20 15:22:58 2021 UTC

This code is a part of Qiskit

© Copyright IBM 2017, 2021.

This code is licensed under the Apache License, Version 2.0. You may
obtain a copy of this license in the LICENSE.txt file in the root directory
of this source tree or at http://www.apache.org/licenses/LICENSE-2.0.

Any modifications or derivative works of this code must retain this
copyright notice, and modified files need to carry a notice indicating
that they have been altered from the originals.

[ ]: