Answered step by step
Verified Expert Solution
Link Copied!

Question

1 Approved Answer

Please SOLVE C++ ,almost done just need iterators, namespace, and display lab The universities really liked the ability to bundle the information for the labs,

Please SOLVE C++ ,almost done just need iterators, namespace, and display lab

The universities really liked the ability to bundle the information for the labs, but now there is some consideration given to increasing the performance of the system that have been accompanied with recommendations. Our task will be to implement these suggested changes.

Recap of current system

The computer lab is a system that hosts users of several universities computer labs, and allows users of the labs to log into and log off from the available machines. The computer lab system also keeps track of the machines that are available and those that are in use, allowing users to locate an existing computer that is free as well as free the computers (remove users) upon the users logout.

Specifications for the program

You have 8 universities under contract. These labs contain computer stations that are hold the work stations numbered as shown in the table below:

Lab Number

Computer station numbers

1

1-19

2

1-15

3

1-24

4

1-33

5

1-61

6

1-17

7

1-55

8

1-37

The universities would like to change the structure of the dynamic array of objects to that of a linked list. This linked list should continue to hold the same information as before, and also continue to store the data dynamically (on the heap). We will be creating linked lists to replace our member arrays, and the pointer array too! Each node will be dynamically allocate for this Linked List. We also will be leveraging one of the major benefits that come with the linked list by allocating only as many nodes as there are active users. What this means is that for each universitys lab, we can grow and shrink the linked list accordingly. We will continue to utilize the parallel arrays from prior, and we will use the maximum size for each linked list from the corresponding values found in the LABSIZES array. Whenever a linked lists size reaches the threshold, issue a message that states the lab is full at this time and to try again later. So, for example, when I have allocated the 19th active node on linked list 1, the next request for a new user will exceed the limit and generate a message (assuming no users had been removed between requests).

Another requirement for the linked list pertains to requests for the removal of a user from a work station. You will have the choice of two mutually exclusive options here to perform this task, and you should explicitly state in your comments which of the two options that you are using. The first option is to remove the node, and rewire the pointers. The second option is to create what is called a tombstone. With this option you leave the node intact, but mark the node as being not in use (use a sentinel?). These tombstones can then be reused for new users by searching through the list and locating one sequentially as you go. Consider how to manage this. Creating tombstones only when the threshold was reached? Allocate the entire linked list and initially fill it with tombstones? Make a choice based on solid reasoning, and weigh the tradeoffs. Overall, the first option of no tombstones allows us to save memory, by only allocating when someone uses a station, and by deallocating a node when the user logs off. Youll have to accommodate the index somehow, and likely that will involve adding another member item to your class to hold it. The overhead to that will be carrying a small int around for each node. The second option yields faster processing because we dont do any individual Input/Output operations (allocations/deallocations) after we do the initial allocation. Notice, with this change you might consider the existing capacity checking procedure and modify that process as you need to with efficiency in mind.

Next, the recommendation has been put forth to make use of iterators for the linked list. An iterator is a generalization of a pointer. Iterators are used to move through the elements in some range of a container. The operations ++ , -- , and re-referencing * are usually defined for an iterator. The basic idea, and in fact the prototypical model for iterators, can easily be seen in the context of linked lists. A linked list is one of the prototypical data structures, and a pointer is a prototypical example of an iterator. Where applicable, use these iterators exclusively for all operations. Construct your iterator as constant iterator where it should be too.

Next, you will create a file for capturing login information. This file will log all of the information and activities in chronological order as new users login, and only for login information and logout. The design of this file is up to you, but this file must contain the following:

Timestamp, a c-string of 20 characters that looks like: Mon Jun 12 15:22:30 Action, a char that is in/out, that is: I (for login), and O (for logout) UserID, this is the integer from the nodes element, can pad with leading zeroes User time, this is our integer from the nodes element. User name, this is our string (putting this last to make it easier to read back).

Each and every time that your program runs, this file will be appended to. The name of the log file is totally up to you, but should be a .txt extension. Design a separate function(s) to handle all of this. Be sure to write only when the user has successfully completed a transaction. Dont forget to think through what happens when a request has to wait because the lab is full.

