在 Python 中一次迭代三个列表?

发布于 2024-11-17 15:50:04 字数 3110 浏览 0 评论 0原文

这可能是一个相当复杂的问题,因为很多人可能不知道我正在编写它的软件:Autodesk Maya 2011。我正在尝试加快一个乏味的缓慢过程(绑定:赋予 3D 角色能力)移动),方法是编写一个自动执行此操作的脚本。

我会尽力解释情况。

我有一个脚本,它接受一个对象,迭代该对象的子对象,将它们存储在列表中,然后将初始对象放在列表的末尾,反转列表,因为它是错误的方式,然后放置初始对象在前面。

问题:存在三个不同的列表,所有对象类型相同但名称不同,并且它们实际上是不同的对象。我的目标是通过生成称为“blendcolors”的节点将它们连接在一起。但是,如果我有一个循环来为列表 A 中的每个对象生成它们,那么我需要将它们连接到其他列表中的对象的循环,但我无法弄清楚这一点。

这是我的代码,它已经被使用过,所以就实际循环而言,它比以前更不完整。

    import maya.cmds as cmds

    def crBC(IKJoint, FKJoint, bindJoint, xQuan, switch):

        # gets children joints of the selected joint
        chHipIK = cmds.listRelatives(IKJoint, ad = True, type = 'joint')
        chHipFK = cmds.listRelatives(FKJoint, ad = True, type = 'joint')
        chHipBind = cmds.listRelatives(bindJoint, ad = True, type = 'joint')
        # list is built backwards, this reverses the list
        chHipIK.reverse()
        chHipFK.reverse()
        chHipBind.reverse()
        # appends the initial joint to the list
        chHipIK.append(IKJoint)
        chHipFK.append(FKJoint)
        chHipBind.append(bindJoint)
        # puts the last joint at the start of the list because the initial joint
        # was added to the end
        chHipIK.insert(0, chHipIK.pop())
        chHipFK.insert(0, chHipFK.pop())
        chHipBind.insert(0, chHipBind.pop())


        # pops off the remaining joints in the list the user does not wish to be blended
        chHipBind[xQuan:] = []

        chHipIK[xQuan:] = []

        chHipFK[xQuan:] = []

       # goes through the bind joints, makes a blend colors for each one, connects
       # the switch to the blender

        for a in chHipBind


            rotBC = cmds.shadingNode('blendColors', asUtility = True, n = a + 'rotate_BC')
            tranBC = cmds.shadingNode('blendColors', asUtility = True, n = a + 'tran_BC')
            scaleBC = cmds.shadingNode('blendColors', asUtility = True, n = a + 'scale_BC')

            cmds.connectAttr(switch + '.ikFkSwitch', rotBC + '.blender')
            cmds.connectAttr(switch + '.ikFkSwitch', tranBC + '.blender')
            cmds.connectAttr(switch + '.ikFkSwitch', scaleBC + '.blender')

        # goes through the ik joints, connects to the blend colors

            for b in chHipIK:
                cmds.connectAttr(b + '.rotate', rotBC + '.color1')
                cmds.connectAttr(b + '.translate', tranBC + '.color1')
                cmds.connectAttr(b + '.scale', scaleBC + '.color1')


            # connects FK joints to the blend colors

            for c in chHipFK:
                cmds.connectAttr(c + '.rotate', rotBC + '.color2')
                cmds.connectAttr(c + '.translate', tranBC + '.color2')
                cmds.connectAttr(c + '.scale', scaleBC + '.color2')

        # connects blend colors to bind joints


            cmds.connectAttr(rotBC + '.output', d + '.rotate')
            cmds.connectAttr(tranBC + '.output', d + '.translate')
            cmds.connectAttr(scaleBC + '.output', d + '.scale')                






    # executes function


    crBC('L_hip_IK', 'L_hip_FK', 'L_hip_JNT', 6, 'L_legSwitch_CTRL')

This might be a rather complex question since it's possible a lot of you don't know the software that I'm writing it for: Autodesk Maya 2011. I am trying to speed up a tedious slow process (rigging: giving 3d characters the ability to move) by writing a script that does it automatically.

