Spaces:
No application file
No application file
| # Copyright 2000 by Jeffrey Chang. All rights reserved. | |
| # Revisions copyright 2001 by Gavin E. Crooks. All rights reserved. | |
| # This file is part of the Biopython distribution and governed by your | |
| # choice of the "Biopython License Agreement" or the "BSD 3-Clause License". | |
| # Please see the LICENSE file that should have been included as part of this | |
| # package. | |
| """A collection of residues from a PDB structure.""" | |
| import re | |
| _pdbid_re = re.compile(r"^(\w\w\w\w)(?:$|\s+|_)(.*)") | |
| _fragment_re = re.compile(r"\(?(\w:)?(-?\w*)-?(-?\w*)\)?(.*)") | |
| class Residues: | |
| """A collection of residues from a PDB structure. | |
| This class provides code to work with SCOP domain definitions. These | |
| are concisely expressed as one or more chain fragments. For example, | |
| "(1bba A:10-20,B:)" indicates residue 10 through 20 (inclusive) of | |
| chain A, and every residue of chain B in the pdb structure 1bba. The pdb | |
| id and brackets are optional. In addition "-" indicates every residue of | |
| a pbd structure with one unnamed chain. | |
| Start and end residue ids consist of the residue sequence number and an | |
| optional single letter insertion code. e.g. "12", "-1", "1a", "1000" | |
| pdbid -- An optional PDB id, e.g. "1bba" | |
| fragments -- A sequence of tuples (chainID, startResID, endResID) | |
| """ | |
| def __init__(self, str=None): | |
| """Initialize the class.""" | |
| self.pdbid = "" | |
| self.fragments = () | |
| if str is not None: | |
| self._parse(str) | |
| def _parse(self, str): | |
| str = str.strip() | |
| # Is there a pdbid at the front? e.g. 1bba A:1-100 | |
| m = _pdbid_re.match(str) | |
| if m is not None: | |
| self.pdbid = m.group(1) | |
| str = m.group(2) # Everything else | |
| if str == "" or str == "-" or str == "(-)": # no fragments, whole sequence | |
| return | |
| fragments = [] | |
| for fragment in str.split(","): | |
| m = _fragment_re.match(fragment) | |
| if m is None: | |
| raise ValueError(f"I don't understand the format of {fragment}") | |
| chain, start, end, postfix = m.groups() | |
| if postfix != "": | |
| raise ValueError(f"I don't understand the format of {fragment}") | |
| if chain: | |
| if chain[-1] != ":": | |
| raise ValueError(f"I don't understand the chain in {fragment}") | |
| chain = chain[:-1] # chop off the ':' | |
| else: | |
| chain = "" | |
| fragments.append((chain, start, end)) | |
| self.fragments = tuple(fragments) | |
| def __str__(self): | |
| """Represent the SCOP residues record as a string.""" | |
| prefix = "" | |
| if self.pdbid: | |
| prefix = self.pdbid + " " | |
| if not self.fragments: | |
| return prefix + "-" | |
| strs = [] | |
| for chain, start, end in self.fragments: | |
| s = [] | |
| if chain: | |
| s.append(f"{chain}:") | |
| if start: | |
| s.append(f"{start}-{end}") | |
| strs.append("".join(s)) | |
| return prefix + ",".join(strs) | |