source: CSE3210/agent33/utility.py

Last change on this file was 74, checked in by wouter, 21 months ago

#6 Added CSE3210 parties

File size: 7.1 KB
Line 
1import math
2import time
3from typing import List, Set, Dict
4
5from geniusweb.issuevalue.Bid import Bid
6from geniusweb.issuevalue.Domain import Domain
7from geniusweb.issuevalue.Value import Value
8from geniusweb.profile.Profile import Profile
9
10
11class AgentUtility:
12
13 def __init__(self, profile: Profile = None, progress=None):
14 self._profile = profile
15 self._progress = progress
16 self._self_bid_history = []
17 self._opponent_weight_heuristic = {}
18 self._issue_count_dict: Dict[str, Dict[Value, int]] = None
19
20 def set_profile(self, profile: Profile):
21 self._profile = profile
22 self._intialize_weights()
23 self._initialize_opponent_issue_count()
24
25 def set_progress(self, progress):
26 self._progress = progress
27
28 def get_weight_heuristic(self):
29 return self._opponent_weight_heuristic
30
31 def _intialize_weights(self):
32 """"
33 Initializes the _opponent_weight_heuristic with values that are equally divided over the issues
34 If there are 2 issues then the initial weight heuristic becomes {(issue1 : 0.5), (issue2: 0.5)}
35 """""
36 weightDict = self._profile.getProfile().getWeights()
37 weightList = []
38 for key, value in weightDict.items():
39 weightList.append((key, value))
40 # sort the weights in decending order
41 self.weights = sorted(weightList, key=lambda tup: tup[1], reverse=True)
42
43 # instantiate opponent_weights heuristic
44 heuristic_weights_dict = weightDict
45 initialWeightDistribution: float = 1 / len(heuristic_weights_dict.items())
46 for key, value in heuristic_weights_dict.items():
47 heuristic_weights_dict[key] = initialWeightDistribution
48 self._opponent_weight_heuristic = heuristic_weights_dict
49
50 def _initialize_opponent_issue_count(self):
51 """""
52 Initializes an empty _issue_count_dict
53 """""
54 domain: Domain = self._profile.getProfile().getDomain()
55 issues: Set[str] = domain.getIssues()
56
57 self._issue_count_dict: Dict[str, Dict[Value, int]] = {}
58 for issue in issues:
59 self._issue_count_dict[issue]: Dict[Value, int] = {}
60 for value in domain.getValues(issue):
61 self._issue_count_dict[issue][value] = 0
62
63 def get_bid_history(self):
64 """""
65 returns the bid history
66 """""
67 return self._self_bid_history
68
69 def speed_factor(self):
70 """""
71 returns progress multiplied by a constant
72 """""
73 return math.ceil(self._progress.get(time.time() * 1000) * 50)
74
75 def update_opponent_issue_count(self, bid):
76 """""
77 Updates the empty _issue_count_dict, by incrementing the counter of that value in each issue of the bid
78 """""
79 for issue, value in bid.getIssueValues().items():
80 self._issue_count_dict[issue][value] += 1
81
82 def get_opponent_issue_count(self):
83 """""
84 Get the normalized _issue_count_dict, it does this by dividing the occurence count of the value by the max occurence count of a value in that issue.
85 This is done for each issue.
86 """""
87
88 normalized_opponent_issue_count: Dict[str, Dict[Value, float]] = {}
89
90 for issue in self._issue_count_dict:
91 normalized_opponent_issue_count[issue] = {}
92 total_issues: int = max(self._issue_count_dict[issue].values())
93 division_factor = total_issues if total_issues != 0 else 1
94 for value in self._issue_count_dict[issue]:
95 normalized_opponent_issue_count[issue][value] = self._issue_count_dict[issue][value] / division_factor
96
97 return normalized_opponent_issue_count
98
99 def update_opponent_weight_heuristic(self, bid: Bid):
100 """"
101 This method updates the opponent weight heuristic accordingly so that the total weight is always 1
102 if issues values are changed we decrease the weight, if they stay the same we increase the weight'
103 "q" is the size of tee changes we make to the weights
104 """
105 if len(self._self_bid_history) > 2:
106 prev_bid = self._self_bid_history[len(self._self_bid_history) - 3][0]
107 else:
108 return
109
110 CONSTANT_q = 0.1
111 # If issues get changed a lot then they are probably less important to the opponents
112 bidIssueValues = bid.getIssueValues()
113 prevBidIssueValues = prev_bid.getIssueValues()
114 differentIssueKeys: [str] = []
115 sameIssueKeys: [str] = []
116
117 for key, value in bidIssueValues.items():
118 # to make sure that the weight stays between 0 and 1 there are extra conditions to see
119 # if the weight of that particular issue can be further incremented or decremented so we don't go above 1 or below 0
120 if value != prevBidIssueValues[key] and self._opponent_weight_heuristic[key] > 0 + CONSTANT_q:
121 differentIssueKeys.append(key)
122 elif self._opponent_weight_heuristic[key] < 1 - CONSTANT_q:
123 sameIssueKeys.append(key)
124
125 # if all the issue values change or if none of the values change don't update the heuristic,
126 if len(sameIssueKeys) != 0 and len(differentIssueKeys) != 0:
127 for key, value in self._opponent_weight_heuristic.items():
128 if key in differentIssueKeys:
129 self._opponent_weight_heuristic[key] -= (CONSTANT_q / len(
130 differentIssueKeys)) # self._opponent_weight_heuristic[key] * n #(n / len(differentIssueKeys))
131 else:
132 self._opponent_weight_heuristic[key] += (CONSTANT_q / len(
133 sameIssueKeys)) # self._opponent_weight_heuristic[key] * n # (n / len(sameIssueKeys))
134
135 def append_to_bid_history(self, bid: Bid, own_bid):
136 """""
137 Adds a bid to the bid history
138 """""
139 self._self_bid_history.append((bid, self._profile.getProfile().getUtility(bid), own_bid))
140
141 def get_last_own_bid_utility(self):
142 """""
143 returns the utility of the last bid made by the agent itself
144 """""
145 if not self._self_bid_history[-1][2]:
146 if len(self._self_bid_history) <= 1:
147 return 1
148 return self._self_bid_history[-2][1]
149 else:
150 return self._self_bid_history[-1][1]
151
152 def get_last_opponent_bid_utility(self):
153 """""
154 returns the utility of the last bid made by the agent itself
155 """""
156 if not self._self_bid_history[-1][2]:
157 return self._self_bid_history[-1][1]
158 else:
159 return self._self_bid_history[-2][1]
160
161 def rate_bid(self, bid: Bid, opponent_issue_percentage: Dict[str, Dict[Value, float]], opponent_issue_weights):
162 """""
163 Given a bid and the normalized _issue_count_dict this method estimates the utility of a Bid
164 """""
165 utility = 0
166 for issue, value in bid.getIssueValues().items():
167 utility += opponent_issue_percentage[issue][value] * opponent_issue_weights[issue]
168 return utility
Note: See TracBrowser for help on using the repository browser.