Consider the following code example for the time (must #include ctime, which you may already have from randomizing):

// current date/time based on current system

time_t now = time(0);

// convert now to c-string form

char* timeOf = ctime(&now);

// we want a way to limit the size to be just 20 in length

timeIn[20] = '\0'; // this effectively truncates the c-string

This code works and can be used directly in your program. Placing spaces between each item/field in your file output will probably be a good idea, in case we need to read this log later (and we will). Make use of manipulators for the output.

Finally, we will now use separate compilation files, and we will try to externalize our CONSTANTS (see below).

Design of the structures

We will continue to use the following code that creates a constant fixed array of length 8 for the labs. This is our array that holds the number of possible work stations. NUMLABS is also created to enable us to add or subtract a lab. Using constants here allows our program to be much more dynamic in terms of modification efforts and control. This array is also used for the allocation of the linked list (the sizes).

Separate files by placing your code into implementations files (.cpp), and also all of your headers (.hpp). A header contains class and functions definitions. The implementation file holds the implementation of the class. By doing this, if our class implementation doesnt change then it wont need to be recompiled. Dont forget your include guards. You will at least have main, a file that has your application (cpp), and your link list class (hpp).

Next, modify this part of your existing code to declare these constants using either an unnamed Namespace or a Namespace named myConstants.

// Global Constants

// Number of computer labs

const int NUMLABS = 8;

// Number of computers in each lab

const int LABSIZES[NUMLABS] = {19, 15, 24, 33, 61, 17, 55, 37};

// Names of university of each lab

const std::string UNIVERSITYNAMES[NUMUNIVERSITIES] = {"The University of Michigan", "The University of Pittsburgh", "Stanford University", "Arizona State University", "North Texas State University", "The University of Alabama, Huntsville", "Princeton University", "Duquesne University"};

You are going to figure out how to share the constants with the other functions. Consider extern to explicitly make the constants NUMLABS, LABSIZES, and UNIVERSITYNAMES external. We want these constant identifiers to be defined in one translation unit (hpp) and shared with other translation units. Dont make extra copies (see the lecture notes).

Consider your login logic and insert the function(s) to add your log file. Make sure you successfully logged in first before adding the record to your file.

Design of the application

Everything else in your system should remain intact, and the functionality should be the same. This means all off the displays (menu, etc) look and behave exactly as they did before. Carefully consider your redesign effort strategy to maintain your functionality, and to change code as minimally as possible. Test thoroughly, and test incrementally.

Thats a lot to change, and at a high level heres what we are doing: 1) convert arrays of objects to linked lists (holding the same objects); 2) distribute code into separate compilation files, 3) convert to iterators for searching, reading, and writing to the linked lists; 4) create a log file for each and every login and logout, and; 5) employ external linkage for the constants listed above.

You may continue to maintain your data as classes in the linked list or convert them to structs, your choice. Your list class may encapsulate a separate node class too (see the demo), but whatever you decide you will want to have all of the supporting methods in your design. Do not forget to manage (and free ~destructor) the LL memory since we are on the heap. Do not use #pragma directives in your files in place of include guards. #Pragma is not approved by the C++ Standards Committee. Be careful not to use the linked lists from the STL either or you will receive no credit L. Yikes!

//main

#include #include #include #include #include #include #include #include #include #include "LinkListNode.hpp" #include #include #include

using std::cin;

using std::cout;

using std::setw;

using std::setfill;

using std::endl;

using std::string;

//Global Constants

const int NUMLABS = 8;

// Size of all labs

const int LABSIZES[NUMLABS] = { 19, 15, 24, 33, 61, 17, 55, 37 };

// Names of university of each lab

const string UNIVERSITYNAMES[NUMLABS] = { "The University of Michigan", "The University of Pittsburgh",

"Stanford University", "Arizona State University", "North Texas State University", "The University of Alabama, Huntsville",

"Princeton University", "Duquesne University" };

void login(LabList&); //Will simulate student login, change value of a lab station to a 5 digit code

void LogOut( LabList); //Will simulate student logout, change value of a lab station to 0

void search( LabList); //will search for an ID, return either lab station or "Student is not logged on"

void display(LabList); //Will show lab of choice on screen, marking stations by number and showing which stations are full and which are empty.

void printMenu(); //Will create UI menu

void printUni(); //Shows list of available universities and which lab number to use when requesting them

int userInput(int, int); //Handles all user input

string userName(); //Verifies input name

bool IDcheck(int, vector); //Checks for the unique IDs of each student, smaller than the entire object array

int main()

{

srand(time(NULL));

bool endFlag = true;

//int userChoice = 0;

LabList uniqueIDs;

printUni();

do

{

printMenu();

switch (userInput(1, 5))

{

case (1) :

login(uniqueIDs);

break;

case (2) :

LogOut(uniqueIDs);

break;

case (3) :

uniqueIDs.search();

break;

case (4) :

uniqueIDs.display();

break;

case (5) :

endFlag = false;

break;

default:

cout << "Input must be an int between 1 and 5. Please try again ";

break;

}

} while (endFlag);

return 0;

}

