Secure your code as it's written. Use Snyk Code to scan source code in minutes - no build needed - and fix issues immediately.
Take a structure and rotate and translate a copy of it, so that they
are not superimposed anymore.
Then superimpose these structure onto each other and expect an
almost perfect match.
"""
fixed = strucio.load_structure(path, model=1)
mobile = fixed.copy()
mobile = struc.rotate(mobile, (1,2,3))
mobile = struc.translate(mobile, (1,2,3))
fitted, transformation = struc.superimpose(
fixed, mobile
)
assert struc.rmsd(fixed, fitted) == pytest.approx(0, abs=6e-4)
fitted = struc.superimpose_apply(mobile, transformation)
assert struc.rmsd(fixed, fitted) == pytest.approx(0, abs=6e-4)
def test_base_pairs_reverse_no_hydrogen(nuc_sample_array, basepairs):
"""
Remove the hydrogens from the sample structure. Then reverse the
order of residues in the atom_array and then test the function
base_pairs.
"""
nuc_sample_array = nuc_sample_array[nuc_sample_array.element != "H"]
# Reverse sequence of residues in nuc_sample_array
reversed_nuc_sample_array = struc.AtomArray(0)
for residue in reversed_iterator(struc.residue_iter(nuc_sample_array)):
reversed_nuc_sample_array = reversed_nuc_sample_array + residue
computed_basepairs = base_pairs(reversed_nuc_sample_array)
check_output(
reversed_nuc_sample_array[computed_basepairs].res_id, basepairs
)
def test_apply_residue_wise(array):
data = struc.apply_residue_wise(array, np.ones(len(array)), np.sum)
assert data.tolist() == [len(array[array.res_id == i])
for i in range(1, 21)]
"""
if ndim > len(input_atoms.shape):
# Cannot run tests if translation vector has more dimensions
# as input coordinates/atoms
return
np.random.seed(random_seed)
vectors = np.random.rand(*struc.coord(input_atoms).shape[-ndim:])
vectors *= 10
neg_vectors = -vectors
if as_list:
vectors = vectors.tolist()
neg_vectors = neg_vectors.tolist()
translated = struc.translate(input_atoms, vectors)
restored = struc.translate(translated, neg_vectors)
assert type(restored) == type(input_atoms)
assert struc.coord(restored).shape == struc.coord(input_atoms).shape
assert np.allclose(
struc.coord(restored), struc.coord(input_atoms), atol=1e-5
)
index_prev_c, index_curr_n, struc.BondType.SINGLE
)
# Add N-terminal hydrogen
atom_n = peptide[(peptide.res_id == 1) & (peptide.atom_name == "N")][0]
atom_h = peptide[(peptide.res_id == 1) & (peptide.atom_name == "H")][0]
coord_h2 = calculate_atom_coord_by_z_rotation(
atom_n.coord, atom_h.coord, -120, N_H_LENGTH
)
atom_h2 = struc.Atom(
coord_h2,
chain_id="A", res_id=1, res_name=atom_h.res_name, atom_name="H2",
element="H"
)
peptide = struc.array([atom_h2]) + peptide
peptide.bonds.add_bond(0, 1, struc.BondType.SINGLE) # H2-N
# Add C-terminal hydroxyl group
last_id = len(sequence)
index_c = np.where(
(peptide.res_id == last_id) & (peptide.atom_name == "C")
)[0][0]
index_o = np.where(
(peptide.res_id == last_id) & (peptide.atom_name == "O")
)[0][0]
coord_oxt = calculate_atom_coord_by_z_rotation(
peptide.coord[index_c], peptide.coord[index_o], connect_angle, C_O_LENGTH
)
coord_hxt = calculate_atom_coord_by_z_rotation(
coord_oxt, peptide.coord[index_c], connect_angle, O_H_LENGTH
)
bonds.add_bond(0, 1, struc.BondType.SINGLE) # N-CA
bonds.add_bond(1, 2, struc.BondType.SINGLE) # CA-C
bonds.add_bond(2, 3, struc.BondType.DOUBLE) # C-O
bonds.add_bond(0, 4, struc.BondType.SINGLE) # N-H
backbone.bonds = bonds
# Get residue from dataset
residue = info.residue(res_name)
# Superimpose backbone of residue
# with backbone created previously
_, transformation = struc.superimpose(
backbone[struc.filter_backbone(backbone)],
residue[struc.filter_backbone(residue)]
)
residue = struc.superimpose_apply(residue, transformation)
# Remove backbone atoms from residue because they are already
# existing in the backbone created prevoisly
side_chain = residue[~np.isin(
residue.atom_name,
["N", "CA", "C", "O", "OXT", "H", "H2", "H3", "HXT"]
)]
# Assemble backbone with side chain (including HA)
# and set annotation arrays
residue = backbone + side_chain
residue.bonds.add_bond(
np.where(residue.atom_name == "CA")[0][0],
np.where(residue.atom_name == "CB")[0][0],
struc.BondType.SINGLE
)
backbone.res_name[:] = res_name
# Add bonds between backbone atoms
bonds = struc.BondList(backbone.array_length())
bonds.add_bond(0, 1, struc.BondType.SINGLE) # N-CA
bonds.add_bond(1, 2, struc.BondType.SINGLE) # CA-C
bonds.add_bond(2, 3, struc.BondType.DOUBLE) # C-O
bonds.add_bond(0, 4, struc.BondType.SINGLE) # N-H
backbone.bonds = bonds
# Get residue from dataset
residue = info.residue(res_name)
# Superimpose backbone of residue
# with backbone created previously
_, transformation = struc.superimpose(
backbone[struc.filter_backbone(backbone)],
residue[struc.filter_backbone(residue)]
)
residue = struc.superimpose_apply(residue, transformation)
# Remove backbone atoms from residue because they are already
# existing in the backbone created prevoisly
side_chain = residue[~np.isin(
residue.atom_name,
["N", "CA", "C", "O", "OXT", "H", "H2", "H3", "HXT"]
)]
# Assemble backbone with side chain (including HA)
# and set annotation arrays
residue = backbone + side_chain
residue.bonds.add_bond(
)[0][0]
curr_residue_mask = peptide.res_id == res_id
# Adjust geometry
curr_coord_n = calculate_atom_coord_by_z_rotation(
peptide.coord[index_prev_c], peptide.coord[index_prev_ca],
connect_angle, C_N_LENGTH
)
peptide.coord[curr_residue_mask] -= peptide.coord[index_curr_n]
peptide.coord[curr_residue_mask] += curr_coord_n
# Adjacent residues should show in opposing directions
# -> rotate residues with even residue ID by 180 degrees
if res_id % 2 == 0:
coord_n = peptide.coord[index_curr_n]
coord_c = peptide.coord[index_curr_c]
peptide.coord[curr_residue_mask] = struc.rotate_about_axis(
atoms = peptide.coord[curr_residue_mask],
axis = coord_c - coord_n,
angle = np.deg2rad(180),
support = coord_n
)
# Add bond between previous C and current N
peptide.bonds.add_bond(
index_prev_c, index_curr_n, struc.BondType.SINGLE
)
# Add N-terminal hydrogen
atom_n = peptide[(peptide.res_id == 1) & (peptide.atom_name == "N")][0]
atom_h = peptide[(peptide.res_id == 1) & (peptide.atom_name == "H")][0]
coord_h2 = calculate_atom_coord_by_z_rotation(
# as the content in ``'secStructList'`` is also calculated by the RCSB.
sse = dssp.DsspApp.annotate_sse(tk_mono)
sse = np.array([dssp_to_abc[e] for e in sse], dtype="U1")
visualize_secondary_structure(sse, tk_mono.res_id[0])
# sphinx_gallery_thumbnail_number = 4
########################################################################
# The one and only difference is that the second helix is slightly
# shorter.
# This is probably caused by different versions of DSSP.
#
# Last but not least we calculate the secondary structure using
# *Biotite*'s built-in method, based on the P-SEA algorithm.
sse = struc.annotate_sse(array, chain_id="A")
visualize_secondary_structure(sse, tk_mono.res_id[0])
plt.show()
Based on the implementation using :class:`ndarray` objects, this package
also contains functions for structure analysis and manipulation.
.. Note::
The universal length unit in *Biotite* is Ã….
This includes coordinates, distances, surface areas, etc.
Creating structures
-------------------
Let's begin by constructing some atoms:
"""
import biotite.structure as struc
atom1 = struc.Atom([0,0,0], chain_id="A", res_id=1, res_name="GLY",
atom_name="N", element="N")
atom2 = struc.Atom([0,1,1], chain_id="A", res_id=1, res_name="GLY",
atom_name="CA", element="C")
atom3 = struc.Atom([0,0,2], chain_id="A", res_id=1, res_name="GLY",
atom_name="C", element="C")
########################################################################
# The first parameter are the coordinates (internally converted into an
# :class:`ndarray`), the other parameters are annotations.
# The annotations shown in this example are mandatory:
# The chain ID, residue ID, residue name, insertion code, atom name,
# element and whether the atom is not in protein/nucleotide chain
# (*hetero*).
# If you miss one of these, they will get a default value.
# The mandatory annotation categories are originated in *ATOM* and
# *HETATM* records in the PDB format.