也许这不是一个合适的标题,但让我解释一下我的问题。
以下是我的数据框:
company manager_1 manager_2 manager_3 manager_4 manager_5 manager_6 _manager_7
Ford AB AC AD AE AF AG AH
BMW BA BC BD BE BF
FIAT CA CB CD CE CF CG
Mercedes BC GA GB
我需要将这些不同的列转换为一个单独的列,并根据我想创建其他列的顺序。我基本上需要的是这个(我不在乎公司名称,因为这只是一个玩具示例)
name order
AB 7
AC 6
AD 5
AE 4
AF 3
AG 2
AH 1
BA 5
BC 4
BD 3
BE 2
BF 1
实际上,manager_7是公司的第一位经理,因此排在第1位,例如对于AH,对应的数字为1。 我试图转置列,但无法获得所需的输出。有帮助吗?
答案 0 :(得分:5)
IIUC,我们只需要在每一行中进行递减计数。我们可以通过堆叠以更方便的顺序获取行值:
new = df.drop("company", 1).stack().to_frame("name")
new["order"] = new.groupby(level=0).cumcount(ascending=False) + 1
new = new.reset_index(drop=True)
给我
In [65]: new
Out[65]:
name order
0 AB 7
1 AC 6
2 AD 5
3 AE 4
4 AF 3
5 AG 2
6 AH 1
7 BA 5
8 BC 4
9 BD 3
10 BE 2
11 BF 1
12 CA 6
13 CB 5
14 CD 4
15 CE 3
16 CF 2
17 CG 1
18 BC 3
19 GA 2
20 GB 1
这假设您未显示的值(例如manager_6 / BMW)实际上为空。如果它们是空字符串,则只需预先添加df = df.replace("", np.nan)
,或在stack
步骤之后手动将其放下。
答案 1 :(得分:2)
这里有点手工。
df = df.drop(['Company'], axis=1)
for col in list(df):
df[col] = df[col].fillna(0)
list_of_rows = []
def len_of_row_without_0(row):
return len([non_zero_value for non_zero_value in row if non_zero_value != 0])
for idx, row in df.iterrows():
row_as_list = row.tolist()
row_as_list = [(element, len_of_row_without_0(row_as_list) - row_as_list.index(element)) for element in row_as_list]
list_of_rows = list_of_rows + row_as_list
data = [element for element in list_of_rows if element[0]!=0]
df = pd.DataFrame(data,columns=['name', 'order'])
它给我的结果与DSM相同:
name order
0 AB 7
1 AC 6
2 AD 5
3 AE 4
4 AF 3
5 AG 2
6 AH 1
7 BA 5
8 BC 4
9 BD 3
10 BE 2
11 BF 1
12 CA 6
13 CB 5
14 CD 4
15 CE 3
16 CF 2
17 CG 1
18 BC 3
19 GA 2
20 GB 1