//Precondition: Two global constants, a jagged array, and an int vector

//Postcondition: A value in one array has been assigned a number between 0 and 99999

void login(LabList& list)

{

int IDspace = (rand() % 99999 + 1); //Creates an ID

cout << "userID: " << setfill('0') << setw(5) << IDspace << endl;

cout << "What is the University Lab Number (1-" << NUMLABS << ") " << endl;

int uni;

cin >> uni;

assert(uni > 0 && uni < 9);

cout << "What station would you like to log in to? (1-" << LABSIZES[uni - 1]<< ")" << endl;

int chair;

cin >> chair;

assert(chair > 0 && chair < LABSIZES[uni-1]);

cout << "What is your name? ";

string user;

cin >> user;

cout << "Please enter the minutes of use for this workstation (15/30/45/60): "; //Verifies time

int input;

bool mistake = false;

do {

cin >> input;

cout << "here" << endl;

if (input != 15 && input != 30 && input != 45 && input != 60)

{

mistake = true;

cout << " Input must be one of the following numbers: 15, 30, 45, 60";

cout << " Please try again ";

cin.clear();

cin.ignore(std::numeric_limits::max(), ' ');

}

} while (mistake);

int Min = input;

cin.clear();

list.insertNode(IDspace, Min, user, uni, chair);

cout << "You have successfully logged in! ";

ofstream output;

output.open("log.txt");

output << "ID: " << IDspace <<", "<< " Name: " << user <<", "<< " University: " <

output << "Station: " << chair <<", "<< " Date: Nov (11/11/17)" <<", "<< " Time: " << Min << " min" << " I/O: " << " I " << endl;

output.close();

}

//Precondition: None

//Postcondition: A menu is printed, informing the user of input options and what each option does.

void printMenu()

{

cout << ' ' << setfill('_') << setw(60) << ' ' << endl;

cout << '|' << setfill('-') << setw(60) << '|' << endl;

cout << '|' << setfill(' ') << setw(42) << "Student Incorperated" << setw(18) << "|" << endl;

cout << '|' << setfill(' ') << setw(38) << "Computer Lab Systems" << setw(22) << "|" << endl;

cout << '|' << setfill('_') << setw(60) << '|' << endl;

cout << '|' << setfill(' ') << setw(32) << "MAIN MENU" << setw(28) << "|" << endl;

cout << '|' << setfill(' ') << setw(35) << "1) Simulate Login" << setw(25) << "|" << endl;

cout << '|' << setfill(' ') << setw(36) << "2) Simulate Logoff" << setw(24) << "|" << endl;

cout << '|' << setfill(' ') << setw(27) << "3) Search" << setw(33) << "|" << endl;

cout << '|' << setfill(' ') << setw(33) << "4) Display labs" << setw(27) << "|" << endl;

cout << '|' << setfill(' ') << setw(25) << "5) Quit" << setw(35) << "|" << endl;

cout << '|' << setfill('_') << setw(60) << '|' << endl;

cout << "Your choice: ";

}

//Precondition: None

//Postcondition: A list is printed, informing the user of input options for all available universities.

void printUni()

{

cout << " Welcome - here is our list of available labs ";

for (int i = 0; i < NUMLABS; i++)

{

cout << "lab # " << i + 1 << " for " << UNIVERSITYNAMES[i] << endl;

}

cout << endl;

}

//Precondition: Minimum and maximum values are set

//Postcondition: An int of neccessary value is returned to the caller

int userInput(int min, int max)

{

int input;

bool mistake;

do {

mistake = false;

cin >> input;

if (cin.fail() || input < min || input > max)

{

mistake = true;

cout << "Input must be an integer between " << min << " and " << max << std::endl;

cout << "Please try again ";

cin.clear();

cin.ignore((std::numeric_limits::max()), ' ');

}

} while (mistake);

return input;

}

void LogOut(LabList list)

{

list.search();

int ID;

list.deleteNode(ID);

cout << "Has logged out! ";

ofstream output;

output.open("log.txt", fstream::app);

output << "ID: " << ID << " I/O: " << " O ";;

output.close();

}

//LinkListNode.hpp

#ifndef LINKLISTNODE_HPP #define LINKLISTNODE_HPP #include

using namespace std; class LabList { public: struct Listnode // the node of the linked list { int ID; int time; string name; int university; int seats; int lab;

struct Listnode * next; }; Listnode *head; //points to the head

//constructor LabList() { head = 0;}

//destructor ~LabList(); void appendNode(int, int); void insertNode(int, int, string, int, int); void deleteNode(int); void displayList() const; void search(); void display() const; };