I'll try my best to explain the situation.

I have a script that takes an object, iterates through the children of that object, stores them in a list, then puts the initial object at the end of the list, reverses the list because it's the wrong way around, then puts the initial object at the front.

Issue: There are three different lists all of the same object TYPE but with different names and they are actually different objects. My goal is to connect them together by generating nodes called 'blendcolors'. But if I have a loop to generate them for each object in list A, then I need loops that also connect them to the objects in other lists and I can not figure this out.

Here is my code, it has been played with so is more incomplete than before as far as the actual loop goes.

    import maya.cmds as cmds

    def crBC(IKJoint, FKJoint, bindJoint, xQuan, switch):

        # gets children joints of the selected joint
        chHipIK = cmds.listRelatives(IKJoint, ad = True, type = 'joint')
        chHipFK = cmds.listRelatives(FKJoint, ad = True, type = 'joint')
        chHipBind = cmds.listRelatives(bindJoint, ad = True, type = 'joint')
        # list is built backwards, this reverses the list
        chHipIK.reverse()
        chHipFK.reverse()
        chHipBind.reverse()
        # appends the initial joint to the list
        chHipIK.append(IKJoint)
        chHipFK.append(FKJoint)
        chHipBind.append(bindJoint)
        # puts the last joint at the start of the list because the initial joint
        # was added to the end
        chHipIK.insert(0, chHipIK.pop())
        chHipFK.insert(0, chHipFK.pop())
        chHipBind.insert(0, chHipBind.pop())


        # pops off the remaining joints in the list the user does not wish to be blended
        chHipBind[xQuan:] = []

        chHipIK[xQuan:] = []

        chHipFK[xQuan:] = []

       # goes through the bind joints, makes a blend colors for each one, connects
       # the switch to the blender

        for a in chHipBind


            rotBC = cmds.shadingNode('blendColors', asUtility = True, n = a + 'rotate_BC')
            tranBC = cmds.shadingNode('blendColors', asUtility = True, n = a + 'tran_BC')
            scaleBC = cmds.shadingNode('blendColors', asUtility = True, n = a + 'scale_BC')

            cmds.connectAttr(switch + '.ikFkSwitch', rotBC + '.blender')
            cmds.connectAttr(switch + '.ikFkSwitch', tranBC + '.blender')
            cmds.connectAttr(switch + '.ikFkSwitch', scaleBC + '.blender')

        # goes through the ik joints, connects to the blend colors

            for b in chHipIK:
                cmds.connectAttr(b + '.rotate', rotBC + '.color1')
                cmds.connectAttr(b + '.translate', tranBC + '.color1')
                cmds.connectAttr(b + '.scale', scaleBC + '.color1')


            # connects FK joints to the blend colors

            for c in chHipFK:
                cmds.connectAttr(c + '.rotate', rotBC + '.color2')
                cmds.connectAttr(c + '.translate', tranBC + '.color2')
                cmds.connectAttr(c + '.scale', scaleBC + '.color2')

        # connects blend colors to bind joints


            cmds.connectAttr(rotBC + '.output', d + '.rotate')
            cmds.connectAttr(tranBC + '.output', d + '.translate')
            cmds.connectAttr(scaleBC + '.output', d + '.scale')                






    # executes function


    crBC('L_hip_IK', 'L_hip_FK', 'L_hip_JNT', 6, 'L_legSwitch_CTRL')

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

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

发布评论

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

评论(5

送君千里 2024-11-24 15:50:04

我不太明白这个问题,你在找吗

import itertools
for a, b, c in itertools.izip(lst1, lst2, lst3):
    ...

izip 的作用是它接受可变数量的参数并返回一个迭代器,该迭代器始终生成参数的相应项(第一次运行中第一个参数的元组,第二次运行中第二个参数的元组)第二次运行,依此类推)。

I do not quite understand the question, are you looking for

import itertools
for a, b, c in itertools.izip(lst1, lst2, lst3):
    ...

?

What izip does is it takes a variable number of arguments and returns an iterator that always yields the respective items of the arguments (a tuple of the first arguments in the first run, a tuple of the second arguments in the second run, and so on and so forth).

