Я думал о решении, однако ... имена столбцов не изменятся.
def combodf(dfx, x):
d = (['_'.join(i) for i in zip(*a)] for a in combinations(df.T.values.tolist(), x))
return pd.DataFrame(d).T
final_df = pd.concat([df, *(combodf(df, i) for i in range(2,6))], 1)
Но, глядя на вашу структуру "столбцов", было бы просто более разумно иметь их в качестве значений.Итак, вот обходной путь, в котором мы перемещаем столбец в последнюю строку.
import pandas as pd
from itertools import combinations
def combodf(dfx, x):
d = [['_'.join(i) for i in zip(*a)] for a in combinations(df.T.values.tolist(), x)]
return pd.DataFrame(d).T
d = {
'AAA': ["xzy", "gze"],
'BBB': ["abc", "hja"],
'CCC': ["dfg", "hza"],
'DDD': ["hij", "klm"],
'EEE': ["lal", "opa"]
}
df = pd.DataFrame(data=d)
df.loc[len(df)] = df.columns # insert columns last row
df = pd.concat([df, *(combodf(df, i) for i in range(2,6))], 1)
df.columns = df.tail(1).values[0] # make last row columns
df = df.drop(2) # drop last row
Сравнение:
print((df == final_df).all().all()) # True
print((df.columns == final_df.columns).all()) # True