001    package market.statistics;
002    
003    import java.util.Calendar;
004    import java.util.Iterator;
005    
006    import market.CIArticle;
007    import market.MarketCalendar;
008    import market.SMarket;
009    import market.UCustomer;
010    import data.CountingStock;
011    import data.events.VetoException;
012    import data.ooimpl.CatalogImpl;
013    
014    
015    /**
016     * Represents a statistics of one month. It contains the statistics of every single offered
017     * article and more general information such as paid wages and miscellaneous costs.
018     * This class is also used as container in which overall statistics of a given range of time are brought
019     * together.
020     * The items of this catalog are {@link CISalesStats}.
021     * @see Statistics#getOverallStats(int, int, int, int)
022     */
023    public class CSalesStats extends CatalogImpl {
024    
025        private int month, year;
026        private int costs, wages;
027        private int revenue = 0;
028    
029        /**
030         * Creates a new statistics container. To month that those statistics have been recorded is passed
031         * via the parameters.
032         * @param year the year in which the statistics were recorded.
033         * @param month the month in which the statistics were recorded.
034         */
035        public CSalesStats(int year, int month) {
036            super(year + "-" + (month < 10 ? "0" : "") + month);
037            this.year = year;
038            this.month = month;
039            Iterator it = SMarket.getArticleCatalog().keySet(null).iterator();
040            while (it.hasNext()) {
041                String id = (String)it.next();
042                CISalesStats ciss = new CISalesStats(id, 0, 0);
043                add(ciss, null);
044            }
045        }
046    
047        /**
048         * @return the statistic's year
049         */
050        public int getYear() {
051            return year;
052        }
053    
054        /**
055         * @return the statistic's month
056         */
057        public int getMonth() {
058            return month;
059        }
060    
061        /**
062         * Initializes the {@link CISalesStats#priceHistory price history} of each article with the current
063         * article's bid. This initial bid is used for calculating average prices over a range of time.
064         * Without it, it would be possible to have an empty price history for the chosen range of time which
065         * makes calculations on this history more difficult.<br>
066         * This method is called only on creation of a CCustomerStats, but it cannot be put into the
067         * constructor, because there are cases when the initialization is not desired.
068         * @see Statistics#getArticleStats(String, int, int, int, int)
069         * @see Statistics#getOverallStats(int, int, int, int)
070         * @see SMarket#c_dailyStats
071         */
072        public void initPriceHistory() {
073            Iterator it = keySet(null).iterator();
074            while (it.hasNext()) {
075                String id = (String)it.next();
076                CISalesStats ciss = get(id);
077                Calendar c = new MarketCalendar(year, month, 1);
078                if (c.before(SMarket.getDateOfOpening())) {
079                    c = SMarket.getDateOfOpening();
080                }
081                //set new price to first day of month or market's opening (only necessary for very first month)
082                ciss.newPriceSet(c, SMarket.getArticleCatalog().get(id).getBid());
083            }
084        }
085    
086        /**
087         * @param key the key of the CISalesStats to be returned.
088         * @return the CISalesStats with the according key.
089         */
090        public CISalesStats get(String key) {
091            try {
092                return (CISalesStats)super.get(key, null, false);
093            }
094            catch (VetoException e) {
095                return null;
096            }
097        }
098    
099        /**
100         * Adds a customer's purchase to the article statistics.
101         * @param customer the customer whose purchase is to be added.
102         * @param discount the discount allowed by the market.
103         */
104        public void addSales(UCustomer customer, double discount) {
105            CountingStock cs = customer.getShoppingBasket();
106            Iterator it = cs.keySet(null).iterator();
107            while (it.hasNext()) {
108                String id = (String)it.next();
109                CIArticle cia = SMarket.getArticleCatalog().get(id);
110                int price = cia.getBid();
111                int amount = cs.countItems(id, null);
112                int revenue = new Double((amount*price)*(1-discount)).intValue();
113                CISalesStats oldEntry = get(id);
114                oldEntry.addAmount(amount);
115                oldEntry.addRevenue(revenue);
116            }
117        }
118    
119        /**
120         * Adds the current date to the order history of an article's statistics, whenever the manager
121         * purchases it.
122         * @see CISalesStats#ordered
123         *
124         * @param cs the manager's purchase.
125         */
126        public void updateOrderHistory(CountingStock cs) {
127            Iterator it = cs.keySet(null).iterator();
128            while (it.hasNext()) {
129                String id = (String)it.next();
130                int amount = cs.countItems(id, null);
131                CISalesStats entry = get(id);
132                entry.ordered(SMarket.getTime(), amount); //update order history
133            }
134        }
135    
136        /**
137         * Adds the value customer's purchase to this month's revenue.
138         * @param revenue the revenue to be added.
139         */
140        public void addRevenue(int revenue) {
141            this.revenue += revenue;
142        }
143    
144        /**
145         * @return this month's revenue.
146         */
147        public int getRevenue() {
148            return revenue;
149        }
150    
151        /**
152         * Sets the miscellaneous costs of the market. Only used while instance of this class represents
153         * the current month.
154         * @param costs the costs to be set.
155         */
156        public void setCosts(int costs) {
157            this.costs = costs;
158        }
159    
160        /**
161         * @return this month's miscellaneous costs.
162         */
163        public int getCosts() {
164            return costs;
165        }
166    
167        /**
168         * @return the costs of all article purchases the manager has made this month.
169         */
170        public int getOrderCosts() {
171            Iterator it = keySet(null).iterator();
172            int sum = 0;
173            while (it.hasNext()) {
174                String id = (String)it.next();
175                CISalesStats ciss = get(id);
176                sum += ciss.getOrderAmount() * SMarket.getArticleCatalog().get(id).getOffer();
177            }
178            return sum;
179        }
180    
181        /**
182         * Saves the sum of the employee's wages. Only used when month ends and statistics are saved to
183         * {@link CCompleteStats}
184         * @param wages the wages to be set.
185         */
186        public void setWages(int wages) {
187            this.wages = wages;
188        }
189    
190        /**
191         * @return the saved wages. Will not work if instance of this class represents current month's statistics.
192         */
193        public int getWages() {
194            return wages;
195        }
196    
197        public String toString() {
198            return "CSalesStats " + getName();
199        }
200    
201        /**
202         * Adds the all order histories which are stored in a different CSalesStats to this one.<br>
203         * Using this method multiple times creates a complete order history for any desired range of time.
204         * With the help of {@link #getOrderCosts()} it is now possible to easily compute the total of
205         * money spent on purchases during that time.
206         *
207         * @param csToAdd the CSalesStats, which contains the order histories to be added.
208         * @see Statistics#getOverallStats(int, int, int, int)
209         */
210        public void addOrders(CSalesStats csToAdd) {
211            Iterator it = keySet(null).iterator();
212            int sum = 0;
213            while (it.hasNext()) {
214                String id = (String)it.next();
215                CISalesStats thisCiss = get(id);
216                CISalesStats newCiss = csToAdd.get(id);
217                thisCiss.appendOrderHistory(newCiss.getOrderHistory());
218            }
219        }
220    }