1#line 1 "/cycamore/src/enrichment.cc"
11#include <boost/lexical_cast.hpp>
13using cyclus::Material;
19 : cyclus::Facility(ctx),
39 ss << cyclus::Facility::str() <<
" with enrichment facility parameters:"
50 Facility::Build(parent);
56 LOG(cyclus::LEV_DEBUG2,
"EnrFac") <<
"Enrichment "
57 <<
" entering the simuluation: ";
58 LOG(cyclus::LEV_DEBUG2,
"EnrFac") <<
str();
70 using cyclus::toolkit::RecordTimeSeries;
71 LOG(cyclus::LEV_INFO4,
"EnrFac") << prototype() <<
" used "
74 LOG(cyclus::LEV_INFO4,
"EnrFac") << prototype() <<
" used "
81std::set<cyclus::RequestPortfolio<Material>::Ptr>
83 using cyclus::RequestPortfolio;
85 std::set<RequestPortfolio<Material>::Ptr> ports;
86 RequestPortfolio<Material>::Ptr port(
new RequestPortfolio<Material>());
88 double amt = mat->quantity();
90 if (amt > cyclus::eps_rsrc()) {
100 cyclus::Bid<Material>* j) {
101 Material::Ptr mat_i = i->offer();
102 Material::Ptr mat_j = j->offer();
104 cyclus::toolkit::MatQuery mq_i(mat_i);
105 cyclus::toolkit::MatQuery mq_j(mat_j);
107 return ((mq_i.mass(922350000) / mq_i.qty()) <=
108 (mq_j.mass(922350000) / mq_j.qty()));
114 cyclus::PrefMap<Material>::type& prefs) {
121 cyclus::PrefMap<Material>::type::iterator reqit;
124 for (reqit = prefs.begin(); reqit != prefs.end(); ++reqit) {
125 std::vector<Bid<Material>*> bids_vector;
126 std::map<Bid<Material>*,
double>::iterator mit;
127 for (mit = reqit->second.begin(); mit != reqit->second.end(); ++mit) {
128 Bid<Material>* bid = mit->first;
129 bids_vector.push_back(bid);
131 std::sort(bids_vector.begin(), bids_vector.end(),
SortBids);
134 double n_bids = bids_vector.size();
137 for (
int bidit = 0; bidit < bids_vector.size(); bidit++) {
138 int new_pref = bidit + 1;
142 Material::Ptr mat = bids_vector[bidit]->offer();
143 cyclus::toolkit::MatQuery mq(mat);
144 if (mq.mass(922350000) == 0) {
150 (reqit->second)[bids_vector[bidit]] = new_pref;
157 const std::vector<std::pair<cyclus::Trade<Material>,
158 Material::Ptr> >& responses) {
161 std::vector<std::pair<cyclus::Trade<Material>,
162 Material::Ptr> >::const_iterator it;
163 for (it = responses.begin(); it != responses.end(); ++it) {
170 cyclus::CommodMap<Material>::type& out_requests) {
171 using cyclus::BidPortfolio;
172 using cyclus::CapacityConstraint;
173 using cyclus::Converter;
174 using cyclus::Request;
175 using cyclus::toolkit::MatVec;
176 using cyclus::toolkit::RecordTimeSeries;
178 std::set<BidPortfolio<Material>::Ptr> ports;
183 BidPortfolio<Material>::Ptr tails_port(
new BidPortfolio<Material>());
185 std::vector<Request<Material>*>& tails_requests =
187 std::vector<Request<Material>*>::iterator it;
188 for (it = tails_requests.begin(); it != tails_requests.end(); ++it) {
193 for (
int k = 0; k < mats.size(); k++) {
194 Material::Ptr m = mats[k];
195 Request<Material>* req = *it;
196 tails_port->AddBid(req, m,
this);
201 CapacityConstraint<Material> tails_constraint(
tails.quantity());
202 tails_port->AddConstraint(tails_constraint);
203 LOG(cyclus::LEV_INFO5,
"EnrFac") << prototype()
204 <<
" adding tails capacity constraint of "
206 ports.insert(tails_port);
210 BidPortfolio<Material>::Ptr commod_port(
new BidPortfolio<Material>());
212 std::vector<Request<Material>*>& commod_requests =
214 std::vector<Request<Material>*>::iterator it;
215 for (it = commod_requests.begin(); it != commod_requests.end(); ++it) {
216 Request<Material>* req = *it;
217 Material::Ptr mat = req->target();
218 double request_enrich = cyclus::toolkit::UraniumAssayMass(mat);
221 (cyclus::AlmostEq(request_enrich,
max_enrich)))) {
222 Material::Ptr offer =
Offer_(req->target());
223 commod_port->AddBid(req, offer,
this);
230 CapacityConstraint<Material> natu(
inventory.quantity(), nc);
231 commod_port->AddConstraint(swu);
232 commod_port->AddConstraint(natu);
234 LOG(cyclus::LEV_INFO5,
"EnrFac")
235 << prototype() <<
" adding a swu constraint of " << swu.capacity();
236 LOG(cyclus::LEV_INFO5,
"EnrFac")
237 << prototype() <<
" adding a natu constraint of " << natu.capacity();
238 ports.insert(commod_port);
245 cyclus::toolkit::MatQuery q(mat);
246 double u235 = q.atom_frac(922350000);
247 double u238 = q.atom_frac(922380000);
248 return (u238 > 0 && u235 / (u235 + u238) >
tails_assay);
253 const std::vector<cyclus::Trade<Material> >& trades,
254 std::vector<std::pair<cyclus::Trade<Material>,
255 Material::Ptr> >& responses) {
261 std::vector<Trade<Material>>::const_iterator it;
262 for (it = trades.begin(); it != trades.end(); ++it) {
263 double qty = it->amt;
264 std::string commod_type = it->bid->request()->commodity();
265 Material::Ptr response;
269 LOG(cyclus::LEV_INFO5,
"EnrFac")
270 << prototype() <<
" just received an order"
272 double pop_qty = std::min(qty,
tails.quantity());
273 response =
tails.Pop(pop_qty, cyclus::eps_rsrc());
275 LOG(cyclus::LEV_INFO5,
"EnrFac")
276 << prototype() <<
" just received an order"
278 response =
Enrich_(it->bid->offer(), qty);
280 responses.push_back(std::make_pair(*it, response));
283 if (cyclus::IsNegative(
tails.quantity())) {
284 std::stringstream ss;
285 ss <<
"is being asked to provide more than its current inventory.";
286 throw cyclus::ValueError(Agent::InformErrorMsg(ss.str()));
289 throw cyclus::ValueError(
"EnrFac " + prototype() +
290 " is being asked to provide more than" +
291 " its SWU capacity.");
298 cyclus::CompMap cm = mat->comp()->atom();
299 bool extra_u =
false;
300 bool other_elem =
false;
301 for (cyclus::CompMap::const_iterator it = cm.begin(); it != cm.end(); ++it) {
302 if (pyne::nucname::znum(it->first) == 92) {
303 if (pyne::nucname::anum(it->first) != 235 &&
304 pyne::nucname::anum(it->first) != 238 && it->second > 0) {
307 }
else if (it->second > 0) {
312 cyclus::Warn<cyclus::VALUE_WARNING>(
313 "More than 2 isotopes of U. "
314 "Istopes other than U-235, U-238 are sent directly to tails.");
317 cyclus::Warn<cyclus::VALUE_WARNING>(
318 "Non-uranium elements are "
319 "sent directly to tails.");
322 LOG(cyclus::LEV_INFO5,
"EnrFac") << prototype() <<
" is initially holding "
327 }
catch (cyclus::Error& e) {
328 e.msg(Agent::InformErrorMsg(e.msg()));
332 LOG(cyclus::LEV_INFO5,
"EnrFac")
333 << prototype() <<
" added " << mat->quantity() <<
" of " <<
feed_commod
334 <<
" to its inventory, which is holding " <<
inventory.quantity()
341 return Material::CreateUntracked(qty,
347 cyclus::toolkit::MatQuery q(mat);
348 cyclus::CompMap comp;
349 comp[922350000] = q.atom_frac(922350000);
350 comp[922380000] = q.atom_frac(922380000);
351 return Material::CreateUntracked(
352 mat->quantity(), cyclus::Composition::CreateFromAtom(comp));
357 using cyclus::toolkit::Assays;
358 using cyclus::toolkit::UraniumAssayMass;
359 using cyclus::toolkit::SwuRequired;
360 using cyclus::toolkit::FeedQty;
361 using cyclus::toolkit::TailsQty;
365 double swu_req = SwuRequired(qty, assays);
366 double natu_req = FeedQty(qty, assays);
371 Material::Ptr natu_matl =
inventory.Pop(pop_qty, cyclus::eps_rsrc());
374 cyclus::toolkit::MatQuery mq(natu_matl);
375 std::set<cyclus::Nuc> nucs;
376 nucs.insert(922350000);
377 nucs.insert(922380000);
378 double natu_frac = mq.mass_frac(nucs);
379 double feed_req = natu_req / natu_frac;
385 if (cyclus::AlmostEq(feed_req,
inventory.quantity())) {
388 r =
inventory.Pop(feed_req, cyclus::eps_rsrc());
390 }
catch (cyclus::Error& e) {
392 std::stringstream ss;
393 ss <<
" tried to remove " << feed_req <<
" from its inventory of size "
395 <<
" and the conversion of the material into natu is "
397 throw cyclus::ValueError(Agent::InformErrorMsg(ss.str()));
402 cyclus::Composition::Ptr comp = mat->comp();
403 Material::Ptr response = r->ExtractComp(qty, comp);
412 LOG(cyclus::LEV_INFO5,
"EnrFac") << prototype()
413 <<
" has performed an enrichment: ";
414 LOG(cyclus::LEV_INFO5,
"EnrFac") <<
" * Feed Qty: " << feed_req;
415 LOG(cyclus::LEV_INFO5,
"EnrFac") <<
" * Feed Assay: "
416 << assays.Feed() * 100;
417 LOG(cyclus::LEV_INFO5,
"EnrFac") <<
" * Product Qty: " << qty;
418 LOG(cyclus::LEV_INFO5,
"EnrFac") <<
" * Product Assay: "
419 << assays.Product() * 100;
420 LOG(cyclus::LEV_INFO5,
"EnrFac") <<
" * Tails Qty: "
421 << TailsQty(qty, assays);
422 LOG(cyclus::LEV_INFO5,
"EnrFac") <<
" * Tails Assay: "
423 << assays.Tails() * 100;
424 LOG(cyclus::LEV_INFO5,
"EnrFac") <<
" * SWU: " << swu_req;
425 LOG(cyclus::LEV_INFO5,
"EnrFac") <<
" * Current SWU capacity: "
433 using cyclus::Context;
436 LOG(cyclus::LEV_DEBUG1,
"EnrFac") << prototype()
437 <<
" has enriched a material:";
438 LOG(cyclus::LEV_DEBUG1,
"EnrFac") <<
" * Amount: " << natural_u;
439 LOG(cyclus::LEV_DEBUG1,
"EnrFac") <<
" * SWU: " << swu;
441 Context* ctx = Agent::context();
442 ctx->NewDatum(
"Enrichments")
443 ->AddVal(
"AgentId",
id())
444 ->AddVal(
"Time", ctx->time())
445 ->AddVal(
"Natural_Uranium", natural_u)
455 Material::Ptr fission_matl =
456 inventory.Pop(pop_qty, cyclus::eps_rsrc());
458 return cyclus::toolkit::UraniumAssayMass(fission_matl);
463 std::string specification = this->spec();
465 ->NewDatum(
"AgentPosition")
466 ->AddVal(
"Spec", specification)
467 ->AddVal(
"Prototype", this->prototype())
468 ->AddVal(
"AgentId",
id())
The Enrichment facility is a simple Agent that enriches natural uranium in a Cyclus simulation.
void RecordPosition()
Records an agent's latitude and longitude to the output db.
cyclus::Material::Ptr Request_()
generates a request for this facility given its current state.
double current_swu_capacity
cyclus::Material::Ptr Enrich_(cyclus::Material::Ptr mat, double qty)
cyclus::Material::Ptr Offer_(cyclus::Material::Ptr req)
Generates a material offer for a given request.
std::string product_commod
virtual std::set< cyclus::RequestPortfolio< cyclus::Material >::Ptr > GetMatlRequests()
The Enrichment request Materials of its given commodity.
virtual void Tock()
Each facility is prompted to its end-of-time-step stuff on the tock of the timer.
cyclus::toolkit::ResBuf< cyclus::Material > tails
bool ValidReq(const cyclus::Material::Ptr mat)
Determines if a particular material is a valid request to respond to.
double intra_timestep_swu_
virtual ~Enrichment()
Destructor for the Enrichment class.
virtual void AdjustMatlPrefs(cyclus::PrefMap< cyclus::Material >::type &prefs)
The Enrichment adjusts preferences for offers of natural uranium it has received to maximize U-235 co...
double SwuCapacity() const
virtual std::string str()
Print information about this agent.
virtual void AcceptMatlTrades(const std::vector< std::pair< cyclus::Trade< cyclus::Material >, cyclus::Material::Ptr > > &responses)
The Enrichment place accepted trade Materials in their Inventory.
double FeedAssay()
calculates the feed assay based on the unenriched inventory
virtual std::set< cyclus::BidPortfolio< cyclus::Material >::Ptr > GetMatlBids(cyclus::CommodMap< cyclus::Material >::type &commod_requests)
Responds to each request for this facility's commodity.
virtual void Tick()
Each facility is prompted to do its beginning-of-time-step stuff at the tick of the timer.
void RecordEnrichment_(double natural_u, double swu)
records and enrichment with the cyclus::Recorder
double intra_timestep_feed_
Enrichment(cyclus::Context *ctx)
Constructor for the Enrichment class.
cyclus::toolkit::ResBuf< cyclus::Material > inventory
virtual void GetMatlTrades(const std::vector< cyclus::Trade< cyclus::Material > > &trades, std::vector< std::pair< cyclus::Trade< cyclus::Material >, cyclus::Material::Ptr > > &responses)
respond to each trade with a material enriched to the appropriate level given this facility's invento...
virtual void Build(cyclus::Agent *parent)
perform module-specific tasks when entering the simulation
void AddMat_(cyclus::Material::Ptr mat)
adds a material into the natural uranium inventory
cyclus::Agent * ConstructEnrichment(cyclus::Context *ctx)
cyclus::toolkit::Position coordinates
bool SortBids(cyclus::Bid< Material > *i, cyclus::Bid< Material > *j)