使用多个for循环优化Python脚本

使用多个for循环优化Python脚本,python,performance,list,optimization,Python,Performance,List,Optimization,我是python方面的新手,在尝试优化脚本以提高速度方面也是新手。我一直在用这个问题来教自己如何编写代码,现在是: 我有一个数据集,其中列出了产品、价值和成本。有三种不同类型的产品A、B、C——每种产品类型有30-100种产品。每种产品都有价值和成本。我必须从产品类型A中选择1种产品,从产品类型B中选择2种产品,从产品类型C中选择3种产品-一旦我使用了一种产品,我就不能再使用它,也不能更换 我的目标是在预算有限的情况下优化产品的价值 考虑到我基本上是在尝试创建一个组合列表,我从那里开始编写了一些

我是python方面的新手,在尝试优化脚本以提高速度方面也是新手。我一直在用这个问题来教自己如何编写代码,现在是:

我有一个数据集,其中列出了产品、价值和成本。有三种不同类型的产品A、B、C——每种产品类型有30-100种产品。每种产品都有价值和成本。我必须从产品类型A中选择1种产品,从产品类型B中选择2种产品,从产品类型C中选择3种产品-一旦我使用了一种产品,我就不能再使用它,也不能更换

我的目标是在预算有限的情况下优化产品的价值

考虑到我基本上是在尝试创建一个组合列表,我从那里开始编写了一些for循环来实现这一点。起初,我试图在循环中做太多的工作,并将数据类型更改为列表,因为根据我的研究,它听起来会加快速度——它确实大大加快了速度

问题是,我最多每秒处理350k条记录,如果列表a中有30条,列表b中有50条,列表c中有50条,我需要大约7小时才能完成

我已经创建了3个列表列表-列表a、列表b和列表c,每个列表都与下面列表a的示例类似。然后,我评估for循环中的每个置换,以查看此置换是否比当前最高值置换具有更高的值,并且成本是否低于约束。如果它满足这些条件,我将它附加到排列组合列表的主列表中

    list_a = [['product1','product1_cost','product1_value'],['product2','product2_cost','product2_value'],...]

    num_a = len(list_a)
    num_b = len(list_b)
    num_c = len(list_c)

    combo_list = [[0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0]] # this is to create the list of lists that I will populate

    a = 0 #for row numbers
    b1 = 0 
    c1 = 0 
    l = 0 #of iterations
    max_value = 0

    for a in range(0,num_a):
      for b1 in range(0,num_b):
        b2 = b1 + 1 #second b
          for b2 in range(b2,num_b):
            for c1 in range(0,num_c):
              c2 = c1 +1 #second c
                for c2 in range(c2,num_C):
                  c3 =c2+1 #third c
                  for c3 in range(c3,num_C):
                    data = [list_a[a][0],list_a[a][1],list_a[a][2],list_b[b1][0],list_b[b1][1],list_b[b1][2],list_b[b2][0],list_b[b2][1],list_b[b2][2],list_c[c1][0],list_c[c1][1],list_c[c1][2],list_c[c2][0],list_c[c2][1],list_c[c2][2],list_c[c3][0],list_c[c3][1],list_c[c3][2]]
                    total_cost = data[1] + data[4] + data[7] + data[10] + data[13] + data[16]
                    total_value = data[2] + data[5] + data[8] + data[11] + data[14] + data[17]
                    data[18]=total_cost
                    data[19]=total_value
                    if total_value >= max_value and total_cost <= constraint:
                      combo_list.append(data)
                      max_value = total_value
                    c3 +=1
                l +=1
                c2 +=1
            c1 +=1
        b2+=1
    b1 +=1
a +=1
然后我将其转换为数据帧或csv


谢谢您的帮助。

因此,我能够使用itertools组合解决这个问题:

tup_b =  itertools.combinations(list_b, 2)
list_b = map(list,tup_b)
df_b = pd.DataFrame(list_b)

#Extending the list
df_b['B'] = df_b[0] + df_b[1] 
df_b = df_b[['B']]

#flatten list
b = df_b.values.tolist()
b = list(itertools.chain(*r))

# adding values and costs
r = len(b)
x=0
for x in range(0,r):
    cost = [b[x][1] +b[x][4]]
    value = [b[x][2] +b[x][5]]
    r[x] = r[x] +cost +value
    x +=1

#shortening list
df_b = pd.DataFrame(b)
df_b = df_b[[0,3,6,7]]
df_b.columns = ['B1','B2','cost','value']
然后,我对结构与上面类似的列表_c做了同样的操作,使用以下方法:

tup_c =  itertools.combinations(list_c, 3)
使用这种方法,处理时间从5小时减少到8分钟


谢谢大家的帮助。

因此,我能够使用itertools组合解决这个问题:

tup_b =  itertools.combinations(list_b, 2)
list_b = map(list,tup_b)
df_b = pd.DataFrame(list_b)

#Extending the list
df_b['B'] = df_b[0] + df_b[1] 
df_b = df_b[['B']]

#flatten list
b = df_b.values.tolist()
b = list(itertools.chain(*r))

# adding values and costs
r = len(b)
x=0
for x in range(0,r):
    cost = [b[x][1] +b[x][4]]
    value = [b[x][2] +b[x][5]]
    r[x] = r[x] +cost +value
    x +=1

#shortening list
df_b = pd.DataFrame(b)
df_b = df_b[[0,3,6,7]]
df_b.columns = ['B1','B2','cost','value']
然后,我对结构与上面类似的列表_c做了同样的操作,使用以下方法:

tup_c =  itertools.combinations(list_c, 3)
使用这种方法,处理时间从5小时减少到8分钟


谢谢大家的帮助。

如果你有速度慢但工作正常的代码要优化,它可能是网站的一个很好的候选者。你可能会发现你的代码更容易推理,你可以将其分解成函数,也许还可以使用一些内置工具,如。为什么你要使用b2循环使用rangeb2、num_b?以及定义b2=b1+1秒b?这似乎是一个潜在的非常混乱的符号。更重要的是,你可以减少表达字符串的次数,用字典而不是列表来计算总开销。这不是背包的问题吗?背包问题不是NP问题吗@马克·托齐——谢谢你指出这一点。我从来没有听说过它,而且它似乎离它很近。我要通读一遍。谢谢如果你有缓慢但有效的代码需要优化,它可能是网站的一个很好的候选者。你可能会发现你的代码更容易推理,你可以把它分解成函数,也许还可以使用一些内置工具,比如。你为什么要用b2在rangeb2,num_b上循环?以及定义b2=b1+1秒b?这似乎是一个潜在的非常混乱的符号。更重要的是,你可以减少表达字符串的次数,用字典而不是列表来计算总开销。这不是背包的问题吗?背包问题不是NP问题吗@马克·托齐——谢谢你指出这一点。我从来没有听说过它,而且它似乎离它很近。我要通读一遍。谢谢