001 package data;
002
003 import java.util.*;
004
005 /**
006 * StockFromValueCreator that tries to fill a Stock using only items from another Stock.
007 *
008 * @author Steffen Zschaler
009 * @version 2.0 18/08/1999
010 * @since v0.5
011 */
012 public class StockFromStockCreator extends Object implements StockFromValueCreator {
013
014 /**
015 * The CatalogItemValue used to determine the CatalogItems' values.
016 */
017 protected CatalogItemValue m_civEvaluator;
018
019 /**
020 * The source Stock.
021 */
022 protected Stock m_stSource;
023
024 /**
025 * Create a new StockFromStockCreator.
026 *
027 * @param stSource the source Stock.
028 * @param civ the CatalogItemValue used to determine the CatalogItems' values.
029 */
030 public StockFromStockCreator(Stock stSource, CatalogItemValue civ) {
031 super();
032
033 m_stSource = stSource;
034 m_civEvaluator = civ;
035 }
036
037 /**
038 * Try to fill the given Stock using only items from the source Stock.
039 *
040 * <p>As this algorithm does not use backtracking, it may not always find a solution even if one would be
041 * possible.</p>
042 *
043 * <p><strong>Attention</strong>: The items that are added to the destination Stock will be removed from the
044 * source Stock.</p>
045 *
046 * @override Never
047 */
048 public Value fillStock(Stock st, Value v, DataBasket db) {
049 Catalog c = st.getCatalog(db);
050
051 if (c != m_stSource.getCatalog(db)) {
052 throw new CatalogConflictException();
053 }
054
055 List<CatalogItem> lCI = new LinkedList<CatalogItem>(); // get the catalog's items
056 for (Iterator<CatalogItem> i = c.iterator(db, false); i.hasNext(); ) {
057 lCI.add(i.next());
058 }
059
060 if (lCI.size() == 0) {
061 return v;
062 }
063
064 Collections.sort(lCI, DefaultCountingStockFromValueCreator.invertedCIValueOrder(m_civEvaluator)); // Sort the items, greates first
065
066 // building the Stock
067 for (Iterator<CatalogItem> i = lCI.iterator(); i.hasNext(); ) {
068
069 CatalogItem ci = i.next();
070 Value vItemValue = m_civEvaluator.getValue(ci);
071
072 for (Iterator<StockItem> j = m_stSource.get(ci.getName(), db, false); j.hasNext(); ) {
073 if (vItemValue.compareTo(v) <= 0) {
074 StockItem si = j.next();
075
076 try {
077 j.remove();
078
079 st.add(si, db);
080
081 v.subtractAccumulating(vItemValue);
082 }
083 catch (UnsupportedOperationException uoe) {}
084 }
085 }
086 }
087
088 return v;
089 }
090 }