Python 投资组合权重的所有可能组合
我正在寻找用Python更好地编写以下代码的技巧和技巧(例如,删除多余的循环和复制,使用更多的拼接) 我对其进行了编码,以根据以下约束条件为N种证券的投资组合创建所有可能的权重组合: 权重来自可能性列表(在本例中为0、.1、.2、.3、.4、.5) 有效投资组合的权重之和必须=1(完全投资) 这不是一种有效的方法,因为组合的数量很快变得难以管理。只是我在努力掌握这门语言 提前感谢大家的帮助Python 投资组合权重的所有可能组合,python,list,combinations,portfolio,Python,List,Combinations,Portfolio,我正在寻找用Python更好地编写以下代码的技巧和技巧(例如,删除多余的循环和复制,使用更多的拼接) 我对其进行了编码,以根据以下约束条件为N种证券的投资组合创建所有可能的权重组合: 权重来自可能性列表(在本例中为0、.1、.2、.3、.4、.5) 有效投资组合的权重之和必须=1(完全投资) 这不是一种有效的方法,因为组合的数量很快变得难以管理。只是我在努力掌握这门语言 提前感谢大家的帮助 import copy as cp def generateWeights (weights,possi
import copy as cp
def generateWeights (weights,possibleWeights,N):
"Generate all possible combinations of weights"
# cycle over number of desired coloumns
for i in range(0,N):
# copy weights to iterate over every element while i pop stuff out of
# the original list
weightsCopy = cp.deepcopy(weights)
for w in weightsCopy:
# make a copy to edit
wtemp = cp.deepcopy(w)
for p in possibleWeights:
# append every possibility
wtemp.append(p)
# I only want combinations with sum == 1 so I can start
# avoiding those that are > 1
if sum(wtemp) <= 1:
weights.append(cp.deepcopy(wtemp))
# get the original wtemp back so I can work on it with my next p
wtemp.pop()
# finished developing the first line of the table. Pop it out and
# move on.
weights.pop(0)
# once again copy weights to iterate over every element while I edit the
# original list
weightsCopy = cp.deepcopy(weights)
for w in weightsCopy:
# remove all possibilities whose sum < 1
# all those > 1 were never added
if sum(w) < 1:
weights.remove(w)
return weights
N=6 # Number of securities
possibleWeights = [0.0,0.1,0.2,0.3,0.4,0.5]
# weights is a coloumn because I want to access its elements and still get
# lists instead of floats.
weights = [[0.0],[0.1],[0.2],[0.3],[0.4],[0.5]]
weights = generateWeights(weights,possibleWeights,N)
作为cp导入副本
def生成权重(权重,可能权重,N):
“生成所有可能的权重组合”
#循环所需列数
对于范围(0,N)内的i:
#复制权重以迭代每个元素,同时从中弹出内容
#原始列表
权重透视=cp.deepcopy(权重)
对于重量中的w:
#复制以进行编辑
wtemp=cp.deepcopy(w)
对于p,在可能的权重中:
#附加所有可能性
wtemp.append(p)
#我只需要sum==1的组合,这样我就可以开始了
#避免那些大于1的
如果总和(wtemp)1从未添加
如果总和(w)<1:
重量。移除(w)
回程重量
N=6#证券数量
可能权重=[0.0,0.1,0.2,0.3,0.4,0.5]
#权重是一个冒号,因为我想访问它的元素,并且仍然可以
#列表而不是浮动。
权重=[[0.0]、[0.1]、[0.2]、[0.3]、[0.4]、[0.5]]
权重=生成权重(权重,可能权重,N)
您可以使用,但是必须增加组合的大小,直到达到数据集的长度
>>> input_list = [0,.1,.2,.3,.4,.5]
>>> from itertools import combinations
>>> valid_combinations = []
>>> for comb_length in range(1,len(input_list)+1):
possible_combinations = combinations(input_list,comb_length)
for comb in possible_combinations:
if sum(comb) ==1:
valid_combinations.append(comb)
>>>valid_combinations
[(0.1, 0.4, 0.5), (0.2, 0.3, 0.5), (0, 0.1, 0.4, 0.5), (0, 0.2, 0.3, 0.5), (0.1, 0.2, 0.3, 0.4), (0, 0.1, 0.2, 0.3, 0.4)]
阅读您的要求,并更新组合==1
,而不是您可以使用的,但是您必须增加组合的大小,直到达到数据集的长度
>>> input_list = [0,.1,.2,.3,.4,.5]
>>> from itertools import combinations
>>> valid_combinations = []
>>> for comb_length in range(1,len(input_list)+1):
possible_combinations = combinations(input_list,comb_length)
for comb in possible_combinations:
if sum(comb) ==1:
valid_combinations.append(comb)
>>>valid_combinations
[(0.1, 0.4, 0.5), (0.2, 0.3, 0.5), (0, 0.1, 0.4, 0.5), (0, 0.2, 0.3, 0.5), (0.1, 0.2, 0.3, 0.4), (0, 0.1, 0.2, 0.3, 0.4)]
阅读您的要求,并更新组合==1
,而不是您可以使用的,但是您必须增加组合的大小,直到达到数据集的长度
>>> input_list = [0,.1,.2,.3,.4,.5]
>>> from itertools import combinations
>>> valid_combinations = []
>>> for comb_length in range(1,len(input_list)+1):
possible_combinations = combinations(input_list,comb_length)
for comb in possible_combinations:
if sum(comb) ==1:
valid_combinations.append(comb)
>>>valid_combinations
[(0.1, 0.4, 0.5), (0.2, 0.3, 0.5), (0, 0.1, 0.4, 0.5), (0, 0.2, 0.3, 0.5), (0.1, 0.2, 0.3, 0.4), (0, 0.1, 0.2, 0.3, 0.4)]
阅读您的要求,并更新组合==1
,而不是您可以使用的,但是您必须增加组合的大小,直到达到数据集的长度
>>> input_list = [0,.1,.2,.3,.4,.5]
>>> from itertools import combinations
>>> valid_combinations = []
>>> for comb_length in range(1,len(input_list)+1):
possible_combinations = combinations(input_list,comb_length)
for comb in possible_combinations:
if sum(comb) ==1:
valid_combinations.append(comb)
>>>valid_combinations
[(0.1, 0.4, 0.5), (0.2, 0.3, 0.5), (0, 0.1, 0.4, 0.5), (0, 0.2, 0.3, 0.5), (0.1, 0.2, 0.3, 0.4), (0, 0.1, 0.2, 0.3, 0.4)]
阅读您的需求并进行更新,使其具有组合==1
,而不是。您应该使用已具备算法的itertools模块来完成大部分需要的工作
from itertools import combinations
def valid_combinations(weights):
'''generator of possible combinations of weights elements that add up to 1'''
list_length = len(weights) # we will need this
for lengths in range(list_length):
for possible in combinations(weights, lengths): # all possible orderings of weights
if sum(possible[:lengths]) == 1: # only generate valid ones
yield possible[:lengths]
>>> original = [0, .1, .2, .3, .4, .5]
>>> print list(valid_combinations(original))
[(0.1, 0.4, 0.5), (0.2, 0.3, 0.5), (0, 0.1, 0.4, 0.5), (0, 0.2, 0.3, 0.5), (0.1, 0.2, 0.3, 0.4), (0, 0.1, 0.2, 0.3, 0.4)]
如果您只对权重的唯一组合感兴趣(顺序不重要),则需要使用组合
,如果确实重要,则应使用排列
,方法如下:
from itertools import permutations
def valid_combinations(weights):
'''generator of possible combinations of weights elements that add up to 1'''
list_length = len(weights) # we will need this
for possible in permutations(weights): # all possible orderings of weights
for lengths in range(list_length): # get all prefix sublists
if sum(possible[:lengths]) == 1: # only generate valid ones
yield possible[:lengths]
>>> original = [0, .1, .2, .3, .4, .5]
>>> print list(valid_combinations(original))
>>> [(0, 0.1, 0.2, 0.3, 0.4), (0, 0.1, 0.2, 0.4, 0.3), (0, 0.1, 0.3, 0.2, 0.4), (0, 0.1, 0.3, 0.4, 0.2), (0, 0.1, 0.4, 0.2, 0.3), (0, 0.1, 0.4, 0.3, 0.2), (0, 0.1, 0.4, 0.5), (0, 0.1, 0.4, 0.5), (0, 0.1, 0.5, 0.4), (0, 0.1, 0.5, 0.4), (0, 0.2, 0.1, 0.3, 0.4), (0, 0.2 ...
您应该使用itertools模块,该模块已经有了算法来完成大部分您想要的任务
from itertools import combinations
def valid_combinations(weights):
'''generator of possible combinations of weights elements that add up to 1'''
list_length = len(weights) # we will need this
for lengths in range(list_length):
for possible in combinations(weights, lengths): # all possible orderings of weights
if sum(possible[:lengths]) == 1: # only generate valid ones
yield possible[:lengths]
>>> original = [0, .1, .2, .3, .4, .5]
>>> print list(valid_combinations(original))
[(0.1, 0.4, 0.5), (0.2, 0.3, 0.5), (0, 0.1, 0.4, 0.5), (0, 0.2, 0.3, 0.5), (0.1, 0.2, 0.3, 0.4), (0, 0.1, 0.2, 0.3, 0.4)]
如果您只对权重的唯一组合感兴趣(顺序不重要),则需要使用组合
,如果确实重要,则应使用排列
,方法如下:
from itertools import permutations
def valid_combinations(weights):
'''generator of possible combinations of weights elements that add up to 1'''
list_length = len(weights) # we will need this
for possible in permutations(weights): # all possible orderings of weights
for lengths in range(list_length): # get all prefix sublists
if sum(possible[:lengths]) == 1: # only generate valid ones
yield possible[:lengths]
>>> original = [0, .1, .2, .3, .4, .5]
>>> print list(valid_combinations(original))
>>> [(0, 0.1, 0.2, 0.3, 0.4), (0, 0.1, 0.2, 0.4, 0.3), (0, 0.1, 0.3, 0.2, 0.4), (0, 0.1, 0.3, 0.4, 0.2), (0, 0.1, 0.4, 0.2, 0.3), (0, 0.1, 0.4, 0.3, 0.2), (0, 0.1, 0.4, 0.5), (0, 0.1, 0.4, 0.5), (0, 0.1, 0.5, 0.4), (0, 0.1, 0.5, 0.4), (0, 0.2, 0.1, 0.3, 0.4), (0, 0.2 ...
您应该使用itertools模块,该模块已经有了算法来完成大部分您想要的任务
from itertools import combinations
def valid_combinations(weights):
'''generator of possible combinations of weights elements that add up to 1'''
list_length = len(weights) # we will need this
for lengths in range(list_length):
for possible in combinations(weights, lengths): # all possible orderings of weights
if sum(possible[:lengths]) == 1: # only generate valid ones
yield possible[:lengths]
>>> original = [0, .1, .2, .3, .4, .5]
>>> print list(valid_combinations(original))
[(0.1, 0.4, 0.5), (0.2, 0.3, 0.5), (0, 0.1, 0.4, 0.5), (0, 0.2, 0.3, 0.5), (0.1, 0.2, 0.3, 0.4), (0, 0.1, 0.2, 0.3, 0.4)]
如果您只对权重的唯一组合感兴趣(顺序不重要),则需要使用组合
,如果确实重要,则应使用排列
,方法如下:
from itertools import permutations
def valid_combinations(weights):
'''generator of possible combinations of weights elements that add up to 1'''
list_length = len(weights) # we will need this
for possible in permutations(weights): # all possible orderings of weights
for lengths in range(list_length): # get all prefix sublists
if sum(possible[:lengths]) == 1: # only generate valid ones
yield possible[:lengths]
>>> original = [0, .1, .2, .3, .4, .5]
>>> print list(valid_combinations(original))
>>> [(0, 0.1, 0.2, 0.3, 0.4), (0, 0.1, 0.2, 0.4, 0.3), (0, 0.1, 0.3, 0.2, 0.4), (0, 0.1, 0.3, 0.4, 0.2), (0, 0.1, 0.4, 0.2, 0.3), (0, 0.1, 0.4, 0.3, 0.2), (0, 0.1, 0.4, 0.5), (0, 0.1, 0.4, 0.5), (0, 0.1, 0.5, 0.4), (0, 0.1, 0.5, 0.4), (0, 0.2, 0.1, 0.3, 0.4), (0, 0.2 ...
您应该使用itertools模块,该模块已经有了算法来完成大部分您想要的任务
from itertools import combinations
def valid_combinations(weights):
'''generator of possible combinations of weights elements that add up to 1'''
list_length = len(weights) # we will need this
for lengths in range(list_length):
for possible in combinations(weights, lengths): # all possible orderings of weights
if sum(possible[:lengths]) == 1: # only generate valid ones
yield possible[:lengths]
>>> original = [0, .1, .2, .3, .4, .5]
>>> print list(valid_combinations(original))
[(0.1, 0.4, 0.5), (0.2, 0.3, 0.5), (0, 0.1, 0.4, 0.5), (0, 0.2, 0.3, 0.5), (0.1, 0.2, 0.3, 0.4), (0, 0.1, 0.2, 0.3, 0.4)]
如果您只对权重的唯一组合感兴趣(顺序不重要),则需要使用组合
,如果确实重要,则应使用排列
,方法如下:
from itertools import permutations
def valid_combinations(weights):
'''generator of possible combinations of weights elements that add up to 1'''
list_length = len(weights) # we will need this
for possible in permutations(weights): # all possible orderings of weights
for lengths in range(list_length): # get all prefix sublists
if sum(possible[:lengths]) == 1: # only generate valid ones
yield possible[:lengths]
>>> original = [0, .1, .2, .3, .4, .5]
>>> print list(valid_combinations(original))
>>> [(0, 0.1, 0.2, 0.3, 0.4), (0, 0.1, 0.2, 0.4, 0.3), (0, 0.1, 0.3, 0.2, 0.4), (0, 0.1, 0.3, 0.4, 0.2), (0, 0.1, 0.4, 0.2, 0.3), (0, 0.1, 0.4, 0.3, 0.2), (0, 0.1, 0.4, 0.5), (0, 0.1, 0.4, 0.5), (0, 0.1, 0.5, 0.4), (0, 0.1, 0.5, 0.4), (0, 0.2, 0.1, 0.3, 0.4), (0, 0.2 ...
谢谢,这比我的烂摊子干净多了!你可以用一个发电机来防止同时占用太多的内存(见我的答案),谢谢,这比我的乱七八糟要干净得多!你可以用一个发电机来防止同时占用太多的内存(见我的答案),谢谢,这比我的乱七八糟要干净得多!你可以用一个发电机来防止同时占用太多的内存(见我的答案),谢谢,这比我的乱七八糟要干净得多!您可以同时使用生成器来防止占用太多内存(请参见我的答案)谢谢,排列部分适用于我的问题,这使我开始研究生成器:)谢谢,排列部分适用于我的问题,这使我开始研究生成器:)谢谢,排列部分适用于我的问题,这使我开始研究生成器:)谢谢,排列部分适用于我的问题,这使我开始研究生成器:)