Python纸浆-没有重复的名称

Python纸浆-没有重复的名称,python,pandas,optimization,pulp,Python,Pandas,Optimization,Pulp,我已经为幻想足球建立了一个优化脚本。基本上,它必须优化6名球员的预测分数,其中有1名队长和5个灵活位置。我的问题是,无论解决者选择谁作为队长,都会被选为FLEX。我想限制它,这样就不会选择重复的玩家名称。除此之外,一切正常,下面是我正在使用的代码和CSV文件示例: ` 进口纸浆 作为pd进口熊猫 将numpy作为np导入 来自itertools进口链 导入csv 文件名='C:/Users/Michael Arena/Desktop/Football/shodown/Simulation\u

我已经为幻想足球建立了一个优化脚本。基本上,它必须优化6名球员的预测分数,其中有1名队长和5个灵活位置。我的问题是,无论解决者选择谁作为队长,都会被选为FLEX。我想限制它,这样就不会选择重复的玩家名称。除此之外,一切正常,下面是我正在使用的代码和CSV文件示例:

`

进口纸浆
作为pd进口熊猫
将numpy作为np导入
来自itertools进口链
导入csv
文件名='C:/Users/Michael Arena/Desktop/Football/shodown/Simulation\u shodown.csv'
原始数据=pd.read\u csv(文件名,engine=“python”,index\u col=False,header=0,delimiter=“,”,quoting=3)
玩家ID=原始数据索引
player\u vars=plup.LpVariable.dicts('player',player\u id,cat='Binary')
prob=纸浆.LpProblem(“DFS优化器”,纸浆.LpProblem)
prob+=plup.lpSum([raw_data['Projection'][i]*player_vars[i]代表player_id中的i])
##总薪金上限:
prob+=plup.lpSum([raw_data['Salary'][i]*player_vars[i]代表player_id中的i])=10000
##总共有6名玩家:
prob+=plup.lpSum([player_vars[i]代表player_id中的i])==6
##5弹性:
prob+=plup.lpSum([player_vars[i]表示player_id中的i,如果原始数据['Position'][i]='FLEX'])>=5
##1船长:
prob+=plup.lpSum([player_vars[i]表示player_id中的i,如果原始数据['Position'][i]='CPT'])==1
纸浆
问题状态
问题解决()
原始数据[“正在起草”]=0.0
对于prob.variables()中的变量:
#集合被起草为LP确定的值
raw#u data.iloc[int(var.name[7:]),7]=var.varValue#第11列=已起草
我的团队=原始数据[原始数据[“正在起草”!=0]
我的团队=我的团队[[“姓名”、“职位”、“团队”、“薪水”、“投射”、“对手”]]
打印(我的团队负责人(10))
打印(“工资上限的总使用金额:{}”。格式(my_team[“salary”].sum())
打印(“投影点:{}”。格式(我的团队[“投影”].sum().round(1)))
打印(我的团队[“投影”].sum().round(1))

这是我刚才提到的解决方案

进口纸浆
将numpy作为np导入
#%%模拟数据的虚拟数组
n层=7
原始数据={}
名称=[chr(ord('A')+i)表示范围内的i(n层)]*2
原始数据['Position']=['FLEX']*nLayers+['CPT']*nLayers
原始数据['Projection']=np.rand.rand(2*n层)*10
原始数据['Salary']=(np.random.rand(2*Nplayers)*10000.aType(int)
玩家ID=np.arange(2*N玩家)
#%%你的代码(我评论了一些东西)
#玩家ID=原始数据索引
player\u vars=plup.LpVariable.dicts('player',player\u id,cat='Binary')
prob=纸浆.LpProblem(“DFS优化器”,纸浆.LpProblem)
prob+=plup.lpSum([raw_data['Projection'][i]*player_vars[i]代表player_id中的i])
##总薪金上限:
prob+=plup.lpSum([raw_data['Salary'][i]*player_vars[i]代表player_id中的i])=10000
##总共有6名玩家:
prob+=plup.lpSum([player_vars[i]代表player_id中的i])==6
##5弹性:
prob+=plup.lpSum([player_vars[i]表示player_id中的i,如果原始数据['Position'][i]='FLEX'])>=5
##1船长:
prob+=plup.lpSum([player_vars[i]表示player_id中的i,如果原始数据['Position'][i]='CPT'])==1
#这里是重要的东西!!!
#您可以创建一种聪明的方法,通过名称将“flex_indx”与“cpt_indx”匹配起来
flex_indx=np.arange(n层)
cpt_indx=np.arange(n层)+n层
对于范围内的i(n层):
prob+=plup.lpSum([player_vars[cpt_indx[i]],player_vars[flex_indx[i]])0:
num=int(v.name[7:])
tot_项目+=原始数据['投影][num]
工资总额+=原始数据['salary'][num]
打印(“%9s:%5s:%4s:%4.1f:%6u%”(v.name,name[num],原始数据['Position'][num],原始数据['Projection'][num],原始数据['Salary'][num]))
打印('-'*40)
打印('TOTAL'+''*20+':%4.1f:%6u'(项目总额、工资总额))
打印('-'*40)

您可能希望将数据分解为(姓名、职位)的双重索引,这样事情就会变得更加容易。这里的另一个解决方案很好,但非常脆弱,因为它假设所有可能是FLEX的名称都与CPT相同,并且顺序相同

这是一个不需要这样做的想法,如果你开发你的模型,它会更加灵活。注意:我使用了
pandas
来像您那样拉入数据,但是您也可以用几行来读取csv。此外,您可以使用pandas索引(在本例中为多索引)构建模型,但我认为基本python索引在本例中更为清晰,因此我将关键数据放入了两个字典中

我缩小了您的模型,从这个.csv中的6个名称-位置对中进行选择:

Name,Pos,  Value, Cost
Bob, FLEX,1.5,10
Sam, FLEX,1.4,8
Tom, FLEX,1.6,9
Bert,FLEX,1.5,9
Tom,CPT,1.2,12
Sam,CPT,1.3,11
剧本
您还可以将CPT选择为FLEX,因为两者都具有较高的“投影”。假设你有
N
玩家按照你的方式组织,那么你想要
player_vars[i]+player_vars[i+N],所以我一直在试图找出如何添加这一约束
#播放器ID中的cptid没有重复的名称:如果原始数据['Position'][cptid]='CPT':prob+=pulp.lpSum([player_vars[i]对于播放器ID中的i,如果原始数据['Name'][i]==原始数据['Name'][cptid]+[-1*播放器变量[cptid]]>=0
。我认为这会奏效,但它不会奏效。您能告诉我如何通过代码/将其添加为约束来实现您的建议吗?对不起,我不太使用纸浆。我会在我有一点时间的时候给你一个更详细的答案,我很抱歉:)你的限制应该是像
palp.lpSum([player_vars[cptid],player_vars[flexid]])嗨,AirSquid,你能看看我上一篇帖子并帮我吗?你对这个问题的回答对我帮助很大,我对我得到的答案感到困惑。非常感谢你能帮我看一看,因为你的评论对这篇文章非常有帮助。非常感谢!
Name,Pos,  Value, Cost
Bob, FLEX,1.5,10
Sam, FLEX,1.4,8
Tom, FLEX,1.6,9
Bert,FLEX,1.5,9
Tom,CPT,1.2,12
Sam,CPT,1.3,11
import pulp
import pandas as pd

data_file = 'data.csv'

df = pd.read_csv(data_file, index_col=['Name', 'Pos'], skipinitialspace=True)
#print(df)

legal_assignments = df.index   # tuples of (name, pos)
name_set = df.index.unique(0)  # a conveniece

costs = df['Cost'].to_dict()
values = df['Value'].to_dict()

# set up LP
draft = pulp.LpVariable.dicts('selected', legal_assignments, cat='Binary')

prob = pulp.LpProblem('the draft', pulp.LpMaximize)

# obj
prob += pulp.lpSum([draft[n, p]*values[n,p] for (n, p) in legal_assignments])

# salary cap
prob += pulp.lpSum([draft[n, p]*costs[n,p] for (n, p) in legal_assignments]) <= 30

# pick 2 FLEX
prob += pulp.lpSum([draft[n, p] for (n, p) in legal_assignments if p == 'FLEX']) == 2

# pick 1 CPT
prob += pulp.lpSum([draft[n, p] for (n, p) in legal_assignments if p == 'CPT']) == 1

# use each player at most only once
for name in name_set:
    prob += pulp.lpSum([draft[n, p] for (n, p) in legal_assignments if n == name]) <=1

prob.solve()

for idx in draft:
    if draft[idx].varValue:
        print(f'hire {idx[0]} for position {idx[1]}')
hire Tom for position FLEX
hire Bert for position FLEX
hire Sam for position CPT