Function isn't displaying the desired output from an array argument - c++

First off, If there's any missing information, or you need to know more, please let me know. I'm not an experienced programmer by any means, and this mostly a project I'm working on for a university course.
This is my function definition:
void DispReport(string names[], int IDs[], int grades[][8], int numStudents, int numClasswork, int numQuizzes) {
The job of this function is to display a full table of student names with their ID numbers and grades. At the start, the function will display headers of "Name", "ID", and so on. Then display a continuous line of hyphens as a border underneath. After that it will start extracting and displaying the names, IDs and grades. This is the loop involved (I realize there's a lot of repetitiveness, sorry):
int Qmin, Qmax, CWmin, CWmax, Total;
for(i = 0; i < numStudents; i++){
cout << i+1 << ".";
cout << setw(11) << names[i];
cout << setw(11) << IDs[i];
//Display Quizzes, and Qmin ,Qmax, and Qavg
for(j = 0; j < numQuizzes; j++){
cout << setw(11) << grades[i][j];
if(grades[i][j] < grades[i][j+1])
Qmin = grades[i][j];
else
Qmax = grades[i][j];
};
cout << setw(11) << Qmin;
cout << setw(11) << Qmax;
cout << setw(11) << (Qmin + Qmax)/2;
//Display Classwork, and CWmin, CWmax, and CWavg
for(j = numQuizzes; j < (numQuizzes + numClasswork); j++){
cout << setw(11) << grades[i][j];
if(grades[i][j] < grades[i][j+1])
CWmin = grades[i][j];
else
CWmax = grades[i][j];
};
cout << setw(11) << CWmin;
cout << setw(11) << CWmax;
cout << setw(11) << (CWmin + CWmax)/2;
};
Running this loop results in nothing, however. It runs once, outputting the very first line, "1.", pauses for a second, then the program terminates. Nothing. I checked to ensure that the function had actually receive the arrays I passed to it, through cout << names[different indexes to check different names] and it was all there. The loop however, wouldn't display them, and I'm not getting any error messages. Any ideas?

Related

std::setw() is not giving desired results

for(int i = 0; i < arr; i++)
{
cout << left << setw(25);
cout << names[i] << " " << age[i];
cout << setw(25);
cout << fname[i] << endl;
}
Here the arrays names,age and fname contain name, age and father's name, respectively.
Output of my code is:
zeel dev 18r k sanghai
amar singh 25r k sanghai
alex pandit 52s n vardhan
After the agecolumn, I want a gap of another 25 columns. How can I do that?
setw() is not working properly.

How do I change a char's values?

I've created a program and it runs, however there are two problems. 1) Char doesn't change values as it should. 2) One of my total variables is stuck on one.
I've tested the code multiple times, and the char deptID is stuck on 'B'. I've tried going through the workflow and it's stuck on the value. Just to make sure, I wrote a cout line to check it throughout the workflow. Regardless of what I input, it's stuck on 'B'.
2) The variable TechTotal is seemingly stuck on 1. I've tested it using different values as well. I also went ahead and used a cout line to determine the value throughout the workflow to no success. I've made sure the variables are correct in calculating the variable. Both are correct.
Here's my main code:
int main(int argc, char** argv) {
welcomeScreen();
long int empID;
int TechAccAvg, TechTixAvg;
int BusTotal, TechTotal, BusAccAvg, BusTixAvg;
char deptID;
for (int i=0; i < 2; i++)
{
cout << "What department are you apart of?\n";
cin >> deptID;
if (deptID = 'B')
{
auto Averages = gatherData(deptID);
BusTixAvg = std::get<0>(Averages);
BusAccAvg = std::get<1>(Averages);
cout << BusTixAvg << endl;
cout << BusAccAvg << endl;
BusTotal = BusTixAvg + BusAccAvg;
cout << "Bus Total: " << BusTotal << endl;
}
else if (deptID = 'T')
{
auto TechAverages = gatherData(deptID);
TechTixAvg = std::get<0>(TechAverages);
TechAccAvg = std::get<1>(TechAverages);
cout << TechTixAvg << endl;
cout << TechAccAvg << endl;
TechTotal = TechTixAvg + TechAccAvg;
cout << "Tech Total: " << TechTotal << endl;
}
}
cout << "Tech: " << TechTotal << endl;
cout << "Business: " << BusTotal << endl;
summaryReport(TechTotal, BusTotal);
goodByeScreen();
return 0;
}```
` std::tuple<int, int> gatherData (char dept)
{
tuple <double, double> Averages;
int employeeNum=0, TotalTix=0, TotalAcc=0, trafficTickets=0, accidents=0;
long int empID=0;
double TixAverage=0, AccAverage=0;
char deptID;
cout << dept << endl;
cout << "How many employees do you have?\n";
cin >> employeeNum;
for(int j = 0; j < employeeNum; j++)
{
cout << "Please enter your employees ID number\n";
cin >> empID;
cout << "How many tickets did they have this year?\n";
cin >> trafficTickets;
TotalTix += trafficTickets;
cout << "How many accidents did they have this year?\n";
cin >> accidents;
TotalAcc += accidents;
}
TixAverage = TotalTix / employeeNum;
AccAverage = TotalAcc / employeeNum;
cout << "Department: " << dept << endl;
cout << "Total employees: " << employeeNum << endl;
cout << "Total tickets: " << TotalTix << endl;
cout << "Total Accidents: " << TotalAcc << endl;
Averages = make_tuple (TotalTix, TotalAcc);
return Averages;
}```
This is used to create the tuple that is used in determining Totals for both 'B' and 'T' depts.
Fixing both the char dept and the TechTotal would fix the entire program, I think. Those are the only things holding the program back. I've been stuck on this problem for a few hours now and I'm kind of lost as to why it's not changing those values. Any help would be appreciated, thank you in advance!
Solution
Replace else if (deptID = 'T') with else if (deptID == 'T') and if (deptID = 'B') with if (deptID == 'B').
Explanation
The single equal sign = means assignment. Therefore, everytime the program runs, deptID will be assigned to B and the statement will return true, satisfying the if statement.
However, you want to compare two values to see if they are equal. Therefore, you must use == (equality).
Because the statements in the else if will never execute, TechTotal will remain uninitialised, and the value in that memory address just so happens to be 1.

Different Outputs of an Atoi Converted String-> int

Here is my input file:
Plain Egg
1.45
Bacon and Egg
2.45
Muffin
0.99
French Toast
1.99
Fruit Basket
2.49
Cereal
0.69
Coffee
0.50
Tea
0.75
This is my code. I'm having no problem when people order 8 or 9 items, but as soon as they enter 10 or more items, I get really weird results and not the nicely printed check that I would like to see. For instance, let's say someone orders 8 items and they input "12345678" for their order. I get this:
But if the user inputs that they want let's say 15 items and they order "123456781234567", I get THIS:
Even when they order 10 items, I get just a blank check :/ :
What in the world is happening with my program? Does it have to do with me using c-strings? I want to understand what is going on inside my little computer and understand the way my computer thinks. If you can explain me this in a very simple way (I'm really new so I need something very explanatory with definitions of your fancy words) and some way I can understand, because like I said, I'm really new to computer science. Thank you.
// Local Restaurant: The 5,000 Fed
#include <cmath>
#include <cstdlib>
#include <fstream>
#include <iomanip>
#include <iostream>
#include <string>
using namespace std;
struct menuItemType {
string menuItem;
double menuPrice;
};
void getData(menuItemType list[]);
string showMenu(menuItemType list[]);
void printCheck(string y, menuItemType list[]);
int main() {
string y;
menuItemType menuList[8];
cout << "Hello and welcome to the 5,000 fed. Your local Long Beach café, "
"whose name is inspired by Jesus' miraculous manifestation "
"of bread to feed the 5k! His disciples helped him in passing out "
"the bread, and so I am here, your waiter, to help you and assist "
"you with your order. ";
getData(menuList);
y = showMenu(menuList);
printCheck(y, menuList);
return 0;
}
void getData(menuItemType list[]) {
string menupricet[8];
ifstream inFile;
inFile.open("menudata.txt");
for (int i = 0; i < 8; i++) {
getline(inFile, list[i].menuItem);
getline(inFile, menupricet[i]);
}
for (int i = 0; i < 8; i++) {
list[i].menuPrice = atof(menupricet[i].c_str());
}
}
string showMenu(menuItemType list[]) {
int amount;
char number;
string reps;
string response = "y";
string total = "";
cout << fixed << setprecision(2);
cout << endl << endl;
cout << "Here is our wonderful menu. I do recommend the french toast, "
"similar to the bread that Jesus ate."
<< endl
<< endl;
for (int i = 0; i < 8; i++) {
cout << i + 1 << ". " << setw(13) << left << list[i].menuItem << setw(8)
<< right << list[i].menuPrice << endl;
}
cout << endl;
cout << "How to order: Write the number you would like and specify how many "
"you want of that item by typing it in multiple times. For instance "
"an input of \"1135777\" means that you want two plain eggs, one "
"muffin, one fruit basket, and three coffees."
<< endl
<< endl;
cout << "How many items are you ordering total?: ";
cin >> amount;
cout << endl;
cout << "Please input your order, and press enter after your order: ";
for (int i = 0; i < amount; i++) {
cin >> number;
total += number;
}
return total;
}
void printCheck(string y, menuItemType list[]) {
int k = 0;
int temp = 0;
double bill = 0;
int newone = 0;
k = atoi(y.c_str());
while (k != 0) {
newone = newone * 10;
newone = newone + k % 10;
k = k / 10;
}
cout << "Thank you for dining at the 5,000 fed. Here's your check:" << endl
<< endl
<< endl;
cout << "_________________" << endl;
while (newone > 0) {
temp = newone % 10;
newone /= 10;
bill += list[temp - 1].menuPrice;
cout << left << setw(15) << list[temp - 1].menuItem << right << setw(5)
<< "|" << list[temp - 1].menuPrice << endl;
}
cout << fixed << setprecision(2);
cout << left << setw(15) << "Amount Due:" << right << setw(10) << "|" << bill
<< endl
<< endl;
}
EDIT:
So someone asked me to paste the output as text instead of images so here are the three outputs:
They order 8 items such as "12345678":
_________________
Plain Egg |1.45
Bacon and Egg |2.45
Muffin |0.99
French Toast |1.99
Fruit Basket |2.49
Cereal |0.69
Coffee |0.50
Tea |0.75
Amount Due: |11.31
They order 15 items such as "123456781234567":
_________________
French Toast |1.99
\365\277\357\376^ޝ-
YW\300\365\277\357\376all\377
\200\367\277\357\376
\370\277\357\376
\227\370\277\357\376
\331\370\277\357\376%\371\277\357\376\262
|0.00
Coffee |0.50
Muffin |0.99
\362\277\357\376x\362\277\357\376x\362\277\357\376x\362\277\357\376Plain Egg33333 |0.00
Plain Egg |1.45
Cereal |0.69
\365\277\357\376^ޝ-YW\300\365\277\357\376all\377\200\367\277\357\376\370\277\357\376\227\370\277\357\376\331\370\277\357\376%\371\277\357\376\262 |0.00
Cereal |0.69
Amount Due: |6.31
They order 10 items such as "1234567812":
_________________
Amount Due: |0.00
The problem in your code is associated with the size of the type int. Here is the solution, you may declare k and new one as unsigned long int so that they can hold up to 4,294,967,295 which still contains only 10 orders.
As a solution, you can use the string y as it is instead of converting to int. So that you can place as many orders as you wish. To traverse through the orders, you can use substr and length function of the string.
Let me re-write the printCheck function for, if I may
void printCheck(string y, menuItemType list[]) {
double bill = 0;
for(int i = 0; i< y.length(); i++)
{
string a = y.substr(i, 1);
int kk = atoi(a.c_str());
bill += list[kk - 1].menuPrice;
cout << left << setw(15) << list[kk - 1].menuItem << right << setw(5)
<< "|" << list[kk - 1].menuPrice << endl;
}
cout << fixed << setprecision(2);
cout << left << setw(15) << "Amount Due:" << right << setw(10) << "|" << bill << endl;
}
I hop this helps. Regards.

C++ array structures

I was reading the chapter on structures in my book, and it got me re-modifying a program I already made, but this time using structures which I have never used before; however, after finishing the program, there's one issue I'm not understanding. The output of the program only displays once. It's in a for loop, and yet even though it asks me to input my information three times, it only outputs the first information.
I'm probably just not understanding how arrays in structures work.
An example of my issue is the following.
I have my output on the following loop
for(int counter = 0; counter <size; counter++)
The size is 3, which would mean I'll get the output printed three times; however the answer I'm getting is the same as if I was asking for the following.
Listofnames[0].F_name
When what I actually want is
Listofnames[0].F_name Listofnames[1].F_name Listofnames[2].F_name
However, I don't want to have to write it three times, I did to test it and it actually worked, but is that the only way to do it? Or did I miss something in my program?
#include <iostream>
#include <string>
#include <iomanip>
using namespace std;
struct Names
{
string F_name; //Creating structure called Names.
string L_name;
char Mi;
};
struct Payrate
{
double rate;
double hoursworked; //Creating structure called Payrate.
double gross;
double net;
};
int main()
{
double stateTax = 0, federalTax = 0, unionFees = 0, timeHalf = 1.5; //Initializing variables.
const int size = 2; //Array size.
Payrate employee[size]; //Structure variables
Names Listofnames[size];
for (int counter = 0; counter < size; counter++) //Initializing for loop.
{
cout << "What's your first name?: " << endl;
cin >> Listofnames[counter].F_name;
cout << "What's your last name?: " << endl; //Displaying names, and hours worked, rate.
cin >> Listofnames[counter].L_name;
cout << "What is your middle initial?: " << endl;
cin >> Listofnames[counter].Mi;
cout << "How many hours did you work? Please enter a number between 1-50: " << endl;
cin >> employee[counter].hoursworked;
cout << "What is your hourly rate? Please enter a number between 1-50: " << endl;
cin >> employee[counter].rate;
if (employee[counter].hoursworked < 0 || employee[counter].hoursworked >50) //Initializing conditional statements.
{
cout << "Sorry you entered a erong entry. Pc shutting off " << endl; //Displays what happens is user inputs a number under 0 or over 50.
}
if (employee[counter].rate < 0 || employee[counter].rate > 50) //Initializing conditional statements.
{
cout << "Sorry you entered a erong entry. Pc shutting off " << endl; //Displays what happens is user inputs a number under 0 or over 50.
}
if (employee[counter].hoursworked <= 40) //Initializing conditional statements.
{
employee[counter].gross = employee[counter].hoursworked * employee[counter].rate; //Calculating gross.
}
else if (employee[counter].hoursworked > 40) //Initializing conditional statements.
{
employee[counter].gross = employee[counter].hoursworked * (employee[counter].rate * timeHalf); //Calculating gross.
}
stateTax = employee[counter].gross * 0.06;
federalTax = employee[counter].gross * 0.12; //Calculates all the tax fees, and net.
unionFees = employee[counter].gross * 0.02;
employee[counter].net = employee[counter].gross - (stateTax + federalTax + unionFees);
}
cout << "FirstN " << "MI " << "LastName " << "\t" << "Rate " << "HoursWorked " << "TimeHalf " << "StateTax " << "FederalTax " << "UnionFees " << "Gross " << " " << "Net " << endl; //Displays header of output.
cout << "==================================================================================================================" << endl;
for (int counter = 0; counter <= size; counter++)
{
//Output.
cout << Listofnames[counter].F_name << "\t" << fixed << setprecision(2) << Listofnames[counter].Mi << " " << Listofnames[counter].L_name << "\t" << employee[counter].rate << "\t" << employee[counter].hoursworked << "\t" << setw(7) << timeHalf << "\t" << setw(8) << stateTax << setw(12) << federalTax << "\t" << unionFees << "\t" << employee[counter].gross << "\t" << employee[counter].net << endl;
system("pause");
}
}
P.s If you had to re modify this program again, what would you use to simplify it. Asking so I can keep re-modifying, and learn more advanced stuff. Vectors, pointers? Thanks in advance.
You have an array with 3 indexes but your loop is only going upto 2 indexes. Change your for loop to this.
for (int counter = 0; counter <= size; counter++)
Now, this loop will print the all the indexes.
Instead of using a static value you can also use this.
for (int counter = 0; counter < sizeof(Listofnames)/sizeof(Listofnames[0]); counter++)
sizeof(Listofnames)/sizeof(Listofnames[0]) This will give you the total size of your array.
Ideone Link

I keep getting the same error message: Segment Fault (core dumped)

I am very new to C++ and all things computer-related, so go easy. I am trying to use a vector for the first time in an assignment for my class. I managed to get my code to compile, but halfway through running, the code reads segment fault (core dumped). I don't know how to use gdb to pinpoint the exact line but I know it occurs in the names function during the loop to organize the names in alphabetical order. I understand there is something wrong with the sizing of my vector, but I don't know how to fix it. I also need a simple solution, as I am not in an advanced class, and can only use what I have learned thus far in class.
I also am aware of how silly my names for things are, and the fact that I have crammed so much into my names function...
Please help me, despite the confusing nature of my code!
#include <iostream>
#include <fstream>
#include <string>
#include <vector>
using namespace std;
int choice(int);
void sortAndSend(vector<string> &names);
int main()
{
ofstream outputFile;
int numOfNames;
int count = 0;
numOfNames = choice(numOfNames);
vector<string> names(numOfNames);
sortAndSend(names);
outputFile.close();
return 0;
}
int choice(int a)
{
cout << "Select a number 1-5 that reflects how many names" << endl
<< "you would like to enter." << endl;
cin >> a;
cout << "You have selected " << a << " names." << endl << endl;
return a;
}
void sortAndSend(vector<string> &names)
{
ofstream outputFile;
string name;
string a;
cout << "You will be asked to enter " << names.size() << " names." << endl
<< "You may enter each individual's "
<< "last name first, followed by the individual's first name, "
<< "then middle name (if applicable)." << endl
<< "Do NOT include any commas." << endl << endl;
cin.ignore();
for (int count = 0; count < names.size(); count++) //Allows user to enter specified # of names
{
cout << "Enter a name now: ";
getline(cin, name);
names[count] = name;
cout << endl << "You have entered " << names[count] << endl << endl;
}
for (int count = 0; count < names.size(); count++)
{
cout << names[count] << endl;
}
for (int count = 0; count < names.size(); count++)
//Arranges names in alphabetical order
//Error occurs here
{
while (names[count] > names[count + 1])
{
a = names[count + 1];
names[count + 1] = names[count];
names[count] = a;
}
}
cout << "Your names are now alphebetized" << endl << endl;
cout << "This is what is being copied to the file named"
<< " 'AlphabeticalOrderEC.txt': " << endl;
for (int count = 0; count < names.size(); count++) //Prints names in alphabetical order
{
cout << names[count] << endl;
}
outputFile.open("AlphabeticalOrderEC"); //Prints names into file
for (int count = 0; count < names.size(); count++)
{
outputFile << names[count] << endl;
}
}
You try to access adress that doesn't blongs to the vector. See at this part of your code :
for (int count = 0; count < names.size(); count++)
{
while (names[count] > names[count + 1])
{
a = names[count + 1];
names[count + 1] = names[count];
names[count] = a;
}
}
you should'n use count + 1, you must do it only when count is less than names.size()-1. You should find another logic that can replace this part of your code. It's like trying to access the 11th element of an array that has only 10.