/* For selections, store the maximum group for
* gmx_ana_selcollection_evaluate_fin() as the value of the root
* element (unused otherwise). */
- if (expr->type != SEL_SUBEXPR && expr->v.u.p->g)
+ if (expr->type != SEL_SUBEXPR && expr->v.u.p->m.mapb.a != NULL)
{
SelectionTreeElementPointer child = expr;
}
if (child->child->flags & SEL_DYNAMIC)
{
+ gmx_ana_index_t g;
+ gmx_ana_index_set(&g, expr->v.u.p->m.mapb.nra, expr->v.u.p->m.mapb.a, 0);
_gmx_selelem_set_vtype(root, GROUP_VALUE);
root->flags |= (SEL_ALLOCVAL | SEL_ALLOCDATA);
_gmx_selvalue_reserve(&root->v, 1);
- gmx_ana_index_copy(root->v.u.g, expr->v.u.p->g, true);
+ gmx_ana_index_copy(root->v.u.g, &g, true);
}
}
}
m->mapb.nr = 0;
m->mapb.index = NULL;
m->mapb.nalloc_index = 0;
+ m->mapb.nra = 0;
+ m->mapb.a = NULL;
+ m->mapb.nalloc_a = 0;
m->orgid = NULL;
m->b.nr = 0;
m->b.index = NULL;
m->refid[i] = i;
m->mapid[i] = m->orgid[i];
}
- m->mapb.nr = m->nr;
+ m->mapb.nr = m->nr;
+ m->mapb.nra = m->b.nra;
+ m->mapb.a = m->b.a;
std::memcpy(m->mapb.index, m->b.index, (m->nr+1)*sizeof(*(m->mapb.index)));
m->bStatic = true;
m->bMapStatic = true;
gmx_ana_indexmap_set_static(gmx_ana_indexmap_t *m, t_blocka *b)
{
sfree(m->mapid);
- m->mapid = m->orgid;
- sfree(m->b.index);
- m->b.nalloc_index = 0;
- m->b.index = b->index;
sfree(m->mapb.index);
- m->mapb.nalloc_index = 0;
- m->mapb.index = m->b.index;
+ sfree(m->b.index);
sfree(m->b.a);
- m->b.nalloc_a = 0;
- m->b.a = b->a;
+ m->mapb.nalloc_index = 0;
+ m->mapb.nalloc_a = 0;
+ m->b.nalloc_index = 0;
+ m->b.nalloc_a = 0;
+ m->mapid = m->orgid;
+ m->mapb.index = b->index;
+ m->mapb.a = b->a;
+ m->b.index = b->index;
+ m->b.a = b->a;
}
/*!
}
dest->nr = src->nr;
dest->mapb.nr = src->mapb.nr;
+ dest->mapb.nra = src->mapb.nra;
+ if (src->mapb.nalloc_a > 0)
+ {
+ if (bFirst)
+ {
+ snew(dest->mapb.a, src->mapb.nalloc_a);
+ dest->mapb.nalloc_a = src->mapb.nalloc_a;
+ }
+ std::memcpy(dest->mapb.a, src->mapb.a, dest->mapb.nra*sizeof(*dest->mapb.a));
+ }
+ else
+ {
+ dest->mapb.a = src->mapb.a;
+ }
std::memcpy(dest->refid, src->refid, dest->nr*sizeof(*dest->refid));
std::memcpy(dest->mapid, src->mapid, dest->nr*sizeof(*dest->mapid));
std::memcpy(dest->mapb.index, src->mapb.index, (dest->mapb.nr+1)*sizeof(*dest->mapb.index));
dest->bMapStatic = src->bMapStatic;
}
+/*! \brief
+ * Helper function to set the source atoms in an index map.
+ *
+ * \param[in,out] m Mapping structure.
+ * \param[in] isize Number of atoms in the \p index array.
+ * \param[in] index List of atoms.
+ */
+static void
+set_atoms(gmx_ana_indexmap_t *m, int isize, int *index)
+{
+ m->mapb.nra = isize;
+ if (m->mapb.nalloc_a == 0)
+ {
+ m->mapb.a = index;
+ }
+ else
+ {
+ for (int i = 0; i < isize; ++i)
+ {
+ m->mapb.a[i] = index[i];
+ }
+ }
+}
+
/*!
* \param[in,out] m Mapping structure.
* \param[in] g Current index group.
{
return;
}
+ // TODO: This could also be optimized away under some bStatic conditions.
+ if (bMaskOnly)
+ {
+ set_atoms(m, m->b.nra, m->b.a);
+ }
+ else
+ {
+ set_atoms(m, g->isize, g->index);
+ }
if (m->type == INDEX_ALL)
{
if (m->b.nr > 0)
{
sfree(m->mapb.index);
}
+ if (m->mapb.nalloc_a > 0)
+ {
+ sfree(m->mapb.a);
+ }
sfree(m->orgid);
if (m->b.nalloc_index > 0)
{
* Mapped block structure.
*
* A block structure that corresponds to the current index group.
+ * \c mapb.nra and \c mapb.a correspond to the last mapped index group.
*/
- t_block mapb;
+ t_blocka mapb;
/*! \brief
* Arbitrary ID numbers for the blocks.
gmx_ana_pos_reserve_forces(p);
}
gmx_ana_pos_set_nr(p, p->m.nr);
- gmx_ana_pos_set_evalgrp(p, &pc->gmax);
}
/*!
/* Update the index map */
if (pc->flags & POS_DYNAMIC)
{
- gmx_ana_pos_set_evalgrp(p, g);
gmx_ana_indexmap_update(&p->m, g, false);
p->nr = p->m.nr;
}
pos->v = NULL;
pos->f = NULL;
gmx_ana_indexmap_clear(&pos->m);
- pos->g = NULL;
pos->nalloc_x = 0;
}
}
}
+/*!
+ * \param[in,out] pos Position data structure.
+ * \param[in] n Maximum number of positions.
+ * \param[in] isize Maximum number of atoms.
+ * \param[in] bVelocities Whether to reserve space for velocities.
+ * \param[in] bForces Whether to reserve space for forces.
+ *
+ * Ensures that enough memory is allocated in \p pos to calculate \p n
+ * positions from \p isize atoms.
+ *
+ * This method needs to be called instead of gmx_ana_pos_reserve() if the
+ * intent is to use gmx_ana_pos_append_init()/gmx_ana_pos_append().
+ */
+void
+gmx_ana_pos_reserve_for_append(gmx_ana_pos_t *pos, int n, int isize,
+ bool bVelocities, bool bForces)
+{
+ gmx_ana_pos_reserve(pos, n, isize);
+ snew(pos->m.mapb.a, isize);
+ pos->m.mapb.nalloc_a = isize;
+ if (bVelocities)
+ {
+ gmx_ana_pos_reserve_velocities(pos);
+ }
+ if (bForces)
+ {
+ gmx_ana_pos_reserve_forces(pos);
+ }
+}
+
/*!
* \param[out] pos Position data structure to initialize.
* \param[in] x Position vector to use.
memcpy(dest->f, src->f, dest->nr*sizeof(*dest->f));
}
gmx_ana_indexmap_copy(&dest->m, &src->m, bFirst);
- dest->g = src->g;
}
/*!
pos->nr = nr;
}
-/*!
- * \param[in,out] pos Position data structure.
- * \param g Evaluation group.
- *
- * The old group, if any, is discarded.
- * Note that only a pointer to \p g is stored; it is the responsibility of
- * the caller to ensure that \p g is not freed while it can be accessed
- * through \p pos.
- */
-void
-gmx_ana_pos_set_evalgrp(gmx_ana_pos_t *pos, gmx_ana_index_t *g)
-{
- pos->g = g;
-}
-
/*!
* \param[in,out] pos Position data structure.
*
void
gmx_ana_pos_empty_init(gmx_ana_pos_t *pos)
{
- pos->nr = 0;
- pos->m.nr = 0;
- pos->m.mapb.nr = 0;
- pos->m.b.nr = 0;
- pos->m.b.nra = 0;
+ pos->nr = 0;
+ pos->m.nr = 0;
+ pos->m.mapb.nr = 0;
+ pos->m.mapb.nra = 0;
+ pos->m.b.nr = 0;
+ pos->m.b.nra = 0;
/* This should not really be necessary, but do it for safety... */
pos->m.mapb.index[0] = 0;
pos->m.b.index[0] = 0;
void
gmx_ana_pos_empty(gmx_ana_pos_t *pos)
{
- pos->nr = 0;
- pos->m.nr = 0;
- pos->m.mapb.nr = 0;
+ pos->nr = 0;
+ pos->m.nr = 0;
+ pos->m.mapb.nr = 0;
+ pos->m.mapb.nra = 0;
/* This should not really be necessary, but do it for safety... */
pos->m.mapb.index[0] = 0;
/* We set the flags to true, although really in the empty state they
/*!
* \param[in,out] dest Data structure to which the new position is appended.
- * \param[in,out] g Data structure to which the new atoms are appended.
* \param[in] src Data structure from which the position is copied.
* \param[in] i Index in \p from to copy.
*/
void
-gmx_ana_pos_append_init(gmx_ana_pos_t *dest, gmx_ana_index_t *g,
- gmx_ana_pos_t *src, int i)
+gmx_ana_pos_append_init(gmx_ana_pos_t *dest, gmx_ana_pos_t *src, int i)
{
int j, k;
dest->m.orgid[j] = src->m.orgid[i];
for (k = src->m.mapb.index[i]; k < src->m.mapb.index[i+1]; ++k)
{
- g->index[g->isize++] = src->g->index[k];
- dest->m.b.a[dest->m.b.nra++] = src->m.b.a[k];
+ dest->m.mapb.a[dest->m.mapb.nra++] = src->m.mapb.a[k];
+ dest->m.b.a[dest->m.b.nra++] = src->m.b.a[k];
}
- dest->m.mapb.index[j+1] = g->isize;
- dest->m.b.index[j+1] = g->isize;
+ dest->m.mapb.index[j+1] = dest->m.mapb.nra;
+ dest->m.b.index[j+1] = dest->m.mapb.nra;
dest->nr++;
dest->m.nr = dest->nr;
dest->m.mapb.nr = dest->nr;
}
/*!
- * \param[in,out] dest Data structure to which the new position is appended
- * (can be NULL, in which case only \p g is updated).
- * \param[in,out] g Data structure to which the new atoms are appended.
+ * \param[in,out] dest Data structure to which the new position is appended.
* \param[in] src Data structure from which the position is copied.
* \param[in] i Index in \p src to copy.
* \param[in] refid Reference ID in \p out
* (all negative values are treated as -1).
- *
- * If \p dest is NULL, the value of \p refid is not used.
*/
void
-gmx_ana_pos_append(gmx_ana_pos_t *dest, gmx_ana_index_t *g,
- gmx_ana_pos_t *src, int i, int refid)
+gmx_ana_pos_append(gmx_ana_pos_t *dest, gmx_ana_pos_t *src, int i, int refid)
{
- int j, k;
-
- for (k = src->m.mapb.index[i]; k < src->m.mapb.index[i+1]; ++k)
+ for (int k = src->m.mapb.index[i]; k < src->m.mapb.index[i+1]; ++k)
{
- g->index[g->isize++] = src->g->index[k];
+ dest->m.mapb.a[dest->m.mapb.nra++] = src->m.mapb.a[k];
}
- if (dest)
+ const int j = dest->nr;
+ if (dest->v)
{
- j = dest->nr;
- if (dest->v)
+ if (src->v)
{
- if (src->v)
- {
- copy_rvec(src->v[i], dest->v[j]);
- }
- else
- {
- clear_rvec(dest->v[j]);
- }
+ copy_rvec(src->v[i], dest->v[j]);
}
- if (dest->f)
+ else
{
- if (src->f)
- {
- copy_rvec(src->f[i], dest->f[j]);
- }
- else
- {
- clear_rvec(dest->f[j]);
- }
+ clear_rvec(dest->v[j]);
}
- copy_rvec(src->x[i], dest->x[j]);
- if (refid < 0)
+ }
+ if (dest->f)
+ {
+ if (src->f)
{
- dest->m.refid[j] = -1;
- dest->m.bStatic = false;
- /* If we are using masks, there is no need to alter the
- * mapid field. */
+ copy_rvec(src->f[i], dest->f[j]);
}
else
{
- if (refid != j)
- {
- dest->m.bStatic = false;
- dest->m.bMapStatic = false;
- }
- dest->m.refid[j] = refid;
- /* Use the original IDs from the output structure to correctly
- * handle user customization. */
- dest->m.mapid[j] = dest->m.orgid[refid];
+ clear_rvec(dest->f[j]);
+ }
+ }
+ copy_rvec(src->x[i], dest->x[j]);
+ if (refid < 0)
+ {
+ dest->m.refid[j] = -1;
+ dest->m.bStatic = false;
+ /* If we are using masks, there is no need to alter the
+ * mapid field. */
+ }
+ else
+ {
+ if (refid != j)
+ {
+ dest->m.bStatic = false;
+ dest->m.bMapStatic = false;
}
- dest->m.mapb.index[j+1] = g->isize;
- dest->nr++;
- dest->m.nr = dest->nr;
- dest->m.mapb.nr = dest->nr;
+ dest->m.refid[j] = refid;
+ /* Use the original IDs from the output structure to correctly
+ * handle user customization. */
+ dest->m.mapid[j] = dest->m.orgid[refid];
}
+ dest->m.mapb.index[j+1] = dest->m.mapb.nra;
+ dest->nr++;
+ dest->m.nr = dest->nr;
+ dest->m.mapb.nr = dest->nr;
}
/*!
pos->m.bMapStatic = false;
}
}
+
+/*!
+ * \param[in,out] g Data structure to which the new atoms are appended.
+ * \param[in] src Data structure from which the position is copied.
+ * \param[in] i Index in \p src to copy.
+ */
+void
+gmx_ana_pos_add_to_group(gmx_ana_index_t *g, gmx_ana_pos_t *src, int i)
+{
+ for (int k = src->m.mapb.index[i]; k < src->m.mapb.index[i+1]; ++k)
+ {
+ g->index[g->isize++] = src->m.mapb.a[k];
+ }
+}
/*
* This file is part of the GROMACS molecular simulation package.
*
- * Copyright (c) 2009,2010,2011,2012, by the GROMACS development team, led by
+ * Copyright (c) 2009,2010,2011,2012,2013, by the GROMACS development team, led by
* David van der Spoel, Berk Hess, Erik Lindahl, and including many
* others, as listed in the AUTHORS file in the top-level source
* directory and at http://www.gromacs.org.
* \see gmx_ana_indexmap_t
*/
gmx_ana_indexmap_t m;
- /*! \brief
- * Pointer to the current evaluation group.
- */
- gmx_ana_index_t *g;
/*! \brief
* Number of elements allocated for \c x.
*/
/** Request memory allocation for forces. */
void
gmx_ana_pos_reserve_forces(gmx_ana_pos_t *pos);
+/** Reserves memory for use with gmx_ana_pos_append_init(). */
+void
+gmx_ana_pos_reserve_for_append(gmx_ana_pos_t *pos, int n, int isize,
+ bool bVelocities, bool bForces);
/** Initializes a \c gmx_ana_pos_t to represent a constant position. */
void
gmx_ana_pos_init_const(gmx_ana_pos_t *pos, const rvec x);
/** Sets the number of positions in a position structure. */
void
gmx_ana_pos_set_nr(gmx_ana_pos_t *pos, int n);
-/** Sets the evaluation group of a position data structure. */
-void
-gmx_ana_pos_set_evalgrp(gmx_ana_pos_t *pos, gmx_ana_index_t *g);
/** Empties a position data structure with full initialization. */
void
gmx_ana_pos_empty_init(gmx_ana_pos_t *pos);
/** Appends a position to a preallocated data structure with full
* initialization. */
void
-gmx_ana_pos_append_init(gmx_ana_pos_t *dest, gmx_ana_index_t *g,
- gmx_ana_pos_t *src, int i);
+gmx_ana_pos_append_init(gmx_ana_pos_t *dest, gmx_ana_pos_t *src, int i);
/** Appends a position to a preallocated data structure. */
void
-gmx_ana_pos_append(gmx_ana_pos_t *dest, gmx_ana_index_t *g,
- gmx_ana_pos_t *src, int i, int refid);
+gmx_ana_pos_append(gmx_ana_pos_t *dest, gmx_ana_pos_t *src, int i, int refid);
/** Updates position data structure state after appends. */
void
gmx_ana_pos_append_finish(gmx_ana_pos_t *pos);
+void
+/** Appends atoms from a position into a preallocated index group. */
+gmx_ana_pos_add_to_group(gmx_ana_index_t *g, gmx_ana_pos_t *src, int i);
#endif
real charge = 0.0;
for (int i = pos.m.mapb.index[b]; i < pos.m.mapb.index[b+1]; ++i)
{
- int index = pos.g->index[i];
+ const int index = pos.m.mapb.a[i];
mass += top->atoms.atom[index].m;
charge += top->atoms.atom[index].q;
}
if (isDynamic())
{
gmx_ana_pos_t &p = rawPositions_;
- gmx_ana_index_copy(p.g, rootElement().v.u.g, false);
- gmx_ana_indexmap_update(&p.m, p.g, hasFlag(gmx::efSelection_DynamicMask));
+ gmx_ana_indexmap_update(&p.m, rootElement().v.u.g,
+ hasFlag(gmx::efSelection_DynamicMask));
p.nr = p.m.nr;
refreshMassesAndCharges(top);
}
fprintf(fp, " ");
printInfo(fp);
fprintf(fp, " Group ");
- gmx_ana_index_dump(fp, p.g, nmaxind);
+ gmx_ana_index_t g;
+ gmx_ana_index_set(&g, p.m.mapb.nra, p.m.mapb.a, 0);
+ gmx_ana_index_dump(fp, &g, nmaxind);
fprintf(fp, " Block (size=%d):", p.m.mapb.nr);
if (!p.m.mapb.index)
//! Total number of atoms in the selection.
int atomCount() const
{
- return data().rawPositions_.g != NULL ? data().rawPositions_.g->isize : 0;
+ return data().rawPositions_.m.mapb.nra;
}
//! Returns atom indices of all atoms in the selection.
ConstArrayRef<int> atomIndices() const
{
- if (data().rawPositions_.g == NULL)
- {
- return ConstArrayRef<int>();
- }
- return ConstArrayRef<int>(data().rawPositions_.g->index,
- data().rawPositions_.g->isize);
+ return ConstArrayRef<int>(sel_->rawPositions_.m.mapb.a,
+ sel_->rawPositions_.m.mapb.nra);
}
//! Number of positions in the selection.
int posCount() const { return data().posCount(); }
//! Return atom indices that make up this position.
ConstArrayRef<int> atomIndices() const
{
- if (sel_->rawPositions_.g == NULL)
+ const int *atoms = sel_->rawPositions_.m.mapb.a;
+ if (atoms == NULL)
{
return ConstArrayRef<int>();
}
- int first = sel_->rawPositions_.m.mapb.index[i_];
- return ConstArrayRef<int>(&sel_->rawPositions_.g->index[first],
- atomCount());
+ const int first = sel_->rawPositions_.m.mapb.index[i_];
+ return ConstArrayRef<int>(&atoms[first], atomCount());
}
/*! \brief
* Returns whether this position is selected in the current frame.
{
t_methoddata_distance *d = (t_methoddata_distance *)data;
- out->nr = pos->g->isize;
+ out->nr = pos->m.mapb.nra;
for (int b = 0; b < pos->nr; ++b)
{
real dist = d->nbsearch.minimumDistance(pos->x[b]);
{
if (d->nbsearch.isWithin(pos->x[b]))
{
- gmx_ana_pos_append(NULL, out->u.g, pos, b, 0);
+ gmx_ana_pos_add_to_group(out->u.g, pos, b);
}
}
}
/*
* This file is part of the GROMACS molecular simulation package.
*
- * Copyright (c) 2009,2010,2011,2012, by the GROMACS development team, led by
+ * Copyright (c) 2009,2010,2011,2012,2013, by the GROMACS development team, led by
* David van der Spoel, Berk Hess, Erik Lindahl, and including many
* others, as listed in the AUTHORS file in the top-level source
* directory and at http://www.gromacs.org.
{
if (accept_insolidangle(pos->x[b], pbc, data))
{
- gmx_ana_pos_append(NULL, out->u.g, pos, b, 0);
+ gmx_ana_pos_add_to_group(out->u.g, pos, b);
}
}
}
/*
* This file is part of the GROMACS molecular simulation package.
*
- * Copyright (c) 2009,2010,2011,2012, by the GROMACS development team, led by
+ * Copyright (c) 2009,2010,2011,2012,2013, by the GROMACS development team, led by
* David van der Spoel, Berk Hess, Erik Lindahl, and including many
* others, as listed in the AUTHORS file in the top-level source
* directory and at http://www.gromacs.org.
gmx_ana_pos_t p1;
/** Other input positions. */
gmx_ana_pos_t p2;
- /** Group to store the output atom indices. */
- gmx_ana_index_t g;
/** Stride for merging (\c stride values from \c p1 for each in \c p2). */
int stride;
} t_methoddata_merge;
{
GMX_THROW(gmx::InconsistentInputError("The number of positions to be merged are not compatible"));
}
- /* We access the m.b.nra field instead of g->isize in the position
- * data structures to handle cases where g is NULL
- * (this occurs with constant positions. */
- gmx_ana_index_reserve(&d->g, d->p1.m.b.nra + d->p2.m.b.nra);
- d->g.isize = d->p1.m.b.nra + d->p2.m.b.nra;
}
/*! \brief
{
out->u.p->m.type = d->p1.m.type;
}
- gmx_ana_pos_reserve(out->u.p, d->p1.nr + d->p2.nr, d->g.isize);
- if (d->p1.v)
- {
- gmx_ana_pos_reserve_velocities(out->u.p);
- }
- if (d->p1.f)
- {
- gmx_ana_pos_reserve_forces(out->u.p);
- }
- gmx_ana_pos_set_evalgrp(out->u.p, &d->g);
+ gmx_ana_pos_reserve_for_append(out->u.p, d->p1.nr + d->p2.nr,
+ d->p1.m.b.nra + d->p2.m.b.nra,
+ d->p1.v != NULL, d->p1.f != NULL);
gmx_ana_pos_empty_init(out->u.p);
- d->g.isize = 0;
}
/*!
{
for (j = 0; j < d->stride; ++j)
{
- gmx_ana_pos_append_init(out->u.p, &d->g, &d->p1, d->stride*i+j);
+ gmx_ana_pos_append_init(out->u.p, &d->p1, d->stride * i + j);
}
- gmx_ana_pos_append_init(out->u.p, &d->g, &d->p2, i);
+ gmx_ana_pos_append_init(out->u.p, &d->p2, i);
}
}
init_output_common(top, out, data);
for (i = 0; i < d->p1.nr; ++i)
{
- gmx_ana_pos_append_init(out->u.p, &d->g, &d->p1, i);
+ gmx_ana_pos_append_init(out->u.p, &d->p1, i);
}
for (i = 0; i < d->p2.nr; ++i)
{
- gmx_ana_pos_append_init(out->u.p, &d->g, &d->p2, i);
+ gmx_ana_pos_append_init(out->u.p, &d->p2, i);
}
}
{
t_methoddata_merge *d = (t_methoddata_merge *)data;
- gmx_ana_index_deinit(&d->g);
sfree(d);
}
{
GMX_THROW(gmx::InconsistentInputError("The number of positions to be merged are not compatible"));
}
- d->g.isize = 0;
gmx_ana_pos_empty(out->u.p);
for (i = 0; i < d->p2.nr; ++i)
{
{
refid = (d->stride+1) * (refid / d->stride) + (refid % d->stride);
}
- gmx_ana_pos_append(out->u.p, &d->g, &d->p1, d->stride*i+j, refid);
+ gmx_ana_pos_append(out->u.p, &d->p1, d->stride*i+j, refid);
}
- refid = (d->stride+1)*d->p2.m.refid[i]+d->stride;
- gmx_ana_pos_append(out->u.p, &d->g, &d->p2, i, refid);
+ refid = (d->stride+1)*d->p2.m.refid[i] + d->stride;
+ gmx_ana_pos_append(out->u.p, &d->p2, i, refid);
}
gmx_ana_pos_append_finish(out->u.p);
}
int i;
int refid;
- d->g.isize = 0;
gmx_ana_pos_empty(out->u.p);
for (i = 0; i < d->p1.nr; ++i)
{
refid = d->p1.m.refid[i];
- gmx_ana_pos_append(out->u.p, &d->g, &d->p1, i, refid);
+ gmx_ana_pos_append(out->u.p, &d->p1, i, refid);
}
for (i = 0; i < d->p2.nr; ++i)
{
{
refid += d->p1.m.b.nr;
}
- gmx_ana_pos_append(out->u.p, &d->g, &d->p2, i, refid);
+ gmx_ana_pos_append(out->u.p, &d->p2, i, refid);
}
gmx_ana_pos_append_finish(out->u.p);
}
/*
* This file is part of the GROMACS molecular simulation package.
*
- * Copyright (c) 2009,2010,2011,2012, by the GROMACS development team, led by
+ * Copyright (c) 2009,2010,2011,2012,2013, by the GROMACS development team, led by
* David van der Spoel, Berk Hess, Erik Lindahl, and including many
* others, as listed in the AUTHORS file in the top-level source
* directory and at http://www.gromacs.org.
{
/** Positions to permute. */
gmx_ana_pos_t p;
- /** Group to receive the output permutation. */
- gmx_ana_index_t g;
/** Number of elements in the permutation. */
int n;
/** Array describing the permutation. */
t_methoddata_permute *d = (t_methoddata_permute *)data;
int i;
- gmx_ana_index_reserve(&d->g, d->p.g->isize);
d->n = param[1].val.nr;
d->perm = param[1].val.u.i;
if (d->p.nr % d->n != 0)
t_methoddata_permute *d = (t_methoddata_permute *)data;
int i, j, b;
- gmx_ana_pos_copy(out->u.p, &d->p, true);
- gmx_ana_pos_set_evalgrp(out->u.p, &d->g);
- d->g.isize = 0;
+ out->u.p->m.type = d->p.m.type;
+ gmx_ana_pos_reserve_for_append(out->u.p, d->p.nr, d->p.m.b.nra,
+ d->p.v != NULL, d->p.f != NULL);
gmx_ana_pos_empty_init(out->u.p);
for (i = 0; i < d->p.nr; i += d->n)
{
for (j = 0; j < d->n; ++j)
{
b = i + d->rperm[j];
- gmx_ana_pos_append_init(out->u.p, &d->g, &d->p, b);
+ gmx_ana_pos_append_init(out->u.p, &d->p, b);
}
}
}
{
t_methoddata_permute *d = (t_methoddata_permute *)data;
- gmx_ana_index_deinit(&d->g);
sfree(d->rperm);
sfree(d);
}
GMX_THROW(gmx::InconsistentInputError(
gmx::formatString("The number of positions to be permuted is not divisible by %d", d->n)));
}
- d->g.isize = 0;
gmx_ana_pos_empty(out->u.p);
for (i = 0; i < d->p.nr; i += d->n)
{
/* De-permute the reference ID */
refid = refid - (refid % d->n) + d->perm[refid % d->n];
}
- gmx_ana_pos_append(out->u.p, &d->g, p, b, refid);
+ gmx_ana_pos_append(out->u.p, p, b, refid);
}
}
gmx_ana_pos_append_finish(out->u.p);
/*
* This file is part of the GROMACS molecular simulation package.
*
- * Copyright (c) 2009,2010,2011,2012, by the GROMACS development team, led by
+ * Copyright (c) 2009,2010,2011,2012,2013, by the GROMACS development team, led by
* David van der Spoel, Berk Hess, Erik Lindahl, and including many
* others, as listed in the AUTHORS file in the top-level source
* directory and at http://www.gromacs.org.
t_methoddata_pos *d = (t_methoddata_pos *)data;
gmx_ana_poscalc_init_pos(d->pc, out->u.p);
- gmx_ana_pos_set_evalgrp(out->u.p, &d->g);
}
/*!
/*! \brief
* Internal utility function for position keyword evaluation.
*
- * \param[in] fr Current frame.
- * \param[in] g Index group for which the coordinates should be evaluated.
* \param[out] out Output array.
* \param[in] pos Position data to use instead of atomic coordinates
* (can be NULL).
* evaluate_z() to do the actual evaluation.
*/
static void
-evaluate_coord(t_trxframe *fr, gmx_ana_index_t *g, real out[],
- gmx_ana_pos_t *pos, int d)
+evaluate_coord(real out[], gmx_ana_pos_t *pos, int d)
{
- int b, i;
- real v;
-
- if (pos)
- {
- for (b = 0; b < pos->nr; ++b)
- {
- v = pos->x[b][d];
- for (i = pos->m.mapb.index[b]; i < pos->m.mapb.index[b+1]; ++i)
- {
- out[i] = v;
- }
- }
- }
- else
+ for (int b = 0; b < pos->nr; ++b)
{
- // TODO: This loop is never reached in the current code.
- // It would be useful to change the code such that it is, mostly for
- // memory efficiency reasons.
- for (i = 0; i < g->isize; ++i)
+ const real v = pos->x[b][d];
+ for (int i = pos->m.mapb.index[b]; i < pos->m.mapb.index[b+1]; ++i)
{
- out[i] = fr->x[g->index[i]][d];
+ out[i] = v;
}
}
+ // TODO: Make this more efficient by directly extracting the coordinates
+ // from the frame coordinates for atomic positions instead of going through
+ // a position calculation.
}
/*!
* Returns the \p x coordinate for each atom in \p out->u.r.
*/
static void
-evaluate_x(t_topology *top, t_trxframe *fr, t_pbc *pbc,
- gmx_ana_pos_t *pos, gmx_ana_selvalue_t *out, void *data)
+evaluate_x(t_topology * /*top*/, t_trxframe * /*fr*/, t_pbc * /*pbc*/,
+ gmx_ana_pos_t *pos, gmx_ana_selvalue_t *out, void * /*data*/)
{
- out->nr = pos->g->isize;
- evaluate_coord(fr, pos->g, out->u.r, pos, XX);
+ out->nr = pos->m.mapb.nra;
+ evaluate_coord(out->u.r, pos, XX);
}
/*!
* Returns the \p y coordinate for each atom in \p out->u.r.
*/
static void
-evaluate_y(t_topology *top, t_trxframe *fr, t_pbc *pbc,
- gmx_ana_pos_t *pos, gmx_ana_selvalue_t *out, void *data)
+evaluate_y(t_topology * /*top*/, t_trxframe * /*fr*/, t_pbc * /*pbc*/,
+ gmx_ana_pos_t *pos, gmx_ana_selvalue_t *out, void * /*data*/)
{
- out->nr = pos->g->isize;
- evaluate_coord(fr, pos->g, out->u.r, pos, YY);
+ out->nr = pos->m.mapb.nra;
+ evaluate_coord(out->u.r, pos, YY);
}
/*!
* Returns the \p z coordinate for each atom in \p out->u.r.
*/
static void
-evaluate_z(t_topology *top, t_trxframe *fr, t_pbc *pbc,
- gmx_ana_pos_t *pos, gmx_ana_selvalue_t *out, void *data)
+evaluate_z(t_topology * /*top*/, t_trxframe * /*fr*/, t_pbc * /*pbc*/,
+ gmx_ana_pos_t *pos, gmx_ana_selvalue_t *out, void * /*data*/)
{
- out->nr = pos->g->isize;
- evaluate_coord(fr, pos->g, out->u.r, pos, ZZ);
+ out->nr = pos->m.mapb.nra;
+ evaluate_coord(out->u.r, pos, ZZ);
}
gmx_ana_poscalc_t *pc, gmx_ana_pos_t *p, int count, const int atoms[],
gmx::test::TestReferenceChecker *checker, const char *name)
{
- // TODO: The group reference may get stored in p and stays there after this
- // function returns.
gmx_ana_index_t g;
g.isize = count;
g.index = const_cast<int *>(atoms);
{
EXPECT_EQ(p->nr, p->m.nr);
EXPECT_EQ(p->nr, p->m.mapb.nr);
- ASSERT_TRUE(p->g != NULL);
gmx::test::TestReferenceChecker compound(
checker->checkCompound("Positions", name));
compound.checkInteger(p->nr, "Count");
{
gmx::test::TestReferenceChecker posCompound(
compound.checkCompound("Position", NULL));
- // Always true; should satisfy clang.
- if (p->g != NULL)
- {
- posCompound.checkSequence(&p->g->index[p->m.mapb.index[i]],
- &p->g->index[p->m.mapb.index[i+1]],
- "Atoms");
- }
+ posCompound.checkSequence(&p->m.mapb.a[p->m.mapb.index[i]],
+ &p->m.mapb.a[p->m.mapb.index[i+1]],
+ "Atoms");
posCompound.checkInteger(p->m.refid[i], "RefId");
if (bCoordinates)
{