假設base_df
是如下所示的微小的數據幀:
In [221]: base_df
Out[221]:
seed
I S
0 a 0
b 1
1 a 2
b 3
注意base_df
具有2級多指數爲行。 (部分問題涉及在傳播的數據框中「傳播」這個多索引的值)。
現在,函數fn
(定義在本文末尾給出)取整數seed
作爲參數,並返回1按字符串鍵索引的列數據框。例如:
In [222]: fn(0)
Out[222]:
F
key
01011 0.592845
10100 0.844266
In [223]: fn(1)
Out[223]:
F
key
11110 0.997185
01000 0.932557
11100 0.128124
我要生成一個新的數據幀,在本質上,通過應用fn
到base_df
每一行,垂直串聯產生的dataframes。更具體地,期望的結果是這樣的:
F
I S key
0 a 01011 0.592845
10100 0.844266
b 11110 0.997185
01000 0.932557
11100 0.128124
1 a 01101 0.185082
01110 0.931541
b 00100 0.070725
11011 0.839949
11111 0.121329
11000 0.569311
IOW,概念上,是通過產生一個「子數據幀」爲base_df
每一行,和垂直方向上串聯這些子dataframes獲得所需的數據幀。每行對應的子數據幀具有3級多索引。該多指數的前兩個水平(I
和S
)來自該行的多指標值base_df
,而其最後一個水平(key
)以及(獨立)F
列的值來自通過fn
爲該行的seed
值返回的數據幀。
我不清楚的部分是如何將行的原始多索引值傳播到fn
爲該行的seed
值創建的數據框的行。
重要:我正在尋找一種方式來做到這一點是不可知的base_df
的多指標的層次的名稱,和其數量。
我嘗試以下
base_df.apply(lambda row: fn(row.seed), axis=1)
...但評估失敗,錯誤
ValueError: Shape of passed values is (4, 2), indices imply (4, 1)
有一些簡便的方法做我想要做什麼?
下面是fn
的定義。就這個問題而言,它的內部是不重要的。重要的是,它需要一個整數seed
作爲參數,並返回一個數據幀,如前所述。
import numpy
def fn(seed, _spec='{{0:0{0:d}b}}'.format(5)):
numpy.random.seed(int(seed))
n = numpy.random.randint(2, 5)
r = numpy.random.rand(n)
k = map(_spec.format, numpy.random.randint(0, 31, size=n))
result = pandas.DataFrame(r, columns=['F'], index=k)
result.index.name = 'key'
return result
在這個例子中,這些鍵發生,以對應於0和31(含)之間的一些整數的二進制表示,但這一事實起着問題沒有作用。