In: Computer Science
Part 1 – Create a Stock Class
Write a class named Stock.
Stock Class Specifications
Include member variables for name (string), price (double), shares (double).
Write a default constructor.
Write a constructor that takes values for all member variables as parameters.
Write a copy constructor.
Implement Get/Set methods for all member variables.
Implement the CalculateValue function. This function should multiply the prices by the shares and return that value. Use the following function header: double CalculateValue().
Add a member overload for the assignment operator.
Add a non-member operator<< overload. Prints the values of all member variables on the given ostream.
Stock Class Updates
The Stock class should implement all the specifications from the first assignment plus the updates and features listed below.
Change all member variables to pointers. You will need to update code in any functions that use these member variables. Do NOT change any function signatures for this class. All functions should operate the same as before from the user of the classes’ perspective. For example, assume the get/set functions for title have the following signatures:
std::string GetName();
void SetName(std::string n);
These signatures should remain exactly the same. The same goes for any other functions that use these member variables. Only the internal implementation of the functions will change to accommodate the use of pointers.
Update the constructors. The constructors should allocate memory for the pointer member variables.
Add a destructor. The destructor should deallocate memory for the pointer member variables.
Update operator= and copy constructor. The operator= and copy constructor should be updated to perform deep copies.
Update operator<<. Make sure it prints out the values and not the addresses.
Add a non-member operator>> overload. The >> operator is used for input. Reads the values of all member variables from the given istream.
You can assume that a one word string is being used for name in order to make it a little easier to code. This is important because if you did not make that assumption you could not use the >> operator to read a string value. The >> operator only reads up until the first whitespace it encounters.
Part 2 – Create a Portfolio Class
Write a class that will store a collection of Stock. This class will be used to keep track of data for multiple Stock class instances. You MUST implement ALL of the specifications below.
Portfolio Class Specifications
Create a private member variable that is a static array of Stock. The size of the array can be whatever you want it to be.
Your class must implement all of the following functions (use the given function prototypes):
void Set(int index, Stock s) – Sets the value at the given index to the given Stock instance. You should test the index to make sure that it is valid. If the index is not valid then do not set the value.
Stock Get(int index) – Return the Stock located at the given index in the array.
int PriceRangeCount(double lowerBound, double upperBound) – Returns the count of the number of Stocks that fall within the given range. For example, assume the following number of Stock prices: 10, 20, 15, 25, 30, 40
If lowerBound is 20 and upperBound is 30 then the returned value should be 3. Any values that fall on the boundaries should be included in the count. In this example we are getting a count of the number of stocks that have a price between $20 and $30. Remember, this function is using price and not value.
Stock MostShares() – Returns the Stock in the Portfolio that has the most shares.
bool FindByName(string name, Stock &v) – Returns true if the Stock with the given name is in the array and false otherwise. If the Stock is in the array you should copy it into the Stock reference parameter.
double TotalValue() – Returns the sum of all Stock values (not prices) in the collection.
int Size() – Returns the size of the array.
void Initialize() – Initializes all of the elements of the array to reasonable default values.
string GetAuthor() – Returns your name. Just hard code your name into the function.
Create a default constructor that will initialize all elements of the array to default values.
Portfolio Class Updates
The Portfolio class should implement all the specifications from the first assignment plus the updates and features listed below.
Dynamic array. Change the internal implementation of the array so that the array is dynamically allocated.
Add a size member variable to the class. This member variable should ALWAYS contain the number of elements in the array (size of the array). Some functions may cause the size of the array to change so make sure that this member variable is updated to reflect the new size.
Update all the necessary code in the class so that it is usable with a dynamic array. One example of this is to change the ending condition of loops that visit all elements of the array. The ending limit should not be hard coded. They should use the new size variable as the ending condition.
Add a one parameter constructor that takes a size. This constructor should dynamically allocate an array of the given size. It should also set the size member variable to reflect the size.
Add a copy constructor. This function should make a deep copy of the passed in instance.
Add a destructor. This function should perform any necessary cleanup.
Add a member overload of operator= (assignment operator). This method should perform a deep copy of the passed in instance. After this function ends the size of the current instance’s array should be the same as the other instance’s array and all the data from the other instance should be copied into the current instance’s array.
Hint: C++ arrays have a fixed size. You may need to delete and then reallocate memory for the current instance’s array in order to make the current instance’s array the same size as the other instance’s array. Be careful for memory leaks.
Add a non-member operator<< overload. Prints the values of all elements of the array on the given ostream.
Add a Resize function. Here is the function signature:
void Resize(int newSize);
This function should create a new array that has the passed in size. You MUST retain any values that were previously in the array. The new array size can be larger or smaller. If the new array size is SMALLER just retain as many elements from the previous array that can fit.
Hint: C++ arrays have a fixed size. You may need to delete and then reallocate memory. Be careful for memory leaks.
Add a function named Clone with the following signature:
Portfolio *Clone();
This method should allocate a new dynamic instance of Portfolio that is a deep copy of the current instance. This method should return a pointer to the new instance.
Part 4 – Main Function
Main should create instances of Stock and Portfolio and contain an automated unit test for both of them.
Automated Test
Part 2 – Console Application - Main Function
Create a C++ console application that imports and uses the static library solution that you created. The console application should have a main function. In main you should create instances of the updated Portfolio class and demonstrate that ALL functions work properly. You can write unit testing code if you want but you are not required to.
Working code implemented in C++ and appropriate comments provided for better understanding.
Here I am attaching code for these files:
main.cpp:
#include <iostream>
#include "stock.h"
#include "portfolio.h"
#include "unit_test.h"
using namespace std;
//****************************************************
// Function: main
//
// Purpose: Provides unit testing of Stock and Portfolio
classes
//
//****************************************************
int main()
{
//Run unit tests
testStockSetGetName();
testStockSetGetPrice();
testStockSetGetShares();
testPortfolioSetGet();
testPortfolioPriceRangeCount();
testPortfolioMostShares();
testPortfolioFindByName();
testPortfolioTotalValue();
return 0;
}
portfolio.cpp:
#include "portfolio.h"
#include "stock.h"
#include <iostream>
#include <string>
using namespace std;
//****************************************************
// Function: Portfolio
//
// Purpose: Default constructor
//
//****************************************************
Portfolio::Portfolio()
{
Initialize();
}
//****************************************************
// Function: Set
//
// Purpose: Puts stock class into the array
//
//****************************************************
void Portfolio::Set(int index, Stock s)
{
if (index >= 0 && index < Size())
{
stockArray[index] = s;
}
else
{
cout << "invalid
index";
}
}
//****************************************************
// Function: Get
//
// Purpose: Returns stock class from given index
//
//****************************************************
Stock Portfolio::Get(int index)
{
return stockArray[index];
}
//****************************************************
// Function: PriceRangeCount
//
// Purpose: Returns amount of stocks whose price is within given
bounds
//
//****************************************************
int Portfolio::PriceRangeCount(double lowerBound, double
upperBound)
{
int count = 0;
//traverse array
for (int i = 0; i < Size(); i++)
{
//if value is in range, add to
count
if (stockArray[i].GetPrice() >=
lowerBound && stockArray[i].GetPrice() <=
upperBound)
{
count++;
}
}
return count;
}
//****************************************************
// Function: MostShares
//
// Purpose: Returns stock class with the most shares
//
//****************************************************
Stock Portfolio::MostShares()
{
Stock most("error", -1, -1);
//traverse array
for (int i = 0; i < Size(); i++)
{
//If stock has more shares, replace
"most"
if (stockArray[i].GetShares() >
most.GetShares())
{
most =
stockArray[i];
}
}
return most;
}
//****************************************************
// Function: FindByName
//
// Purpose: Determines if given stock name is within the
array
//
//****************************************************
bool Portfolio::FindByName(string name, Stock & v)
{
//traverse array
for (int i = 0; i < Size(); i++)
{
//check if stock is in array
if (stockArray[i].GetName() ==
name)
{
v =
stockArray[i];
return
true;
}
}
return false;
}
//****************************************************
// Function: TotalValue
//
// Purpose: Returns the total value of all stock in the array
//
//****************************************************
double Portfolio::TotalValue()
{
double total = 0;
//traverse array
for (int i = 0; i < Size(); i++)
{
total +=
stockArray[i].CalculateValue();
}
return total;
}
//****************************************************
// Function: Size
//
// Purpose: Returns the size of the array
//
//****************************************************
int Portfolio::Size()
{
return 10;
}
//****************************************************
// Function: Initialize
//
// Purpose: Initializes all members of the array to defaults
//
//****************************************************
void Portfolio::Initialize()
{
//create each element of the array
for (int i = 0; i < Size(); i++)
{
stockArray[i] = Stock("", 0,
0);
}
}
//****************************************************
// Function: GetAuthor
//
// Purpose: Returns name of the author
//
//****************************************************
std::string Portfolio::GetAuthor()
{
return "John Doe";
}
portfolio.h:
#ifndef PORTFOLIO_H
#define PORTFOLIO_H
#include "stock.h"
#include <iostream>
#include <string>
class Portfolio
{
private:
Stock stockArray[10];
public:
//Constructor
Portfolio();
//Setter
void Set(int index, Stock s);
//Getter
Stock Get(int index);
//Functions
void Initialize();
int PriceRangeCount(double lowerBound, double
upperBound);
int Size();
double TotalValue();
bool FindByName(std::string name, Stock &v);
std::string GetAuthor();
Stock MostShares();
};
#endif
stock.cpp:
#include "stock.h"
#include <string>
#include <iostream>
using namespace std;
//****************************************************
// Function: Stock
//
// Purpose: Default constructor
//
//****************************************************
Stock::Stock()
{
name = "no name";
price = 0;
shares = 0;
}
//****************************************************
// Function: Stock
//
// Purpose: Constructor with input data to initialize
//
//****************************************************
Stock::Stock(std::string name, double price, double shares)
{
this->name = name;
this->price = price;
this->shares = shares;
}
//****************************************************
// Function: Stock
//
// Purpose: Copy constructor
//
//****************************************************
Stock::Stock(const Stock &rhs)
{
name = rhs.name;
price = rhs.price;
shares = rhs.shares;
}
//****************************************************
// Function: SetName
//
// Purpose: Setter for name
//
//****************************************************
void Stock::SetName(std::string name)
{
this->name = name;
}
//****************************************************
// Function: SetPrice
//
// Purpose: Setter for price
//
//****************************************************
void Stock::SetPrice(double price)
{
this->price = price;
}
//****************************************************
// Function: SetShares
//
// Purpose: Setter for shares
//
//****************************************************
void Stock::SetShares(double shares)
{
this->shares = shares;
}
//****************************************************
// Function: GetName
//
// Purpose: Getter for name
//
//****************************************************
std::string Stock::GetName()
{
return name;
}
//****************************************************
// Function: GetPrice
//
// Purpose: Getter for price
//
//****************************************************
double Stock::GetPrice()
{
return price;
}
//****************************************************
// Function: GetShares
//
// Purpose: Getter for shares
//
//****************************************************
double Stock::GetShares()
{
return shares;
}
//****************************************************
// Function: CalculateValue
//
// Purpose: Returns the total value of the stock
//
//****************************************************
double Stock::CalculateValue()
{
return price * shares;
}
//****************************************************
// Function: operator=
//
// Purpose: Overloading = operator to copy data
//
//****************************************************
Stock& Stock::operator=(const Stock& rhs)
{
name = rhs.name;
price = rhs.price;
shares = rhs.shares;
return *this;
}
//****************************************************
// Function: operator<<
//
// Purpose: Overloading << operator to print data
//
//****************************************************
std::ostream& operator<<(std::ostream& output, Stock
&rhs)
{
output <<
"Name: " << rhs.name <<
endl <<
"Price: " << rhs.price
<< endl <<
"Shares: " << rhs.shares
<< endl;
return output;
}
stock.h:
#ifndef STOCK_H
#define STOCK_H
#include <string>
#include <iostream>
class Stock
{
private:
std::string name;
double price;
double shares;
public:
//Constructors
Stock();
Stock(std::string name, double price, double
shares);
Stock(const Stock &rhs);
//Setters
void SetName(std::string name);
void SetPrice(double price);
void SetShares(double shares);
//Getters
std::string GetName();
double GetPrice();
double GetShares();
//Functions
double CalculateValue();
//Operator Overload
Stock& operator=(const Stock& rhs);
friend std::ostream&
operator<<(std::ostream& output, Stock &rhs);
};
std::ostream& operator<<(std::ostream& output, Stock &rhs);
#endif
unit_test.cpp:
#include "unit_test.h"
#include "stock.h"
#include "portfolio.h"
#include <iostream>
#include <string>
using namespace std;
//****************************************************
// Function: testStockSetGetName
//
// Purpose: Provides unit testing for Stock class SetName and
GetName
//
//****************************************************
void testStockSetGetName()
{
const string testString = "testString";
Stock s;
//create test data
s.SetName(testString);
//test function
if (s.GetName() == testString)
{
cout << "Stock Set/Get Name:
Pass" << endl;
}
else
{
cout << "Stock Set/Get Name:
Fail" << endl;
}
}
//****************************************************
// Function: testStockSetGetPrice
//
// Purpose: Provides unit testing for Stock class SetPrice and
GetPrice
//
//****************************************************
void testStockSetGetPrice()
{
const double testDouble = 25.0;
Stock s;
//create test data
s.SetPrice(testDouble);
//test function
if (s.GetPrice() == testDouble)
{
cout << "Stock Set/Get Price:
Pass" << endl;
}
else
{
cout << "Stock Set/Get Price:
Fail" << endl;
}
}
//****************************************************
// Function: testStockSetGetShares
//
// Purpose: Provides unit testing for Stock class SetPrice and
GetPrice
//
//****************************************************
void testStockSetGetShares()
{
const double testDouble = 25.0;
Stock s;
//create test data
s.SetShares(testDouble);
//test function
if (s.GetShares() == testDouble)
{
cout << "Stock Set/Get
Shares: Pass" << endl;
}
else
{
cout << "Stock Set/Get
Shares: Fail" << endl;
}
}
//****************************************************
// Function: testPortfolioSetGet
//
// Purpose: Provides unit testing for Portfolio class Set and
Get
//
//****************************************************
void testPortfolioSetGet()
{
Portfolio p;
Stock s;
bool getSetPassed = true;
//create test stock
s.SetName("testName");
s.SetPrice(12);
s.SetShares(11);
p.Initialize();
//test each index
for (int i = 0; i < p.Size(); i++)
{
//set data to index
p.Set(i, s);
//test each member
variable
if (p.Get(i).GetName() !=
s.GetName() ||
p.Get(i).GetPrice() != s.GetPrice() ||
p.Get(i).GetShares() != s.GetShares())
{
getSetPassed =
false;
}
}
//print results
if (getSetPassed == true)
{
cout << "Portfolio Set/Get:
Pass" << endl;
}
else
{
cout << "Portfolio Set/Get:
Fail" << endl;
}
}
//****************************************************
// Function: testPortfolioPriceRangeCount
//
// Purpose: Provides unit testing for Portfolio class
PriceRangeCount
//
//****************************************************
void testPortfolioPriceRangeCount()
{
const int testLowerBound = 20;
const int testUpperBound = 30;
const int rangeCount = 3;
Stock a;
Stock b;
Stock c;
Stock d;
Stock e;
Stock f;
Portfolio p;
//create test stocks
a.SetPrice(10);
b.SetPrice(20);
c.SetPrice(15);
d.SetPrice(25);
e.SetPrice(30);
f.SetPrice(40);
//set test stocks to p
p.Initialize();
p.Set(0, a);
p.Set(1, b);
p.Set(2, c);
p.Set(3, d);
p.Set(4, e);
p.Set(5, f);
//test function
if (p.PriceRangeCount(testLowerBound, testUpperBound)
== rangeCount)
{
cout << "Portfolio
PriceRangeCount: Pass" << endl;
}
else
{
cout << "Portfolio
PriceRangeCount: Fail" << endl;
}
}
//****************************************************
// Function: testPortfolioMostShares
//
// Purpose: Provides unit testing for Portfolio class
MostShares
//
//****************************************************
void testPortfolioMostShares()
{
Stock a;
Stock b;
Stock c;
Stock d;
Stock e;
Stock f;
Portfolio p;
//create test stocks
a.SetShares(12);
b.SetShares(22);
c.SetShares(34);
d.SetShares(41);
e.SetShares(16);
f.SetShares(9);
//set test stocks to p
p.Initialize();
p.Set(0, a);
p.Set(1, b);
p.Set(2, c);
p.Set(3, d);
p.Set(4, e);
p.Set(5, f);
//test function
if (p.MostShares().GetShares() == d.GetShares())
{
cout << "Portfolio
MostShares: Pass" << endl;
}
else
{
cout << "Portfolio
MostShares: Fail" << endl;
}
}
//****************************************************
// Function: testPortfolioFindByName
//
// Purpose: Provides unit testing for Stock class FindByName
//
//****************************************************
void testPortfolioFindByName()
{
const string testName = "delta";
Stock a;
Stock b;
Stock c;
Stock d;
Stock e;
Stock f;
Stock s;
Portfolio p;
//create test stocks
a.SetName("alpha");
b.SetName("beta");
c.SetName("gamma");
d.SetName("delta");
e.SetName("eta");
f.SetName("theta");
//set test stocks to p
p.Initialize();
p.Set(0, a);
p.Set(1, b);
p.Set(2, c);
p.Set(3, d);
p.Set(4, e);
p.Set(5, f);
//test function
p.FindByName(testName, s);
if (p.FindByName(testName, s) == true &&
s.GetName() == d.GetName())
{
cout << "Portfolio
FindByName: Pass" << endl;
}
else
{
cout << "Portfolio
FindByName: Fail" << endl;
}
}
//****************************************************
// Function: testPortfolioTotalValue
//
// Purpose: Provides unit testing for Portfolio class
TotalValue
//
//****************************************************
void testPortfolioTotalValue()
{
const double totalValue = 1021;
Stock a;
Stock b;
Stock c;
Stock d;
Stock e;
Stock f;
Portfolio p;
//create test stocks
a.SetPrice(12);
a.SetShares(6);
b.SetPrice(24);
b.SetShares(0);
c.SetPrice(11);
c.SetShares(19);
d.SetPrice(9);
d.SetShares(31);
e.SetPrice(13);
e.SetShares(14);
f.SetPrice(31);
f.SetShares(9);
//set test stocks to p
p.Initialize();
p.Set(0, a);
p.Set(1, b);
p.Set(2, c);
p.Set(3, d);
p.Set(4, e);
p.Set(5, f);
//test function
if (p.TotalValue() == totalValue)
{
cout << "Portfolio
TotalValue: Pass" << endl;
}
else
{
cout << "Portfolio
TotalValue: Pass" << endl;
}
}
unit_test.h:
#ifndef TEST_H
#define TEST_H
void testStockSetGetName();
void testStockSetGetPrice();
void testStockSetGetShares();
void testPortfolioSetGet();
void testPortfolioPriceRangeCount();
void testPortfolioMostShares();
void testPortfolioFindByName();
void testPortfolioTotalValue();
#endif
Sample Output Screenshots: