1 | package negotiator.boaframework.acceptanceconditions.anac2010;
|
---|
2 |
|
---|
3 | import java.util.ArrayList;
|
---|
4 | import java.util.List;
|
---|
5 | import java.util.Map;
|
---|
6 |
|
---|
7 | import genius.core.BidHistory;
|
---|
8 | import genius.core.bidding.BidDetails;
|
---|
9 | import genius.core.boaframework.AcceptanceStrategy;
|
---|
10 | import genius.core.boaframework.Actions;
|
---|
11 | import genius.core.boaframework.NegotiationSession;
|
---|
12 | import genius.core.boaframework.OfferingStrategy;
|
---|
13 | import genius.core.boaframework.OpponentModel;
|
---|
14 | import genius.core.issue.Issue;
|
---|
15 | import genius.core.issue.IssueReal;
|
---|
16 | import genius.core.issue.ValueReal;
|
---|
17 | import genius.core.utility.AdditiveUtilitySpace;
|
---|
18 | import genius.core.utility.Evaluator;
|
---|
19 | import negotiator.boaframework.sharedagentstate.anac2010.NozomiSAS;
|
---|
20 |
|
---|
21 | /**
|
---|
22 | * This is the decoupled Acceptance Conditions for Nozomi (ANAC2010). The code
|
---|
23 | * was taken from the ANAC2010 Nozomi and adapted to work within the BOA
|
---|
24 | * framework.
|
---|
25 | *
|
---|
26 | * Decoupling Negotiating Agents to Explore the Space of Negotiation Strategies
|
---|
27 | * T. Baarslag, K. Hindriks, M. Hendrikx, A. Dirkzwager, C.M. Jonker
|
---|
28 | *
|
---|
29 | * @author Alex Dirkzwager, Mark Hendrikx
|
---|
30 | */
|
---|
31 | public class AC_Nozomi extends AcceptanceStrategy {
|
---|
32 |
|
---|
33 | private double maxUtilityOfPartnerBid = 0.0;
|
---|
34 | private int measureT = 1;
|
---|
35 | private int continuousKeep = 0;
|
---|
36 | private BidDetails maxBid;
|
---|
37 |
|
---|
38 | /**
|
---|
39 | * Empty constructor for the BOA framework.
|
---|
40 | */
|
---|
41 | public AC_Nozomi() {
|
---|
42 | }
|
---|
43 |
|
---|
44 | public AC_Nozomi(NegotiationSession negoSession, OfferingStrategy strat) throws Exception {
|
---|
45 | init(negoSession, strat, null, null);
|
---|
46 | }
|
---|
47 |
|
---|
48 | @Override
|
---|
49 | public void init(NegotiationSession negoSession, OfferingStrategy strat, OpponentModel opponentModel,
|
---|
50 | Map<String, Double> parameters) throws Exception {
|
---|
51 | this.negotiationSession = negoSession;
|
---|
52 | offeringStrategy = strat;
|
---|
53 |
|
---|
54 | // checking if offeringStrategy helper is a BRAMAgentHelper
|
---|
55 | if (offeringStrategy.getHelper() == null || (!offeringStrategy.getHelper().getName().equals("Nozomi"))) {
|
---|
56 | helper = new NozomiSAS(negotiationSession, offeringStrategy.getNextBid());
|
---|
57 | } else {
|
---|
58 | helper = (NozomiSAS) offeringStrategy.getHelper();
|
---|
59 | }
|
---|
60 |
|
---|
61 | maxBid = negotiationSession.getMaxBidinDomain();
|
---|
62 | try {
|
---|
63 | ((NozomiSAS) helper).setRestoreBid(negotiationSession.getUtilitySpace().getMaxUtilityBid());
|
---|
64 | } catch (Exception e) {
|
---|
65 | e.printStackTrace();
|
---|
66 | }
|
---|
67 | }
|
---|
68 |
|
---|
69 | @Override
|
---|
70 | public Actions determineAcceptability() {
|
---|
71 | try {
|
---|
72 | BidDetails prevBid = negotiationSession.getOwnBidHistory().getLastBidDetails();
|
---|
73 | BidDetails partnerBid = negotiationSession.getOpponentBidHistory().getLastBidDetails();
|
---|
74 | double prevUtility;
|
---|
75 | if (!negotiationSession.getOwnBidHistory().getHistory().isEmpty()) {
|
---|
76 | prevUtility = negotiationSession.getOwnBidHistory().getLastBidDetails().getMyUndiscountedUtil();
|
---|
77 | } else {
|
---|
78 | prevUtility = 1;
|
---|
79 | }
|
---|
80 | double offeredUtil = negotiationSession.getOpponentBidHistory().getLastBidDetails().getMyUndiscountedUtil();
|
---|
81 | double time = negotiationSession.getTime();
|
---|
82 |
|
---|
83 | ArrayList<BidDetails> list = (ArrayList<BidDetails>) negotiationSession.getOpponentBidHistory()
|
---|
84 | .getHistory();
|
---|
85 | BidHistory historyList = new BidHistory((ArrayList<BidDetails>) list.clone());
|
---|
86 | BidDetails lastBid = negotiationSession.getOpponentBidHistory().getLastBidDetails();
|
---|
87 | historyList.getHistory().remove(lastBid);
|
---|
88 |
|
---|
89 | if (!historyList.getHistory().isEmpty())
|
---|
90 | maxUtilityOfPartnerBid = historyList.getBestBidDetails().getMyUndiscountedUtil();
|
---|
91 |
|
---|
92 | // this comes from other method in Nozomi (not in isAccept)
|
---|
93 | if (maxUtilityOfPartnerBid > ((NozomiSAS) helper).getMaxCompromiseUtility()) {
|
---|
94 | ((NozomiSAS) helper).setMaxCompromiseUtility(maxUtilityOfPartnerBid);
|
---|
95 | }
|
---|
96 |
|
---|
97 | if (((NozomiSAS) helper).getMaxCompromiseUtility() > maxBid.getMyUndiscountedUtil() * 0.95) {
|
---|
98 | ((NozomiSAS) helper).setMaxCompromiseUtility(maxBid.getMyUndiscountedUtil() * 0.95);
|
---|
99 | }
|
---|
100 |
|
---|
101 | if (continuousKeep <= 0) {
|
---|
102 | if (helper != offeringStrategy.getHelper()) {
|
---|
103 | ((NozomiSAS) helper).updateRestoreBid(offeringStrategy.getNextBid().getBid());
|
---|
104 | }
|
---|
105 | }
|
---|
106 |
|
---|
107 | if (time > (double) measureT * 3.0) {
|
---|
108 | if (helper != offeringStrategy.getHelper()) {
|
---|
109 | ((NozomiSAS) helper).checkCompromise(time);
|
---|
110 | }
|
---|
111 | measureT++;
|
---|
112 | }
|
---|
113 |
|
---|
114 | if ((negotiationSession.getOwnBidHistory().getLastBidDetails() != null)
|
---|
115 | && offeringStrategy.getNextBid().getMyUndiscountedUtil() == negotiationSession.getOwnBidHistory()
|
---|
116 | .getLastBidDetails().getMyUndiscountedUtil()) {
|
---|
117 | continuousKeep++;
|
---|
118 | } else {
|
---|
119 | continuousKeep = 0;
|
---|
120 | }
|
---|
121 |
|
---|
122 | if (offeredUtil > maxUtilityOfPartnerBid) {
|
---|
123 | ((NozomiSAS) helper).setMaxUtilityPartnerBidDetails(partnerBid);
|
---|
124 | maxUtilityOfPartnerBid = offeredUtil;
|
---|
125 | ((NozomiSAS) helper).setUpdateMaxPartnerUtility(true);
|
---|
126 | }
|
---|
127 |
|
---|
128 | if (offeredUtil > maxBid.getMyUndiscountedUtil() * 0.95 || offeredUtil >= prevUtility) {
|
---|
129 | return Actions.Accept;
|
---|
130 |
|
---|
131 | } else {
|
---|
132 | List<Issue> issues = negotiationSession.getIssues();
|
---|
133 |
|
---|
134 | double evalGap = 0.0;
|
---|
135 | for (Issue issue : issues) {
|
---|
136 | int issueID = issue.getNumber();
|
---|
137 |
|
---|
138 | switch (issue.getType()) {
|
---|
139 | case REAL:
|
---|
140 | IssueReal issueReal = (IssueReal) issue;
|
---|
141 | ValueReal valueReal = (ValueReal) prevBid.getBid().getValue(issueID);
|
---|
142 | ValueReal partnerValueReal = (ValueReal) partnerBid.getBid().getValue(issueID);
|
---|
143 | double gap = Math.abs(valueReal.getValue() - partnerValueReal.getValue());
|
---|
144 | if (gap > (issueReal.getUpperBound() - issueReal.getLowerBound()) / 100) {
|
---|
145 | evalGap += 0.5;
|
---|
146 | }
|
---|
147 | break;
|
---|
148 | default:
|
---|
149 | if ((prevBid != null)
|
---|
150 | && !prevBid.getBid().getValue(issueID).equals(partnerBid.getBid().getValue(issueID))) {
|
---|
151 | evalGap += 0.5;
|
---|
152 | }
|
---|
153 | break;
|
---|
154 | }
|
---|
155 |
|
---|
156 | Evaluator eval = ((AdditiveUtilitySpace) negotiationSession.getUtilitySpace())
|
---|
157 | .getEvaluator(issueID);
|
---|
158 |
|
---|
159 | try {
|
---|
160 | evalGap += Math.abs(eval.getEvaluation(
|
---|
161 | (AdditiveUtilitySpace) negotiationSession.getUtilitySpace(), prevBid.getBid(), issueID)
|
---|
162 | - eval.getEvaluation((AdditiveUtilitySpace) negotiationSession.getUtilitySpace(),
|
---|
163 | partnerBid.getBid(), issueID));
|
---|
164 | } catch (Exception e) {
|
---|
165 | evalGap += 1.0;
|
---|
166 | }
|
---|
167 |
|
---|
168 | evalGap += 0.5;
|
---|
169 | }
|
---|
170 |
|
---|
171 | evalGap /= 2.0 * (double) issues.size();
|
---|
172 | if (time < 0.50) {
|
---|
173 | if (negotiationSession.getOpponentBidHistory().getLastBidDetails() != null
|
---|
174 | && offeredUtil > ((NozomiSAS) helper).getMaxCompromiseUtility()
|
---|
175 | && offeredUtil >= maxUtilityOfPartnerBid) {
|
---|
176 | double acceptCoefficient = -0.1 * time + 1.0;
|
---|
177 | // double sameIssueRatio = (double)sameIssueNumber /
|
---|
178 | // (double)issues.size();
|
---|
179 | if (evalGap < 0.30 && offeredUtil > prevUtility * acceptCoefficient) {
|
---|
180 | return Actions.Accept;
|
---|
181 |
|
---|
182 | }
|
---|
183 | }
|
---|
184 | } else if (time < 0.80) {
|
---|
185 | if (negotiationSession.getOpponentBidHistory().getLastBidDetails() != null
|
---|
186 | && offeredUtil > ((NozomiSAS) helper).getMaxCompromiseUtility() * 0.95
|
---|
187 | && offeredUtil > maxUtilityOfPartnerBid * 0.95) {
|
---|
188 | double diffMyBidAndOffered = prevUtility - offeredUtil;
|
---|
189 | // double ratioOfferedToMaxUtility = offeredUtil /
|
---|
190 | // maxUtility;
|
---|
191 | // double ratioOfferedToMaxOffered = offeredUtil /
|
---|
192 | // maxUtilityOfPartnerBid;
|
---|
193 |
|
---|
194 | if (diffMyBidAndOffered < 0.0)
|
---|
195 | diffMyBidAndOffered = 0.0;
|
---|
196 |
|
---|
197 | double acceptCoefficient = -0.16 * (time - 0.50) + 0.95;
|
---|
198 | // double sameIssueRatio = (double)sameIssueNumber /
|
---|
199 | // (double)issues.size();
|
---|
200 | if (evalGap < 0.35 && offeredUtil > prevUtility * acceptCoefficient) {
|
---|
201 | return Actions.Accept;
|
---|
202 | }
|
---|
203 | }
|
---|
204 | } else {
|
---|
205 |
|
---|
206 | if (negotiationSession.getOpponentBidHistory().getLastBidDetails() != null
|
---|
207 | && offeredUtil > ((NozomiSAS) helper).getPrevMaxCompromiseUtility() * 0.90
|
---|
208 | && offeredUtil > maxUtilityOfPartnerBid * 0.95) {
|
---|
209 |
|
---|
210 | double restoreEvalGap = 0.0;
|
---|
211 | for (Issue issue : issues) {
|
---|
212 | int issueID = issue.getNumber();
|
---|
213 |
|
---|
214 | switch (issue.getType()) {
|
---|
215 | case REAL:
|
---|
216 | IssueReal issueReal = (IssueReal) issue;
|
---|
217 | ValueReal valueReal = (ValueReal) ((NozomiSAS) helper).getPrevRestoreBid()
|
---|
218 | .getValue(issueID);
|
---|
219 | ValueReal partnerValueReal = (ValueReal) partnerBid.getBid().getValue(issueID);
|
---|
220 | double gap = Math.abs(valueReal.getValue() - partnerValueReal.getValue());
|
---|
221 | if (gap > (issueReal.getUpperBound() - issueReal.getLowerBound()) / 100) {
|
---|
222 | restoreEvalGap += 0.5;
|
---|
223 | }
|
---|
224 | break;
|
---|
225 | default:
|
---|
226 | if (!((NozomiSAS) helper).getPrevRestoreBid().getValue(issueID)
|
---|
227 | .equals(partnerBid.getBid().getValue(issueID))) {
|
---|
228 | restoreEvalGap += 0.5;
|
---|
229 | }
|
---|
230 | break;
|
---|
231 | }
|
---|
232 |
|
---|
233 | Evaluator eval = ((AdditiveUtilitySpace) negotiationSession.getUtilitySpace())
|
---|
234 | .getEvaluator(issueID);
|
---|
235 |
|
---|
236 | try {
|
---|
237 | restoreEvalGap += Math.abs(
|
---|
238 | eval.getEvaluation((AdditiveUtilitySpace) negotiationSession.getUtilitySpace(),
|
---|
239 | prevBid.getBid(), issueID)
|
---|
240 | - eval.getEvaluation(
|
---|
241 | (AdditiveUtilitySpace) negotiationSession.getUtilitySpace(),
|
---|
242 | partnerBid.getBid(), issueID));
|
---|
243 | } catch (Exception e) {
|
---|
244 | restoreEvalGap += 1.0;
|
---|
245 | }
|
---|
246 |
|
---|
247 | restoreEvalGap += 0.5;
|
---|
248 | }
|
---|
249 | restoreEvalGap /= 2.0 * (double) issues.size();
|
---|
250 |
|
---|
251 | double threshold = 0.40;
|
---|
252 |
|
---|
253 | if (time > 0.90) {
|
---|
254 | threshold = 0.50;
|
---|
255 | }
|
---|
256 |
|
---|
257 | if (restoreEvalGap <= threshold || evalGap <= threshold) {
|
---|
258 |
|
---|
259 | return Actions.Accept;
|
---|
260 | }
|
---|
261 | }
|
---|
262 | }
|
---|
263 | }
|
---|
264 | } catch (Exception e) {
|
---|
265 | e.printStackTrace();
|
---|
266 | return Actions.Reject;
|
---|
267 | }
|
---|
268 | return Actions.Reject;
|
---|
269 | }
|
---|
270 |
|
---|
271 | @Override
|
---|
272 | public String getName() {
|
---|
273 | return "2010 - Nozomi";
|
---|
274 | }
|
---|
275 | } |
---|