如何使用Biopandas保存PDB文件?
我有一个经过处理的pdb文件,想进一步处理它并根据聚类算法的标签将其分成4 个不同的文件,这些标签保存在 'hlabs' 变量中。我的文件是 '1asy_pocket.pdb',可以用biopandas进行处理。然而,在构建了4 个不同的DataFrame之后,我无法将每个DataFrame保存到不同的文件中。
from biopandas.pdb import PandasPdb
import pandas as pd
from distances import hlabs
pdb = PandasPdb().read_pdb('1asy_pocket.pdb')
print(pdb.df.keys())
atoms_df = pdb.df['ATOM']
hetatm_df = pdb.df['HETATM']
atoms = pd.concat([atoms_df, hetatm_df])
print(atoms)
series = pd.Series(hlabs, name="labels")
data = pd.concat([atoms, series], axis=1)
fragments = data.groupby(['labels'])
groups = []
names = []
for name, group in fragments:
print(group.shape)
group = pd.DataFrame(group)
group = group.drop(['labels'], axis=1)
groups.append(group)
names.append(name)
numbers = range(0, len(groups))
numbers = list(map(str, numbers))
print(numbers)
for x, y in zip(groups, numbers):
x.to_pdb(path='file'+y+'.pdb',
records=['ATOM', 'HETATM'])
这里的问题在于,biopandas期望得到的不是一个dataframe (x),而是一个biopandas对象 pdb:
File "/hdda/mihai/first_model/pdb_test/april_test/pockets/./bpd.py", line 35, in <module>
x.to_pdb(path='file'+y+'.pdb',
^^^^^^^^
File "/hdda/mihai/miniconda/pytorch_env/lib/python3.13/site-packages/pandas/core/generic.py", line 6321, in __getattr__
return object.__getattribute__(self, name)
~~~~~~~~~~~~~~~~~~~~~~~^^^^^^^^^^^^
AttributeError: 'DataFrame' object has no attribute 'to_pdb'. Did you mean: 'to_hdf'?
是否有可能把这4 个DataFrame转换成biopandas对象?
解决方案
看起来你必须为每个组创建一个新的对象 PandasPdb,并手动将 DataFrame 赋值给 df(或更确切地说赋值给 _df,如 源代码 所示)——大致像这样:
groups = []
names = []
for name, group in fragments:
print(f"{group.shape=}")
group = pd.DataFrame(group) # I'm not sure if this is needed
group = group.drop(["labels"], axis=1)
new_pdb = PandasPdb()
new_pdb._df["ATOM"] = group
new_pdb._df["HETATM"] = hetatm_df # it seems it is empty in original file
groups.append(new_pdb)
names.append(name)
顺便说一句:
你可以使用 enumerate() 代替 range() 与 zip() 的组合。
你也可以使用 f-string,在文件名 f"file{index}.pdb" 中直接使用数字
for index, group in enumerate(groups):
group.to_pdb(path=f"file{index}.pdb", records=["ATOM", "HETATM"])
你甚至可以用一个for循环来替代两个for循环
# names = []
for index, (name, group) in enumerate(fragments):
print(f"{group.shape=}")
group = pd.DataFrame(group) # I'm not sure if this is needed
group = group.drop(["labels"], axis=1)
new_pdb = PandasPdb()
new_pdb._df["ATOM"] = group
new_pdb._df["HETATM"] = hetatm_df # it seems it is empty in original file.
new_pdb.to_pdb(path=f"file{index}.pdb", records=["ATOM", "HETATM"])
# names.append(name)
用于测试的完整工作代码,示例文件
github.com/MIhaitrm/test/blob/master/1asy_pocket.pdb。
我没有 distances.hlabs,所以用随机值创建了 hlabs
from biopandas.pdb import PandasPdb
import pandas as pd
# from distances import hlabs
def version_1():
groups = []
names = []
for name, group in fragments:
print(f"{group.shape=}")
group = pd.DataFrame(group) # I'm not sure if this is needed
group = group.drop(["labels"], axis=1)
new_pdb = PandasPdb()
new_pdb._df["ATOM"] = group
new_pdb._df["HETATM"] = hetatm_df # it seems it is empty in original file.
groups.append(new_pdb)
names.append(name)
# numbers = list(range(len(groups)))
# print(numbers)
for index, group in enumerate(groups):
group.to_pdb(path=f"file{index}.pdb", records=["ATOM", "HETATM"])
def version_2():
# names = []
for index, (name, group) in enumerate(fragments):
print(f"{group.shape=}")
group = pd.DataFrame(group) # I'm not sure if this is needed
group = group.drop(["labels"], axis=1)
new_pdb = PandasPdb()
new_pdb._df["ATOM"] = group
new_pdb._df["HETATM"] = hetatm_df # it seems it is empty in original file.
new_pdb.to_pdb(path=f"file{index}.pdb", records=["ATOM", "HETATM"])
# names.append(name)
# --- main ---
pdb = PandasPdb().read_pdb("1asy_pocket.pdb")
print("--- pdb.df.keys() ---")
print(pdb.df.keys())
atoms_df = pdb.df["ATOM"]
hetatm_df = pdb.df["HETATM"]
print("--- atoms_df ---")
print(atoms_df)
print("--- hetatm_df ---")
print(hetatm_df)
atoms = pd.concat([atoms_df, hetatm_df])
print("--- atoms ---")
print(atoms)
# create random values in hlabs
import random
hlabs = random.choices(["A", "B", "C", "D"], k=len(atoms))
series = pd.Series(hlabs, name="labels")
data = pd.concat([atoms, series], axis=1)
fragments = data.groupby(["labels"])
version_1()
# version_2()
站内所有文章版权归属LeftHeroAI导航站,无授权禁止任何主体转载、抄袭、复制内容,亦不得私自架设镜像站点。一经侵权,本站将通过法律途径追责。