Go to the documentation of this file.00001 #include <actasp/GraphPolicy.h>
00002
00003 #include <actasp/action_utils.h>
00004 #include "reasoners/LexComparator.h"
00005
00006 #include <algorithm>
00007 #include <typeinfo>
00008 #include <iostream>
00009 #include <iterator>
00010
00011 using namespace std;
00012
00013 namespace actasp {
00014
00015 GraphPolicy::GraphPolicy(const ActionSet& actions) : policy(), allActions(actions), plans(), planIndex() {}
00016
00017 ActionSet GraphPolicy::actions(const std::set<AspFluent>& state) const throw() {
00018
00019 std::map<set<AspFluent>, ActionSet >::const_iterator acts = policy.find(state);
00020
00021 if(acts != policy.end()) {
00022 return acts->second;
00023 }
00024
00025 return ActionSet();
00026 }
00027
00028 void GraphPolicy::merge(const PartialPolicy* otherPolicy) {
00029 const GraphPolicy *other = dynamic_cast<const GraphPolicy*>(otherPolicy);
00030 if(other != NULL)
00031 merge(other);
00032 else
00033 throw runtime_error("method not implemented for a partial policy other than GraphPolicy");
00034 }
00035
00036 void GraphPolicy::merge(const AnswerSet& plan) throw(logic_error) {
00037
00038 plans.push_back(list<AspFluent>());
00039 PlanList::iterator currentPlan = --plans.end();
00040
00041 unsigned int planLength = plan.maxTimeStep();
00042
00043 set<AspFluent> state = plan.getFluentsAtTime(0);
00044
00045 for (int timeStep = 1; timeStep <=planLength; ++timeStep) {
00046
00047 set<AspFluent> stateWithAction = plan.getFluentsAtTime(timeStep);
00048
00049
00050 set<AspFluent>::iterator actionIt = find_if(stateWithAction.begin(),stateWithAction.end(),IsAnAction(allActions));
00051
00052 if(actionIt == stateWithAction.end())
00053 throw logic_error("GraphPolicy: no action for some state");
00054
00055 AspFluent action = *actionIt;
00056
00057
00058 stateWithAction.erase(actionIt);
00059
00060 ActionSet &stateActions = policy[state];
00061
00062 stateActions.insert(action);
00063
00064 currentPlan->push_back(action);
00065
00066 std::list<AspFluent>::const_iterator currentAction = --currentPlan->end();
00067 planIndex[state].push_back(make_pair(currentPlan,currentAction));
00068
00069 state = stateWithAction;
00070
00071 }
00072
00073 }
00074
00075 struct MergeActions {
00076 MergeActions( std::map<std::set<AspFluent>, ActionSet, StateComparator<AspFluent> > &policy) : policy(policy) {}
00077
00078 void operator()(const std::pair<set<AspFluent>, ActionSet >& stateActions) {
00079
00080 map<set<AspFluent>, ActionSet >::iterator found = policy.find(stateActions.first);
00081 if(found == policy.end())
00082 policy.insert(stateActions);
00083
00084 else {
00085 found->second.insert(stateActions.second.begin(),stateActions.second.end());
00086 }
00087
00088
00089 }
00090
00091 std::map<std::set<AspFluent>, ActionSet, StateComparator<AspFluent> > &policy;
00092 };
00093
00094 void GraphPolicy::merge(const GraphPolicy* otherPolicy) {
00095
00096 set_union(otherPolicy->allActions.begin(),otherPolicy->allActions.end(),
00097 allActions.begin(),allActions.end(),
00098 inserter(allActions,allActions.begin()));
00099
00100 for_each(otherPolicy->policy.begin(),otherPolicy->policy.end(),MergeActions(policy));
00101
00102 PlanList::iterator firstPlan = plans.end();
00103 plans.insert(plans.end(),otherPolicy->plans.begin(), otherPolicy->plans.end());
00104
00105 PlanIndex::const_iterator stateOtherPolicy = otherPolicy->planIndex.begin();
00106
00107
00108 for(; stateOtherPolicy != otherPolicy->planIndex.end(); ++stateOtherPolicy) {
00109
00110 PlanReference newList;
00111
00112 PlanReference::const_iterator oldReference = stateOtherPolicy->second.begin();
00113
00114 for(; oldReference != stateOtherPolicy->second.end(); ++oldReference) {
00115 size_t planDist = distance(otherPolicy->plans.begin(),oldReference->first);
00116
00117 PlanList::iterator newPlan = firstPlan;
00118 advance(newPlan,planDist);
00119
00120 size_t actionDist = distance(oldReference->first->begin(),oldReference->second);
00121 list<AspFluent>::iterator newAction = newPlan->begin();
00122 advance(newAction,actionDist);
00123
00124 newList.push_back(make_pair(newPlan,newAction));
00125
00126 }
00127
00128 PlanReference &stateProcessed = planIndex[stateOtherPolicy->first];
00129 stateProcessed.insert(stateProcessed.end(),newList.begin(), newList.end());
00130
00131 }
00132
00133 }
00134
00135 bool GraphPolicy::empty() const throw() {
00136 return policy.empty();
00137 }
00138
00139 std::vector<actasp::AnswerSet> GraphPolicy::plansFrom(const std::set<AspFluent>& state) throw() {
00140
00141 vector<AnswerSet> result;
00142
00143 PlanIndex::const_iterator stateIt = planIndex.find(state);
00144 if(stateIt == planIndex.end())
00145 return result;
00146
00147 set< list<AspFluent>, LexComparator > plans;
00148 PlanReference::const_iterator planIt = stateIt->second.begin();
00149
00150 for(; planIt != stateIt->second.end(); ++planIt)
00151 plans.insert( list<AspFluent>(planIt->second,planIt->first->end()) );
00152
00153 set< list<AspFluent>, LexComparator >::const_iterator solutions = plans.begin();
00154 for(; solutions != plans.end(); ++solutions) {
00155
00156 result.push_back(AnswerSet(solutions->begin(), solutions->end()));
00157
00158
00159
00160 }
00161
00162
00163
00164 return result;
00165 }
00166
00167
00168 }