def calculate_contacts(dirs, contact_function, native_pairs, nonnative_pairs, r0_native, r0_nonnative): """Calculate contacts for trajectories""" n_frames = np.sum( [file_len("%s/Q.dat" % dirs[i]) for i in range(len(dirs))]) Qi_contacts = np.zeros((n_frames, native_pairs.shape[0]), float) Ai_contacts = np.zeros((n_frames, nonnative_pairs.shape[0]), float) logging.info("calculating native/nonnative contacts") chunk_sum = 0 # Loop over trajectory subdirectories. for n in range(len(trajfiles)): # Loop over chunks of each trajectory. for chunk in md.iterload(trajfiles[n], top="%s/Native.pdb" % dirs[0]): chunk_len = chunk.n_frames r_temp = md.compute_distances(chunk, native_pairs, periodic=False) Qi_temp = contact_function(r_temp, r0_native) Qi_contacts[chunk_sum:chunk_sum + chunk_len, :] = Qi_temp r_temp = md.compute_distances(chunk, nonnative_pairs, periodic=False) Ai_temp = contact_function(r_temp, r0_nonnative) Ai_contacts[chunk_sum:chunk_sum + chunk_len, :] = Ai_temp chunk_sum += chunk_len A = np.sum(Ai_contacts, axis=1) return Qi_contacts, Ai_contacts, A
def test_ca_distances_with_residues_not_containing_cas_with_exclusions( self): # Load test geom geom = mdtraj.load(self.pdbfile) # No exclusions feat_EN2 = MDFeaturizer(self.bogus_geom_pdbfile) feat_EN2.add_distances_ca(excluded_neighbors=2) EN2_pairs = [ [1, 5], [1, 7], [3, 7], ] # Check indices assert (np.allclose(EN2_pairs, feat_EN2.active_features[0].distance_indexes)) # Check distances D = mdtraj.compute_distances(geom, EN2_pairs) assert (np.allclose(D, feat_EN2.transform(geom))) # excluded_neighbors=1 ## will yield the same as before, because the first neighbor # doesn't conting CA's anyway feat_EN1 = MDFeaturizer(self.bogus_geom_pdbfile) feat_EN1.add_distances_ca(excluded_neighbors=1) EN1_pairs = [[1, 3], [1, 5], [1, 7], [3, 5], [3, 7], [5, 7]] assert (np.allclose(EN1_pairs, feat_EN1.active_features[0].distance_indexes)) D = mdtraj.compute_distances(geom, EN1_pairs) assert (np.allclose(D, feat_EN1.transform(geom)))
def test_Group_Mindist_All_Three_Groups_threshold(self): threshold = .7 group0 = [0, 20, 30, 0] group1 = [1, 21, 31, 1] group2 = [2, 22, 32, 2] self.feat.add_group_mindist(group_definitions=[group0, group1, group2], threshold=threshold) D = self.feat.transform(self.traj) # Now the references, computed separately for each combination of groups dist_list_01 = np.array( list(product(np.unique(group0), np.unique(group1)))) dist_list_02 = np.array( list(product(np.unique(group0), np.unique(group2)))) dist_list_12 = np.array( list(product(np.unique(group1), np.unique(group2)))) Dref_01 = mdtraj.compute_distances(self.traj, dist_list_01).min(1) Dref_02 = mdtraj.compute_distances(self.traj, dist_list_02).min(1) Dref_12 = mdtraj.compute_distances(self.traj, dist_list_12).min(1) Dref = np.vstack((Dref_01, Dref_02, Dref_12)).T Dbinary = np.zeros_like(Dref) I = np.argwhere(Dref <= threshold) Dbinary[I[:, 0], I[:, 1]] = 1 assert np.allclose(D, Dbinary) assert len(self.feat.describe()) == self.feat.dimension()
def cmap_Cheng(traj_generator, mask1, mask2, pairs, topology): """ Calculate contact maps between mask1 and mask2 as described in [1]. Parameters ---------- traj_generator: generator MD trajectory as obtained through the load_Trajs_generator() function mask1, mask2, pairs: Two masks and the corresponding residue-residue list of tuples as obtained from the get_residuepairs() function Returns ------- contact_frequency: np.array of shape (len(mask1), len(mask2)) Contact map between mask1 and mask2. Can be used directly as input by the sns.heatmap() function. References ---------- [1] Cheng, Y. et al., 2014. Biophysical Journal, 107(7), pp.1675–1685. """ print("Starting the cmap_Cheng calculation...") top = md.load_prmtop(topology) frequency = np.zeros(len(pairs)) frame_count = 0 for traj_chunk in traj_generator: frame_count += traj_chunk.n_frames index = 0 # To iterate through the residue-residue pair list for residue_pair in pairs: # Atom selection for each residue in the pair c_atoms_residue1 = top.select("resid %d and (type C)" % residue_pair[0]) c_atoms_residue2 = top.select("resid %d and type C" % residue_pair[1]) not_c_atoms_residue1 = top.select("resid %d and not type C" % residue_pair[0]) not_c_atoms_residue2 = top.select("resid %d and not type C" % residue_pair[1]) # Calculate all the possible distances between the C-C atoms and # the non C-C atoms. Results are stored in two np.arrays of shape: # (traj_chunk.n_frames, c_atoms_residue1*c_atoms_residue2) # (traj_chunk.n_frames, non_c_atoms_residue1*non_c_atoms_residue2) c_atoms_dist = md.compute_distances(traj_chunk, cartesianProduct(c_atoms_residue1, c_atoms_residue2)) not_c_atoms_dist = md.compute_distances(traj_chunk, cartesianProduct(not_c_atoms_residue1, not_c_atoms_residue2)) # Implementation of the contact condition if (((c_atoms_dist <= 5.4).sum(1).any() > 0) and ((not_c_atoms_dist <= 4.6).sum(1).any() > 0)): frequency[index] += 1 index += 1 contact_frequency = ( frequency / frame_count).reshape(len(mask1), len(mask2)) print('Number of analyzed frames: %d\n' % frame_count) print('Aggregate simulation time: %2.f ns\n' % (frame_count * 0.02 * args.stride)) return(contact_frequency)
def atom_pair_dist(pair='Y36CG_R54CZ', y=[0.25, 1.75]): top = wstr[0].topology s = pair.split('_') pair_ix = [[top.select('residue=={0} and name=={1}'.format(s[0][1:3], s[0][3:]))[0], top.select('residue=={0} and name=={1}'.format(s[1][1:3], s[1][3:]))[0]]] distws = array([md.compute_distances(i, atom_pairs=pair_ix, periodic=False).ravel() for i in wstr]).T distns = array([md.compute_distances(i, atom_pairs=pair_ix, periodic=False).ravel() for i in nstr]).T figure(1) plot(distns, 'C1.', markersize=1) plot(distws, 'C0.', markersize=1, alpha=0.5) ylim(y) savefig('SUMO1_2asq_dist_{}.jpg'.format(pair), dpi=600) figure(2, figsize=(3.2, 4.8)) hist(distns.ravel(), color='C1', bins=100, linewidth=1, orientation='horizontal') hist(distws.ravel(), color='C0', alpha=0.6, bins=100, linewidth=1, orientation='horizontal') legend(['no SIM', 'with SIM'], frameon=0) ylim(y) savefig('SUMO1_2asq_dist_{}_hist.jpg'.format(pair), dpi=600)
def check_clashes(torsion_name, conf, cutoffnonh=0.210, cutoffoneh=0.140, cutoffoxy=0.140, cutofftwoh=0.100): bonds = [] mol = md.load('%s_%s_%s.mol2' % (torsion_name, conf, 0)) for bond in mol.topology.bonds: bonds.append([bond.atom1.index, bond.atom2.index]) #print('%s_%s_%s.mol2' %(torsion_name,conf ,0)) #print('cutoff cutoffnonh=%s ,cutoffoneh=%s ,cutoffoxy=%s ,cutofftwoh=%s' %(cutoffnonh ,cutoffoneh,cutoffoxy,cutofftwoh)) for i in range(-180, 180, 10): pairs_non_h = [] pairs_one_h = [] pairs_two_h = [] pairs_one_h_one_ox = [] bonds = [] mol = md.load('%s_%s_%s.mol2' % (torsion_name, conf, i)) for bond in mol.topology.bonds: bonds.append([bond.atom1.index, bond.atom2.index]) for at1 in mol.topology.atoms: for at2 in mol.topology.atoms: if at1 != at2 and [at1.index, at2.index] not in bonds and [ at2.index, at1.index ] not in bonds: if at1.element.atomic_number == 1 and at2.element.atomic_number == 1: pairs_two_h.append([at1.index, at2.index]) elif (at1.element.atomic_number == 1 or at2.element.atomic_number == 1) and (at1.element.atomic_number == 8 or at2.element.atomic_number == 8): pairs_one_h_one_ox.append([at1.index, at2.index]) elif (at1.element.atomic_number == 1 or at2.element.atomic_number == 1): pairs_one_h.append([at1.index, at2.index]) else: pairs_non_h.append([at1.index, at2.index]) if min(md.compute_distances(mol, pairs_non_h)[0]) < cutoffnonh: print('non hydrogen') return False if min(md.compute_distances(mol, pairs_one_h)[0]) < cutoffoneh: print('one hydrogen') return False if min(md.compute_distances(mol, pairs_two_h)[0]) < cutofftwoh: print('two hydrogen') return False if min(md.compute_distances(mol, pairs_one_h_one_ox)[0]) < cutoffoxy: print('oxygen', min(md.compute_distances(mol, pairs_one_h_one_ox)[0])) return False pairs_non_h.clear() pairs_one_h.clear() pairs_two_h.clear() return True
def _verify_closest_contact(traj): group1 = np.array([i for i in range(N_ATOMS//2)], dtype=np.int) group2 = np.array([i for i in range(N_ATOMS//2, N_ATOMS)], dtype=np.int) contact = find_closest_contact(traj, group1, group2) pairs = np.array([(i,j) for i in group1 for j in group2], dtype=np.int) dists = md.compute_distances(traj, pairs, True)[0] dists2 = md.compute_distances(traj, pairs, False)[0] nearest = np.argmin(dists) eq(float(dists[nearest]), contact[2], decimal=5) assert((pairs[nearest,0] == contact[0] and pairs[nearest,1] == contact[1]) or (pairs[nearest,0] == contact[1] and pairs[nearest,1] == contact[0]))
def distance_space(traj): """Convert a trajectory (or traj list) to distance space By default, this will compute ALL pair-wise distances and return a vector (or list of vectors if list of trajectories is provided) """ if isinstance(traj, list): pairs = get_pairlist(traj[0]) return [md.compute_distances(k, pairs) for k in traj] else: pairs = get_pairlist(traj) return md.compute_distances(traj, pairs)
def distance_space(traj): """Convert a trajectory (or traj list) to distance space By default, this will compute ALL pair-wise distances and return a vector (or list of vectors if list of trajectories is provided) """ if isinstance(traj, list): pairs = get_pairlist(traj[0]) return [md.compute_distances(k,pairs) for k in traj] else: pairs = get_pairlist(traj) return md.compute_distances(traj,pairs)
def best_hummer_q(traj, native, verbose=False, native_cutoff=0.45): """Compute the fraction of native contacts according the definition from Best, Hummer and Eaton [1]. Adapted from: 'http://mdtraj.org/latest/examples/native-contact.html' Parameters ---------- traj : md.Trajectory The trajectory to do the computation for native : md.Trajectory The 'native state'. This can be an entire trajecory, or just a single frame. Only the first conformation is used Returns ------- q : np.array, shape=(len(traj),) The fraction of native contacts in each frame of `traj` References ---------- ..[1] Best, Hummer, and Eaton, "Native contacts determine protein folding mechanisms in atomistic simulations" PNAS (2013) """ BETA_CONST = 50 # 1/nm LAMBDA_CONST = 1.8 NATIVE_CUTOFF = native_cutoff # nanometers # get the indices of all of the heavy atoms heavy = native.topology.select_atom_indices('heavy') # get the pairs of heavy atoms which are farther than 3 # residues apart heavy_pairs = np.array( [(i,j) for (i,j) in itertools.combinations(heavy, 2) if abs(native.topology.atom(i).residue.index - \ native.topology.atom(j).residue.index) > 3]) # compute the distances between these pairs in the native state heavy_pairs_distances = md.compute_distances(native[0], heavy_pairs)[0] # and get the pairs s.t. the distance is less than NATIVE_CUTOFF native_contacts = heavy_pairs[heavy_pairs_distances < NATIVE_CUTOFF] if verbose: print("Number of native contacts", len(native_contacts)) # now compute these distances for the whole trajectory r = md.compute_distances(traj, native_contacts) # and recompute them for just the native state r0 = md.compute_distances(native[0], native_contacts) q = np.mean(1.0 / (1 + np.exp(BETA_CONST * (r - LAMBDA_CONST * r0))), axis=1) return q
def get_dist_mdtraj(n=5): traj = mdtraj.load_pdb("tutorial/data/drd3_gi_pd.pdb") dist_arr = np.zeros((n, n)) # for i in range(n): # for j in range(n): i = 0 while i < 100: if i == 0: print(mdtraj.compute_distances(traj, [[0, 1]])) else: mdtraj.compute_distances(traj, [[0, 1]]) i += 1 h.heap().dump("benchmarking/heaps/4_mdtraj.out")
def calculate_debye_energy(self, traj, total=True): """Calculate the one-body burial potential Parameters ---------- traj : mdtraj.Trajectory Trajectory to calculate energy over. sum : opt, bool If true (default) return the sum of the burial potentials. If false, return the burial energy of each individual residue. """ debye = self.potential_forms["DEBYE"] bb_traj = self.backbone_mapping.map_traj(traj) r = md.compute_distances(bb_traj, self._debye_pairs) if total: Vdebye = np.zeros(bb_traj.n_frames, float) else: Vdebye = np.zeros((bb_traj.n_frames, self.n_debye_pairs), float) for i in range(self.n_debye_pairs): qi = self._debye_charges[i,0] qj = self._debye_charges[i,1] kij = self._debye_kij[i] if total: Vdebye += debye.V(r[:,i], qi, qj, kij) else: Vdebye[:, i] = debye.V(r[:,i], qi, qj, kij) return Vdebye
def indx_dists(trj, center_mol, cut): nmols = trj.xyz.shape[1] pairs = np.zeros((nmols, 2)) pairs[:,0] = np.arange(nmols) pairs[:,1] = center_mol*np.ones(nmols) ds = mdtraj.compute_distances(trj, pairs) return [i for i in ds if i < cut]
def compute_Epot_residues(trj, res1, res2, periodic=True, opt=True): """ Compute the electrostatic energy of each pair of atoms in the two residues during the trajectory Return: Epot: array that contains the energy per frame in kJ/mol ideal_dist: idealized distance of two charged particles with the residue charges and Epot """ # no energy for interaction with itself if res1 == res2: Epot = np.zeros(trj.n_frames) ideal_dist = np.zeros(trj.n_frames) return Epot, ideal_dist qq = np.array([q1*q2 for (q1, q2) in itertools.product(res1.atom_charges, res2.atom_charges)]) pairs = itertools.product(res1.atom_indices, res2.atom_indices) distances = md.compute_distances(trj, pairs, periodic=periodic, opt=opt) Epot = (qq / distances).sum(1) # kJ / mol # Idealised distance of two charges with this energy qq_ideal = res1.charge * res2.charge if np.abs(qq_ideal) > 0: ideal_dist = (qq_ideal) / Epot else: ideal_dist = np.zeros(trj.n_frames) # convert to gromacs units Epot *= ke_gu return Epot, ideal_dist
def get_pca_array(list_chunks, topology): """ Takes a list of mdtraj.Trajectory objects and featurize them to backbone - Alpha Carbons pairwise distances. Perform 2 component Incremental PCA on the featurized trajectory. Parameters ---------- list_chunks: list of mdTraj.Trajectory objects topology: str Name of the Topology file Returns ------- Y: np.array shape(frames, features) """ pca = IncrementalPCA(n_components=2) top = md.load_prmtop(topology) ca_backbone = top.select("name CA") pairs = top.select_pairs(ca_backbone, ca_backbone) pair_distances = [] for chunk in list_chunks: X = md.compute_distances(chunk, pairs) pair_distances.append(X) distance_array = np.concatenate(pair_distances) print("No. of data points: %d" % distance_array.shape[0]) print("No. of features (pairwise distances): %d" % distance_array.shape[1]) Y = pca.fit_transform(distance_array) return Y
def check_bonds(self): self.section("Bond Check (without PBCs)") radii = [] pairs = [] for (a, b) in self.topology.bonds: try: radsum = COVALENT_RADII[a.element.symbol] + COVALENT_RADII[b.element.symbol] except KeyError: raise NotImplementedError("I don't have radii information for all of your atoms") radii.append(radsum) pairs.append((a.index, b.index)) radii = np.array(radii) pairs = np.array(pairs) distances = md.compute_distances(self.t, pairs, periodic=False) low, high = self.bond_low * radii, self.bond_high * radii extreme = np.logical_or(distances < low, distances > high) if np.any(extreme): frames, bonds = np.nonzero(extreme) frame, bond = frames[0], bonds[0] a1 = self.topology.atom(pairs[bond][0]) a2 = self.topology.atom(pairs[bond][0]) self.log("error: atoms (%s) and (%s) are bonded according to the topology " % (a1, a2)) self.log("but they are a distance of %.3f nm apart in frame %d" % (distances[frame, bond], frame)) else: self.log("All good.")
def calc_obs(traj): arg_cz_id = 2442 glu_cd_id = 862 lys_nz_id = 634 tyr_oh_id = 2019 inactive = mdt.load("./topologies/inactive.pdb") active = mdt.load("./topologies/active.pdb") aloop_atoms_list = [i.index for residue in np.arange(147, 168) for i in inactive.topology.residue(residue).atoms] all_heavy = [i.index for i in inactive.topology.atoms if i.residue.is_protein and i.element.name != "hydrogen"] print("Processing %s" % traj) # load the trajectory trj = mdt.load(traj, atom_indices=np.arange(inactive.n_atoms)) inactive_rms = mdt.rmsd(trj, inactive, atom_indices=all_heavy) active_rms = mdt.rmsd(trj, active, atom_indices=all_heavy) aloop_rms = mdt.rmsd(trj, inactive, frame=0, atom_indices=aloop_atoms_list) distances = mdt.compute_distances(trj, np.vstack(([arg_cz_id, glu_cd_id], [lys_nz_id, glu_cd_id]))) return dict( fname=os.path.basename(traj), inactive_rmsd=inactive_rms, active_rmsd=active_rms, aloop_inactive_rmsd=aloop_rms, glu_arg=distances[:, 0], gly_lys=distances[:, 1], )
def distance_matrix_loop(self, i): print(str(i + 1) + '/' + str(self.nResidues)) for j in range(i + 1, self.nResidues): # i before atomInd1 = self.allInds[i] atomInd2 = self.allInds[j] atom_pairs = self.getAtomPairs(atomInd1, atomInd2) distances = md.compute_distances(self.traj, atom_pairs, periodic=False) #may have to compute distances myself if pdb_load error #print distances; #print '---------------------------------------------------' if len(distances) == 0: print('The chosen residue does not exist!') # The distance between residues is min distance between all heavy atoms. Take mean over all frames. self.distanceMatrix[i, j] = np.mean(np.min(distances, axis=1), axis=0) self.distanceMatrix[j, i] = np.mean(np.min(distances, axis=1), axis=0) return
def calc_native_nonative_pair_energy(self, traj, n_native_pairs, sum=True): """Energy for pair interactions Parameters ---------- traj : mdtraj.Trajectory sum : bool (opt.) If sum=True return the total energy. """ r = md.compute_distances(traj, self._pair_idxs) if sum: Enat = np.zeros(traj.n_frames, float) Enon = np.zeros(traj.n_frames, float) else: Enat = np.zeros((traj.n_frames, n_native_pairs), float) Enon = np.zeros((traj.n_frames, self.n_pairs - n_native_pairs), float) for i in range(n_native_pairs): if sum: Enat += self._pairs[i].V(r[:, i]) else: Enat[:, i] = self._pairs[i].V(r[:, i]) for i in range(n_native_pairs, self.n_pairs): if sum: Enon += self._pairs[i].V(r[:, i]) else: Enon[:, i - n_native_pairs] = self._pairs[i].V(r[:, i]) return Enat, Enon
def struct_factor(self,Q,R,dt): """ See equations (6) and (4) in ref [2] """ water_pairs = np.array(list(combinations(sorted(self.water_inds),2))) step = int(dt/self.time_step) frame_steps= [step+random.randint(-int(step/2),int(step/2)) \ for ii in range(int(self.total_time/dt))] while sum(frame_steps)>self.n_frames-1: frame_steps = frame_steps[:-1] # print ('the average time between each configuration is %f ps' % (np.mean(frame_steps)*self.time_step)) N_QR = [] current_frame = 0 for this_step in frame_steps: current_frame += this_step water_dist = md.compute_distances(self.traj[current_frame],water_pairs)[0] # unit in nm N_QR.append(self.single_frame_N_QR(Q,R,water_dist)) # equation (4) in ref [2] err_Sn_QR = np.std(N_QR)/len(N_QR) if Q == 0: # equation (7) in ref [2] Sn_QR = np.mean(N_QR)-4./3.*np.pi*self.rho*R**3.0 else: # equations (4a-d) in ref [1] Sn_QR = np.mean(N_QR)-4./3.*np.pi*self.rho*3./Q**3.*(np.sin(Q*R)-Q*R*np.cos(Q*R)) return Sn_QR, err_Sn_QR
def _calc_min_distance(self, walker): """Min-min distance for a walker. Parameters ---------- walker : object implementing the Walker interface Returns ------- min_distance : float """ cell_lengths, cell_angles = box_vectors_to_lengths_angles(walker.state['box_vectors']) t2 = time.time() # make a traj out of it so we can calculate distances through # the periodic boundary conditions walker_traj = mdj.Trajectory(walker.state['positions'], topology=self._mdj_top, unitcell_lengths=cell_lengths, unitcell_angles=cell_angles) t3 = time.time() # calculate the distances through periodic boundary conditions # and get hte minimum distance min_distance = np.min(mdj.compute_distances(walker_traj, it.product(self.ligand_idxs, self.receptor_idxs), periodic=self._periodic) ) t4 = time.time() logging.info("Make a traj: {0}; Calc dists: {1}".format(t3-t2,t4-t3)) return min_distance
def calculate_stride_distances(self, stride, equil_steps): t = DistanceCalculator(self.proj_num, 0, 0, 0) indices = t.get_distance_indices() runs, clones, gens = self.data.shape[0], self.data.shape[1], self.data.shape[2] npy_path = '/home/server/git/fah-scripts/DataAnalysisScripts/stride_dist/stride_dist_%d.npy' % self.proj_num if not os.path.isfile(npy_path): arr = np.empty((runs, clones, gens), dtype=np.ndarray) np.save(npy_path, arr) arr = np.load(npy_path) for i in range(runs): for j in range(clones): for k in range(gens): if arr[i][j][k] is None and os.path.isdir('/home/server/server2/data/SVR166219/PROJ%d/RUN%d/CLONE%d/results%d' % (self.proj_num, i, j, k)): distances = [] x = 0 while True: try: if k == 0 and j == 0 and i == 0 and x < equil_steps: x += stride continue t = DistanceCalculator(self.proj_num, i, j, k) distances.append(md.compute_distances(t.traj[x], indices)) del t except: break x += stride if len(distances) > 0: arr[i][j][k] = np.asarray(np.concatenate(distances)) print('Calculated distances of index[%d][%d][%d]' % (i, j, k)) else: break print('Distances saved') np.save(npy_path, arr)
def test_nearest_nbs(cut_off,frame_ind): nearest_nbs = [] for this_ind in test.water_inds[0:2]: nbs = md.compute_neighbors(test.traj[frame_ind], cut_off,[this_ind],haystack_indices = test.water_inds)[0] print this_ind while len(nbs)!=3: if len(nbs) > 3: pairs = [[this_ind,this_nb] for this_nb in nbs] distances=md.compute_distances(test.traj[frame_ind],pairs)[0] print distances min_three = f(distances,3) print min_three print nbs nbs = [nbs[ii] for ii in min_three] else: print 'increase cut_off!' nbs.append(this_ind) nbs.sort() if nbs in nearest_nbs: print "not unique" else: nearest_nbs.append(nbs) return np.array(nearest_nbs)
def calculate_and_filter_by_dist(self, atom_A_name, atom_B_name, distance_cutoff): self.coordinates_array = [] coords = {"frame": [], "atom_A_index": [], "X": [], "Y": [], "Z": []} for chunk_ind, chunk in enumerate(self.traj): top, bonds = chunk.top.to_dataframe() atom_A_top = top[top.name == atom_A_name] atom_B_top = top[top.name == atom_B_name] for f_ind, frame in enumerate(chunk): for atom_A_ind in atom_A_top.index: # print vco_ind atom_pairs = np.array([[atom_A_ind, j] for j in atom_B_top.index]) # print atom_pairs distances = md.compute_distances(frame, atom_pairs) xyz = frame.xyz[:, atom_A_ind, :] if len(distances[distances <= distance_cutoff]): coords["frame"].extend((chunk * chunk_index) + f_ind) coords["atom_A_index"].extend(atom_A_ind) coords["X"].extend(xyz[0, 0]) coords["Y"].extend(xyz[0, 1]) coords["Z"].extend(xyz[0, 2]) self.coordinates_array.append([(chunk * chunk_index) + f_ind, \ atom_A_ind, xyz[0, 0], xyz[0, 1], xyz[0, 2]]) self.coordenates = pd.DataFrame(coords) pickle.dump(coords, open("coordenates.p", "wb"), protocol=2) return self.coordenates
def afterMove(self, nca_context): """ This method is called at the end of the NCMC portion if the context needs to be checked or modified before performing the move at the halfway point. This function ensures the water is still within a sphere of self.radius at the end of the move. Parameters ---------- context: simtk.openmm.Context object Context containing the positions to be moved. Returns ------- context: simtk.openmm.Context object The same input context, but whose context were changed by this function. """ before_final_move_pos = nca_context.getState( getPositions=True).getPositions(asNumpy=True) # Update positions for distance calculation movePos_a = np.copy(before_final_move_pos) * before_final_move_pos.unit self.traj.xyz[0, :, :] = movePos_a pairs = self.traj.topology.select_pairs( np.array(self.atom_indices[0]).flatten(), np.array(self.protein_atoms).flatten()) water_distance = mdtraj.compute_distances(self.traj, pairs, periodic=True) # If the water is outside of the radius, reject the move if water_distance > np.linalg.norm(self.radius._value): nca_context._integrator.setGlobalVariableByName( "protocol_work", 999999) return nca_context
def get_atom_distances(traj): """ compute all atom distances for each frame in traj Parameters ---------- traj : mdtraj.Trajectory trajectory to analyze Returns ------- atom_distances : np.ndarray numpy array containing all atom distances atom_pairs : np.ndarray numpy array containing the atom pairs corresponding to each feature of atom_distances """ n_atoms = traj.n_atoms atom_pairs = np.array([(i, j) for i in xrange(n_atoms) for j in xrange(i + 1, n_atoms)]) atom_distances = md.compute_distances(traj, atom_pairs) return atom_distances, atom_pairs
def get_states_Vij(model,bounds): """ Load trajectory, state indicators, and contact energy """ traj = md.load("traj.xtc",top="Native.pdb") ## Loading from file takes most time. rij = md.compute_distances(traj,model.contacts-np.ones(model.contacts.shape),periodic=False) Q = np.loadtxt("Q.dat") ## To Do: Generalize to different reaction coordinates state_indicator = np.zeros(len(Q),int) ## Assign every frame a state label. State indicator is integer 1-N for N states. for state_num in range(len(bounds)-1): instate = (Q > bounds[state_num]).astype(int)*(Q <= bounds[state_num+1]).astype(int) state_indicator[instate == 1] = state_num+1 if any(state_indicator == 0): num_not_assign = sum((state_indicator == 0).astype(int)) print " Warning! %d frames were not assigned out of %d total frames!" % (num_not_assign,len(Q)) ## Boolean arrays that indicate which state each frame is in. ## States are defined by their boundaries along coordinate Q. U = ((Q > bounds[1]).astype(int)*(Q < bounds[2]).astype(int)).astype(bool) TS = ((Q > bounds[3]).astype(int)*(Q < bounds[4]).astype(int)).astype(bool) N = ((Q > bounds[5]).astype(int)*(Q < bounds[6]).astype(int)).astype(bool) Nframes = float(sum(N.astype(int))) Uframes = float(sum(U.astype(int))) TSframes = float(sum(TS.astype(int))) Vij = model.calculate_contact_potential(rij) return traj,U,TS,N,Uframes,TSframes,Nframes,Vij
def distance_matrix_semi_bin_loop(self, i): # Compute a semi-binary contact map. Residue pair within the cutoff (5 angstrom) is a contact. Outside, the "degree" of contact decreases with a gaussian (for smoothness). print(str(i + 1) + '/' + str(self.nResidues)) std_dev = 0.1667 # 1.667 angstrom standard deviation => gives 1e-5 weight at 0.8 nm. cutoff = 0.45 # within 4.5 angstrom, the weight is 1. # Compute normalizing factor cutoff_value = np.exp(-cutoff**2 / (2 * std_dev**2)) for j in range(i + 1, self.nResidues): atomInd1 = self.allInds[i] atomInd2 = self.allInds[j] atom_pairs = self.getAtomPairs(atomInd1, atomInd2) distances = md.compute_distances(self.traj, atom_pairs, periodic=False) minDistances = np.min(distances, axis=1) gaussians = np.exp(-minDistances**2 / (2 * std_dev**2)) / cutoff_value gaussians[minDistances < cutoff] = 1.0 if len(distances) == 0: print('The chosen residue does not exist!') # The distance between residues is min distance between all heavy atoms. Take mean over all frames. self.distanceMatrix[i, j] = np.mean(gaussians, axis=0) self.distanceMatrix[j, i] = np.mean(gaussians, axis=0) return
def contact_calpha(self, cutoff=0.5): """Compute the Capha contact map of the protein itself. Parameters ---------- cutoff : float, default = 0.5 nm The distance cutoff for contacts Returns ------- cmap : np.ndarray, shape = [N, N] The alphaC contact map, N is the number of residues """ # define pairs c_alpha_indices = self.top.select("name CA") print("Number of Calpha atoms ", c_alpha_indices.shape) pairs_ = list(itertools.product(c_alpha_indices, c_alpha_indices)) distance_matrix_ = mt.compute_distances(self.pdb, atom_pairs=pairs_)[0] distance_matrix_ = distance_matrix_.reshape((-1, c_alpha_indices.shape[0])) cmap = (distance_matrix_ <= cutoff)*1.0 return cmap
def filtered_candidate_pairs_by_chain(traj, cand_aromatic_dict, soft_cutoff_dist): filtered_candidate_pairs = {} pairKeys = [] atomPairs = [] tempDict = {} for k1 in cand_aromatic_dict.keys(): for k2 in cand_aromatic_dict.keys(): if(k1 != k2 and (k1, k2) not in tempDict and (k2, k1) not in tempDict): tempDict[(k1, k2)] = 1 aromatic1 = cand_aromatic_dict[k1] aromatic2 = cand_aromatic_dict[k2] generatePairKeys(pairKeys, atomPairs, k1, aromatic1, k2, aromatic2) # calculate atom pair distances atomPairs = np.array(atomPairs) pairDistances = md.compute_distances(traj, atomPairs) for time in range(len(pairDistances)): t_distances = pairDistances[time] for i in range(0, len(t_distances), 9): arom_arom_distances = t_distances[i:i+9] if(min(arom_arom_distances) <= soft_cutoff_dist): arom1_key = pairKeys[i][0][0] arom2_key = pairKeys[i][1][0] if(time not in filtered_candidate_pairs.keys()): filtered_candidate_pairs[time] = {arom1_key:[arom2_key]} else: if(arom1_key not in filtered_candidate_pairs[time].keys()): filtered_candidate_pairs[time][arom1_key] = [arom2_key] else: filtered_candidate_pairs[time][arom1_key].append(arom2_key) filtered_candidate_pairs = fillTimeGaps(range(len(pairDistances)), filtered_candidate_pairs) return filtered_candidate_pairs
def getInverseCalphaDistanceMatrix(self, traj, allInds): # Compute one C-alpha distance matrix. # - traj is a one-frame trajectory. # Construct the distance matrix [nResidues x nResidues] with the distance # between residues defined as the minimum distance between C_alphas of the two residues. nResidues = int(len(allInds)) distanceMatrix = np.zeros((nResidues, nResidues)) # Compute distance matrix for i in range(0, nResidues): for j in range(i + 1, nResidues): # Get all atom pairs atom_pairs = np.zeros((1, 2)) if len(allInds[i] != 0) and len(allInds[j] != 0): atom_pairs[0, 0] = allInds[i] atom_pairs[0, 1] = allInds[j] distances = md.compute_distances(traj, atom_pairs, periodic=False) if len(distances) == 0: print('The chosen residue does not exist!') # The distance between residues is min distance between all heavy atoms. # Take residual to get rid of cut-off. minDistance = np.min(distances, axis=1) distanceMatrix[i, j] = 1 / minDistance distanceMatrix[j, i] = 1 / minDistance return distanceMatrix
def test_equality_with_cgnet_distances(): # Make sure CA distances are consistent with GeometryFeature geom_feature = GeometryFeature(feature_tuples='all_backbone', n_beads=beads) out = geom_feature.forward(data_tensor) molecule = CGMolecule(names=names, resseq=resseq, resmap=resmap) traj = molecule.make_trajectory(data) # Calculate all pairs of CA distances CA_inds = [i for i, name in enumerate(names) if name == 'CA'] CA_pairs = [] # these are feature tuples for i, ind1 in enumerate(CA_inds[:-1]): for j, ind2 in enumerate(CA_inds[i + 1:]): CA_pairs.append((ind1, ind2)) mdtraj_CA_dists = md.compute_distances(traj, CA_pairs) # map each CA distance feature tuple to the integer index CA_feature_tuple_dict = { key: i for i, key in enumerate(geom_feature.descriptions['Distances']) if key in CA_pairs } # retrieve CA distances only from the feature object cgnet_CA_dists = geom_feature.distances.numpy( )[:, [CA_feature_tuple_dict[key] for key in CA_pairs]] np.testing.assert_allclose(mdtraj_CA_dists, cgnet_CA_dists, rtol=1e-6)
def load_data(self, fname, temperature): """ Load a data file and format for later use For Proteins, it uses the self.pairs to load the pair-pair distances for every frame. This is the data format that would be used for computing the energy later. Args: fname (string): Name of a file to load. temperature (float/np.ndarray): Temperature of this data set. Return: Array (floats): First index is frame, second index is the temperature followed by every pair in the order of pairs. *** BUG NOTE *** The results from hepsilon and dhepsilon function from get_potentials_epsilon will differ from the Protein method's results EVEN IF you use the same traj file. This is because mdtraj default output is numpy.float32, while the result of appending the temperature to the pair-distance output results in a numpy.float64. Comparison of the resultant data matrix would be exact suggesting there is no error. But when computing the potential energy using the model._pairs[i].dVdeps function will result in a different result, due to their differing precision on input. """ traj = md.load(fname, top=self.model.mapping.topology) data = md.compute_distances(traj, self.use_pairs, periodic=False) temperature = np.ones((np.shape(data)[0],1)) * temperature all_data = np.append(temperature, data, axis=1) return all_data
def get_rij_Vp(model): ''' Load trajectory, state indicators, and contact energy ''' #assumes you are in the directory with traj.xtc and Native.pdb time1 = time.time() traj = md.load("traj.xtc",top="Native.pdb") # Loading from file takes most time. time2 = time.time() print " Loading traj took: %.2f sec = %.2f min" % (time2-time1,(time2-time1)/60.) # rij is a matrix, where first index represents trajectory step, and the second index represents the different pairs time1 = time.time() rij = md.compute_distances(traj,model.pairs-np.ones(model.pairs.shape),periodic=False) time2 = time.time() print " Calculating rij took: %.2f sec = %.2f min" % (time2-time1,(time2-time1)/60.) # IS NOW GENERALIZED FOR FITTING SUBSET OF MODEL PARAMETERS time1 = time.time() Vp = np.zeros((traj.n_frames,model.n_fitting_params),float) print "**********************************" print model.n_fitting_params print "**********************************" for i in range(model.n_fitting_params): param_idx = model.fitting_params[i] # Loop over interactions that use this parameter for j in range(len(model.model_param_interactions[param_idx])): pair_idx = model.model_param_interactions[param_idx][j] Vp[:,i] = Vp[:,i] + model.pair_V[pair_idx](rij[:,pair_idx]) time2 = time.time() print " Calculating Vp took: %.2f sec = %.2f min" % (time2-time1,(time2-time1)/60.) return traj,rij,Vp
def _compute_distances(self, rep_id): """ Computes the interatomic distances for all pairs of atoms. Parameters ---------- rep_id : int ID number of the replica of interest. Returns ------- numpy.ndarray Interatomic distances for all specified atom pairs. Shape is (n_frames, n_pairs). Raises ------ IndexError If `rep_id` is not an index in `replica`. AssertionError If the trajectory associated with `rep_id` does not exist. AssertionError If the atom pairs have not been determined. """ if rep_id > len(self.replica) - 1: raise IndexError(str(rep_id) + " is outside of index range.") assert self.replica[rep_id]['traj'],\ "Trajectory does not exist." assert self._pairs, "Atom pairs not determined yet." return md.compute_distances(self.replica[rep_id]['traj'], self._pairs, periodic=self.pbc)
def _generate_direct_correlation(trj, cutoff=1.0): """ Generate direct correlation matrix from a COM-based mdtraj.Trajectory. Parameters ---------- trj : mdtraj.Trajectory Trajectory for which "atom" sites are to be considered cutoff : float, default = 0.8 Distance cutoff below which two sites are considered paired Returns ------- direct_corr : np.ndarray, dtype=np.int32 Direct correlation matrix """ size = trj.top.n_residues direct_corr = np.zeros((size, size), dtype=np.int32) for row in range(size): for col in range(size): if row == col: direct_corr[row, col] = 1 else: dist = md.compute_distances(trj, atom_pairs=[(row, col)]) if dist < cutoff: direct_corr[row, col] = 1 direct_corr[col, row] = 1 return direct_corr
def obs_function(trajchunk): r = md.compute_distances(trajchunk,pairs,periodic=periodic) Econtact = np.zeros(trajchunk.n_frames,float) for i in range(pairs.shape[0]): pair_Vi = get_pair_potential(pair_type[i]) Econtact += eps[i]*pair_Vi(r[:,i],*contact_params[i]) return Econtact
def transform(self, traj): """ Transform a trajectory into the OO features Parameters ---------- traj : mdtraj.Trajectory Returns ------- Xnew : np.ndarray sorted distances for each water molecule distances : np.ndarray distances between each water molecule """ oxygens = np.array([i for i in xrange(traj.n_atoms) if traj.top.atom(i).element.symbol == 'O']) hydrogens = np.array([i for i in xrange(traj.n_atoms) if traj.top.atom(i).element.symbol == 'H']) pairsOH = np.array([(i, j) for i in oxygens for j in hydrogens]) distances = md.compute_distances(traj, pairsOH) distances = distances.reshape((traj.n_frames, len(oxygens), len(hydrogens))) Xnew = copy.copy(distances) Xnew.sort() distances = get_square_distances(traj, oxygens) if not self.n_waters is None: Xnew = Xnew[:, :, :(2 * self.n_waters)] return Xnew, distances
def test_no_indices(): for fn in ['2EQQ.pdb', '1bpi.pdb']: for opt in [True, False]: t = md.load(get_fn(fn)) assert md.compute_distances(t, np.zeros((0,2), dtype=int), opt=opt).shape == (t.n_frames, 0) assert md.compute_angles(t, np.zeros((0,3), dtype=int), opt=opt).shape == (t.n_frames, 0) assert md.compute_dihedrals(t, np.zeros((0,4), dtype=int), opt=opt).shape == (t.n_frames, 0)
def get_square_distances(traj, aind=None): """ The the atom distances in for a subset of a trajectory and return it as a square distance matrix Parameters ---------- traj : mdtraj.Trajectory trajectory object aind : np.ndarray, optional atom indices to compute distances between Returns ------- distances : np.ndarray, shape = [traj.n_frames, aind.shape[0], aind.shape[0]] distances between the atoms in aind """ if aind is None: aind = np.arange(traj.n_atoms) pairs_ind = np.array([(i, j) for i in xrange(len(aind)) for j in xrange(i + 1, len(aind))]) pairs = np.array([(aind[i], aind[j]) for i, j in pairs_ind]) distances = md.compute_distances(traj, pairs) distances = md.geometry.squareform(distances, pairs_ind) return distances
def calculate_debye_energy(self, traj, total=True): """Calculate the one-body burial potential Parameters ---------- traj : mdtraj.Trajectory Trajectory to calculate energy over. sum : opt, bool If true (default) return the sum of the burial potentials. If false, return the burial energy of each individual residue. """ debye = self.potential_forms["DEBYE"] bb_traj = self.backbone_mapping.map_traj(traj) r = md.compute_distances(bb_traj, self._debye_pairs) if total: Vdebye = np.zeros(bb_traj.n_frames, float) else: Vdebye = np.zeros((bb_traj.n_frames, self.n_debye_pairs), float) for i in range(self.n_debye_pairs): qi = self._debye_charges[i, 0] qj = self._debye_charges[i, 1] kij = self._debye_kij[i] if total: Vdebye += debye.V(r[:, i], qi, qj, kij) else: Vdebye[:, i] = debye.V(r[:, i], qi, qj, kij) return Vdebye
def max_atom_distance(file_or_trajectory): trajectory = _traj_from_file_or_traj(file_or_trajectory) positions = trajectory.xyz[0] hull = scipy.spatial.ConvexHull(positions) atom_pairs = list(itertools.combinations(hull.vertices, 2)) distances = md.compute_distances(trajectory, atom_pairs)[0] return distances.max()
def parse_pdb(pdb_fname, base_fname=None): """Returns a graph object with available connectivity information""" trj = md.load(pdb_fname).center_coordinates() G = make_bondgraph(trj.top) connect_dict = get_pdb_connect_dict(pdb_fname) if len(connect_dict) != trj.top.n_atoms: raise ValueError( f"Error reading {pdb_fname}. Connect dict ({len(connect_dict)}) != {trj.top.n_atoms} atoms" ) connect_dict = {trj.top.atom(k): v for k, v in connect_dict.items()} nx.set_node_attributes(G, connect_dict, "connect") xyz_dict = {atom: xyz for atom, xyz in zip(trj.top.atoms, trj.xyz[0])} nx.set_node_attributes(G, xyz_dict, "xyz") if base_fname is not None: G_base = parse_pdb(pdb_fname=base_fname, base_fname=None) mapping = subgraph_match(G, G_base)[0] base_connect = { k: G_base.nodes[v]["connect"] for k, v in mapping.items() } nx.set_node_attributes(G, base_connect, "connect") edge_idxs = np.empty(shape=(G.number_of_edges(), 2), dtype=np.int) for i, edge in enumerate(G.edges): edge_idxs[i] = edge[0].index, edge[1].index edge_distances = md.compute_distances(trj, edge_idxs)[0] distance_dict = {edge: dis for edge, dis in zip(G.edges, edge_distances)} nx.set_edge_attributes(G, distance_dict, "distance") return G
def map(self, traj): dists = mdtraj.compute_distances( traj, self.distance_indexes, periodic=self.periodic) res = np.zeros( (len(traj), self.distance_indexes.shape[0]), dtype=np.float32) I = np.argwhere(dists <= self.threshold) res[I[:, 0], I[:, 1]] = 1.0 return res
def get_rij_Vij(model): """ Load trajectory, state indicators, and contact energy """ traj = md.load("traj.xtc",top="Native.pdb") ## Loading from file takes most time. rij = md.compute_distances(traj,model.contacts-np.ones(model.contacts.shape),periodic=False) Vij = model.calculate_contact_potential(rij) return traj,rij,Vij
def map(self,traj): from model_builder.models.pairwise_potentials import get_pair_potential r = mdtraj.compute_distances(traj, self.pairs, periodic=self.periodic) Epair = np.zeros((traj.n_frames, self.dimension), float) for i in range(self.pairs.shape[0]): Vi = get_pair_potential(self.pair_type[i]) Epair[:,0] += self.eps[i]*Vi(r[:,i],*self.pair_params[i]) return Epair
def extract_neighbors(chunk, pairs, n_nearest, n_A, n_B): cutoff = 0.52 # nanometers # Adapted from Ondrej distances = md.compute_distances(chunk, pairs, opt=True).reshape((-1, n_B, n_A)) # structure is: idx_nearest[i_frame][i_B][i_neighbor] idx_nearest = [[np.where(distances[i_frame,iB,:] < cutoff)[0] for iB in range(n_B)] for i_frame in range(len(chunk))] return distances, idx_nearest
def calculate_average_Jacobian(model,fitopts, FRET_pairs=def_FRET_pairs, spacing=defspacing ): """ Calculate the average feature vector (ddG's) and Jacobian """ if "t_fit" in fitopts: fit_temp = fitopts["t_fit"] else: raise IOError("Missing the fit_temperature, please specify in .ini file") if "fret_pairs" in fitopts: fret_pairs = fitopts["fret_pairs"] FRET_pairs = np.array(fret_pairs) - 1 print "The FRET pairs are:" print FRET_pairs if "spacing" in fitopts: spacing = fitopts["spacing"] ##Define location of logical files cwd = os.getcwd() subdir = model.name iteration = fitopts["iteration"] sub = "%s/%s/iteration_%d" % (cwd,subdir,iteration) traj_location = "%s/%d_0" % (sub, fit_temp) sim_location = "%s/fitting_%d" % (sub,iteration) ##define location of logical files os.chdir(traj_location) ## Get trajectory, state indicators, contact energy print "Working on calculating model's trajectory and contact info" traj,rij,qij = get_rij_Vp(model) ## Get simulation feature print "Now working on calculating the trajectories" FRETr = md.compute_distances(traj,residues, periodic=False) sim_feature, sim_slices = calc_sim_bins(sim_location, FRETr, fit_temp, residues=FRET_pairs, spacing=spacing, weights=None) beta = 1.0 * (GAS_CONSTANT_KJ_MOL*float(fit_temp)) #save the temperature this was done in if not os.path.isdir("%s/newton"%sub): os.mkdir("%s/newton"%sub) f = open("%s/newton/temp-used-here.txt"%sub, "w") f.write(str(fit_temp)) f.close() os.chdir(cwd) print "Computing Jacobian and Simparams for the temperature %d, with spacing %f" % (fit_temp, spacing) Jacobian = compute_Jacobian_basic(qij,sim_feature, sim_slices, beta) sim_feature_err = sim_feature ** 0.5 Jacobian_err = np.zeros(np.shape(Jacobian)) return sim_feature, sim_feature_err, Jacobian, Jacobian_err
def compute_residue_distance(trj, residues1, residues2, periodic=True, opt=True, verbose=False): distance_min = np.zeros([len(residues1), len(residues2), trj.n_frames]) distance_mean = np.zeros([len(residues1), len(residues2), trj.n_frames]) distance_sc_min = np.zeros([len(residues1), len(residues2), trj.n_frames]) distance_sc_mean = np.zeros([len(residues1), len(residues2), trj.n_frames]) for i, res1 in enumerate(residues1): for j, res2 in enumerate(residues2): distance = md.compute_distances(trj, itertools.product(res1.atom_indices, res2.atom_indices), periodic=periodic, opt=opt) distance_sc = md.compute_distances(trj, itertools.product(res1.sidechain_indices, res2.sidechain_indices), periodic=periodic, opt=opt) distance_min [i,j,:] = distance.min(1) distance_mean [i,j,:] = distance.mean(1) distance_sc_min [i,j,:] = distance_sc.min(1) distance_sc_mean[i,j,:] = distance_sc.mean(1) return distance_min, distance_mean, distance_sc_min, distance_sc_mean
def calculate_water_energy(self, traj, local_density=None, total=True, split=False, dgamma=False): """Calculate the one-body burial potential Parameters ---------- traj : mdtraj.Trajectory Trajectory to calculate energy over. total : opt, bool If true (default) return the sum of the burial potentials. If false, return the burial energy of each individual residue. split : opt, bool If False (default) do nothing. If True, return individual energy values for water term and protein term. dgamma : opt, bool If split, then it returns the individual dgamma values """ water = self.potential_forms["WATER"] bb_traj = self.backbone_mapping.map_traj(traj) r = md.compute_distances(bb_traj, self._contact_pairs) if local_density is None: res_local_density = self._calculate_local_density(bb_traj) else: res_local_density = local_density if total: Vwater = np.zeros(bb_traj.n_frames, float) else: Vwater = np.zeros((bb_traj.n_frames, self.n_pairs), float) if split: split_water = np.zeros((bb_traj.n_frames, self.n_pairs), float) split_protein = np.zeros((bb_traj.n_frames, self.n_pairs), float) for i in range(self.n_pairs): rhoi = res_local_density[:,self._contact_res_idxs[i,0]] rhoj = res_local_density[:,self._contact_res_idxs[i,1]] gamma_water = self.gamma_water[self._contact_gamma_idxs[i,0], self._contact_gamma_idxs[i,1]] gamma_protein = self.gamma_protein[self._contact_gamma_idxs[i,0], self._contact_gamma_idxs[i,1]] if not split: if total: Vwater += water.V(r[:,i], rhoi, rhoj, gamma_water, gamma_protein) else: Vwater[:,i] = water.V(r[:,i], rhoi, rhoj, gamma_water, gamma_protein) else: if dgamma: split_water[:,i] = -water.lambda_water * water.dVdgamma_water(r[:,i], rhoi, rhoj) split_protein[:,i] = -water.lambda_water * water.dVdgamma_protein(r[:,i], rhoi, rhoj) else: split_water[:,i] = -water.lambda_water * gamma_water * water.dVdgamma_water(r[:,i], rhoi, rhoj) split_protein[:,i] = -water.lambda_water * gamma_protein * water.dVdgamma_protein(r[:,i], rhoi, rhoj) if split: return split_water, split_protein else: return Vwater
def _run_amber_traj(trajname, ext_ref): # Test triclinic case where simple approach in Tuckerman text does not # always work traj = md.load(get_fn(trajname), top=get_fn("test.parm7")) distopt = md.compute_distances(traj, [[0, 9999]], opt=True) distslw = md.compute_distances(traj, [[0, 9999]], opt=False) dispopt = md.compute_displacements(traj, [[0, 9999]], opt=True) dispslw = md.compute_displacements(traj, [[0, 9999]], opt=False) eq(distopt, distslw, decimal=5) eq(dispopt, dispslw, decimal=5) assert_allclose(distopt.flatten(), ext_ref, atol=2e-5) # Make sure distances from displacements are the same eq(np.sqrt((dispopt.squeeze() ** 2).sum(axis=1)), distopt.squeeze()) eq(np.sqrt((dispslw.squeeze() ** 2).sum(axis=1)), distslw.squeeze()) eq(dispopt, dispslw, decimal=5)
def compute_neighbors_reference(traj, cutoff, query_indices, haystack_indices=None): if haystack_indices is None: haystack_indices = range(traj.n_atoms) # explicitly enumerate the pairs of query-haystack indices we need to # check pairs = np.array([(q, i) for i in haystack_indices for q in query_indices if i != q]) dists = md.compute_distances(traj, pairs) # some of the haystack might be within cutoff of more than one of the # query atoms, so we need unique reference = [np.unique(pairs[dists[i]< cutoff, 1]) for i in range(traj.n_frames)] return reference
def transform(self, traj): # compute dihedral energy phi = md.compute_dihedrals(traj, self.dihedrals) Edih = np.array(map(lambda x,y: x(y), self.Vdih, phi.T)).T # compute pair energy r = md.compute_distances(traj, self.pairs) Epair = np.array(map(lambda x,y: x(y), self.Vpair, r.T)).T return np.hstack((Edih, Epair))
def distance_space(traj, top=None, pairs=None): """Convert a trajectory (or traj list) to distance space By default, this will compute ALL pair-wise distances and return a vector (or list of vectors if list of trajectories is provided) If a NDarray of conformations is passed, the associated topology must be provided to recreate the trajectory """ if isinstance(traj, np.ndarray): if top is None: logging.error("Cannot calculate distances from NDArray. Topology is needed.") return None else: traj = md.Trajectory(traj, top) if isinstance(traj, list): if pairs is None: pairs = get_pairlist(traj[0]) return [md.compute_distances(k,pairs) for k in traj] else: if pairs is None: pairs = get_pairlist(traj) return md.compute_distances(traj,pairs)
def add_fragment_memory(self, traj, protein_index, frag_index, length, weight): #construct list of atoms from the fragment index fragment_top = traj.top fragment_atom_list = [] for idx in np.arange(frag_index, frag_index+length): for atom in fragment_top.residue(idx).atoms: if atom.name in ["CA", "CB"]: fragment_atom_list.append(atom) protein_top = self.three_bead_topology #traj files write three beads protein_atom_list = [] for idx in np.arange(protein_index, protein_index+length): for atom in protein_top.residue(idx).atoms: if atom.name in ["CA", "CB"]: protein_atom_list.append(atom) #check the lists, make sure the sequences match assert len(protein_atom_list) == len(fragment_atom_list) #generate a list of pairs of atoms and indices fragment_atom_pairs = [] distance_pairs = [] protein_atom_pairs = [] num_atoms = len(fragment_atom_list) for idx in range(num_atoms): frag_atm1 = fragment_atom_list[idx] prot_atm1 = protein_atom_list[idx] for jdx in np.arange(idx+1, num_atoms): frag_atm2 = fragment_atom_list[jdx] prot_atm2 = protein_atom_list[jdx] #only add pairs separated by two residues separation = frag_atm1.residue.index-frag_atm2.residue.index if np.abs(separation) > 2: fragment_atom_pairs.append([frag_atm1, frag_atm2]) protein_atom_pairs.append([prot_atm1, prot_atm2]) distance_pairs.append([frag_atm1.index,frag_atm2.index]) else: pass #compute distances if np.shape(distance_pairs)[0] == 0: raise IOError("No Distance Pairs found!") distances = md.compute_distances(traj, distance_pairs, periodic=False) distances = distances.transpose()[:,0] * 10.#reform to NX1 array #add to the Hamiltonian, each fragment term to a list fragment = awsem.AWSEM_POTENTIALS["FRAGMENT"](protein_atom_pairs, distances, weight=weight) try: self.fragment_potentials.append(fragment) except AttributeError: self.fragment_potentials = [fragment]
def calculate_helix_energy(self, traj, local_density=None, total=True): """Calculate the one-body burial potential Parameters ---------- traj : mdtraj.Trajectory Trajectory to calculate energy over. local_density : np.ndarray (traj.n_frames, traj.n_residues) Local protein density around each residue for all frames in traj. sum : opt, bool If true (default) return the sum of the burial potentials. If false, return the burial energy of each individual residue. """ helix = self.potential_forms["HELIX"] bb_traj = self.backbone_mapping.map_traj(traj) r_ON = md.compute_distances(bb_traj, self._helix_ON_pairs) r_OH = md.compute_distances(bb_traj, self._helix_OH_pairs) if local_density is None: res_local_density = self._calculate_local_density(bb_traj) else: res_local_density = local_density if total: Vhelix = np.zeros(bb_traj.n_frames, float) else: Vhelix = np.zeros((bb_traj.n_frames, self.n_alpha_helix), float) for i in range(self.n_alpha_helix): rhoi = res_local_density[:,self._helix_res_idxs[i,0]] rhoi_4 = res_local_density[:,self._helix_res_idxs[i,1]] fai = self._helix_fai[i] fai_4 = self._helix_fai_4[i] if total: Vhelix += helix.V(r_ON[:,i], r_OH[:,i], rhoi, rhoi_4, fai, fai_4) else: Vhelix[:, i] = helix.V(r_ON[:,i], r_OH[:,i], rhoi, rhoi_4, fai, fai_4) return Vhelix