How to prevent stack smashing detected? - c++

I am trying to write a program to get student data (student id, subject results) from user input and align them based on their total marks. But when I try to input till the 5th student the stack smashing detected the error that occured. And I can't find a way to solve this problem...
It would be really helpful if anyone can give me some advice about it. Thanks in advance
My code:
h file
#include <string>
#include <iostream>
using namespace std;
class student
{
private:
char id[100];
int eng, math, jan, total;
public:
void getInput(void);//ユーザーから学生のデータを入力してもらう
void putInput(void);//最後の結果を表示する
friend void sort(student std[]);//総得点の高い順に各人のデータを並べ替える
friend void avg(student std[]);//各科目と総得点の平均値を計算する
};
cpp file
#include <string>
#include <iostream>
#include "report1.h"
using namespace std;
#define MAX 10
void student::getInput(void)//ユーザーから学生のデータを入力してもらう
{
cout << "IDを入力してください:";
cin >> id;
cout << "英語の点数:";
cin >> eng;
cout << "数学の点数:";
cin >> math;
cout << "国語の点数:";
cin >> jan;
total = eng + math + jan;
}
void student::putInput(void)//最後の結果を表示する
{
cout << id << "\t" << eng << "\t" << math << "\t" << jan << "\t" << total << endl;
}
void sort(student std[])//総得点の高い順に各人のデータを並べ替える
{
int i, j;
for ( i = 0; i < MAX-1; i++)
{
for ( j = i+1; j < MAX; j++)
{
if (std[i].total < std[j].total)//一つ後ろのデータが確認中のデータより大きいなら、並べ替える
{
student temp;
temp = std[i];
std[i] = std[j];
std[j] = temp;
}
}
}
}
void avg(student std[])//各科目と総得点の平均値を計算する
{
int i;
int eng_total, math_total, jan_total, total_total;
double eng_avg, math_avg, jan_avg, total_avg;
eng_total = 0;
math_total = 0;
jan_total = 0;
total_total = 0;
for ( i = 0; i < MAX; i++)
{
eng_total += std[i].eng;
math_total += std[i].math;
jan_total += std[i].jan;
total_total += std[i].total;
}
eng_avg = (double)eng_total/MAX;
math_avg = (double)math_total/MAX;
jan_avg = (double)jan_total/MAX;
total_avg = (double)total_total/MAX;
cout << "Avg\t" << eng_avg << "\t" << math_avg << "\t" << jan_avg << "\t" << total_avg << endl;
}
int main()
{
student std[MAX-1];
int i, j;
for ( i = 0; i < MAX; i++)
{
cout << i+1 << "番目の学生データを入力してください。" << endl;
std[i].getInput();
}
sort(std);
cout << endl;
cout << "ID_No" << "\tEng" << "\tMath" << "\tJan" << "\tTotal" << endl;
for ( i = 0; i < MAX; i++)
{
std[i].putInput();
}
avg(std);
return 0;
}

Related

Unable to get invalid emails

