Beispiel #1
0
        // process a structure
        public double CalculateChi2(ref FilteringResult fr)
        {
            Molecule m;

            if (fr.MoleculeWeakReference == null || !fr.MoleculeWeakReference.TryGetTarget(out m))
            {
                m = new Molecule(fr.FullFileName);
            }
            fr.MoleculeWeakReference = new WeakReference <Molecule>(m);
            if (m.Error.Length > 0)
            {
                System.Windows.Forms.MessageBox.Show("Error reading file " + fr.FullFileName + ": " + m.Error, "Error",
                                                     System.Windows.Forms.MessageBoxButtons.OK, System.Windows.Forms.MessageBoxIcon.Error);
                return(MiscData.ENotCalculated);
            }
            AVEngine         av = new AVEngine(m, avparam);
            Int32            natom, ilp = 0, ilp1, ilp2, iref, nref_total = 0;
            List <Vector3[]> avcache = new List <Vector3[]>(labelingpos.Count);

            Vector3[]     t;
            Vector3[]     rmp = new Vector3[labelingpos.Count];
            Vector3       cr, cm; Matrix3 U;
            ReferenceAtom rr;
            Double        R06 = _filterParameters.R0 * _filterParameters.R0 * _filterParameters.R0 *
                                _filterParameters.R0 * _filterParameters.R0 * _filterParameters.R0,
                          dr, refrmsd_t = 0.0;

            fr.E        = 0.0;
            fr.InvalidR = 0;
            fr.RefRMSD  = 0.0;
            fr.Sigma1   = 0;
            fr.Sigma2   = 0;
            fr.Sigma3   = 0;

            foreach (LabelingPosition l in this.labelingpos)
            {
                // calculate AVs and mean positions
                if (l.AVData.AVType == AVSimlationType.SingleDyeR)
                {
                    natom = Array.BinarySearch <Int32>(m.OriginalAtomID, l.AVData.AtomID);
                    av.Calculate1R(l.AVData.L, l.AVData.W, l.AVData.R, natom);
                    t = new Vector3[av.R.Length];
                    Array.Copy(av.R, t, av.R.Length);
                    avcache.Add(t);
                    rmp[ilp++] = av.Rmp;
                }
                else if (l.AVData.AVType == AVSimlationType.ThreeDyeR)
                {
                    natom = Array.BinarySearch <Int32>(m.OriginalAtomID, l.AVData.AtomID);
                    av.Calculate3R(l.AVData.L, l.AVData.W, l.AVData.R1, l.AVData.R2, l.AVData.R3, natom);
                    t = new Vector3[av.R.Length];
                    Array.Copy(av.R, t, av.R.Length);
                    avcache.Add(t);
                    rmp[ilp++] = av.Rmp;
                }
                else if (l.AVData.AVType == AVSimlationType.None && referenceAtoms[ilp].Length > 0)
                {
                    // align reference atoms with the structure
                    // translation
                    cr = new Vector3();
                    cm = new Vector3();
                    for (iref = 0; iref < referenceAtoms[ilp].Length; iref++)
                    {
                        rr    = referenceAtoms[ilp][iref];
                        natom = rr.ConvertedN;
                        cr   += rr;
                        cm   += new Vector3(m.XLocal[natom] + m.CM.X, m.YLocal[natom] + m.CM.Y, m.ZLocal[natom] + m.CM.Z);
                    }
                    cr *= -1.0 / ((Double)referenceAtoms[ilp].Length);
                    cm *= -1.0 / ((Double)referenceAtoms[ilp].Length);

                    // rotation: see also SimulationResult.CalculateBestFitRotation
                    Mapack.Matrix Rxt = new Mapack.Matrix(referenceAtoms[ilp].Length, 3);
                    Mapack.Matrix Ry  = new Mapack.Matrix(3, referenceAtoms[ilp].Length);

                    for (iref = 0; iref < referenceAtoms[ilp].Length; iref++)
                    {
                        rr           = referenceAtoms[ilp][iref];
                        natom        = rr.ConvertedN;
                        Rxt[iref, 0] = rr.X + cr.X; Rxt[iref, 1] = rr.Y + cr.Y; Rxt[iref, 2] = rr.Z + cr.Z;
                        Ry[0, iref]  = m.XLocal[natom] + m.CM.X + cm.X;
                        Ry[1, iref]  = m.YLocal[natom] + m.CM.Y + cm.Y;
                        Ry[2, iref]  = m.ZLocal[natom] + m.CM.Z + cm.Z;
                    }

                    // Kabsch solution
                    Mapack.Matrix R = Ry * Rxt;
                    Mapack.SingularValueDecomposition svdR = new Mapack.SingularValueDecomposition(R);
                    Mapack.Matrix V  = svdR.VMatrix;
                    Mapack.Matrix rS = new Mapack.Matrix(3, 3);
                    rS[0, 0] = 1.0 / svdR.Diagonal[0];
                    rS[1, 1] = 1.0 / svdR.Diagonal[1];
                    rS[2, 2] = (R.Determinant > 0.0) ? 1.0 / svdR.Diagonal[2] : -1.0 / svdR.Diagonal[2];
                    Mapack.Matrix Um = R * V * rS * V.Transpose();
                    U = new Matrix3(Um[0, 0], Um[0, 1], Um[0, 2],
                                    Um[1, 0], Um[1, 1], Um[1, 2], Um[2, 0], Um[2, 1], Um[2, 2]);
                    U = Matrix3.RepairRotation(U);

                    // reference rmsd
                    for (iref = 0; iref < referenceAtoms[ilp].Length; iref++)
                    {
                        rr         = referenceAtoms[ilp][iref];
                        natom      = rr.ConvertedN;
                        refrmsd_t += Vector3.SquareNormDiff(U * (rr + cr),
                                                            new Vector3(m.XLocal[natom], m.YLocal[natom], m.ZLocal[natom]) + m.CM + cm);
                        nref_total++;
                    }

                    rmp[ilp++] = U * (l + cr) - cm;
                    avcache.Add(new Vector3[0]);
                }
                else
                {
                    rmp[ilp++] = l;
                    avcache.Add(new Vector3[0]);
                }
            }

            // calculate mp and FRET distances
            Distance d, dmp;
            Int32    activeR = 0;

            fr.RModel            = new DistanceList(dist.Count);
            fr.RmpModel          = new DistanceList(dist.Count);
            fr.RmpModel.DataType = dist.DataType;
            for (Int32 i = 0; i < dist.Count; i++)
            {
                dmp           = new Distance();
                d             = new Distance();
                dmp.Position1 = dist[i].Position1;
                dmp.Position2 = dist[i].Position2;
                d.Position1   = dist[i].Position1;
                d.Position2   = dist[i].Position2;
                ilp1          = labelingpos.FindIndex(d.Position1);
                ilp2          = labelingpos.FindIndex(d.Position2);
                dmp.R         = Vector3.Abs(rmp[ilp1] - rmp[ilp2]);
                if (dist.DataType == DistanceDataType.Rmp ||
                    labelingpos[ilp1].AVData.AVType == AVSimlationType.None || labelingpos[ilp2].AVData.AVType == AVSimlationType.None)
                {
                    d.R = dmp.R; // i.e. no clouds -> Rmp
                }
                else if (dist.DataType == DistanceDataType.RDAMeanE)
                {
                    if (avcache[ilp1].Length == 0 || avcache[ilp2].Length == 0)
                    {
                        d.R = Double.NaN;
                    }
                    else
                    {
                        d.R = FpsNativeWrapper.RdaMeanEFromAv(avcache[ilp1], avcache[ilp1].Length, avcache[ilp2], avcache[ilp2].Length,
                                                              avparam.ESamples, rnd.Next(), this._filterParameters.R0);
                    }
                }
                else if (dist.DataType == DistanceDataType.RDAMean)
                {
                    if (avcache[ilp1].Length == 0 || avcache[ilp2].Length == 0)
                    {
                        d.R = Double.NaN;
                    }
                    else
                    {
                        d.R = FpsNativeWrapper.RdaMeanFromAv(avcache[ilp1], avcache[ilp1].Length, avcache[ilp2], avcache[ilp2].Length,
                                                             avparam.ESamples, rnd.Next());
                    }
                }

                fr.RModel.Add(d);
                fr.RmpModel.Add(dmp);

                dr = d.R - dist[i].R;
                if (Double.IsNaN(d.R))
                {
                    fr.InvalidR++;
                }
                else if (!this._filterParameters.OptimizeSelected || dist[i].IsSelected)
                {
                    fr.E += dr > 0.0 ? dr * dr / dist[i].ErrPlus / dist[i].ErrPlus :
                            dr * dr / dist[i].ErrMinus / dist[i].ErrMinus;
                    activeR++;
                    if (dr > dist[i].ErrPlus)
                    {
                        fr.Sigma1++;
                    }
                    if (dr > 2.0 * dist[i].ErrPlus)
                    {
                        fr.Sigma2++;
                    }
                    if (dr > 3.0 * dist[i].ErrPlus)
                    {
                        fr.Sigma3++;
                    }
                    if (dr < -dist[i].ErrMinus)
                    {
                        fr.Sigma1++;
                    }
                    if (dr < -2.0 * dist[i].ErrMinus)
                    {
                        fr.Sigma2++;
                    }
                    if (dr < -3.0 * dist[i].ErrMinus)
                    {
                        fr.Sigma3++;
                    }
                }
            }

            fr.E       = fr.E / (Double)activeR;
            fr.RefRMSD = nref_total == 0 ? 0.0 : Math.Sqrt(refrmsd_t / (Double)nref_total);
            return(fr.E);
        }