清眉祭 2024-11-24 15:50:04

Python3答案:

for a, b, c in zip(lst1, lst2, lst3):
    ...

Python3 answer:

for a, b, c in zip(lst1, lst2, lst3):
    ...
秋叶绚丽 2024-11-24 15:50:04

为什么会出现“存在相同对象类型的三个不同列表”?为什么不能修复此问题以创建一个列表,其中所有三个对象都正确匹配?

一个简单的映射很有可能比三个并行列表更好。

具体来说,您需要修复 chHipIK = cmds.listRelatives(IKJoint, ad = True, type = 'joint') 才能像这样工作。

chHipIK = [ { 'IK': ik } for ik in mds.listRelatives(IKJoint, ad = True, type = 'joint') ]
for i, fk in enumerate(cmds.listRelatives(FKJoint, ad = True, type = 'joint')):
    chHipIK[i]['FK']= fk
for i, bind in enumerate(cmds.listRelatives(bindJoint, ad = True, type = 'joint')):
    chHipIK[i]['FK']= bind

因此,chHipIK 是一个包含所有三部分信息的映射列表。

Why are there "There are three different lists all of the same object TYPE"? Why can't this be fixed to create one list, where all three objects are matched correctly?

Odds are good that a simple mapping would be better than three parallel lists.

Specifically, you need to fix chHipIK = cmds.listRelatives(IKJoint, ad = True, type = 'joint') to work like this.

chHipIK = [ { 'IK': ik } for ik in mds.listRelatives(IKJoint, ad = True, type = 'joint') ]
for i, fk in enumerate(cmds.listRelatives(FKJoint, ad = True, type = 'joint')):
    chHipIK[i]['FK']= fk
for i, bind in enumerate(cmds.listRelatives(bindJoint, ad = True, type = 'joint')):
    chHipIK[i]['FK']= bind

So that chHipIK is a list of mappings that has all three pieces of information.

萌逼全场 2024-11-24 15:50:04

@florian mayer 使用 zip 或 izip 的方式工作得很好,但您也可以使用枚举来获取列表计数,

list_a  = ["x", "y"]
list_b  = ["k", "j"]
list_c  = ["m", "n"]

for count, item in enumerate(list_a):
    print item, list_b[count], list_c[count]

@florian mayer way with zip or izip works really fine, but you can also use the enumerate to get the list count,

list_a  = ["x", "y"]
list_b  = ["k", "j"]
list_c  = ["m", "n"]

for count, item in enumerate(list_a):
    print item, list_b[count], list_c[count]
心清如水 2024-11-24 15:50:04

Python 的 zip_longest 函数创建一个对象,允许您迭代数据集合(即迭代器),该对象连接每次迭代的元素。迭代继续进行,直到最长的迭代耗尽。默认情况下,“None”值用作zip_longest函数的空填充值,但我们可以使用字符串“UNKNOWN” 这里是为了更好的格式和我们自己的目的。

这是代码:

from itertools import zip_longest
 
prims = ["CubeA", "CubeB", "CubeC"]
sizes = [50, 100]
animations = [True, False]
 
for prim, size, animated in zip_longest(prims, sizes, animations, fillvalue="UNKNOWN"):
    print(prim, "has a size", size, "and animated:", animated)

### Results ###

# CubeA has a size 50 and animated: True
# CubeB has a size 100 and animated: False
# CubeC has a size UNKNOWN and animated: UNKNOWN

Python's zip_longest function creates an object that allows you to iterate over collections of data (i.e. iterator), that concatenates the elements from each iteration. The iteration continues until the longest iteration is exhausted. By default, a "None" value is used as the empty fill-value of a zip_longest function, but we can use the string "UNKNOWN" here for a nicer formatting and for our own purposes.

Here's the code:

from itertools import zip_longest
 
prims = ["CubeA", "CubeB", "CubeC"]
sizes = [50, 100]
animations = [True, False]
 
for prim, size, animated in zip_longest(prims, sizes, animations, fillvalue="UNKNOWN"):
    print(prim, "has a size", size, "and animated:", animated)

### Results ###

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