此字典理解与此“ for”循环有何不同?

时间:2019-05-18 02:55:02

标签: python python-3.x for-loop dictionary-comprehension

我尝试用字典理解和for循环来实现一种算法,我相信这两种算法都可以达到相同的结果。

字典理解

for i in range(num_iter):
    new_state_values = {s: get_new_state_value(mdp, state_values, s, gamma) for s in mdp.get_all_states()}

for循环

for i in range(num_iter):
    for s in mdp.get_all_states():
        new_state_values[s] = get_new_state_value(mdp, state_values, s, gamma)

在我的算法运行时,这些实现了截然不同的结果。有人可以指出两个区别在哪里吗?

详细信息

完整算法在下面

# parameters
gamma = 0.9  # discount for MDP
num_iter = 100  # maximum iterations, excluding initialization
min_difference = 0.001  # stop VI if new values are this close to old values (or closer)

# initialize V(s)
state_values = {s: 0 for s in mdp.get_all_states()}

for i in range(num_iter):
    new_state_values = {s: get_new_state_value(mdp, state_values, s, gamma) for s in mdp.get_all_states()}

    # Compute difference
    diff = max(abs(new_state_values[s] - state_values[s]) for s in mdp.get_all_states())
    state_values = new_state_values

    if diff < min_difference:
        print("Terminated")
        break

“ for-loop”版本几乎不运行任何迭代,而字典理解则运行更多次迭代。

更新:以上代码可以正常工作并收敛(我想这是最Python的imo)。接受的答案可以很好地了解不同的方法。

1 个答案:

答案 0 :(得分:3)

非综合版本会累积值,而不丢弃外部循环先前运行中的值。如果要使其等效,则需要更改:

for i in range(num_iter):
    for s in mdp.get_all_states():
        new_state_values[s] = get_new_state_value(mdp, state_values, s, gamma)

收件人:

for i in range(num_iter):
    new_state_values = {}  # NEW!!!
    for s in mdp.get_all_states():
        new_state_values[s] = get_new_state_value(mdp, state_values, s, gamma)

new_state_values重新初始化为干净的dict

在您的完整代码中,不理解的解决方案会将state_valuesnew_state_values都保留为 same dict的别名(所以{{1} }会随着您的使用而发生变化),使问题更加严重; state_values理解可以通过构建新的dict来解决它,而无需在构建时修改dict