Beispiel #2
0
        // two molecules
        private Boolean CheckForClashes(int im1, int im2)
        {
            Molecule m1 = _molecules[im1];
            Molecule m2 = _molecules[im2];
            Vector3  dcm = translation[im1] - translation[im2], rc1, rc2;

            // check clusters
            Vector3[]   rc2cache = new Vector3[m2.AtomClusters.Length];
            double      sumr, dsq, dx2, dy2, dz2;
            Vector3     sumrv;
            AtomCluster c1, c2;
            Matrix3     rot1to2 = Matrix3.Transpose(rotation[im2]) * rotation[im1];
            Matrix3     rot2to1 = Matrix3.Transpose(rot1to2);
            Vector3     dcm1t   = Matrix3.Transpose(rotation[im1]) * dcm;
            Vector3     dcm2t   = Matrix3.Transpose(rotation[im2]) * dcm;

            int[] c2tocheck = new int[m2.AtomClusters.Length];
            int   j2, n2tocheck;

            int[] mustbechecked1 = new int[m1.AtomClusters.Length];
            int[] mustbechecked2 = new int[m2.AtomClusters.Length];

            // check if we can skip some of m2
            n2tocheck = 0;
            for (int j = 0; j < m2.AtomClusters.Length; j++)
            {
                c2    = m2.AtomClusters[j];
                rc2   = rot2to1 * c2 - dcm1t;
                dx2   = rc2.X * rc2.X;
                dy2   = rc2.Y * rc2.Y;
                dz2   = rc2.Z * rc2.Z;
                sumrv = m1.MaxRadius + c2.ClusterRadius;
                if ((dy2 + dz2 <= sumrv.X * sumrv.X) && (dx2 + dz2 <= sumrv.Y * sumrv.Y) && (dx2 + dy2 <= sumrv.Z * sumrv.Z))
                {
                    rc2cache[n2tocheck]    = c2;
                    c2tocheck[n2tocheck++] = j;
                }
            }

            for (int i = 0; i < m1.AtomClusters.Length; i++)
            {
                c1  = m1.AtomClusters[i];
                rc1 = rot1to2 * c1 + dcm2t;
                // if completely out of reach, skip the check
                dx2   = rc1.X * rc1.X;
                dy2   = rc1.Y * rc1.Y;
                dz2   = rc1.Z * rc1.Z;
                sumrv = m2.MaxRadius + c1.ClusterRadius;
                if ((dy2 + dz2 > sumrv.X * sumrv.X) || (dx2 + dz2 > sumrv.Y * sumrv.Y) || (dx2 + dy2 > sumrv.Z * sumrv.Z))
                {
                    continue;
                }
                // otherwise check selected clusters from m2
                for (int j = 0; j < n2tocheck; j++)
                {
                    j2   = c2tocheck[j];
                    rc2  = rc2cache[j];
                    c2   = m2.AtomClusters[j2];
                    dsq  = Vector3.SquareNormDiff(rc1, rc2);
                    sumr = c1.ClusterRadius + c2.ClusterRadius;
                    if (dsq < sumr * sumr) // clusters overlap, check all atoms
                    {
                        mustbechecked1[i]  = 1;
                        mustbechecked2[j2] = 1;
                        // clash |= CheckForClashes(c1, c2, im1, im2, dcm); // => replaced with unmanaged
                    }
                }
            }

            // this runs in m1's coordinate system!
            Vector3 fclash = new Vector3(), tclash1 = new Vector3(), tclash2 = new Vector3();
            double  dEClash = FpsNativeWrapper.CheckForClashes(FpsNativeWrapper.Aligned16(m1.XYZvdwRVectorArray),
                                                               FpsNativeWrapper.Aligned16(m2.XYZvdwRVectorArray), m1.AtomClusters, m2.AtomClusters,
                                                               m1.AtomClusters.Length, m2.AtomClusters.Length, mustbechecked1, mustbechecked2,
                                                               rot2to1, -dcm1t, kclash, ref fclash, ref tclash1, ref tclash2);

            force[im1]  += rotation[im1] * fclash;
            force[im2]  -= rotation[im1] * fclash;
            torque[im1] += rotation[im1] * tclash1;
            torque[im2] += rotation[im1] * tclash2;
            Eclash      += dEClash;

            return(dEClash > 1.0e-8);
        }
