/*!
 * \param[in] g     Index group to check.
 * \param[in] type  Block data to check against.
 * \param[in] top   Topology data.
 * \returns   true if \p g consists of one or more complete elements of type
 *   \p type, false otherwise.
 *
 * \p g is assumed to be sorted, otherwise may return false negatives.
 *
 * If \p type is \ref INDEX_ATOM, the return value is always true.
 * If \p type is \ref INDEX_UNKNOWN or \ref INDEX_ALL, the return value is
 * always false.
 */
bool
gmx_ana_index_has_complete_elems(gmx_ana_index_t *g, e_index_t type,
                                 t_topology *top)
{
    // TODO: Consider whether unsorted groups need to be supported better.
    switch (type)
    {
        case INDEX_UNKNOWN:
        case INDEX_ALL:
            return false;

        case INDEX_ATOM:
            return true;

        case INDEX_RES:
        {
            int      i, ai;
            int      id, prev;

            prev = -1;
            for (i = 0; i < g->isize; ++i)
            {
                ai = g->index[i];
                id = top->atoms.atom[ai].resind;
                if (id != prev)
                {
                    if (ai > 0 && top->atoms.atom[ai-1].resind == id)
                    {
                        return false;
                    }
                    if (i > 0 && g->index[i-1] < top->atoms.nr - 1
                        && top->atoms.atom[g->index[i-1]+1].resind == prev)
                    {
                        return false;
                    }
                }
                prev = id;
            }
            if (g->index[i-1] < top->atoms.nr - 1
                && top->atoms.atom[g->index[i-1]+1].resind == prev)
            {
                return false;
            }
            break;
        }

        case INDEX_MOL:
            return gmx_ana_index_has_full_blocks(g, &top->mols);
    }
    return true;
}
Ejemplo n.º 2
0
/*!
 * \param[in] g     Index group to check.
 * \param[in] type  Block data to check against.
 * \param[in] top   Topology data.
 * \returns   TRUE if \p g consists of one or more complete elements of type
 *   \p type, FALSE otherwise.
 *
 * If \p type is \ref INDEX_ATOM, the return value is always TRUE.
 * If \p type is \ref INDEX_UNKNOWN or \ref INDEX_ALL, the return value is
 * always FALSE.
 */
bool
gmx_ana_index_has_complete_elems(gmx_ana_index_t *g, e_index_t type,
                                 t_topology *top)
{
    switch (type)
    {
        case INDEX_UNKNOWN:
        case INDEX_ALL:
            return FALSE;

        case INDEX_ATOM:
            return TRUE;

        case INDEX_RES:
        {
            int      i, ai;
            int      id, prev;

            prev = -1;
            for (i = 0; i < g->isize; ++i)
            {
                ai = g->index[i];
                id = top->atoms.atom[ai].resind;
                if (id != prev)
                {
                    if (ai > 0 && top->atoms.atom[ai-1].resind == id)
                    {
                        return FALSE;
                    }
                    if (i > 0 && g->index[i-1] < top->atoms.nr - 1
                        && top->atoms.atom[g->index[i-1]+1].resind == prev)
                    {
                        return FALSE;
                    }
                }
                prev = id;
            }
            if (g->index[i-1] < top->atoms.nr - 1
                && top->atoms.atom[g->index[i-1]+1].resind == prev)
            {
                return FALSE;
            }
            break;
        }

        case INDEX_MOL:
            return gmx_ana_index_has_full_blocks(g, &top->mols);
    }
    return TRUE;
}