标准化或缩放 pandas multi-index 上的列
Normalize or scale columns on pandas multi-index
我有一个包含两个索引的大数据框。第一个是索引日期,第二个是标签索引,每天都以不特定的顺序出现。每列每天都需要在 -1 和 1 之间进行归一化或缩放。我附上了一张图片,显示了需要标准化的区域。所以基本上我需要按列和日期规范化的数据,如果这有意义的话。由于我正在处理的数据非常大,因此我提供了一些示例代码来生成用于测试的副本。
import pandas as pd
import numpy as np
#For repeatability
np.random.seed(0)
#The index's
arrays = [
np.array([
"Day1", "Day1", "Day1", "Day1", "Day1",
"Day2", "Day2", "Day2", "Day2", "Day2",
"Day3", "Day3", "Day3", "Day3", "Day3"
]),
np.array([
"a", "b", "c", "d", "e",
"a", "b", "c", "d", "e",
"a", "b", "c", "d", "e"
])
]
#Create the sample dataframe
df = pd.DataFrame(np.random.randn(15, 4), index=arrays, columns=["100", "200", "300", "400"])
#Output the dataframe
print(df) #End of code
"""
100 200 300 400
Day1 a 1.764052 0.400157 0.978738 2.240893
b 1.867558 -0.977278 0.950088 -0.151357
c -0.103219 0.410599 0.144044 1.454274
d 0.761038 0.121675 0.443863 0.333674
e 1.494079 -0.205158 0.313068 -0.854096
Day2 a -2.552990 0.653619 0.864436 -0.742165
b 2.269755 -1.454366 0.045759 -0.187184
c 1.532779 1.469359 0.154947 0.378163
d -0.887786 -1.980796 -0.347912 0.156349
e 1.230291 1.202380 -0.387327 -0.302303
Day3 a -1.048553 -1.420018 -1.706270 1.950775
b -0.509652 -0.438074 -1.252795 0.777490
c -1.613898 -0.212740 -0.895467 0.386902
d -0.510805 -1.180632 -0.028182 0.428332
e 0.066517 0.302472 -0.634322 -0.362741
"""
下面是此示例的输出,其中包含我需要在 -1 和 1 之间缩放的字段
不,索引未标记。
我对 pandas groupby 不是很熟悉,但它可能是需要使用的。我愿意接受任何方法或建议。
最简单的方法是在 pandas
之外使用 scikit-learn
包。
from sklearn.preprocessing import MinMaxScaler
scaler = MinMaxScaler(feature_range=(-1,1))
# Group by level 0, which is the first index corresponding to 'Dayx'
# After applying the scaling function (which output a Numpy array), convert it to a dataframe
df_scaled = df.groupby(level=0).apply(lambda x : pd.DataFrame(scaler.fit_transform(x), columns=x.columns, index=x.index).round(5))
print(df_scaled)
这给你:
100 200 300 400
Day1 a 0.89496 0.98495 1.00000 1.00000
b 1.00000 -1.00000 0.93135 -0.54589
c -1.00000 1.00000 -1.00000 0.49168
d -0.12293 0.58365 -0.28161 -0.23246
e 0.62098 0.11266 -0.59500 -1.00000
Day2 a -1.00000 0.52713 1.00000 -1.00000
b 1.00000 -0.69484 -0.30804 -0.00925
c 0.69438 1.00000 -0.13358 1.00000
d -0.30944 -1.00000 -0.93703 0.60402
e 0.56893 0.84524 -1.00000 -0.21476
Day3 a -0.32714 -1.00000 -1.00000 1.00000
b 0.31425 0.14014 -0.45953 -0.01429
c -1.00000 0.40178 -0.03366 -0.35194
d 0.31288 -0.72205 1.00000 -0.31613
e 1.00000 1.00000 0.27758 -1.00000
进一步,为了帮助你理解groupby
,它实际上是根据你指定的组来拆分数据框(即在上面的例子中,组是第一级索引,Dayx
。第一组基本上是这样的:
100 200 300 400
Day1 a 1.764052 0.400157 0.978738 2.240893
b 1.867558 -0.977278 0.950088 -0.151357
c -0.103219 0.410599 0.144044 1.454274
d 0.761038 0.121675 0.443863 0.333674
e 1.494079 -0.205158 0.313068 -0.854096
然后将函数 scaler.fit_transform()
应用于这些数据帧中的每一个(成组)。
希望对您有所帮助!
我有一个包含两个索引的大数据框。第一个是索引日期,第二个是标签索引,每天都以不特定的顺序出现。每列每天都需要在 -1 和 1 之间进行归一化或缩放。我附上了一张图片,显示了需要标准化的区域。所以基本上我需要按列和日期规范化的数据,如果这有意义的话。由于我正在处理的数据非常大,因此我提供了一些示例代码来生成用于测试的副本。
import pandas as pd
import numpy as np
#For repeatability
np.random.seed(0)
#The index's
arrays = [
np.array([
"Day1", "Day1", "Day1", "Day1", "Day1",
"Day2", "Day2", "Day2", "Day2", "Day2",
"Day3", "Day3", "Day3", "Day3", "Day3"
]),
np.array([
"a", "b", "c", "d", "e",
"a", "b", "c", "d", "e",
"a", "b", "c", "d", "e"
])
]
#Create the sample dataframe
df = pd.DataFrame(np.random.randn(15, 4), index=arrays, columns=["100", "200", "300", "400"])
#Output the dataframe
print(df) #End of code
"""
100 200 300 400
Day1 a 1.764052 0.400157 0.978738 2.240893
b 1.867558 -0.977278 0.950088 -0.151357
c -0.103219 0.410599 0.144044 1.454274
d 0.761038 0.121675 0.443863 0.333674
e 1.494079 -0.205158 0.313068 -0.854096
Day2 a -2.552990 0.653619 0.864436 -0.742165
b 2.269755 -1.454366 0.045759 -0.187184
c 1.532779 1.469359 0.154947 0.378163
d -0.887786 -1.980796 -0.347912 0.156349
e 1.230291 1.202380 -0.387327 -0.302303
Day3 a -1.048553 -1.420018 -1.706270 1.950775
b -0.509652 -0.438074 -1.252795 0.777490
c -1.613898 -0.212740 -0.895467 0.386902
d -0.510805 -1.180632 -0.028182 0.428332
e 0.066517 0.302472 -0.634322 -0.362741
"""
下面是此示例的输出,其中包含我需要在 -1 和 1 之间缩放的字段
不,索引未标记。
我对 pandas groupby 不是很熟悉,但它可能是需要使用的。我愿意接受任何方法或建议。
最简单的方法是在 pandas
之外使用 scikit-learn
包。
from sklearn.preprocessing import MinMaxScaler
scaler = MinMaxScaler(feature_range=(-1,1))
# Group by level 0, which is the first index corresponding to 'Dayx'
# After applying the scaling function (which output a Numpy array), convert it to a dataframe
df_scaled = df.groupby(level=0).apply(lambda x : pd.DataFrame(scaler.fit_transform(x), columns=x.columns, index=x.index).round(5))
print(df_scaled)
这给你:
100 200 300 400
Day1 a 0.89496 0.98495 1.00000 1.00000
b 1.00000 -1.00000 0.93135 -0.54589
c -1.00000 1.00000 -1.00000 0.49168
d -0.12293 0.58365 -0.28161 -0.23246
e 0.62098 0.11266 -0.59500 -1.00000
Day2 a -1.00000 0.52713 1.00000 -1.00000
b 1.00000 -0.69484 -0.30804 -0.00925
c 0.69438 1.00000 -0.13358 1.00000
d -0.30944 -1.00000 -0.93703 0.60402
e 0.56893 0.84524 -1.00000 -0.21476
Day3 a -0.32714 -1.00000 -1.00000 1.00000
b 0.31425 0.14014 -0.45953 -0.01429
c -1.00000 0.40178 -0.03366 -0.35194
d 0.31288 -0.72205 1.00000 -0.31613
e 1.00000 1.00000 0.27758 -1.00000
进一步,为了帮助你理解groupby
,它实际上是根据你指定的组来拆分数据框(即在上面的例子中,组是第一级索引,Dayx
。第一组基本上是这样的:
100 200 300 400
Day1 a 1.764052 0.400157 0.978738 2.240893
b 1.867558 -0.977278 0.950088 -0.151357
c -0.103219 0.410599 0.144044 1.454274
d 0.761038 0.121675 0.443863 0.333674
e 1.494079 -0.205158 0.313068 -0.854096
然后将函数 scaler.fit_transform()
应用于这些数据帧中的每一个(成组)。
希望对您有所帮助!