Beispiel #3
0
        /// <summary>
        /// Read reference atoms from an LP file
        /// </summary>
        /// <param name="m">Example molecule</param>
        /// <param name="classicpdb">True for pdb line format, false if tab-delimited</param>
        public void ReadRefAtoms(Molecule m, Boolean classicpdb)
        {
            // re-read the lp file to get reference frames
            referenceAtoms = new List <ReferenceAtom[]>(labelingpos.Count);
            Int32 j;

            String[] strdata;
            strdata = System.IO.File.ReadAllLines(labelingpos.FullPath);

            String[] tmpstr;
            Double   x, y, z;

            Char[]          separator = new Char[] { ' ', '\t' };
            ReferenceAtom[] reftmp;
            for (Int32 i = 0; i < strdata.Length; i++)
            {
                // find LP line
                if (!LabelingPositionList.ValidLPLine(strdata[i]))
                {
                    continue;
                }
                // now LP is found, count following pdb lines if any
                j = 0;
                if (classicpdb)
                {
                    while (i + j + 1 < strdata.Length && strdata[i + j + 1].Length > 54 && strdata[i + j + 1].Substring(0, 4) == "ATOM")
                    {
                        j++;
                    }
                }
                else
                {
                    while (i + j + 1 < strdata.Length && strdata[i + j + 1].Length > 10 && strdata[i + j + 1].Substring(0, 4) == "ATOM")
                    {
                        j++;
                    }
                }
                reftmp = new ReferenceAtom[j];
                // read reference atoms
                j = 0;
                if (classicpdb)
                {
                    while (i + j + 1 < strdata.Length && strdata[i + j + 1].Length > 54 && strdata[i + j + 1].Substring(0, 4) == "ATOM")
                    {
                        tmpstr = strdata[i + j + 1].Split(separator, StringSplitOptions.RemoveEmptyEntries);
                        reftmp[j].OriginalN  = Int32.Parse(tmpstr[1]);
                        reftmp[j].ConvertedN = Array.BinarySearch <Int32>(m.OriginalAtomID, reftmp[j].OriginalN);
                        if (Double.TryParse(strdata[i + j + 1].Substring(30, 8), out x) &&
                            Double.TryParse(strdata[i + j + 1].Substring(38, 8), out y) &&
                            Double.TryParse(strdata[i + j + 1].Substring(46, 8), out z))
                        {
                            reftmp[j].X = x;
                            reftmp[j].Y = y;
                            reftmp[j].Z = z;
                        }
                        j++;
                    }
                }
                else
                {
                    while (i + j + 1 < strdata.Length && strdata[i + j + 1].Length > 10 && strdata[i + j + 1].Substring(0, 4) == "ATOM")
                    {
                        tmpstr = strdata[i + j + 1].Split(separator, StringSplitOptions.RemoveEmptyEntries);
                        reftmp[j].OriginalN  = Int32.Parse(tmpstr[1]);
                        reftmp[j].ConvertedN = Array.BinarySearch <Int32>(m.OriginalAtomID, reftmp[j].OriginalN);
                        if (Double.TryParse(tmpstr[6], out x) &&
                            Double.TryParse(tmpstr[7], out y) &&
                            Double.TryParse(tmpstr[8], out z))
                        {
                            reftmp[j].X = x;
                            reftmp[j].Y = y;
                            reftmp[j].Z = z;
                        }
                        j++;
                    }
                }
                referenceAtoms.Add(reftmp);
                i += j;
            }
        }