1 | package agents.anac.y2017.geneking;
|
---|
2 |
|
---|
3 | import java.io.IOException;
|
---|
4 | import java.util.ArrayList;
|
---|
5 | import java.util.HashMap;
|
---|
6 | import java.util.List;
|
---|
7 | import java.util.Map;
|
---|
8 | import java.util.Random;
|
---|
9 | import java.util.Set;
|
---|
10 |
|
---|
11 | import genius.core.AgentID;
|
---|
12 | import genius.core.Bid;
|
---|
13 | import genius.core.actions.Accept;
|
---|
14 | import genius.core.actions.Action;
|
---|
15 | import genius.core.actions.EndNegotiation;
|
---|
16 | import genius.core.actions.Offer;
|
---|
17 | import genius.core.issue.ISSUETYPE;
|
---|
18 | import genius.core.issue.Issue;
|
---|
19 | import genius.core.issue.IssueDiscrete;
|
---|
20 | import genius.core.issue.IssueInteger;
|
---|
21 | import genius.core.issue.IssueReal;
|
---|
22 | import genius.core.issue.Value;
|
---|
23 | import genius.core.issue.ValueDiscrete;
|
---|
24 | import genius.core.issue.ValueInteger;
|
---|
25 | import genius.core.issue.ValueReal;
|
---|
26 | import genius.core.list.Tuple;
|
---|
27 | import genius.core.parties.AbstractNegotiationParty;
|
---|
28 | import genius.core.parties.NegotiationInfo;
|
---|
29 | import genius.core.persistent.StandardInfo;
|
---|
30 | import genius.core.persistent.StandardInfoList;
|
---|
31 | import genius.core.utility.EvaluatorDiscrete;
|
---|
32 |
|
---|
33 | /**
|
---|
34 | * @author W.Pasman Some improvements over the standard SimpleAgent.
|
---|
35 | *
|
---|
36 | * Random Walker, Zero Intelligence Agent
|
---|
37 | */
|
---|
38 |
|
---|
39 | class IssueFreqRank {// ある論点中の頻度等
|
---|
40 | private HashMap<String, Integer> frequenceS;// 各提案内容の頻度
|
---|
41 | private int sum;// 全頻度の合計
|
---|
42 | private int maxFreq;// 最大頻度
|
---|
43 | private double average;// 頻度の平均
|
---|
44 | private double variance;// 頻度の分散
|
---|
45 | private double pseudoWeight;// 疑似重み
|
---|
46 |
|
---|
47 | IssueFreqRank(List<ValueDiscrete> valueS, ValueDiscrete aSelected) {
|
---|
48 | frequenceS = new HashMap<String, Integer>();
|
---|
49 | for (ValueDiscrete valueD : valueS) {
|
---|
50 | frequenceS.put(valueD.getValue(), 0);
|
---|
51 | }
|
---|
52 | sum = 0;
|
---|
53 | maxFreq = 0;
|
---|
54 | average = 0;
|
---|
55 | variance = 0;
|
---|
56 | pseudoWeight = 0;
|
---|
57 | addFreq(aSelected.getValue());
|
---|
58 | }
|
---|
59 |
|
---|
60 | public HashMap<String, Integer> getFrequenceS() {
|
---|
61 | return (frequenceS);
|
---|
62 | }
|
---|
63 |
|
---|
64 | public int getSum() {
|
---|
65 | return (sum);
|
---|
66 | }
|
---|
67 |
|
---|
68 | public int getMaxFreq() {
|
---|
69 | return (maxFreq);
|
---|
70 | }
|
---|
71 |
|
---|
72 | public double getAverage() {
|
---|
73 | return (average);
|
---|
74 | }
|
---|
75 |
|
---|
76 | public double getVariance() {
|
---|
77 | return (variance);
|
---|
78 | }
|
---|
79 |
|
---|
80 | public double pseudoWeight() {
|
---|
81 | return (pseudoWeight);
|
---|
82 | }
|
---|
83 |
|
---|
84 | public void addFreq(String aSelected) {
|
---|
85 | int current = frequenceS.get(aSelected);
|
---|
86 | frequenceS.put(aSelected, current + 1);
|
---|
87 | sum += 1;
|
---|
88 | average = sum / frequenceS.size();
|
---|
89 | double vSum = 0;
|
---|
90 | for (HashMap.Entry<String, Integer> entry : frequenceS.entrySet()) {// 全ての値を調べる
|
---|
91 | if (maxFreq < entry.getValue()) {
|
---|
92 | maxFreq = entry.getValue();// 最大頻度を更新
|
---|
93 | }
|
---|
94 | double diff = entry.getValue() - average;
|
---|
95 | vSum += (diff * diff);
|
---|
96 | }
|
---|
97 | variance = Math.sqrt(vSum);
|
---|
98 | }
|
---|
99 |
|
---|
100 | }
|
---|
101 |
|
---|
102 | public class GeneKing extends AbstractNegotiationParty {// Agent
|
---|
103 | private Bid lastPartnerBid;
|
---|
104 | private static double MINIMUM_BID_UTILITY = 0.3;
|
---|
105 | //
|
---|
106 | private StandardInfoList history;
|
---|
107 | // private AbstractUtilitySpace utilitySpace;
|
---|
108 | ArrayList<Bid> geneS = new ArrayList<Bid>();// 遺伝子(入札内容)
|
---|
109 | ArrayList<Offer> foreignS = new ArrayList<Offer>();// 外来遺伝子(相手からの入札内容)
|
---|
110 | ArrayList<Offer> tailForeignS = new ArrayList<Offer>();
|
---|
111 | ArrayList<Bid> eliteS = new ArrayList<Bid>();// 優秀な個体(効用値の高い入札)
|
---|
112 | Bid offeredBid = null;
|
---|
113 | Bid myLastBid = null;
|
---|
114 | long initNum = 2000;// 初期個体数
|
---|
115 | int crossNum = 5;// 交叉回数
|
---|
116 | int limitForeignSNum = 500;
|
---|
117 | int maxForeignSNum = 200;
|
---|
118 | int maxNum = 300;
|
---|
119 | int MaxChangeNum = 100;
|
---|
120 | double acceptableUtility = 0.0;
|
---|
121 | double tgtUtility = 1.0;
|
---|
122 | final double VALIANCE = 0.05;
|
---|
123 | Random randomnr = new Random();
|
---|
124 | EvaluatorDiscrete evaluator = new EvaluatorDiscrete();
|
---|
125 | // HashMap<String,ArrayList<ArrayList<String>>> discreteRankS = new
|
---|
126 | // HashMap<String,ArrayList<ArrayList<String>>>();
|
---|
127 | HashMap<String, HashMap<String, Double>> dValueRankS = new HashMap<String, HashMap<String, Double>>();
|
---|
128 | HashMap<AgentID, HashMap<String, IssueFreqRank>> dFreqRankS2 = new HashMap<AgentID, HashMap<String, IssueFreqRank>>();
|
---|
129 | double utilWaight = 3.0, simWaight = 1.0;
|
---|
130 |
|
---|
131 | double getSimilarity2(Bid aBid1, Bid aBid2) {
|
---|
132 | double sim = 0;
|
---|
133 | List<Issue> IssueS1 = aBid1.getIssues();
|
---|
134 | int index = 0;
|
---|
135 | int len = IssueS1.size();
|
---|
136 | while (index < len) {
|
---|
137 | Issue issue1 = IssueS1.get(index);
|
---|
138 | switch (issue1.getType()) {
|
---|
139 | case DISCRETE: {
|
---|
140 | ValueDiscrete valueDiscrete1 = (ValueDiscrete) aBid1
|
---|
141 | .getValue(issue1.getNumber());
|
---|
142 | ValueDiscrete valueDiscrete2 = (ValueDiscrete) aBid2
|
---|
143 | .getValue(issue1.getNumber());
|
---|
144 | HashMap<String, Double> drank = dValueRankS
|
---|
145 | .get(issue1.getName());
|
---|
146 | String fName = valueDiscrete1.getValue(),
|
---|
147 | mName = valueDiscrete2.getValue();
|
---|
148 | double bigger = drank.get(fName), smaller = drank.get(mName);
|
---|
149 | if (bigger < smaller) {
|
---|
150 | double temp = bigger;
|
---|
151 | bigger = smaller;
|
---|
152 | smaller = temp;
|
---|
153 | }
|
---|
154 | double diff = bigger - smaller;
|
---|
155 | if (diff < 0) {
|
---|
156 | diff *= -1;
|
---|
157 | }
|
---|
158 | double finalDiff = (1 - diff / drank.size()) / len;
|
---|
159 | if (finalDiff < 0) {
|
---|
160 | finalDiff = 0;
|
---|
161 | }
|
---|
162 | // System.out.println("fr="+bigger+" fn="+fName+" mr="+smaller+"
|
---|
163 | // mn="+mName+" diff="+diff+" size="+drank.size());
|
---|
164 | sim += finalDiff;
|
---|
165 | break;
|
---|
166 | }
|
---|
167 | case INTEGER: {
|
---|
168 | ValueInteger valueInt1 = (ValueInteger) aBid1
|
---|
169 | .getValue(issue1.getNumber());
|
---|
170 | ValueInteger valueInt2 = (ValueInteger) aBid2
|
---|
171 | .getValue(issue1.getNumber());
|
---|
172 | double diff = (double) valueInt1.getValue()
|
---|
173 | - (double) valueInt2.getValue();
|
---|
174 | // System.out.println("Idiff="+diff);
|
---|
175 | if (diff < 0) {
|
---|
176 | diff *= -1.0;
|
---|
177 | }
|
---|
178 | IssueInteger issueInt = (IssueInteger) IssueS1.get(index);
|
---|
179 | double finalDiff = (1 - diff
|
---|
180 | / (issueInt.getUpperBound() - issueInt.getLowerBound()))
|
---|
181 | / len;
|
---|
182 | if (finalDiff < 0) {
|
---|
183 | finalDiff = 0;
|
---|
184 | }
|
---|
185 | sim += finalDiff;
|
---|
186 | break;
|
---|
187 | }
|
---|
188 | default: {
|
---|
189 | break;
|
---|
190 | }
|
---|
191 | }
|
---|
192 | ++index;
|
---|
193 | }
|
---|
194 | return (sim);
|
---|
195 | }
|
---|
196 |
|
---|
197 | double getAveSim(Bid aAlpha, List<Offer> aBetaS) {
|
---|
198 | double sim = 0;
|
---|
199 | for (Offer beta : aBetaS) {
|
---|
200 | sim += getSimilarity2(aAlpha, beta.getBid());
|
---|
201 | // System.out.print(" sim="+sim);
|
---|
202 | }
|
---|
203 | sim /= aBetaS.size();
|
---|
204 | // System.out.println(" total="+sim);
|
---|
205 | return (sim);
|
---|
206 | }
|
---|
207 |
|
---|
208 | double getExUtility2(Bid aBid, HashMap<String, IssueFreqRank> aFreqRankS) {
|
---|
209 | double util = 0;
|
---|
210 | List<Issue> issueS = utilitySpace.getDomain().getIssues();
|
---|
211 | for (Issue issue : issueS) {
|
---|
212 | switch (issue.getType()) {
|
---|
213 | case DISCRETE: {
|
---|
214 | IssueFreqRank freqRank = aFreqRankS.get(issue.getName());// 順位
|
---|
215 | int freqValue = freqRank.getFrequenceS()
|
---|
216 | .get(aBid.getValue(issue.getNumber()));
|
---|
217 | if (freqValue == 0) {
|
---|
218 | freqValue += 1;
|
---|
219 | }
|
---|
220 | double nFreqValue = (double) freqValue
|
---|
221 | / (double) freqRank.getMaxFreq();
|
---|
222 | util += nFreqValue / issueS.size();
|
---|
223 | break;
|
---|
224 | }
|
---|
225 | case INTEGER: {
|
---|
226 | util += ((ValueInteger) (aBid.getValue(issue.getNumber())))
|
---|
227 | .getValue();
|
---|
228 | break;
|
---|
229 | }
|
---|
230 | }
|
---|
231 | }
|
---|
232 | return (util);
|
---|
233 | }
|
---|
234 |
|
---|
235 | double getMyEvaluation(Bid aBid, List<Offer> aMotherS) {
|
---|
236 | Set<AgentID> set = dFreqRankS2.keySet();
|
---|
237 | double exUtil1 = 0, exUtil2 = 0, count = 0;
|
---|
238 | for (AgentID id : set) {
|
---|
239 | if (count == 0) {
|
---|
240 | // exUtil1 = getExUtility(aBid,dFreqRankS.get(id));
|
---|
241 | exUtil1 = getExUtility2(aBid, dFreqRankS2.get(id));
|
---|
242 | } else {
|
---|
243 | // exUtil2 = getExUtility(aBid,dFreqRankS.get(id));
|
---|
244 | exUtil2 = getExUtility2(aBid, dFreqRankS2.get(id));
|
---|
245 | }
|
---|
246 | ++count;
|
---|
247 | }
|
---|
248 | double diff = (exUtil1 - exUtil2) * 2;
|
---|
249 | if (diff < 0) {
|
---|
250 | diff *= -1;
|
---|
251 | }
|
---|
252 | double util = utilitySpace.getUtility(aBid),
|
---|
253 | sim = getAveSim(aBid, aMotherS);
|
---|
254 | double newEval = util * utilWaight + sim * simWaight + exUtil1 + exUtil2
|
---|
255 | - diff;
|
---|
256 | // System.out.println("(u,s,e1,e2,d)="+"("+util+","+sim+","+exUtil1+","+exUtil2+","+diff+")");
|
---|
257 | return (newEval);
|
---|
258 | }
|
---|
259 |
|
---|
260 | ArrayList<Bid> chooseEliteS3(ArrayList<Bid> aGeneS, List<Offer> aMotherS) {
|
---|
261 | eliteS = new ArrayList<Bid>();
|
---|
262 | Bid best = new Bid(aGeneS.get(0));
|
---|
263 | double util = utilitySpace.getUtility(best);
|
---|
264 | double sim = getAveSim(best, aMotherS);
|
---|
265 | double bestEval = 0;
|
---|
266 | // System.out.println(" (u,s)=("+util+","+sim+")");
|
---|
267 | ArrayList<Bid> newGeneS = new ArrayList<Bid>(aGeneS);
|
---|
268 | int index, count;
|
---|
269 | while (eliteS.size() < maxNum) {
|
---|
270 | index = 0;
|
---|
271 | count = 0;
|
---|
272 | bestEval = -10;
|
---|
273 | for (Bid gene : newGeneS) {
|
---|
274 | double eval = getMyEvaluation(gene, aMotherS);
|
---|
275 | if (eval > bestEval) {
|
---|
276 | best = gene;
|
---|
277 | bestEval = eval;
|
---|
278 | index = count;
|
---|
279 | }
|
---|
280 | ++count;
|
---|
281 | }
|
---|
282 | eliteS.add(best);
|
---|
283 | newGeneS.remove(index);// 加えた入札を消す
|
---|
284 | if (newGeneS.size() == 0) {
|
---|
285 | break;
|
---|
286 | }
|
---|
287 | }
|
---|
288 | util = utilitySpace.getUtility(best);
|
---|
289 | sim = getAveSim(best, aMotherS);
|
---|
290 | // System.out.println(" (u,s)2=("+util+","+sim+")");
|
---|
291 | return (eliteS);
|
---|
292 | }
|
---|
293 |
|
---|
294 | Bid chooseBest(ArrayList<Bid> aGeneS) {
|
---|
295 | Bid best = new Bid(aGeneS.get(0));
|
---|
296 | double bestEval = getMyEvaluation(best, tailForeignS);
|
---|
297 | for (Bid gene : aGeneS) {
|
---|
298 | double eval = getMyEvaluation(gene, tailForeignS);
|
---|
299 | if (eval > bestEval) {
|
---|
300 | best = gene;
|
---|
301 | bestEval = eval;
|
---|
302 | }
|
---|
303 | }
|
---|
304 | return (best);
|
---|
305 | }
|
---|
306 |
|
---|
307 | private Bid getRandomBidGK() {
|
---|
308 | HashMap<Integer, Value> values = new HashMap<Integer, Value>(); // pairs
|
---|
309 | // <issuenumber,chosen
|
---|
310 | // value
|
---|
311 | // string>
|
---|
312 | List<Issue> issues = utilitySpace.getDomain().getIssues();
|
---|
313 | Random randomnr = new Random();
|
---|
314 | Bid bid = null;
|
---|
315 | do {
|
---|
316 | for (Issue lIssue : issues) {
|
---|
317 | switch (lIssue.getType()) {
|
---|
318 | case DISCRETE: {// 文字列
|
---|
319 | IssueDiscrete lIssueDiscrete = (IssueDiscrete) lIssue;
|
---|
320 | int optionIndex = randomnr
|
---|
321 | .nextInt(lIssueDiscrete.getNumberOfValues());
|
---|
322 | values.put(lIssue.getNumber(),
|
---|
323 | lIssueDiscrete.getValue(optionIndex));
|
---|
324 | break;
|
---|
325 | }
|
---|
326 | case REAL: {//
|
---|
327 | IssueReal lIssueReal = (IssueReal) lIssue;
|
---|
328 | int optionInd = randomnr.nextInt(
|
---|
329 | lIssueReal.getNumberOfDiscretizationSteps() - 1);
|
---|
330 | values.put(lIssueReal.getNumber(), new ValueReal(lIssueReal
|
---|
331 | .getLowerBound()
|
---|
332 | + (lIssueReal.getUpperBound()
|
---|
333 | - lIssueReal.getLowerBound()) * (optionInd)
|
---|
334 | / (lIssueReal
|
---|
335 | .getNumberOfDiscretizationSteps())));
|
---|
336 | break;
|
---|
337 | }
|
---|
338 | case INTEGER: {
|
---|
339 | IssueInteger lIssueInteger = (IssueInteger) lIssue;
|
---|
340 | int optionIndex2 = lIssueInteger.getLowerBound()
|
---|
341 | + randomnr.nextInt(lIssueInteger.getUpperBound()
|
---|
342 | - lIssueInteger.getLowerBound());
|
---|
343 | values.put(lIssueInteger.getNumber(),
|
---|
344 | new ValueInteger(optionIndex2));
|
---|
345 | break;
|
---|
346 | }
|
---|
347 | default: {
|
---|
348 | System.out.println("issue type " + lIssue.getType()
|
---|
349 | + " not supported by geneKing");
|
---|
350 | }
|
---|
351 | }
|
---|
352 | }
|
---|
353 | bid = new Bid(utilitySpace.getDomain(), values);
|
---|
354 | } while (utilitySpace.getUtility(bid) < MINIMUM_BID_UTILITY);
|
---|
355 |
|
---|
356 | return (bid);
|
---|
357 | }
|
---|
358 |
|
---|
359 | private ArrayList<Bid> getRandomBidS() {
|
---|
360 | ArrayList<Bid> initS = new ArrayList<Bid>();
|
---|
361 | while (initS.size() < initNum) {
|
---|
362 | Bid newBid = null;
|
---|
363 | // do{
|
---|
364 | newBid = getRandomBidGK();
|
---|
365 | // }while(initS.contains(newBid));
|
---|
366 | initS.add(newBid);
|
---|
367 | }
|
---|
368 | return (initS);
|
---|
369 | }
|
---|
370 |
|
---|
371 | Bid uniformCrossOver5(Bid aFather, Bid aMother,
|
---|
372 | HashMap<String, IssueFreqRank> aFreqRankS) {
|
---|
373 | Bid child = new Bid(aFather);
|
---|
374 | List<Issue> genome = child.getIssues();
|
---|
375 | for (Issue value : genome) {
|
---|
376 | switch (value.getType()) {
|
---|
377 | case DISCRETE: {
|
---|
378 | IssueDiscrete lIssueDis = (IssueDiscrete) value;
|
---|
379 | String fName = ((ValueDiscrete) aFather
|
---|
380 | .getValue(value.getNumber())).getValue();// 父親の文字列
|
---|
381 | String mName = ((ValueDiscrete) aMother
|
---|
382 | .getValue(value.getNumber())).getValue();// 母親の文字列
|
---|
383 | // System.out.println("f="+evaluator.getValue(((ValueDiscrete)aFather.getValue(value.getNumber())))
|
---|
384 | // +"m="
|
---|
385 | // +evaluator.getValue(((ValueDiscrete)aMother.getValue(value.getNumber()))));
|
---|
386 | if (fName == mName) {// 互いに同じ提案だった場合
|
---|
387 | child.putValue(value.getNumber(),
|
---|
388 | aFather.getValue(value.getNumber()));
|
---|
389 | } else {// 提案が異なる場合
|
---|
390 | HashMap<String, Double> rank = dValueRankS
|
---|
391 | .get(lIssueDis.getName());
|
---|
392 | HashMap<String, Integer> aFreqRank = aFreqRankS
|
---|
393 | .get(value.getName()).getFrequenceS();
|
---|
394 | double bigger = rank.get(fName) * aFreqRank.get(fName),
|
---|
395 | smaller = rank.get(mName) * aFreqRank.get(mName);
|
---|
396 | if (bigger < smaller) {
|
---|
397 | double temp = bigger;
|
---|
398 | bigger = smaller;
|
---|
399 | smaller = temp;
|
---|
400 | }
|
---|
401 | ArrayList<String> midS = new ArrayList<String>();
|
---|
402 | for (HashMap.Entry<String, Double> entry : rank
|
---|
403 | .entrySet()) {// 全ての値を調べる
|
---|
404 | double newMid = entry.getValue()
|
---|
405 | * aFreqRank.get(entry.getKey());
|
---|
406 | if (bigger >= newMid && smaller <= newMid) {
|
---|
407 | midS.add(entry.getKey());
|
---|
408 | }
|
---|
409 | }
|
---|
410 | int newSeed = randomnr.nextInt(midS.size());
|
---|
411 | child.putValue(value.getNumber(),
|
---|
412 | new ValueDiscrete(midS.get(newSeed)));
|
---|
413 | } // else
|
---|
414 | break;
|
---|
415 | }
|
---|
416 | case INTEGER: {
|
---|
417 | IssueInteger lIssueInteger = (IssueInteger) value;
|
---|
418 | int bigger = ((ValueInteger) aFather
|
---|
419 | .getValue(value.getNumber())).getValue();
|
---|
420 | int smaller = ((ValueInteger) aMother
|
---|
421 | .getValue(value.getNumber())).getValue();
|
---|
422 | if (bigger < smaller) {
|
---|
423 | int temp = bigger;
|
---|
424 | bigger = smaller;
|
---|
425 | smaller = temp;
|
---|
426 | }
|
---|
427 | int optionIndex = smaller
|
---|
428 | + randomnr.nextInt(bigger - smaller + 1);
|
---|
429 | child.putValue(lIssueInteger.getNumber(),
|
---|
430 | new ValueInteger(optionIndex));
|
---|
431 | break;
|
---|
432 | }
|
---|
433 | default: {
|
---|
434 | System.out.println("issue type " + value.getType()
|
---|
435 | + " not supported by geneKing");
|
---|
436 | }
|
---|
437 | }// switch
|
---|
438 | } // for
|
---|
439 | return (child);
|
---|
440 | }
|
---|
441 |
|
---|
442 | // 突然変異を起こす
|
---|
443 | Bid mutation(Bid aOriginal) {
|
---|
444 | Bid mutant = new Bid(aOriginal);
|
---|
445 | List<Issue> genome = mutant.getIssues();
|
---|
446 | for (Issue issue : genome) {
|
---|
447 | int rot = randomnr.nextInt(70);
|
---|
448 | if (rot == 0) {// 値が一致したときのみ変異させる
|
---|
449 | switch (issue.getType()) {
|
---|
450 | case DISCRETE: {
|
---|
451 | IssueDiscrete lIssueDiscrete = (IssueDiscrete) issue;
|
---|
452 | int optionIndex = randomnr
|
---|
453 | .nextInt(lIssueDiscrete.getNumberOfValues());
|
---|
454 | mutant.putValue(issue.getNumber(),
|
---|
455 | lIssueDiscrete.getValue(optionIndex));
|
---|
456 | break;
|
---|
457 | }
|
---|
458 | case INTEGER: {
|
---|
459 | IssueInteger lIssueInteger = (IssueInteger) issue;
|
---|
460 | int optionIndex = lIssueInteger.getLowerBound()
|
---|
461 | + randomnr.nextInt(lIssueInteger.getUpperBound()
|
---|
462 | - lIssueInteger.getLowerBound());
|
---|
463 | mutant.putValue(lIssueInteger.getNumber(),
|
---|
464 | new ValueInteger(optionIndex));
|
---|
465 | break;
|
---|
466 | }
|
---|
467 | case REAL: {
|
---|
468 | IssueReal lIssueReal = (IssueReal) issue;
|
---|
469 | int optionInd = randomnr.nextInt(
|
---|
470 | lIssueReal.getNumberOfDiscretizationSteps() - 1);
|
---|
471 | mutant.putValue(lIssueReal.getNumber(), new ValueReal(
|
---|
472 | lIssueReal.getLowerBound() + (lIssueReal
|
---|
473 | .getUpperBound()
|
---|
474 | - lIssueReal.getLowerBound()) * (optionInd)
|
---|
475 | / (lIssueReal
|
---|
476 | .getNumberOfDiscretizationSteps())));
|
---|
477 | break;
|
---|
478 | }
|
---|
479 | default: {
|
---|
480 | System.out.println("issue type " + issue.getType()
|
---|
481 | + " not supported by geneKing");
|
---|
482 | }
|
---|
483 | }// switch
|
---|
484 | } // if
|
---|
485 | } // for
|
---|
486 | return (mutant);
|
---|
487 | }
|
---|
488 |
|
---|
489 | ArrayList<Bid> makeNextG3(ArrayList<Bid> aCurrentS,
|
---|
490 | ArrayList<Offer> aForeignS) {
|
---|
491 | ArrayList<Bid> nextGeneS = new ArrayList<Bid>();
|
---|
492 | int tail = aForeignS.size();
|
---|
493 | int len = 8;
|
---|
494 | int start = tail - len;
|
---|
495 | if (start < 0) {
|
---|
496 | start = 0;
|
---|
497 | }
|
---|
498 | tailForeignS = new ArrayList<Offer>(aForeignS.subList(start, tail));
|
---|
499 | // System.out.println("0Len="+aCurrentS.size()+"
|
---|
500 | // 1Len="+aForeignS.size()+" 2Len="+tailForeignS.size()+"
|
---|
501 | // start="+start+" tail="+tail);
|
---|
502 | Bid lastBid = null;
|
---|
503 | for (Bid alpha : aCurrentS) {
|
---|
504 | for (Offer beta : tailForeignS) {
|
---|
505 | for (int i = 0; i < crossNum; ++i) {
|
---|
506 | // Bid child = uniformCrossOver3(alpha,beta.getBid());
|
---|
507 | Bid child = uniformCrossOver5(alpha, beta.getBid(),
|
---|
508 | dFreqRankS2.get(beta.getAgent()));
|
---|
509 | child = mutation(child);
|
---|
510 | double util = utilitySpace.getUtility(child);
|
---|
511 | // System.out.print(util+ "");
|
---|
512 | if (util > 0 && !child.equals(lastBid)) {
|
---|
513 | nextGeneS.add(child);
|
---|
514 | lastBid = child;
|
---|
515 | }
|
---|
516 | }
|
---|
517 | }
|
---|
518 | }
|
---|
519 | // System.out.println("NextG="+nextGeneS.size());
|
---|
520 | nextGeneS = chooseEliteS3(nextGeneS, tailForeignS);
|
---|
521 | // System.out.println("NextG2="+nextGeneS.size());
|
---|
522 | return (nextGeneS);
|
---|
523 | }
|
---|
524 |
|
---|
525 | void genelogy() {
|
---|
526 | if (foreignS.size() == 0) {
|
---|
527 | Bid newBid = chooseBest(geneS);
|
---|
528 | myLastBid = newBid;
|
---|
529 | System.out.println("No foreignS!");
|
---|
530 | return;
|
---|
531 | } else {
|
---|
532 | ArrayList<Bid> nextS = makeNextG3(geneS, foreignS);
|
---|
533 | // System.out.println("NextLen="+nextS.size());
|
---|
534 | Bid newBid = chooseBest(nextS);
|
---|
535 | if (myLastBid != null) {
|
---|
536 | // double newEval =
|
---|
537 | // utilitySpace.getUtility(newBid)*utilWaight+getAveSim(newBid,foreignS)*simWaight;
|
---|
538 | double newEval = getMyEvaluation(newBid, tailForeignS);
|
---|
539 | double lastEval = getMyEvaluation(myLastBid, tailForeignS);
|
---|
540 | if (newEval > lastEval) {
|
---|
541 | myLastBid = newBid;
|
---|
542 | // System.out.println("New Best!");
|
---|
543 | }
|
---|
544 | } else {
|
---|
545 | myLastBid = newBid;
|
---|
546 | }
|
---|
547 | geneS = new ArrayList<Bid>(nextS);// 全入れ替え
|
---|
548 | }
|
---|
549 | }
|
---|
550 |
|
---|
551 | private boolean isAcceptableGK() {
|
---|
552 | double offeredUtil = 0.0;
|
---|
553 | if (offeredBid != null) {
|
---|
554 | offeredUtil = utilitySpace.getUtility(offeredBid);
|
---|
555 | }
|
---|
556 | double myUtil = 1.0;
|
---|
557 | if (myLastBid != null) {
|
---|
558 | myUtil = utilitySpace.getUtility(myLastBid);
|
---|
559 | }
|
---|
560 | if (offeredUtil >= myUtil - VALIANCE) {// 自分の提案以上のものか、その近くであった場合
|
---|
561 | return (true);
|
---|
562 | }
|
---|
563 | return (false);
|
---|
564 | }
|
---|
565 |
|
---|
566 | private HashMap<String, Double> makeRank2(IssueDiscrete aIssue) {
|
---|
567 | HashMap<String, Double> rRank = new HashMap<String, Double>();
|
---|
568 | List<ValueDiscrete> valueS = aIssue.getValues();
|
---|
569 | for (ValueDiscrete valueD : valueS) {
|
---|
570 | // Integer newEval = evaluator.getValue(valueD);//評価値に直す
|
---|
571 | double newEval = (double) (evaluator.getValue(valueD))
|
---|
572 | / evaluator.getEvalMax();
|
---|
573 | System.out.println("newEval=" + newEval);
|
---|
574 | // Integer newEval =
|
---|
575 | // EvaluatorDiscrete.this.getEvaluationNotNormalized(valueD);
|
---|
576 | rRank.put(valueD.getValue(), newEval);
|
---|
577 | }
|
---|
578 | return (rRank);
|
---|
579 | }
|
---|
580 |
|
---|
581 | private void makeRankS(List<Issue> aIssueS) {
|
---|
582 | System.out.println("Make Rank Start!");
|
---|
583 | int count = 0;
|
---|
584 | for (Issue issue : aIssueS) {
|
---|
585 | if (issue.getType().equals(ISSUETYPE.DISCRETE)) {
|
---|
586 | try {
|
---|
587 | evaluator.loadFromXML(
|
---|
588 | utilitySpace.toXML().getChildElementsAsList().get(0)
|
---|
589 | .getChildElementsAsList().get(count));
|
---|
590 | // evaluator.loadFromXML(issue.toXML());
|
---|
591 | // evaluator.setXML(issue.toXML());
|
---|
592 | // System.out.println("evaluator="+((EvaluatorDiscrete)evaluator).getEvalMax());
|
---|
593 | } catch (IOException e) {
|
---|
594 |
|
---|
595 | }
|
---|
596 | // discreteRankS.put(issue.getName(),
|
---|
597 | // makeRank((IssueDiscrete)issue));
|
---|
598 | dValueRankS.put(issue.getName(),
|
---|
599 | makeRank2((IssueDiscrete) issue));
|
---|
600 | System.out.println("issue-N Finish!");
|
---|
601 | } // if
|
---|
602 | ++count;
|
---|
603 | } // for
|
---|
604 | }
|
---|
605 |
|
---|
606 | private void initInitNum() {
|
---|
607 | long candidateNum = 1;
|
---|
608 | candidateNum = utilitySpace.getDomain().getNumberOfPossibleBids();
|
---|
609 | if (initNum > candidateNum) {
|
---|
610 | initNum = candidateNum;
|
---|
611 | }
|
---|
612 | }
|
---|
613 |
|
---|
614 | private void initGK() {
|
---|
615 | history = (StandardInfoList) getData().get();
|
---|
616 |
|
---|
617 | if (!history.isEmpty()) {
|
---|
618 | // example of using the history. Compute for each party the maximum
|
---|
619 | // utility of the bids in last session.
|
---|
620 | Map<String, Double> maxutils = new HashMap<String, Double>();
|
---|
621 | StandardInfo lastinfo = history.get(history.size() - 1);
|
---|
622 | for (Tuple<String, Double> offered : lastinfo.getUtilities()) {
|
---|
623 | String party = offered.get1();
|
---|
624 | Double util = offered.get2();
|
---|
625 | maxutils.put(party, maxutils.containsKey(party)
|
---|
626 | ? Math.max(maxutils.get(party), util) : util);
|
---|
627 | }
|
---|
628 | System.out.println(maxutils); // notice tournament suppresses all
|
---|
629 | // output.
|
---|
630 | }
|
---|
631 |
|
---|
632 | MINIMUM_BID_UTILITY = utilitySpace.getReservationValueUndiscounted();
|
---|
633 | if (MINIMUM_BID_UTILITY < utilitySpace
|
---|
634 | .getReservationValueUndiscounted()) {
|
---|
635 | MINIMUM_BID_UTILITY = utilitySpace
|
---|
636 | .getReservationValueUndiscounted();
|
---|
637 | }
|
---|
638 | acceptableUtility = MINIMUM_BID_UTILITY;
|
---|
639 | System.out.println("get issueS!");
|
---|
640 | List<Issue> issueS = utilitySpace.getDomain().getIssues();
|
---|
641 | System.out.println("got issueS!");
|
---|
642 | makeRankS(issueS);
|
---|
643 | System.out.println("Made Rank");
|
---|
644 | initInitNum();
|
---|
645 | geneS = getRandomBidS();
|
---|
646 | double bestUtil = 0;
|
---|
647 | for (StandardInfo stdInfo : history) {
|
---|
648 | Tuple agreement = stdInfo.getAgreement();
|
---|
649 | if (agreement != null) {
|
---|
650 | double newUtil = (double) agreement.get2();
|
---|
651 | if (newUtil > bestUtil && newUtil > 0.7) {
|
---|
652 | bestUtil = newUtil;
|
---|
653 | myLastBid = (Bid) agreement.get1();
|
---|
654 | }
|
---|
655 | if (newUtil > 0.7) {
|
---|
656 | geneS.add((Bid) agreement.get1());
|
---|
657 | }
|
---|
658 | }
|
---|
659 | // System.out.println("profile="+stdInfo.getAgentProfiles());
|
---|
660 | // System.out.println("stdInfo="+stdInfo.getUtilities());
|
---|
661 | // System.out.println("agree="+stdInfo.getAgreement());
|
---|
662 | }
|
---|
663 | }
|
---|
664 |
|
---|
665 | private String getNameGK() {
|
---|
666 | return ("GeneKing");
|
---|
667 | }
|
---|
668 |
|
---|
669 | private double getAverageUtility() {
|
---|
670 | double average = 0;
|
---|
671 | for (Offer foreign : tailForeignS) {
|
---|
672 | average += utilitySpace.getUtility(foreign.getBid());
|
---|
673 | }
|
---|
674 | average /= tailForeignS.size();
|
---|
675 | return (average);
|
---|
676 | }
|
---|
677 |
|
---|
678 | private Action chooseActionGK() {
|
---|
679 | double time = timeline.getTime();
|
---|
680 | if (time > 0.99) {// 締め切り間近の場合
|
---|
681 | double partnerUtil = getAverageUtility();
|
---|
682 | if (partnerUtil >= acceptableUtility) {
|
---|
683 | acceptableUtility = partnerUtil;
|
---|
684 | }
|
---|
685 |
|
---|
686 | if (getAverageUtility() < MINIMUM_BID_UTILITY) {
|
---|
687 | System.out.println("End Negotiation!");
|
---|
688 | return (new EndNegotiation(getPartyId()));
|
---|
689 | } else if (partnerUtil >= acceptableUtility) {// 最後の提案が良かった場合
|
---|
690 | return (new Accept(getPartyId(), lastPartnerBid));
|
---|
691 | } else {
|
---|
692 | genelogy();
|
---|
693 | return (new Offer(getPartyId(), myLastBid));
|
---|
694 | }
|
---|
695 | } else {// まだ余裕のある場合
|
---|
696 | if (isAcceptableGK()) {
|
---|
697 | return (new Accept(getPartyId(), lastPartnerBid));
|
---|
698 | } else {
|
---|
699 | genelogy();
|
---|
700 | return (new Offer(getPartyId(), myLastBid));
|
---|
701 | }
|
---|
702 | }
|
---|
703 | }
|
---|
704 |
|
---|
705 | private IssueFreqRank makeFreqRank2(IssueDiscrete aIssue,
|
---|
706 | ValueDiscrete aSelected) {
|
---|
707 | IssueFreqRank rRank = new IssueFreqRank(aIssue.getValues(), aSelected);
|
---|
708 | return (rRank);
|
---|
709 | }
|
---|
710 |
|
---|
711 | private HashMap<String, IssueFreqRank> makeFreqRankS2(Bid aBid) {
|
---|
712 | HashMap<String, IssueFreqRank> rFreqRankS = new HashMap<String, IssueFreqRank>();
|
---|
713 | List<Issue> issueS = utilitySpace.getDomain().getIssues();
|
---|
714 | for (Issue issue : issueS) {
|
---|
715 | if (issue.getType().equals(ISSUETYPE.DISCRETE)) {// DISCRETE型だった場合
|
---|
716 | IssueDiscrete dIssue = (IssueDiscrete) issue;
|
---|
717 | rFreqRankS.put(issue.getName(), makeFreqRank2(dIssue,
|
---|
718 | (ValueDiscrete) (aBid.getValue(dIssue.getNumber()))));
|
---|
719 | }
|
---|
720 | }
|
---|
721 | return (rFreqRankS);
|
---|
722 | }
|
---|
723 |
|
---|
724 | private void updateFreqRank2(ValueDiscrete aSelected, IssueFreqRank aRank) {
|
---|
725 | aRank.addFreq(aSelected.getValue());
|
---|
726 | }
|
---|
727 |
|
---|
728 | void updateFreqRankS2(Bid aBid,
|
---|
729 | HashMap<String, IssueFreqRank> adFreqRankS) {
|
---|
730 | List<Issue> issueS = utilitySpace.getDomain().getIssues();
|
---|
731 | for (Issue issue : issueS) {
|
---|
732 | if (issue.getType().equals(ISSUETYPE.DISCRETE)) {// DISCRETE型だった場合
|
---|
733 | updateFreqRank2(
|
---|
734 | (ValueDiscrete) (aBid.getValue(issue.getNumber())),
|
---|
735 | adFreqRankS.get(issue.getName()));
|
---|
736 | }
|
---|
737 | }
|
---|
738 | }
|
---|
739 |
|
---|
740 | // Offerのリストの長さをチェックし、長すぎた場合は後方のみを残す
|
---|
741 | ArrayList<Offer> reduceList(ArrayList<Offer> aList, int aMaxSize) {
|
---|
742 | ArrayList<Offer> rList = new ArrayList<Offer>(
|
---|
743 | aList.subList(aList.size() - aMaxSize, aList.size()));
|
---|
744 | return (rList);
|
---|
745 | }
|
---|
746 |
|
---|
747 | private void ReceiveMessageGK(Action aAction) {
|
---|
748 | AgentID id = aAction.getAgent();
|
---|
749 | if (aAction instanceof Offer) {
|
---|
750 | offeredBid = new Bid(((Offer) aAction).getBid()); // 提案された合意案候補
|
---|
751 | foreignS.add((Offer) aAction);
|
---|
752 | if (dFreqRankS2.containsKey(id)) {// 登録されていた場合
|
---|
753 | updateFreqRankS2(offeredBid, dFreqRankS2.get(id));
|
---|
754 | } else {// まだ登録されていない場合
|
---|
755 | dFreqRankS2.put(id, makeFreqRankS2(offeredBid));
|
---|
756 | }
|
---|
757 | lastPartnerBid = offeredBid;
|
---|
758 | // System.out.println("aAction="+offeredBid+"
|
---|
759 | // len="+foreignS.size()+" "+aAction.getAgent());
|
---|
760 | } else if (aAction instanceof Accept) {// 受け入れだった場合
|
---|
761 | Bid accepted = new Bid(((Accept) aAction).getBid());
|
---|
762 | Offer accOffer = new Offer(aAction.getAgent(), accepted);
|
---|
763 | foreignS.add(accOffer);
|
---|
764 | if (dFreqRankS2.containsKey(id)) {// 登録されていた場合
|
---|
765 | updateFreqRankS2(accepted, dFreqRankS2.get(id));
|
---|
766 | } else {// まだ登録されていない場合
|
---|
767 | dFreqRankS2.put(id, makeFreqRankS2(accepted));
|
---|
768 | }
|
---|
769 | }
|
---|
770 | if (foreignS.size() > limitForeignSNum) {
|
---|
771 | foreignS = reduceList(foreignS, maxForeignSNum);// 数が増えすぎたら昔のものを減らす
|
---|
772 | }
|
---|
773 |
|
---|
774 | }
|
---|
775 |
|
---|
776 | @Override
|
---|
777 | public void init(NegotiationInfo info) {
|
---|
778 | super.init(info);
|
---|
779 | System.out.println("Discount Factor is "
|
---|
780 | + info.getUtilitySpace().getDiscountFactor());
|
---|
781 | System.out.println("Reservation Value is "
|
---|
782 | + info.getUtilitySpace().getReservationValueUndiscounted());
|
---|
783 | MINIMUM_BID_UTILITY = info.getUtilitySpace()
|
---|
784 | .getReservationValueUndiscounted();
|
---|
785 | initGK();
|
---|
786 | }
|
---|
787 |
|
---|
788 | @Override
|
---|
789 | public Action chooseAction(List<Class<? extends Action>> validActions) {
|
---|
790 | return (chooseActionGK());
|
---|
791 | }
|
---|
792 |
|
---|
793 | @Override
|
---|
794 | public void receiveMessage(AgentID sender, Action action) {
|
---|
795 | super.receiveMessage(sender, action);
|
---|
796 | ReceiveMessageGK(action);
|
---|
797 | }
|
---|
798 |
|
---|
799 | @Override
|
---|
800 | public String getDescription() {
|
---|
801 | return "ANAC2017";
|
---|
802 | }
|
---|
803 | }
|
---|