IMP logo
IMP Reference Guide  2.15.0
The Integrative Modeling Platform
Restraint.h
Go to the documentation of this file.
1 /**
2  * \file IMP/Restraint.h
3  * \brief Abstract base class for all restraints.
4  *
5  * Copyright 2007-2021 IMP Inventors. All rights reserved.
6  *
7  */
8 
9 #ifndef IMPKERNEL_RESTRAINT_H
10 #define IMPKERNEL_RESTRAINT_H
11 
12 #include <IMP/kernel_config.h>
13 #include "ModelObject.h"
14 #include "ScoreAccumulator.h"
15 #include "DerivativeAccumulator.h"
16 #include "constants.h"
17 #include "base_types.h"
18 #include <IMP/InputAdaptor.h>
19 #include <IMP/deprecation_macros.h>
20 #include <IMP/nullptr.h>
21 #include <IMP/RestraintInfo.h>
22 
23 IMPKERNEL_BEGIN_NAMESPACE
24 class DerivativeAccumulator;
25 
26 //! A restraint is a term in an \imp ScoringFunction.
27 /**
28  To implement a new restraint, just implement the two methods:
29  - IMP::Restraint::do_add_score_and_derivatives()
30  - IMP::ModelObject::do_get_inputs();
31  and use the macro to handle IMP::Object
32  - IMP_OBJECT_METHODS()
33 
34  \note When logging is VERBOSE, restraints should print enough information
35  in evaluate to reproduce the entire flow of data in evaluate. When
36  logging is TERSE the restraint should print out only a constant number of
37  lines per evaluate call.
38 
39  \note Physical restraints should use the units of kcal/mol for restraint
40  values and kcal/mol/A for derivatives.
41 
42  When implementing an expensive restraint it makes sense to support early
43  abort of evaluation if the user is only interested in good scores or scores
44  below a threshold. To do this, look at the fields of the ScoreAccumulator
45  object such as
46  - ScoreAccumulator::get_is_evaluate_if_below(),
47  - ScoreAccumulator::get_is_evaluate_if_good()
48  - ScoreAccumulator::get_maximum()
49 
50  \headerfile Restraint.h "IMP/Restraint.h"
51 
52  See IMP::example::ExampleRestraint for an example.
53  */
54 class IMPKERNELEXPORT Restraint : public ModelObject {
55  public:
56  /** Create a restraint and register it with the model. The restraint is
57  not added to the implicit scoring function in the Model.*/
58  Restraint(Model *m, std::string name);
59 
60  /** Compute and return the current score for the restraint.
61  */
62  double get_score() const;
63 
64 #ifndef IMP_DOXYGEN
65  //! Return the score for this restraint for the current state of the model.
66  /** \return Current score.
67  */
68  double evaluate(bool calc_derivs) const;
69 
70  double evaluate_if_good(bool calc_derivatives) const;
71 
72  //! \see Model::evaluate_with_maximum()
73  double evaluate_if_below(bool calc_derivatives, double max) const;
74 
75  /** \name Evaluation implementation
76  These methods are called in order to perform the actual restraint
77  scoring. The restraints should assume that all appropriate ScoreState
78  objects have been updated and so that the input particles and containers
79  are up to date. The returned score should be the unweighted score.
80 
81  \note These functions probably should be called \c do_evaluate, but
82  were grandfathered in.
83  \note Although the returned score is unweighted, the DerivativeAccumulator
84  passed in should be properly weighted.
85  @{
86  */
87  //! Return the unweighted score for the restraint.
88  virtual double unprotected_evaluate(DerivativeAccumulator *da) const;
89  /** The function calling this will treat any score >= get_maximum_score
90  as bad and so can return early as soon as such a situation is found.*/
91  virtual double unprotected_evaluate_if_good(DerivativeAccumulator *da,
92  double max) const {
93  IMP_UNUSED(max);
94  return unprotected_evaluate(da);
95  }
96 
97  //! The function calling this will treat any score >= max as bad.
98  virtual double unprotected_evaluate_if_below(DerivativeAccumulator *da,
99  double max) const {
100  IMP_UNUSED(max);
101  return unprotected_evaluate(da);
102  }
103 /** @} */
104 
105 #endif
106 
107  //! \return static key:value information about this restraint, or null.
108  /** \return a set of key:value pairs that contain static information
109  about this restraint (i.e. information that doesn't change during
110  a sampling run, such as the type of restraint or filename from
111  which information is read). Usually this includes a "type" key with
112  the fully qualified classname (e.g. IMP.mymodule.MyRestraint).
113  If no such information is available, a null pointer is returned.
114  This information is used when writing restraints to files, e.g. by
115  the IMP.rmf module.
116  */
117  virtual RestraintInfo *get_static_info() const {
118  return nullptr;
119  }
120 
121  //! \return dynamic key:value information about this restraint, or null.
122  /** \return a set of key:value pairs that contain dynamic information
123  about this restraint (i.e. information that changes during a sampling
124  run, such as scores or cross correlations).
125  If no such information is available, a null pointer is returned.
126  This information is used when writing restraints to files, e.g. by
127  the IMP.rmf module.
128  */
129  virtual RestraintInfo *get_dynamic_info() const {
130  return nullptr;
131  }
132 
133  //! Perform the actual restraint scoring.
134  /** The restraints should assume that all appropriate ScoreState
135  objects have been updated and so that the input particles and containers
136  are up to date. The returned score should be the unweighted score.
137  */
138  void add_score_and_derivatives(ScoreAccumulator sa) const;
139 
140  //! Decompose this restraint into constituent terms
141  /** Given the set of input particles, decompose the restraint into parts
142  that are as simple as possible. For many restraints, the simplest
143  part is simply the restraint itself.
144 
145  If a restraint can be decomposed, it should return a
146  RestraintSet so that the maximum score and weight can be
147  passed properly.
148 
149  The restraints returned have had set_model() called and so can
150  be evaluated.
151  */
153 
154  //! Decompose this restraint into constituent terms for the current conf
155  /** \return a decomposition that is value for the current conformation,
156  but will not necessarily be valid if any of the particles are
157  changed. This is the same as create_decomposition() for
158  non-conditional restraints.
159 
160  The restraints returned have had set_model() called and so can be
161  evaluated.
162  */
163  Restraint *create_current_decomposition() const;
164 
165  /** \name Weights
166  Each restraint's contribution to the model score is weighted. The
167  total weight for the restraint is the some over all the paths containing
168  it. That is, if a restraint is in a RestraintSet with weight .5 and
169  another with weight 2, and the restraint itself has weight 3, then the
170  total weight of the restraint is \f$.5 \cdot 3 + 2 \cdot 3 = 7.5 \f$.
171  @{
172  */
173  void set_weight(Float weight);
174  Float get_weight() const { return weight_; }
175  /** @} */
176  /** \name Filtering
177  We are typically only interested in "good" conformations of
178  the model. These are described by specifying maximum scores
179  per restraint (or RestraintSet). Samplers, optimizers
180  etc are free to ignore configurations they encounter which
181  go outside these bounds.
182 
183  \note The maximum score is for the unweighted restraint.
184  That is, the restraint evaluation is bad if the value
185  is greater than the maximum score divided by the weight.
186  @{
187  */
188  double get_maximum_score() const { return max_; }
189  void set_maximum_score(double s);
190 /** @} */
191 
192 //! Create a scoring function with only this restraint.
193 /** \note This method cannot be implemented in Python due to memory
194  management issues (and the question of why you would ever
195  want to).
196  */
197 #ifndef SWIG
198  virtual
199 #endif
200  ScoringFunction *
201  create_scoring_function(double weight = 1.0,
202  double max = NO_MAX) const;
203 #if !defined(IMP_DOXYGEN)
204  void set_last_score(double s) const { last_score_ = s; }
205 #endif
206 
207  /** Return the (unweighted) score for this restraint last time it was
208  evaluated.
209  \note If some sort of special evaluation (eg Model::evaluate_if_good())
210  was the last call, the score, if larger than the max, is not accurate.
211  */
212  virtual double get_last_score() const { return last_score_; }
213  /** Return whether this restraint violated its maximum last time it was
214  evaluated.
215  */
216  bool get_was_good() const { return get_last_score() < max_; }
217 
219 
220  protected:
221  /** A Restraint should override this if it wants to decompose itself
222  for domino and other purposes. The returned restraints will be made
223  into a RestraintSet if needed, with suitable weight and maximum score.
224  */
226  return Restraints(1, const_cast<Restraint *>(this));
227  }
228  /** A Restraint should override this if it wants to decompose itself
229  for display and other purposes. The returned restraints will be made
230  into a RestraintSet if needed, with suitable weight and maximum score.
231 
232  The returned restraints should be only the non-zero terms and should
233  have their last scores set appropriately.
234  */
236  return do_create_decomposition();
237  }
238  //! A restraint should override this to compute the score and derivatives.
239  virtual void do_add_score_and_derivatives(ScoreAccumulator sa) const;
240 
241  /** No outputs. */
243 
244  private:
245  ScoringFunction *create_internal_scoring_function() const;
246 
247  double weight_;
248  double max_;
249  mutable double last_score_;
250  // cannot be released outside the class
251  mutable Pointer<ScoringFunction> cached_internal_scoring_function_;
252 };
253 
254 //! Provide a consistent interface for things that take Restraints as arguments.
255 /**
256  \note Passing an empty list of restraints should be supported, but problems
257  could arise, so be alert (the problems would not be subtle).
258 */
259 class IMPKERNELEXPORT RestraintsAdaptor :
260 #if !defined(SWIG) && !defined(IMP_DOXYGEN)
261  public Restraints
262 #else
263  public InputAdaptor
264 #endif
265  {
266  static Restraint *get(Restraint *r) { return r; }
267 
268  public:
269  RestraintsAdaptor() {}
270  RestraintsAdaptor(const Restraints &sf) : Restraints(sf) {}
272  : Restraints(sf.begin(), sf.end()) {}
273  RestraintsAdaptor(Restraint *sf) : Restraints(1, sf) {}
274 #ifndef IMP_DOXYGEN
275  template <class T>
276  RestraintsAdaptor(internal::PointerBase<T> t)
277  : Restraints(1, get(t)) {}
278 #endif
279 };
280 
281 //! Return the decomposition of a list of restraints.
282 IMPKERNELEXPORT Restraints create_decomposition(const RestraintsTemp &rs);
283 
284 IMPKERNEL_END_NAMESPACE
285 
286 #endif /* IMPKERNEL_RESTRAINT_H */
Control display of deprecation information.
const double NO_MAX
Use this value when you want to turn off maximum for restraint evaluation.
Basic types used by IMP.
IMP::Vector< IMP::Pointer< Restraint > > Restraints
Definition: base_types.h:83
Class for adding scores from restraints to the model.
virtual RestraintInfo * get_static_info() const
Definition: Restraint.h:117
Various useful constants.
virtual RestraintInfo * get_dynamic_info() const
Definition: Restraint.h:129
Class for adding derivatives from restraints to the model.
virtual Restraints do_create_decomposition() const
Definition: Restraint.h:225
ModelObjectsTemp do_get_outputs() const
Definition: Restraint.h:242
#define IMP_REF_COUNTED_DESTRUCTOR(Name)
Ref counted objects should have private destructors.
A smart pointer to a reference counted object.
Definition: Pointer.h:87
ScoringFunction * create_scoring_function(RestraintType *rs, double weight=1.0, double max=NO_MAX, std::string name=std::string())
Create a ScoringFunction on a single restraint.
Definition: generic.h:23
IMP::Vector< IMP::WeakPointer< ModelObject > > ModelObjectsTemp
Definition: base_types.h:86
Class for storing model, its restraints, constraints, and particles.
Definition: Model.h:72
Base class for objects in a Model that depend on other objects.
Definition: ModelObject.h:26
Convenience class to accept multiple input types.
virtual Restraints do_create_current_decomposition() const
Definition: Restraint.h:235
Provide a nullptr keyword analog.
#define IMP_UNUSED(variable)
Provide a consistent interface for things that take Restraints as arguments.
Definition: Restraint.h:259
Class for adding up scores during ScoringFunction evaluation.
Restraints create_decomposition(const RestraintsTemp &rs)
Return the decomposition of a list of restraints.
Report key:value information on restraints.
Definition: RestraintInfo.h:35
Base class for objects in a Model that depend on other objects.
virtual double get_last_score() const
Definition: Restraint.h:212
bool get_was_good() const
Definition: Restraint.h:216
Represents a scoring function on the model.
Report key:value information on restraints.
double Float
Basic floating-point value (could be float, double...)
Definition: types.h:20
Convenience class to accept multiple input types.
Definition: InputAdaptor.h:25
Class for adding derivatives from restraints to the model.
A restraint is a term in an IMP ScoringFunction.
Definition: Restraint.h:54