我为具有给定数量的粒子N
和网站Mtot
的bosson生成Fock基础(量子力学),它只是构建一组包含必须Mtot
个位置的列表覆盖N
项(请参阅下面的代码)。然后我构建了另一个列表,列表包含M
个站点(Mtot = 2 * M),并且所有可能的粒子/项目n = 0,1,2 ... N. (在我的代码中,我的工作是N = 2,M = 2以简化)
import numpy as np
from scipy.special import binom
M = 2
Mtot = 2*M
N = 2
def generate(N,nb):
states = np.zeros((int(binom(nb+N-1, nb)), N), dtype=int)
states[0, 0]=nb
ni = 0 # init
for i in xrange(1, states.shape[0]):
states[i,:N-1] = states[i-1, :N-1]
states[i,ni] -= 1
states[i,ni+1] += 1+states[i-1, N-1]
if ni >= N-2:
if np.any(states[i, :N-1]):
ni = np.nonzero(states[i, :N-1])[0][-1]
else:
ni += 1
return states.tolist()
basis = generate(Mtot,N)
reduced_basi = []
for i in xrange(N+1):
reduced_basi.append(generate(M,i))
现在,重点是我想获得一个列表,其中包含reduced_basi
内可能连接到basis
内其他状态的可能状态的索引。例如,使用此前面的代码,我们将获得:
basis = [[2, 0, 0, 0], [1, 1, 0, 0], [1, 0, 1, 0], [1, 0, 0, 1], [0, 2, 0, 0], [0, 1, 1, 0], [0, 1, 0, 1], [0, 0, 2, 0], [0, 0, 1, 1], [0, 0, 0, 2]]
reduced_basi = [[[0, 0]], [[1, 0], [0, 1]], [[2, 0], [1, 1], [0, 2]]]
因此,reduced_basi
的{{1}}的第一项可以与[0, 0]
,[0, 0, 2, 0]
和[0, 0, 1, 1]
相关联,然后[0, 0, 0, 2]
它可能与[1,0]
...有关,因此,我要构建的列表必须具有第一个组件:[1, 0, 1, 0], [1, 0, 0, 1]
(其中7,8,9是{{1}的对应索引}状态遵循相同的顺序)和第二个:index_list[0] = [7,8,9]
。最后它必须以sistematically方式完成,因此我必须为这个特殊情况获得以下列表(我已经手动计算过):
basis
知道如何实现这个?
答案 0 :(得分:2)
您可以定义一个函数:
def samestart(pattern,sequence):
for i,d in enumerate(pattern):
if d != sequence[i]:
return False
return True
您实际上可以将其重写为:
def samestart(pattern,sequence):
return all(x == y for x,y in zip(pattern,sequence))
接下来,你可以简单地使用列表理解:
[[i for i,sequence in enumerate(basis) if samestart(pattern,sequence)] for patterns in reduced_basi for pattern in patterns]
在python
中产生:
$ python3
Python 3.5.2 (default, Nov 17 2016, 17:05:23)
[GCC 5.4.0 20160609] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> def samestart(pattern,sequence):
... for i,d in enumerate(pattern):
... if d != sequence[i]:
... return False
... return True
...
>>> basis = [[2, 0, 0, 0], [1, 1, 0, 0], [1, 0, 1, 0], [1, 0, 0, 1], [0, 2, 0, 0], [0, 1, 1, 0], [0, 1, 0, 1], [0, 0, 2, 0], [0, 0, 1, 1], [0, 0, 0, 2]]
>>> reduced_basi = [[[0, 0]], [[1, 0], [0, 1]], [[2, 0], [1, 1], [0, 2]]]
>>> [[i for i,sequence in enumerate(basis) if samestart(pattern,sequence)] for patterns in reduced_basi for pattern in patterns]
[[7, 8, 9], [2, 3], [5, 6], [0], [1], [4]]
效率并不高:人们肯定可以在这里使用散列来提升性能。
如果你可以做出假设所有“模式”的长度为2,你可以简单地推导出它并构造一个字典。例如:
result = {}
for idx,base in enumerate(basis):
pattern = tuple(base[0:2])
patlist = result.get(pattern)
if patlist is not None:
patlist.append(idx)
else:
result[pattern] = [idx]
这将生成字典result
:
>>> result
{(0, 1): [5, 6], (2, 0): [0], (0, 0): [7, 8, 9], (1, 0): [2, 3], (1, 1): [1], (0, 2): [4]}