IMP  2.0.1
The Integrative Modeling Platform
kernel/ScoreAccumulator.h
Go to the documentation of this file.
1 /**
2  * \file IMP/kernel/ScoreAccumulator.h \brief Class for adding scores from
3  * restraints to the model.
4  *
5  * Copyright 2007-2013 IMP Inventors. All rights reserved.
6  *
7  */
8 
9 #ifndef IMPKERNEL_SCORE_ACCUMULATOR_H
10 #define IMPKERNEL_SCORE_ACCUMULATOR_H
11 
12 #include <IMP/kernel/kernel_config.h>
13 #include "DerivativeAccumulator.h"
14 #include "constants.h"
16 #include <IMP/base/value_macros.h>
17 #include <IMP/base/thread_macros.h>
18 #include <IMP/base/log_macros.h>
19 #include <IMP/base/tuple_macros.h>
20 #include <IMP/base/math.h>
21 #include <IMP/base/nullptr.h>
22 #include <IMP/base/exception.h>
23 
24 IMPKERNEL_BEGIN_NAMESPACE
25 
26 class Restraint;
27 
28 /** A class for storing evaluation state.*/
30  double score;
31  bool good;
32  EvaluationState(double oscore, bool ogood): score(oscore), good(ogood) {}
33  EvaluationState(): score(BAD_SCORE), good(false){}
34  IMP_SHOWABLE_INLINE(EvaluationState, out << score << " " << good;);
35 };
37 
38 //! Class for adding up scores during ScoringFunction evaluation.
39 /** This provides a place to accumulate scores from Restraint
40  evaluation. A new ScoreAccumulator is created for each Restraint
41  evaluation context (eg each Restraint::add_score_and_derivatives() call).
42  As a result, the ScoreAccumulator can automatically handle
43  restraint and derivative weights, keeping track of maximum scores
44  and other needed bookkeeping.
45 */
46 class IMPKERNELEXPORT ScoreAccumulator: public base::Value {
47  EvaluationState *score_;
48  DerivativeAccumulator weight_;
49  double global_max_;
50  double local_max_;
51  bool deriv_;
52  bool abort_on_bad_;
53  friend class ScoringFunction;
54  friend class Restraint;
55  ScoreAccumulator(EvaluationState *s, double weight, bool deriv,
56  double global_max, double local_max, bool abort_on_bad):
57  score_(s),
58  weight_(weight),
59  global_max_(global_max),
60  local_max_(local_max),
61  deriv_(deriv),
62  abort_on_bad_(abort_on_bad) {}
63 
64 
65 public:
66  /** For swig, makes invalid (not null) state.*/
67  ScoreAccumulator(): score_(nullptr) {}
68  /** Compose outer accumulator with one for this restraint. */
70  const Restraint *r);
71 
72  /** Compose outer accumulator with one for this restraint. */
74  double weight, double local_max) {
75  operator=(o);
76  weight_= DerivativeAccumulator(o.weight_, weight);
77  local_max_= std::min(local_max, o.local_max_);
78  }
79 
80  /** Add to the total score. It will be weighted appropriately
81  internally. */
82  void add_score(double score) {
83  double wscore= weight_.get_weight()*score;
84 IMP_OMP_PRAGMA(atomic)
85  score_->score += wscore;
86  if (score > local_max_) {
87 IMP_OMP_PRAGMA(critical (imp_abort))
88  score_->good= false;
89  }
90  IMP_LOG_VERBOSE( "Score is now " << score_->score << std::endl);
91  }
92 
93  //! Return if the score already exceeds the maximum
94  /** Expensive restraints can check this during evaluation to determin
95  if another restraint has aborted evaluation.
96  */
97  bool get_abort_evaluation() const {
98  if (global_max_== NO_MAX && !abort_on_bad_) return false;
99  if (abort_on_bad_) {
100  bool good;
101 IMP_OMP_PRAGMA(critical (imp_abort))
102  good= score_->good;
103  return !good;
104  } else {
105  // be lazy for now
106  //#pragma omp flush (score_->score)
107  double score= score_->score;
108  return score > global_max_;
109  }
110  }
111 
112  /** Return true if the current evaluation being done is one where
113  scores are only consider if they are below some threshold
114  (get_maximum()). */
115  bool get_is_evaluate_if_below() const {return global_max_ != NO_MAX;}
116  /** Return true if the current evaluation should abort if any restraint
117  is above its maximum allowed good score. Restraints that take
118  advantage of this in evaluation should simply consult
119  get_maximum() as that will take into account both their maximum
120  and that on any RestraintSets that contain them and are being
121  evaluated.
122  */
123  bool get_is_evaluate_if_good() const {return abort_on_bad_;}
124  /** The maximum allowed score for the
125  Restraint::do_add_score_and_derivatives() call. */
126  double get_maximum() const {return std::min(global_max_, local_max_);}
127 
128  DerivativeAccumulator *get_derivative_accumulator() {
129  if (deriv_) {
130  return &weight_;
131  } else {
132  return nullptr;
133  }
134  }
135 
136  IMP_SHOWABLE_INLINE(ScoreAccumulator, out << *score_);
137 };
138 
140 
141 IMPKERNEL_END_NAMESPACE
142 
143 #endif /* IMPKERNEL_SCORE_ACCUMULATOR_H */