I'm unable to get invalid emails to print in my code. I'm able to call the student roster just fine but that's about it.
#include <iostream>
#include <string>
#include "student.h"
#include "degree.h"
#include "roster.h"
using namespace std;
int main()
{
const string studentData[] =
{
"A1,John,Smith,John1989#gm ail.com,20,30,35,40,SECURITY",
"A2,Suzan,Erickson,Erickson_1990#gmailcom,19,50,30,40,NETWORK",
"A3,Jack,Napoli,The_lawyer99yahoo.com,19,20,40,33,SOFTWARE",
"A4,Erin,Black,Erin.black#comcast.net,22,50,58,40,SECURITY",
};
Roster* classRoster = new Roster(numberOfStudents);
for (int i = 0; i < numberOfStudents; ++i)
{
cout << studentData[i] << "," << endl;
}
cout << endl;
cout << "Invalid emails:";
for (int i = 0; i < numberOfStudents; ++i)
{
classRoster->printInvalidEmails();
}
cout << "Average days per class for each student" << endl;
for (int i = 0; i < numberOfStudents; ++i)
{
cout << endl;
}
cout << endl;
classRoster->printByDegreeProgram();
cout << endl;
system("pause");
return 0;
}
Here is my roster.cpp
#include <iostream>
#include <string>
#include "student.h"
#include "degree.h"
#include "roster.h"
using namespace std;
Roster::Roster()
{
This->rosterSize = 0;
this->lastIndex = -1;
this->classRosterArray = nullptr;
}
Roster::Roster(int rosterSize)
{
this->rosterSize = rosterSize;
this->lastIndex = -1;
this->classRosterArray = new Student * [rosterSize];
}
void Roster::add(string studentId, string firstName, string lastName,
string
emailAddress, int age,
int daysInCourse1, int daysInCourse2, int daysInCourse3, Degree degree)
{
}
void Roster::remove(string studentId)
{
for (int i = 0; i <= lastIndex; ++i)
{
if (classRosterArray[i] == nullptr)
{
cout << "ERROR: Student with ID: " << studentId << " not found" <<
endl;
break;
}
else if (studentId == classRosterArray[i]->getStudentId())
{
classRosterArray[i] = nullptr;
cout << "Student removed" << endl;
}
}
}
void Roster::printAll()
{
for (int i = 0; i <= this->lastIndex; ++i)
{
(this->classRosterArray)[i]->print();
}
}
void Roster::printAverageDaysInCourse(string studentId)
{
bool found = false;
for (int i = 0; i <= lastIndex; ++i) {
if ((*classRosterArray[i]).getStudentId() == studentId) {
found = true;
int average = 0;
average = (classRosterArray[i]->getNumberOfDaysToCompleteCourse()
[0]
+ classRosterArray[i]->getNumberOfDaysToCompleteCourse()[1] +
classRosterArray[i]->getNumberOfDaysToCompleteCourse()[2]) /
3;
cout << "Average days it took student " << studentId << " to
complete
a course: " << average
<< " days" << endl;
}
}
if (!found) cout << "Student not found." << endl;
}
void Roster::printInvalidEmails()
{
for (int i = 0; i < numberOfStudents; ++i)
{
string email = classRosterArray[i]->getEmailAddress();
bool isBad = false;
size_t at = email.find("#");
size_t period = email.find(".");
if (at == string::npos)
{
cout << "Invalid email. Missing # symbol." << endl;
}
else if (period == string::npos)
{
cout << "Invalid email. Missing a period." << endl;
}
else if (email.find(" ") != string::npos)
{
cout << "Invalid email. Spaces not allowed." << endl;
}
}
}
void Roster::printByDegreeProgram()
{
for (int i = 0; i < degreeType; ++i)
{
cout << &Roster::printByDegreeProgram;
}
}
Roster::~Roster()
{
for (int i = 0; i < numberOfStudents; ++i)
{
delete classRosterArray[i];
}
}
I'm just starting out and am not sure if i've totally messed myself up. Any help would be greatly appreciated. I thought might have been able to figure it out and i've tried a few different times but still unable to correct.

C++ - Reading from a file bug

