# Sorting the element in a PDB text file

I am a new user of Mathematica and currently using version 9. I want to rearrange the element of one PDB text file with respect to another PDB text file. Suppose I have a PDB file like this:

HETATM    1   C1 UNK     0      14.406  17.458  -0.592  1.00  0.00           C
HETATM    2   H1 UNK     0      15.490  17.698  -0.832  1.00  0.00           H
HETATM    3   C2 UNK     0      13.604  17.656  -1.892  1.00  0.00           C
HETATM    4   H2 UNK     0      14.009  16.956  -2.694  1.00  0.00           H
HETATM    5   H3 UNK     0      13.710  18.738  -2.241  1.00  0.00           H
HETATM    6   H4 UNK     0      12.506  17.420  -1.717  1.00  0.00           H
HETATM    7   C3 UNK     0      13.987  18.450   0.505  1.00  0.00           C
HETATM    8   O1 UNK     0      14.203  19.812  -0.103  1.00  0.00           O
HETATM    9   H5 UNK     0      12.905  18.324   0.828  1.00  0.00           H
HETATM   10   H6 UNK     0      14.669  18.317   1.409  1.00  0.00           H


Now I want to rearrange the above file with respect to the following file:

HETATM    1   H2 UNK     0      14.009  16.956  -2.694  1.00  0.00           H
HETATM    2   H1 UNK     0      15.490  17.698  -0.832  1.00  0.00           H
HETATM    3   C3 UNK     0      13.987  18.450   0.505  1.00  0.00           C
HETATM    4   H6 UNK     0      14.669  18.317   1.409  1.00  0.00           H
HETATM    5   H3 UNK     0      13.710  18.738  -2.241  1.00  0.00           H
HETATM    6   O1 UNK     0      14.203  19.812  -0.103  1.00  0.00           O
HETATM    7   C2 UNK     0      13.604  17.656  -1.892  1.00  0.00           C
HETATM    8   C1 UNK     0      14.406  17.458  -0.592  1.00  0.00           C
HETATM    9   H5 UNK     0      12.905  18.324   0.828  1.00  0.00           H
HETATM   10   H4 UNK     0      12.506  17.420  -1.717  1.00  0.00           H


-
You have to be a more precise about the type of rearrangement you want. The examples you provide leave us guessing what to do. – Sjoerd C. de Vries Apr 17 '13 at 5:06

I don't know if you wish to renumber your lines sequentially or not. I also don't know if lines are certain to be unique. I will have to make assumptions.

You first need to read your tables into Mathematica. This can be done with Import, though you should also look at ReadList for maximum performance.

I will call the tables t1 and t2:

{t1, t2} = Import /@ {"file1.txt", "file2.txt"};


A quite general approach is to create a look-up table with the position of each element in t2. I don't know if you will need to match on all fields after the third one, or if it is sufficient to match on the third field (column) only. I shall assume all fields after the third, and use the Part specification 3 ;;. This look-up table is in the form of replacement rules, optimized with Dispatch:

rls = Dispatch @ MapIndexed[Rule, t2[[All, 3 ;;]]];


We can apply it like this (note matching Part spec; Grid is only for display):

SortBy[t1, #[[3 ;;]] /. rls &] // Grid


$\begin{array}{ccccccccccc} \text{HETATM} & 4 & \text{H2} & \text{UNK} & 0 & 14.009 & 16.956 & -2.694 & 1. & 0. & H \\ \text{HETATM} & 2 & \text{H1} & \text{UNK} & 0 & 15.49 & 17.698 & -0.832 & 1. & 0. & H \\ \text{HETATM} & 7 & \text{C3} & \text{UNK} & 0 & 13.987 & 18.45 & 0.505 & 1. & 0. & C \\ \text{HETATM} & 10 & \text{H6} & \text{UNK} & 0 & 14.669 & 18.317 & 1.409 & 1. & 0. & H \\ \text{HETATM} & 5 & \text{H3} & \text{UNK} & 0 & 13.71 & 18.738 & -2.241 & 1. & 0. & H \\ \text{HETATM} & 8 & \text{O1} & \text{UNK} & 0 & 14.203 & 19.812 & -0.103 & 1. & 0. & O \\ \text{HETATM} & 3 & \text{C2} & \text{UNK} & 0 & 13.604 & 17.656 & -1.892 & 1. & 0. & C \\ \text{HETATM} & 1 & \text{C1} & \text{UNK} & 0 & 14.406 & 17.458 & -0.592 & 1. & 0. & C \\ \text{HETATM} & 9 & \text{H5} & \text{UNK} & 0 & 12.905 & 18.324 & 0.828 & 1. & 0. & H \\ \text{HETATM} & 6 & \text{H4} & \text{UNK} & 0 & 12.506 & 17.42 & -1.717 & 1. & 0. & H \end{array}$

If you wish to fix columns one and two and only change the following columns you could do that like this:

t3 = t1;

t3[[All, 3 ;;]] = SortBy[t3[[All, 3 ;;]], # /. rls &];

t3 // Grid


Another method that is fast, but perhaps hard to follow is this:

ords = Ordering @ #[[All, 3 ;;]] & /@ {t1, t2};

t1[[ #[[Ordering @ #2]] ]] & @@ ords // Grid

-
Thanks a lot. Actually I want to fix first two column. How will i save the edited file into PDB format? – Sushanta Apr 17 '13 at 19:52
@Sushanta support for that format is described here. What have you tried and where are you running into trouble? – Mr.Wizard Apr 17 '13 at 20:52
@Mr.Wizard the lines are certain to be unique, since these files represent molecular structures, and one cannot meaningfully have two identical atoms on top of each other. – Oleksandr R. Jun 16 '13 at 1:19
@Oleksandr Good to know, but probably a bit late to be helpful this time. :^) – Mr.Wizard Jun 16 '13 at 20:17