CYCLUS
greedy_preconditioner.cc
Go to the documentation of this file.
2 
3 #include <algorithm>
4 #include <assert.h>
5 #include <numeric>
6 #include <string>
7 
8 #include <boost/lambda/bind.hpp>
9 
10 #include "cyc_std.h"
11 #include "logger.h"
12 
13 namespace l = boost::lambda;
14 
15 namespace cyclus {
16 
17 inline double SumPref(double total, std::pair<Arc, double> pref) {
18  return total += pref.second;
19 }
20 
22  std::map<Arc, double>& prefs = n->prefs;
23  return prefs.size() > 0 ?
24  std::accumulate(prefs.begin(), prefs.end(), 0.0, SumPref) / prefs.size() :
25  0;
26 }
27 
29 
31  const std::map<std::string, double>& commod_weights)
32  : commod_weights_(commod_weights) {
33  if (commod_weights_.size() != 0)
34  ProcessWeights_(END);
35 };
36 
38  const std::map<std::string, double>& commod_weights,
39  WgtOrder order)
40  : commod_weights_(commod_weights) {
41  if (commod_weights_.size() != 0)
42  ProcessWeights_(order);
43 };
44 
46  avg_prefs_.clear();
47 
48  std::vector<RequestGroup::Ptr>& groups =
49  const_cast<std::vector<RequestGroup::Ptr>&>(graph->request_groups());
50 
51  std::vector<RequestGroup::Ptr>::iterator it;
52  for (it = groups.begin(); it != groups.end(); ++it) {
53  std::vector<ExchangeNode::Ptr>& nodes =
54  const_cast<std::vector<ExchangeNode::Ptr>&>((*it)->nodes());
55 
56  // get avg prefs
57  for (int i = 0; i != nodes.size(); i++) {
58  avg_prefs_[nodes[i]] = AvgPref(nodes[i]);
59  }
60 
61  // sort nodes by weight
62  std::stable_sort(
63  nodes.begin(), nodes.end(),
64  l::bind(&GreedyPreconditioner::NodeComp, this, l::_1, l::_2));
65 
66  // get avg group weights
67  group_weights_[*it] = GroupWeight(*it, &commod_weights_, &avg_prefs_);
68  CLOG(LEV_DEBUG1) << "Group weight value during graph preconditioning is "
69  << group_weights_[*it] << ".";
70  }
71 
72  // sort groups by avg weight
73  std::stable_sort(
74  groups.begin(), groups.end(),
75  l::bind(&GreedyPreconditioner::GroupComp, this, l::_1, l::_2));
76 
77  // clear graph-specific state
78  group_weights_.clear();
79 }
80 
81 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
82 void GreedyPreconditioner::ProcessWeights_(WgtOrder order) {
83  double min = std::min_element(
84  commod_weights_.begin(),
85  commod_weights_.end(),
87 
88  double max = std::max_element(
89  commod_weights_.begin(),
90  commod_weights_.end(),
92 
93  assert(commod_weights_.size() == 0 || min >= 0);
94 
95  std::map<std::string, double>::iterator it;
96  switch (order) {
97  case REVERSE:
98  for (it = commod_weights_.begin();
99  it != commod_weights_.end();
100  ++it) {
101  it->second = max + min - it->second; // reverses order
102  }
103  break;
104  default: // do nothing
105  break;
106  }
107 
108  for (it = commod_weights_.begin();
109  it != commod_weights_.end();
110  ++it) {
111  CLOG(LEV_INFO1) << "GreedyPreconditioner commodity weight value for "
112  << it->first
113  << " is " << it->second;
114  }
115 }
116 
117 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
119  std::map<std::string, double>* weights,
120  std::map<ExchangeNode::Ptr, double>* avg_prefs) {
121  std::vector<ExchangeNode::Ptr>& nodes = g->nodes();
122  double sum = 0;
123 
125  for (int i = 0; i != nodes.size(); i++) {
126  n = nodes[i];
127  sum += NodeWeight(n, weights, (*avg_prefs)[n]);
128  }
129  return nodes.size() > 0 ? sum / nodes.size() : 0;
130 }
131 
132 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
134  std::map<std::string, double>* weights,
135  double avg_pref) {
136  double commod_weight = (weights->size() != 0) ? (*weights)[n->commod] : 1;
137  double node_weight = commod_weight * (1 + avg_pref / (1 + avg_pref));
138 
139  CLOG(LEV_DEBUG5) << "Determining node weight: ";
140  CLOG(LEV_DEBUG5) << " commodity weight: " << commod_weight;
141  CLOG(LEV_DEBUG5) << " avg pref: " << avg_pref;
142  CLOG(LEV_DEBUG5) << " node weight: " << node_weight;
143 
144  return node_weight;
145 }
146 
147 } // namespace cyclus
GreedyPreconditioner()
constructor if weights are given in heaviest-first order
a less-than comparison for pairs
Definition: cyc_std.h:11
bool NodeComp(const ExchangeNode::Ptr l, const ExchangeNode::Ptr r)
a comparitor for ordering containers of ExchangeNode::Ptrs in descending order based on their commodi...
boost::shared_ptr< RequestGroup > Ptr
boost::shared_ptr< ExchangeNode > Ptr
#define CLOG(level)
Definition: logger.h:39
double GroupWeight(RequestGroup::Ptr g, std::map< std::string, double > *weights, std::map< ExchangeNode::Ptr, double > *avg_prefs)
debugging information - most verbose
Definition: logger.h:62
Information helpful for simulation users and developers alike - least verbose.
Definition: logger.h:53
const double g
Definition: material.h:18
double SumPref(double total, std::pair< Arc, double > pref)
a flag for commodity weights given in the reverse order,
Code providing rudimentary logging capability for the Cyclus core.
taken directly from OsiSolverInterface.cpp on 2/17/14 from https://projects.coin-or.org/Osi/browser/trunk.
Definition: agent.cc:14
debugging information - least verbose
Definition: logger.h:58
double AvgPref(ExchangeNode::Ptr n)
bool GroupComp(const RequestGroup::Ptr l, const RequestGroup::Ptr r)
a comparitor for ordering containers of Request::Ptrs in descending order based on their average comm...
const std::vector< RequestGroup::Ptr > & request_groups() const
double NodeWeight(ExchangeNode::Ptr n, std::map< std::string, double > *weights, double avg_pref)
An ExchangeGraph is a resource-neutral representation of a ResourceExchange.
void Condition(ExchangeGraph *graph)
conditions the graph as described above
WgtOrder
the order of commodity weights