My program is working as I want it to work (It is on Bosnian language so the cout of the program is not that important). The program is about reading some text from file and then couting what I want to
The only problem I have with this program is that for some reason it is showing the two 0 0 at the end of the text file even though I do not have it in my text file
Here is the code:
#include <iostream>
#include <fstream>
#include <string>
#include <algorithm>
using namespace std;
struct proizvod
{
char naziv[100];
char proizvodac[100];
int cijena = 0;
int kolicina = 0;
};
bool poredjenje(proizvod a, proizvod b)
{
if (a.cijena != b.cijena )
return a.cijena > b.cijena;
}
void sortiranje(proizvod a[], int n)
{
sort(a, a+n, poredjenje);
}
int main()
{
ifstream datoteka;
datoteka.open("proizvodi.txt.txt");
int brojStvari = 0;
int sumaProizvoda = 0;
int ukupnaVrijednost = 0;
char* spisakProizvoda[100];
int brojFIAT = 0;
int spisakCijena = 0;
proizvod automobili[100];
if (datoteka.fail())
{
cout << "Ne postojeca datoteka";
exit(1);
}
while (datoteka.good() && !datoteka.eof())
{
datoteka >> automobili[brojStvari].naziv >> automobili[brojStvari].proizvodac >> automobili[brojStvari].cijena >> automobili[brojStvari].kolicina;
++brojStvari;
++sumaProizvoda;
}
for (int i = 0; i < brojStvari; i++)
{
cout << automobili[i].naziv << " " << automobili[i].proizvodac << " " << automobili[i].cijena << " " << automobili[i].kolicina << endl;
}
for (int i = 0; i < brojStvari; i++)
{
ukupnaVrijednost += automobili[i].cijena;
if (automobili[i].kolicina == 0)
{
spisakProizvoda[i] = automobili[i].proizvodac;
}
else if (automobili[i].proizvodac == "FIAT")
{
brojFIAT++;
}
}
char pomocna[100];
cout << endl;
cout << "Ukupan broj proizvoda u datoteci: " << sumaProizvoda << endl;
cout << "Ukupan vrijednost proizvoda u datoteci: " << ukupnaVrijednost << endl;
cout << "Spisak automobila sa cijenom 0 su: ";
for (int i = 0; i < brojStvari; i++)
{
if (!spisakProizvoda[i])
{
cout << "Ne postoje ti proizvodi " << endl;
break;
}
else
cout << spisakProizvoda[i] << endl;
}
cout << "Broj prozivoda koji proizvodi FIAT: " << brojFIAT << endl;
cout << "Sortirani proizvodi prema cijeni: " << endl;
sortiranje(automobili, brojStvari);
for (int i = 0; i < brojStvari; i++)
{
cout << automobili[i].proizvodac << endl;
}
return 0;
}
And here is the cout
Golf Volskwagen 5000 5
AudiRS5 Audi 50000 3
0 0
Ukupan broj proizvoda u datoteci: 3
Ukupan vrijednost proizvoda u datoteci: 55000
Spisak automobila sa cijenom 0 su: Ne postoje ti proizvodi
Broj prozivoda koji proizvodi FIAT: 0
Sortirani proizvodi prema cijeni:
Audi
Volskwagen
Can anybody tell me what is the problem ?
P.S : Sorry if you do not understand the program itself I apologize sincerely
You are seeing the extra 0 0 at end most likely due to an extra empty line at end of proizvodi.txt.txt file. This happens because the new line is also accepted as input but since there are no entries, the entries in struct proizvod retain default 0 values for cijena and kolicina which gets printed out as 0 0.
Update your main() code to reading file like follow and it will work as expected:
while (datoteka >> automobili[brojStvari].naziv >>
automobili[brojStvari].proizvodac >> automobili[brojStvari].cijena >>
automobili[brojStvari].kolicina) {
++brojStvari;
++sumaProizvoda;
}

C++ My files were working before I attempted to move them into a source file, and now there are no errors and nothing being displayed

My apologies for being a little vague about the issue(s) in the topic, but I really am not sure. I am attempting to create a course_directory as a lab project for school, and up until now everything had been progressing quite well. I have written and tested each of the function in the main.cpp before attempting to move the class functions into the .hpp file. My goal is to have nothing in main except for a call to "Run" that will open a file, and in turn make a call to "displayMenu", and allow the user to interact with the information as they choose, but now everything is compiling correctly, and nothing is being displayed.
Course_directory.hpp
#include "Course_Directory.h"
using namespace std;
Course_Directory::Course_Directory(){};
Course_Directory courses[1001];
void Course_Directory::displayMenu(){
cout << "1.Print all courses" << endl;
cout << "2.Print all courses for a department" << endl;
cout << "3.Print roster for a course" << endl;
cout << "4.Print the largest class" << endl;
cout << "5.Swap two classes" << endl;
cout << "6.Print schedule for a student" << endl;
cout << "7.Exit" << endl;
char dept[50], dept2[50];
int courseNo, courseNo2, i, choice;
while (choice != 7) {
cout << "\nEnter your choice: ";
cin >> choice;
if (choice == 1)
printAllCourses(i);
else if (choice == 2) {
cout << "\nEnter department name:";
cin >> dept;
for(int j = 0; j < sizeof(dept); j++)
{
dept[j] = (toupper(dept[j]));
}
coursesInDept(dept, i);
}
else if (choice == 3) {
cout << "\nEnter course number:";
cin >> courseNo;
studentsInCourse(courseNo, i);
}
else if (choice == 4) {
largestClass(i);
}
else if (choice == 5) {
cout << "\nEnter first department name :";
cin >> dept;
for(int j = 0; j < sizeof(dept); j++)
{
dept[j] = (toupper(dept[j]));
}
cout << "\nEnter first course number: ";
cin >> courseNo;
cout << "\nEnter second department name :";
cin >> dept2;
for(int k = 0; k < sizeof(dept2); k++)
{
dept2[k] = (toupper(dept2[k]));
}
cout << "\nEnter second course number: ";
cin >> courseNo2;
swap2(dept, courseNo, dept2, courseNo2, i);
}
else if (choice == 6) {
int id;
cout << "\nEnter a student Id:";
cin >> id;
schedule(id, i);
}
}
cout << "Goodbye!\n";
}
void Course_Directory::printAllCourses(int len){
for (int i = 0; i < len; i++)
cout << "Course name: " << courses[i].courseName << ", Course
number: " << courses[i].courseNum << endl;
cout << len;
}
void Course_Directory::coursesInDept(char *dept, int len) {
for (int i = 0; i < len; i++)
if (strcmp(dept, courses[i].courseName) == 0)
cout << "Course Name: " << courses[i].courseName << ",
Course number: " << courses[i].courseNum << endl;
}
void Course_Directory::studentsInCourse(int courseNo, int len) {
for (int i = 0; i < len; i++)
if (courseNo == courses[i].courseNum) {
for (int m = 0; m < courses[i].numStudents - 1; m++)
cout << courses[i].IDs[m] << ",";
cout << courses[i].IDs[courses[i].numStudents - 1] <<
endl;
}
}
void Course_Directory::largestClass(int len) {
int max = -999;
for (int i = 0; i < len; i++) {
if (courses[i].numStudents > max)
max = courses[i].numStudents;
}
for (int i = 0; i < len; i++) {
if (courses[i].numStudents == max){
cout << "\nThe largest class is in department: " <<
courses[i].courseName
<< ", and the course number is: " << courses[i].courseNum
<< "\n";
cout << "The class currently has " << max << " students
enrolled.\n";
}
}
}
void Course_Directory::swap2(char *firstDep, int firstNo, char
*secondDep, int secondNo, int len) {
Course_Directory temp;
int firstIndex, secondIndex;
for (int i = 0; i < len; i++) {
if (strcmp(firstDep, courses[i].courseName) == 0 &&
courses[i].courseNum == firstNo)
firstIndex = i;
if (strcmp(secondDep, courses[i].courseName) == 0 &&
courses[i].courseNum == secondNo)
secondIndex = i;
}
temp = courses[firstIndex];
courses[firstIndex] = courses[secondIndex];
courses[secondIndex] = temp;
}
void Course_Directory::schedule(int id, int len) {
cout << "Courses student " << id << " is enrolled in: " << endl;
for (int i = 0; i < len; i++) {
for (int j = 0; j < courses[i].numStudents; j++)
if (courses[i].IDs[j] == id)
cout << courses[i].courseNum << " \n";
}
}
Course_Directory.h
#ifndef COURSE_DIRECTORY_H
#define COURSE_DIRECTORY_H
#include <iostream>
using namespace std;
class Course_Directory{
private:
int* deptSize;
string filename;
public:
char courseName[1001];
int courseNum;
int numStudents;
int IDs[1001];
int* choice;
void displayMenu();
Course_Directory();
//Course_Directory(const Course_Directory& original);
//~Course_Directory();
//void run(string);
void coursesInDept(char*, int);
void studentsInCourse(int, int);
void largestClass(int);
void swap2(char*, int, char*, int, int);
void schedule(int, int);
void printAllCourses(int);
};
#include "Course_Directory.hpp"
#endif //COURSE_DIRECTORY_H
main.cpp
#include "Course_Directory.h"
using namespace std;
class Course_Directory;
int main() {
ifstream file;
file.open("input.txt");
char *token;
int i = 0, j;
Course_Directory courses[100];
if (!file.fail()) {
std::string line;
while (getline(file, line)) {
j = 0;
char *str = const_cast<char *>(line.c_str());
token = strtok(str, " ");
while (token != NULL)
{
if (j == 0)
strcpy(courses[i].courseName, token);
else if (j == 1)
courses[i].courseNum = atoi(token);
else if (j == 2)
courses[i].numStudents = atoi(token);
else
courses[i].IDs[j - 3] = atoi(token);
j++;
token = strtok(NULL, " ");
cout << courses[i].courseName << endl;
}
i++;
}
file.close();
}
else{
cout << "File not found." << endl;
}
//menu
Course_Directory displayMenu();
return 0;
}
If I leave Course_Directory off of displayMenu(); then I get "displayMenu" was not declared in this scope. I'm not sure what the problem is or why the menu will not display. Any help would be greatly appreciated!

How to do selection sort?

Count all the records from the file "8.dat". To read each individual recording perform dynamic memory capture.
Sort the records to different keys:
Item number (ascending);
The cost (descending);
Number of stock (descending).
Use selection sort
Total sorting will be done 12 times, each time the array is sorted in its original condition.
For each case count of comparisons to and permutations.
Below code implements insertion sort. Twice, without saying so much.
I need to use selection sort. How to do selection sort?
#include <iostream>
#include <fstream>
#include <conio.h>
using namespace std;
struct PRICE
{
int number;
char name[20];
int cost;
int quantity;
} *pm;
int Menu();
void PrintPRICE(PRICE);
void sort_cost(PRICE*, int);
void sort_quantity(PRICE*, int);
long file_size(const char*);
int main()
{
int count = 0;
const char *fname = "D:\8.dat";
FILE* file = fopen(fname, "r");
if (file != NULL)
{
long size = file_size(fname);
count = size / sizeof PRICE;
pm = new PRICE[count];
fread(pm, sizeof PRICE, count, file);
fclose(file);
}
for (int i=0; i<count; i++)
{
PrintPRICE(pm[i]);
cout << endl;
}
int ch = Menu();
switch (ch)
{
case 1:
{
sort_cost(pm, count);
cout << endl;
cout << " Result: " << endl;
cout << "-----------------------" << endl;
for (int i=0; i<count; i++)
{
PrintPRICE(pm[i]);
cout << endl;
}
break;
}
case 2:
{
sort_quantity(pm, count);
cout << " Result: " << endl;
cout << "-----------------------" << endl;
for (int i=0; i<count; i++)
{
PrintPRICE(pm[i]);
cout << endl;
}
break;
}
default: break;
}
delete [] pm;
_getch();
}
void PrintPRICE(PRICE price)
{
cout << " Product: " << price.name << endl;
cout << " Number of orden: " << price.number << endl;
cout << " Product cost: " << price.cost << endl;
cout << " Quantity in stock: " << price.quantity << endl;
cout << "-----------------------------------n" << endl;
}
long file_size(const char* filename)
{
FILE *Pfile = NULL;
Pfile = fopen(filename, "rb");
fseek(Pfile, 0, SEEK_END);
long size = ftell(Pfile);
fclose(Pfile);
return size;
}
void sort_cost(PRICE* array, int count)
{
int change = 0;
int comparesion = 0;
for (int i=1; i<count; i++)
{
PRICE key = array[i];
int j = i - 1;
comparesion++;
while (i>=0 && array[i].cost>key.cost)
{
array[j + 1] = array[j];
j = j - 1;
change++;
}
array[j + 1] = key;
}
cout << "n Quantity change: " << change << endl;
cout << " Quantity comparesion: " << comparesion << endl;
}
void sort_quantity(PRICE* array, int count)
{
int change = 0;
int comparesion = 0;
for (int i=1; i<count; i++)
{
PRICE key = array[i];
int j = i - 1;
comparesion++;
while (j>=0 && array[i].quantity>key.quantity)
{
array[j + 1] = array[j];
j = j - 1;
change++;
}
array[j + 1] = array[j];
}
cout << "n Quantity change: " << change << endl;
cout << " Quantity comparesion: " << comparesion << endl;
}
int Menu()
{
int n;
cout << " 1 - Sort by cost" << endl;
cout << " 2 - Sort by quantity" << endl;
cout << "n Your choice: "; cin >> n;
return n;
}
source code for the selection sort
void selectSort(int arr[], int n)
{
int pos_min,temp;
for (int i=0; i < n-1; i++)
{
pos_min = i;
for (int j=i+1; j < n; j++)
{
if (arr[j] < arr[pos_min])
pos_min=j;
}
if (pos_min != i)
{
temp = arr[i];
arr[i] = arr[pos_min];
arr[pos_min] = temp;
}
}
}

Compare Class Object using bubble sort

Task: Model in OOP a class named Student containing name, surname and the marks from the winter session exams. Display the name of the students who have arrears exams and the first three students in the group.
I have troubles in comparing the marks(first three students).
My code:
#define _CRT_SECURE_NO_WARNINGS
#include<iostream>
using namespace std;
#include <string>
#include<stdio.h>
class Student {
private:
char nume[10];
char prenume[20];
double matematica;
double fizica;
double programare;
public:
Student(char num[10], char pren[20], double mate, double fiz, double progra);
void afis();
void citire_stud();
int restanta();
double media();
};
Student::Student(char num[10] = "", char pren[20] = "", double mate = 0, double fiz = 0, double progra = 0)
{
strcpy(nume, num);
strcpy(prenume, pren);
matematica = mate;
fizica = fiz;
programare = progra;
}
void Student::afis()
{
cout << "Nume: " << nume << endl;
cout << "Prenume: " << prenume << endl;
cout << "Nota la matematica: " << matematica << endl;
cout << "Nota fizica: " << fizica << endl;
cout << "Nota programare: " << programare << endl;
cout << endl;
}
void Student::citire_stud()
{
char num[10];
char pren[20];
double mate, fiz, progra;
cout << "Introduceti numele studentului: " << endl;
cin >> num;
strcpy(nume, num);
cout << "Introduceti preumele studentului: " << endl;
cin >> pren;
strcpy(prenume, pren);
cout << "Introduceti nota la mate studentului: " << endl;
cin >> mate;
matematica = mate;
cout << "Introduceti nota la fizica studentului: " << endl;
cin >> fiz;
fizica = fiz;
cout << "Introduceti nota la programare studentului: " << endl;
cin >> progra;
programare = progra;
}
int Student::restanta() //arrears
{
if (matematica < 5 || programare <5 || fizica < 5)
return 1;
else return 0;
}
double Student::media()
{
double med;
med = (matematica + fizica + programare) / 3;
return med;
}
void main()
{
int cont = 0;
int res[10];
int nr;
cout << "Cati studenti sunt(max 10): "; //How many students
cin >> nr;
Student ob2[10], temp;
for (int i = 0;i < nr;i++)
{
ob2[i].citire_stud();
if (ob2[i].restanta())
{
res[cont++] = i;
}
}
if (cont == 0)
{
cout << "Nu sunt studenti restanti! " << endl;
goto jmp;
}
else
{
cout << "\nStundetii restanti sunt: " << endl;
int i = 0;
int k = 0;
do
{
k = res[i];
ob2[k].afis();
i++;
} while (i != cont);
}
jmp:
cout << "\n\n\n\nStudentii in ordinea medilor sunt: " << endl;
for (int i = 0;i < nr;i++)
{
if (ob2[i].media() < ob2[i + 1].media()) //Not working
{
temp = ob2[i];
ob2[i] = ob2[i + 1];
ob2[i + 1] = temp;
}
}
for (int i = 0;i < nr;i++)
ob2[i].afis();
system("pause");
}
Output: Output
It should be: 9 - 7 - 5
Your bubble sort is broken. A) You need 2 loops. B) you go out of bounds. Change it to something like:
for (int j = 0; j < nr; j++)
{
for (int i = 0;i < nr - 1 ; i++)
{
if (ob2[i].media() < ob2[i + 1].media())
{
temp = ob2[i];
ob2[i] = ob2[i + 1];
ob2[i + 1] = temp;
}
}
}