Skip to content

Instantly share code, notes, and snippets.

@ereidland
Last active December 15, 2015 14:58
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save ereidland/5278241 to your computer and use it in GitHub Desktop.
Save ereidland/5278241 to your computer and use it in GitHub Desktop.
Example 5 at Library
#define MAX_INVENTORY 100
//Arguments to use in cin.ignore:
#define IGNORE_ARGS 256, '\n'
#include <fstream>
#include <iomanip>
#include <iostream>
#include <string>
using namespace std;
bool readInventory(string filename);
double checkout();
bool updateInventory(string filename);
struct Product
{
int code; //Product code.
string name; //Product name.
double cost; //Product cost.
bool byPounds; //By pounds (or by unit)
//Union: Variables of the same type take up the same place in memory,
//And since we don't access either of them at the same time, the code doesn't break.
union
{
double pounds; //Pounds in inventory.
int units; //Units in inventory.
};
//Normal if:
//if (condition)
// { code }
//else { other code }
//The inline if:
//(condition ? code : other code)
void print() //Print out this product.
{
cout << setw(8) << "Name:" << name << endl
<< setw(8) << "Code:" << code << endl
<< setw(8) << "Cost:" << cost << endl
<< setw(8) << "By pounds:" << (byPounds ? "true" : "false") << endl
<< setw(8) << (!byPounds ? "Units:" : "Pounds:") << (byPounds ? pounds : units) << endl;
}
};
Product * inventory; //Pointer to first element in array of products.
int inventoryCount = 0;
Product * getProduct(int code);
int main()
{
//1. Read in and store inventory.
readInventory("items.txt"); //Read in the inventory from items.txt;
double cost = checkout();
cout << "Total cost: $" << setprecision(2) << fixed << cost << endl;
//2. Get item code from user.
//3. If valid
//4. Request units/pounds based on product type.
//5. If valid and quantity is in inventory
//6. Add to cart, go to step 2.
//7. else if 0, exit
//8. else print error, go back to 2.
//9. Print receipt. If over 50, discount 5%
updateInventory("items.txt");
//Delete the inventory. Note the [] required to let delete know we are deleting an array and not a pointer.
delete [] inventory;
return 0;
}
bool readInventory(string filename)
{
//Initialize product array of MAX_INVENTORY size.
inventory = new Product[MAX_INVENTORY];
inventoryCount = 0;
ifstream in(filename);
if (!in.is_open())
{
cout << "Could not open " << filename << endl;
return false;
}
while (!in.eof() && inventoryCount < MAX_INVENTORY)
{
Product product;
in >> product.code;
if (in.fail())
{
cout << "Invalid product code." << endl;
return false;
}
in >> product.name;
if (in.fail())
{
cout << "Invalid product name." << endl;
return false;
}
in >> product.byPounds;
if (in.fail())
{
cout << "Invalid product byPounds (bool)." << endl;
return false;
}
in >> product.cost;
if (in.fail())
{
cout << "Invalid product cost." << endl;
return false;
}
if (product.byPounds)
{
in >> product.pounds;
if (in.fail())
{
cout << "Invalid product weight." << endl;
return false;
}
}
else
{
in >> product.units;
if (in.fail())
{
cout << "Invalid product count." << endl;
return false;
}
}
product.print();
inventory[inventoryCount] = product;
inventoryCount++;
}
return true;
}
Product * getProduct(int code)
{
for (int i = 0; i < inventoryCount; i++)
if (inventory[i].code == code) //If codes match.
return &inventory[i]; //Returning refrence to inventory[i]
return NULL;
}
double checkout()
{
double cost = 0;
int code;
while (true)
{
cout << "Enter product code: " << endl;
cin >> code;
if (cin.fail())
{
cout << "Invalid product code!" << endl;
cin.clear();
cin.ignore(IGNORE_ARGS);
continue; //Continue skips all execution in this iteration of the loop, allowing us to jump to the next iteration.
}
if (code == 0)
{
cout << "Done checking out. Cost: " << cost << endl;
if (cost > 50)
{
cout << "Discount: " << setprecision(2) << fixed << cost * 0.05 << endl;
cost *= 0.95; //Discount by %5.
}
return cost;
}
Product * item = getProduct(code);
if (!item)
{
cout << "Item not found.";
continue;
}
if ((item->byPounds && item->pounds <= 0) || (!item->byPounds && item->units <= 0))
{
cout << "There's nothing left of that item.";
continue;
}
cout << "Enter " << (item->byPounds ? "pounds" : "weight") << " (max " << (item->byPounds ? item->pounds : item->units) << "): ";
if (item->byPounds)
{
double pounds;
cin >> pounds;
if (cin.fail())
{
cout << "Invalid weight." << endl;
}
else if (pounds > item->pounds)
{
cout << "Not enough pounds left of that item." << endl;
}
else if (pounds < 0)
{
cout << "Can't buy a negative weight (that's called giving)" << endl;
}
else
{
double added = pounds * item->cost;
item->pounds -= pounds;
cout << "Added " << pounds << " pounds of " << item->name << " for $" << setprecision(2) << fixed << added << endl;
cost += added;
}
}
else
{
int units;
cin >> units;
if (cin.fail())
{
cout << "Invalid weight." << endl;
}
else if (units > item->units)
{
cout << "Not enough units left of that item." << endl;
}
else if (units < 0)
{
cout << "Can't buy a negative units (that's called giving)" << endl;
}
else
{
double added = units * item->cost;
item->units -= units;
cout << "Added " << units << " of " << item->name << " for $" << setprecision(2) << fixed << added << endl;
cost += added;
}
}
//Make sure it's clean for the next iteration.
cin.clear();
cin.ignore(IGNORE_ARGS); //So input doesn't keep coming back on fail.
}
return cost;
}
bool updateInventory(string filename)
{
ofstream out(filename);
for (int i = 0; i < inventoryCount; i++)
{
//Write out all elements separated by space.
out << inventory[i].code << " "
<< inventory[i].name << " "
<< inventory[i].byPounds << " "
<< inventory[i].cost << " "
<< (inventory[i].byPounds ? inventory[i].pounds : inventory[i].units) << endl;
}
out.close();
return false;
}
@ereidland
Copy link
Author

Removed #define/#ifdef and #include, as they were only used in example.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment