我有一个数据框,如下所示,
我需要将那些以Distance *开头的列转换为数据类型整数(目前它们是字符串格式),然后进一步过滤那些。
我可以这样做,分别为每一列,但我的数据框很大,有很多列
a.Distance0=a.Distance0.astype(int)
a.Distance1=a.Distance1.astype(int)
此后,我需要根据以Distance开头的列过滤掉这些行,得到两列作为输出,所以我作为输入数据框的最终输出是,
Head1 Header Dis
ABC SAP 115590
ABC GRN 426250
KLM DSQ 120001
我试图使用下面的代码到达那里,那就是我正在过滤那些以Distance> = 100000开头的行,而我只想要那些具有三列值的行,如上所述。 这是我尝试过的,但是这个解决方案给了我所有的列
a.loc[a[a[a.columns[pd.Series(a.columns).str.startswith('Distance')]] >= 100000].dropna(how='all', axis=0).index]
但是它给出了结果,但我得到的所有列都是这样的,
RNA PC NA PC0 Strand0 Distance0 PC1 Strand1 Distance1
RP11 RNF223 (+11559), AGRN (+42625) 0 RNF223 + 115590 AGRN + 42625
RP13 CORT (-19440), APITD1 (+177) 0 CORT - 254880 APITD1 + 177
任何帮助或建议都会非常棒。!!!
答案 0 :(得分:1)
如果要更改以Distance
开头的每列的类型,可以使用循环:
list_col = []
for col in a.columns:
if (len(col) > 8) & (col[:8] == 'Distance'):
list_col.appen(col)
a[list_col] = a[list_col].astype(int)
然后创建一个连接不同Distance值的数据帧:
frames = []
for i in len(list_col):
temp = df[['Head1','Header'+str(i),list_col[i]]]
temp.columns = ['Head1','Header','Distance']
frames.append(temp)
output = pd.concat(drames)
(请注意,这意味着您的列名称要格式良好,您可能需要根据append
中的实际名称进行调整)
然后你过滤:
output = out[out.Distance >= 100000]
这可能在您第一次尝试使用数据帧时无效,因为我假设您的数据帧列(只有我们感兴趣的列)被调用如下:
Head1 Header0 Distance0 Header1 Distance1 Header2 Distance2
依此类推......(再一次,我们不关心其他专栏,因为他们不会干涉此代码)
答案 1 :(得分:1)
请注意,我已将您的第一个Head1列重命名为Header(您的示例中有重复的列)。
我设置的Dataframe与您的不同,但足够接近。我没有填写与问题无关的专栏。
这是我的设置代码:
import pandas as pd
df = pd.DataFrame([],
columns=["Header",
"LongHeader",
"Head0",
"Strand0",
"Distance0",
"Head1",
"Strand1",
"Distance1",
"Head2",
"Strand2",
"Distance2"])
df["Header"] = ["ABC", "EFG", "HIJ", "KLM", "SOS"]
df["LongHeader"] = ["1", "2", "3", "4", "5"]
df["Head0"] = ["SAP", "HES3", "CORT", "AAD", "MFA"]
df["Strand0"] = ["+", "-", "-", "-", "-"]
df["Distance0"] = ["115590", "6350", "19440", "25488", "11174"]
df["Head1"] = ["GRN", "CMT", "API", "DH", "13A2"]
df["Strand1"] = ["+", "-", "-", "-", "-"]
df["Distance1"] = ["426250", "1902", "177", "1341", "19763"]
df["Head2"] = ["None", "None", "None", "DSQ", "None"]
df["Strand2"] = ["+", "-", "-", "-", "-"]
df["Distance2"] = ["None", "None", "None", "120001", "None"]
print df
其中的数据类似于您的示例:
Header LongHeader Head0 Strand0 Distance0 Head1 Strand1 Distance1 Head2
0 ABC 1 SAP + 115590 GRN + 426250 None
1 EFG 2 HES3 - 6350 CMT - 1902 None
2 HIJ 3 CORT - 19440 API - 177 None
3 KLM 4 AAD - 25488 DH - 1341 DSQ
4 SOS 5 MFA - 11174 13A2 - 19763 None
这是执行工作的代码。主要思想是提取Headx和Distancex列,并将它们叠加在一起。然后将Distance的dtype更改为int,并且仅保留Distance> gt = = 100000的行。
frames_to_concat = []
for col in df:
if col.startswith("Dis"):
dis_num = col[-1] # Extract the # from a column like Distance# or Dis#
frame_to_concat = df[["Header", "Head" + dis_num, "Distance" + dis_num]]
frame_to_concat.columns = ["Header", "Head", "Distance"]
frames_to_concat.append(frame_to_concat)
stacked_columns = pd.concat(frames_to_concat)
stacked_columns = stacked_columns[stacked_columns["Distance"] != "None"]
stacked_columns["Distance"] = stacked_columns["Distance"].astype(int)
result = stacked_columns[stacked_columns["Distance"] > 100000]
print result
给出了:
# Output:
Header Head Distance
0 ABC SAP 115590
0 ABC GRN 426250
3 KLM DSQ 120001
下次你问一个问题时,不要让潜在的回答者如此努力。提供设置代码!!!
您必须稍微修改此解决方案以与您的实际列名对齐,我不确定由于重复列问题而应该实际调用它们。 HTH!