/*
* $Author: bhevans $
* $Date: 1996/06/05 21:23:43 $
* $Source: /home/phoenix/cscstd/ijkl/jlarsen/box/RCS/StorageUnit.java,v $
* $Revision: 1.4 $
* $Log: StorageUnit.java,v $
# Revision 1.4 1996/06/05 21:23:43 bhevans
# *** empty log message ***
#
# Revision 1.3 1996/06/05 21:21:31 bhevans
# fixed ftr # 9
#
# Revision 1.2 1996/06/05 18:12:42 bhevans
# Fixed changes per 5.26 ftr
#
# Revision 1.1 1996/05/26 22:48:32 bhevans
# Initial revision
#
*/
package com.nanosoft.pcm.machine;
import java.util.*;
import java.io.*;
import com.nanosoft.pcm.machine.*;
/**
* The storage unit contains all information regarding the products
* available for selling.
* @see StorageItem
* @see StItem
* @version $Revision: 1.4 $
* @author $Author: bhevans $
*/
public class StorageUnit {
private int DEF_ITEMS = 16; // Default Storage Space
private String Fname = "storage.default";
private Hashtable Table;
private StItem theCheapestItem;
private StItem tmpItem;
private CurrencyAcceptor CurAcceptor;
/**
* Precondition: expectedSize not < 1 and legal fileName. An illegal
* filename will cause the program to abort.
* @param expectedSize The expected number of different product
* types to store.
* @param fileName The file from which to load the default storage.
* @exeception MemoryError Thrown when an illegal expectedSize is reached.
* An invalid fileName will abort the program.
*/
public StorageUnit(int expectedSize, String fileName, CAccpt CurrencyAcceptor)
throws MemoryError {
if ( expectedSize < 1 ) { throw new MemoryError(); }
else {
Table = new Hashtable( (int)(1 + expectedSize * 1.35) + 1, 0.75f);
theCheapestItem = new StItem();
CurAcceptor = CAccpt;
this.loadTable( fileName );
CurAcceptor.updateLowestCostItem(this.findLowestCostItem());
}
}
/**
* Precondition: all Objects are valid.
* @param aSelection The keypress associated with the selection.
* @return A boolean value describing whether the product type
* has is listed in the inventory, disregarding the quantity on hand.
*/
public boolean isValidSelection(String aSelection) {
return ( Table.get(aSelection) != null );
}
/**
* Precondition: all Objects are valid.
* @param aSelection The keypress associated with the selection.
* @return A boolean value describing whether the product has a non-zero
* quantity on hand. Returns false if the type is not
* listed in the inventory.
*/
public boolean isInStock(String aSelection) {
tmpItem = (StItem) Table.get(aSelection);
return ( (tmpItem != null) && ( tmpItem.Quantity > 0) );
}
/**
* Precondition: input must cast into a StorageItem
* This little method does nothing useful, something must
* have been implemented incorrectly.
* @param anItem The StorageItem from which to extract the price.
* @return The price of the item.
*/
public MoneyAmount checkPrice (StorageItem anItem) {
tmpItem = (StItem) Table.get(anItem.getSelectionCode() );
return ( tmpItem.Item.getPrice() );
}
/**
* Performance consideration: this function enumerates through the table
* iff. the currently lowest priced item is out of stock.
* @return The lowest priced product type.
*/
public StorageItem findLowestCostItem() {
if ( theCheapestItem.Quantity == 0 ) {
Enumeration enum = Table.keys();
long price = Long.MAX_VALUE;
while ( enum.hasMoreElements() ) {
tmpItem = (StItem) enum.nextElement();
if ( ( tmpItem.Quantity != 0 ) &&
( (tmpItem.Item.getPrice()).getAmount() <
(theCheapestItem.Item.getPrice()).getAmount() )) {
theCheapestItem = tmpItem;
}
}
}
return theCheapestItem.Item;
}
/**
* Dispenses the product and reduces the quantity on-hand associated
* with the product.
* @param aSelection The keypress associated with the selection.
* @exception MemoryError Thrown when given an invalid selection.
*/
public void dispenceItem(String aSelection)
throws MemoryError {
if ( ! isInStock(aSelection) ) {
throw new MemoryError();
}
else {
tmpItem = (StItem) Table.remove(aSelection);
tmpItem.Quantity -= 1;
Table.put(aSelection,tmpItem);
CurAcceptor.updateLowestCostItem(this.findLowestCostItem());
}
}
/**
* @param anItem The StorageItem from which to extract the key.
* @see StorageItem#isValidSelection
*/
public boolean searchForItem(StorageItem anItem){
return isValidSelection( anItem.getSelectionCode() );
}
/**
* Precondition: The selection is valid.
* @param aSelection The keypress associated with the selection.
* @return A MoneyAmount representing the price of the item.
*/
public MoneyAmount getPrice(String aSelection) {
tmpItem = (StItem) Table.get(aSelection);
return tmpItem.Item.getPrice();
}
/**
* @return The price of the cheapest product in stock.
* @see StorageUnit#findLowestCostItem
*/
public MoneyAmount getLowestCostItem() {
this.findLowestCostItem();
return theCheapestItem.Item.getPrice();
}
/**
* Precondition: The key is unique.
* @param aSelection The keypress associated with the selection.
* @param aKey The keypress associated with the selection.
* @param aDescr A description for item ( its name ).
* @param aPrice A price associated with buying the item.
* @param aQuantity An inital quantity for the item.
*/
protected void insertItem(String aKey, String aDescr, MoneyAmount aPrice,
int aQuantity)
throws MemoryError {
StItem aTempItem = new StItem();
if ( ! this.isValidSelection(aKey) ) {
aTempItem = new StItem();
aTempItem.Quantity = aQuantity;
aTempItem.Item = null;
aTempItem.Item = new StorageItem(aKey, aDescr, aPrice );
Table.put(aKey, aTempItem);
}
else throw new MemoryError();
}
/**
* Precondition: filename exists, file is correctly made. The
* following code segment will insert 20 twinkies at $50 a pop.
*
* # File produced by Bob
* # Insert item one...
* A2
* Twinkies
* 5000
* 20
*
* @param aFileName The filename from which to load the storage.
*/
protected void loadTable ( String aFileName )
{
RandomAccessFile FileIn;
StorageItem Item;
String Control;
String bufs[];
double aPrice;
try {
bufs = new String[10];
FileIn = new RandomAccessFile(aFileName,"r");
Control = FileIn.readLine();
while(Control != null) {
if ( Control.startsWith("#") ) { ; }
else if ( Control.substring(0,1) == " " ||
Control.substring(0,1) == "\n") { ; }
else {
bufs[0] = Control.substring(2); // Key
bufs[1] = FileIn.readLine(); // Description
bufs[2] = FileIn.readLine(); // Price
bufs[3] = FileIn.readLine(); // Number
aPrice = (new Double(bufs[2])).doubleValue();
this.insertItem( bufs[0],
bufs[1],
new MoneyAmount(aPrice),
Integer.parseInt(bufs[3]));
}
Control = FileIn.readLine();
}
}
catch(java.lang.Exception e) {
System.err.println(e.toString());
System.exit(1);
}
}
}
/**
* @see StorageUnit
* @see StorageItem
* @version $Revision: 1.4 $
* @author $Author: bhevans $
*/
class StItem {
public StorageItem Item;
public int Quantity;
public StItem() { Quantity = 0; }
}