我有多个(类型)输入放在列表x
中,我正在使用test train split
进行操作:
x = [some_matrix, scalar_value, something_else, ...]
x0_train, x0_test, x1_train, x1_test, ... , y_train, y_test =
train_test_split(x[0],x[1],... , y, test_size=0.2, random_state=np.random, shuffle=True)
我设法将输入参数x[0], x[1], ...
更改为*x
:
x0_train, x0_test, x1_train, x1_test, ... , y_train, y_test =
train_test_split(*x, y, test_size=0.2, random_state=np.random, shuffle=True)
# But I have to manually repack
x_train = [x0_train, x1_train]
x_test = [x0_test, x1_test]
但有没有办法接收它而无需手动重新包装?相当于:
*x_train, *x_test, y_train, y_test =
train_test_split(*x, y, test_size=0.2, random_state=np.random, shuffle=True)
或者还有其他办法吗?例如:构建字典并使用**解包,但我仍然有同样的问题。无论如何(例如,存在)约定是什么?
答案 0 :(得分:1)
解包只是一种将列表,元组或其他可迭代元素分配给多个变量的方法。 “重新包装”的常规方法是在列表(或元组)中收集这些变量:
In [48]: a,b,c = [[1,2,3],3,[4,5]]
In [49]: a
Out[49]: [1, 2, 3]
In [50]: b
Out[50]: 3
In [51]: c
Out[51]: [4, 5]
In [52]: [a,b,c]
Out[52]: [[1, 2, 3], 3, [4, 5]]
这是最小的成本,因为只是Python玩对象指针。没有大数据块的副本。
我不熟悉train_test_split
行动的详细信息。您的输入和输出表明正在执行类似
alist = [(x[mask], x[~mask]) for x in xinput]
alist = itertools.chain(*alist)
也就是说,它对每个输入*args
应用某种拆分,索引或切片,然后展平结果列表。
较新的Pythons有某种形式的*
或...
解包,它将多个项目分配给变量。我没有太多使用它,所以必须查阅文档。但在这种情况下,我认为你想要收集一些列表中的所有其他值。我可以看到通过迭代和列表追加来做到这一点。使用一个列表理解即使不是不可能也很棘手,但是两个很好。
'*'语法:
In [55]: a, *b = [[1,2,3],3,[4,5]]
In [56]: a
Out[56]: [1, 2, 3]
In [57]: b
Out[57]: [3, [4, 5]]
In [58]: [a,b]
Out[58]: [[1, 2, 3], [3, [4, 5]]]
In [59]: [a,*b]
Out[59]: [[1, 2, 3], 3, [4, 5]]
在作业中不能有2个(或更多)已加星标的表达式。
受到列表推导的启发,这是另一种收集列表中其他项目的方法:
In [65]: *a, = [1,2,3],[4,5],[10,11,12],[13,14]
In [66]: a
Out[66]: [[1, 2, 3], [4, 5], [10, 11, 12], [13, 14]]
In [67]: a[::2]
Out[67]: [[1, 2, 3], [10, 11, 12]]
In [68]: a[1::2]
Out[68]: [[4, 5], [13, 14]]
答案 1 :(得分:0)
这解决了 zigzag split 问题:
recv = [None for i in range(2*len(x))]
*recv, y_train, y_test = train_test_split(*x, y, test_size=0.2, random_state=np.random, shuffle=True)
# Edit: credits hpaulj
x_train = recv[::2]
x_test = recv[1::2]
此外,如果有一种复制参考的方法,这也可以使用
x_train = [ None for _ in range(len(x))]
x_test = [ None for _ in range(len(x))]
recv = [item for sublist in zip(x_train, x_test) for item in sublist]
# But unfortunately the above line gives only the values and not references
# Hence doesn't work
*recv, y_train, y_test = train_test_split(*x, y, test_size=0.2, random_state=np.random, shuffle=True)