Python 列表内元素转移到另一个,自己写的却不明白为何

发布于 2022-09-12 03:32:35 字数 2026 浏览 20 评论 0

题目:将list1内元素移动到list2,最后list1为空。

# 我的代码:
list1=["c++","java","python","sql","javascript"]
list2=[]
for i in range(len(list1)):
    a=list1.pop()
    list2.append(a)
print("list1=",list1)
print("list2=",list2)
运行结果: (暂且不管顺序)
list1= []
list2= ['javascript', 'sql', 'python', 'java', 'c++']

我想知道for in过程中发生了什么,于是加了几行print

list1=["c++","java","python","sql","javascript"]
list2=[]
for i in range(len(list1)):
    print(i)
    print(len(list1))
    print(range(len(list1)))
    print("__ __ __ __ __ __ __ __\n")
    a=list1.pop()
    list2.append(a)
print("list1=",list1)
print("list2=",list2)
# 结果:
0
5
range(0, 5)
__ __ __ __ __ __ __ ___

1
4
range(0, 4)
__ __ __ __ __ __ __ ___

2
3
range(0, 3)
__ __ __ __ __ __ __ ___

3
2
range(0, 2)
__ __ __ __ __ __ __ ___

4
1
range(0, 1)
__ __ __ __ __ __ __ ___

list1= []
list2= ['javascript', 'sql', 'python', 'java', 'c++']

i / len(list1) / range(len(list1))同时变化:

遍历12345
i01234
len(list1)54321
range(len(list1))range(0, 5)range(0, 4)range(0, 3)range(0, 2)range(0, 1)

i 是从range(len(list1))中逐次取值的,那么应该在第4次就取不到值然后截止了—— i=3 & range(len(list1))=range(0, 2) 是矛盾的啊~

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

想你只要分分秒秒 2022-09-19 03:32:35

for i in 表达式x 这里的表达式只在循环开始时演算一次
相当于

y=表达式x
for i in y:
  ...

list1=["c++","java","python","sql","javascript"]
list2=[]
for i in range(len(list1)):
    print(i)
    print(len(list1))
    print(range(len(list1)))
    print("__ __ __ __ __ __ __ __\n")
    a=list1.pop()
    list2.append(a)
    pass

print("list1=",list1)
print("list2=",list2)

存成 test.py
执行 python -m dis test.py

会得到字节码如下:

  1           0 LOAD_CONST               0 ('c++')
              3 LOAD_CONST               1 ('java')
              6 LOAD_CONST               2 ('python')
              9 LOAD_CONST               3 ('sql')
             12 LOAD_CONST               4 ('javascript')
             15 BUILD_LIST               5
             18 STORE_NAME               0 (list1)

  2          21 BUILD_LIST               0
             24 STORE_NAME               1 (list2)

  3          27 SETUP_LOOP              89 (to 119)
             30 LOAD_NAME                2 (range)
             33 LOAD_NAME                3 (len)
             36 LOAD_NAME                0 (list1)
             39 CALL_FUNCTION            1
             42 CALL_FUNCTION            1
             45 GET_ITER            
        >>   46 FOR_ITER                69 (to 118)
             49 STORE_NAME               4 (i)

  4          52 LOAD_NAME                4 (i)
             55 PRINT_ITEM          
             56 PRINT_NEWLINE       

  5          57 LOAD_NAME                3 (len)
             60 LOAD_NAME                0 (list1)
             63 CALL_FUNCTION            1
             66 PRINT_ITEM          
             67 PRINT_NEWLINE       

  6          68 LOAD_NAME                2 (range)
             71 LOAD_NAME                3 (len)
             74 LOAD_NAME                0 (list1)
             77 CALL_FUNCTION            1
             80 CALL_FUNCTION            1
             83 PRINT_ITEM          
             84 PRINT_NEWLINE       

  7          85 LOAD_CONST               5 ('__ __ __ __ __ __ __ __\n')
             88 PRINT_ITEM          
             89 PRINT_NEWLINE       

  8          90 LOAD_NAME                0 (list1)
             93 LOAD_ATTR                5 (pop)
             96 CALL_FUNCTION            0
             99 STORE_NAME               6 (a)

  9         102 LOAD_NAME                1 (list2)
            105 LOAD_ATTR                7 (append)
            108 LOAD_NAME                6 (a)
            111 CALL_FUNCTION            1
            114 POP_TOP             

 10         115 JUMP_ABSOLUTE           46
        >>  118 POP_BLOCK           

 12     >>  119 LOAD_CONST               6 ('list1=')
            122 LOAD_NAME                0 (list1)
            125 BUILD_TUPLE              2
            128 PRINT_ITEM          
            129 PRINT_NEWLINE       

 13         130 LOAD_CONST               7 ('list2=')
            133 LOAD_NAME                1 (list2)
            136 BUILD_TUPLE              2
            139 PRINT_ITEM          
            140 PRINT_NEWLINE       
            141 LOAD_CONST               8 (None)
            144 RETURN_VALUE        

这里简化一下, for 循环编译后,分成二阶段执行,一个是SETUP_LOOP,一个是FOR_ITER:

  3          27 SETUP_LOOP              89 (to 119)
 ...  #初始化阶段
             45 GET_ITER            #得到迭代变量
        >>   46 FOR_ITER                69 (to 118)
...   #循环体

 10         115 JUMP_ABSOLUTE           46  

循环第二阶段是在46 FOR_ITER ~ JUMP_ABSOLUTE 46这两条之间进行,不会再对初始化代码的运行,但循环本身是围绕迭代变量进行的(上面的 range的结果[0,1,2,3,4]),如果这个变量本身发生了变化,自然会影响到循环的.

゛清羽墨安 2022-09-19 03:32:35

我的问题栏太乱了,所以我把一些东西写在这,希望帮助我的朋友看这里。
求助了几个论坛,目前只有咱这个站有热心前辈帮忙,但也许是我提问水平有限,我还是一头雾水,于是在朋友提醒下去stackoverflow看了看,由于英文很差,用google翻译磕磕绊绊的发了贴。

也许是时差,答复的很快,有个人特意解释了一篇。

原文:
The for instruction is creating an iterator from the object specified after in. This iterator is returning the next() of this iterator at each iteration. When you pop item out of list (first method) next() as no more value after 3 iterations and stops. When you use the range the range object and its iterator are created first and remain unchanged by the list pop.

google翻译:
for指令从in之后指定的对象创建一个迭代器。此迭代器在每次迭代时都返回该迭代器的next()。 当您从列表中弹出项目(第一种方法)时,next()作为3次迭代并停止后没有更多值。 使用范围时,将首先创建范围对象及其迭代器,并在列表弹出窗口中保持不变。

由于我的英文太烂,只读出一个信息:len()函数就是本质与list1不同的! list1在for in 循环中每次都会变动,所以遍历起来会不完整; 而len()函数就是有一个特征——在for in循环中第一次执行就定型,不论在循环中如何更改,i 只会在循环初始的len()函数中遍历.

我不知道译文是否正确,我理解是否到位,但好像也只能这样了。
谢谢 Yujiaao 的帮助,感谢。

唉~ 还是感叹,自学真的很多坑。

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文