#endif // TREENODE_HPP

LinkListNode.cpp

#ifndef LINKLISTNODE_CPP

#define LINKLISTNODE_CPP

#include "LinkListNode.hpp"

#include

#include

#include

#include

//**************************************************

// Destructor *

// This function deletes every node in the list. *

// pre: n/a *

// post: destroyed object *

//**************************************************

LabList::~LabList()

{

Listnode *nodePtr; // To traverse the list

Listnode *nextNode; // To point to the next node

// Position nodePtr at the head of the list.

nodePtr = head;

// While nodePtr is not at the end of the list...

while (nodePtr != 0)

{

// Save a pointer to the next node.

nextNode = nodePtr->next;

// Delete the current node.

delete nodePtr;

// Position nodePtr at the next node.

nodePtr = nextNode;

}

}

//I used most of this code from the notes on Springboard !

//Appendnode funtion

//Precondition - given a char as a parameter

//Appends a new node to the end of the link list that points to the null pointer

void LabList::appendNode(int uni, int seat)

{

Listnode *newNode;

Listnode *nodePtr;

newNode = new Listnode;

newNode->university = uni;

newNode->seats = seat;

newNode->next = 0;

if(!head)

head = newNode;

else

{

nodePtr = head;

//finding the last node in the list

while(nodePtr->next)

nodePtr = nodePtr->next;

nodePtr->next = newNode;

}

}

//I used most of this code from the notes on Springboard !

//precondition - given a char as a parameter

//postcondition - inserts a new node that is inserted where that new node's value is less than one sequencially in the list

// and then points to the next one in the list

void LabList::insertNode(int ID, int time, string name, int uni, int seat)

{

Listnode *newNode;

Listnode *nodePtr;

Listnode *previousNode = 0;

newNode = new Listnode;

newNode->ID = ID;

newNode->time = time;

newNode->name = name;

newNode->university = uni;

newNode->seats = seat;

if(!head)

{

head = newNode;

newNode->next = 0;

}

else

{

nodePtr = head;

previousNode = 0;

while(nodePtr != 0 && nodePtr->ID < previousNode->ID) // I used the less than since the insertNode function was to insert the values in descending order.

{

previousNode = nodePtr;

nodePtr = nodePtr->next;

}

if(previousNode == 0)

{

head = newNode;

newNode->next = nodePtr;

}

else

{

previousNode->next = newNode;

newNode->next = nodePtr;

}

}

cout << "Done!" << endl;

}

//I used most of this code from the notes on Springboard !

//precondition - is given a character as a parameter

//postcondition - deletes the node who's data is the character given as a parameter and then has the previous node point

// to the next node in the list

void LabList::deleteNode(int ID)

{

Listnode *nodePtr;

Listnode *previousNode;

if (!head)

return;

if (head->ID == ID)

{

nodePtr = head->next;

delete head;

head = nodePtr;

}

else

{

nodePtr = head;

while(nodePtr != 0 && nodePtr->ID != ID)

{

previousNode = nodePtr;

nodePtr = nodePtr->next;

}

if (nodePtr)

{

previousNode->next = nodePtr->next;

delete nodePtr;

}

}

Listnode * listptr = head;

while(listptr != nullptr)

{

if(listptr->ID == ID)

cout << "did not log out!" << endl;

listptr = listptr->next;

}

}

void LabList::search()

{

int searchID = 0;

cout << "ID of student you are searching for? ";

cin >> searchID;

Listnode* current = head; // Initialize current position at the front of the linked list

bool flag = false;

while (current != NULL)

{

if (current->ID == searchID)

{

flag = true;

break;

}

current = current->next;

}

if(flag == false)

cout << "No user with the given ID found" << endl;

else

{

cout << "Here is the user's information:" << endl;

cout << "User's ID Number is: " << current->ID << endl;

cout << "User's Name is: " << current->name << endl;

cout << "Chosen University is: " << current->university << endl;

cout << "Users Computer is: " << current->seats << endl;

cout << "User's Time is: " << current->time << endl;

}

}

void LabList::display() const

{

#endif // LINKLISTNODE_CPP

Step by Step Solution

There are 3 Steps involved in it

Step: 1

blur-text-image

Get Instant Access to Expert-Tailored Solutions

See step-by-step solutions with expert insights and AI powered tools for academic success

Step: 2

blur-text-image

Step: 3

blur-text-image

Ace Your Homework with AI

Get the answers you need in no time with our AI-driven, step-by-step assistance

Get Started

Students also viewed these Databases questions