Runtime error: program has stopped responding - c++

My program is to calculate the price of resources based on the resources that their neighbors have.
It compiles, but at run-time, it breaks and says that the program has stopped responding.
Any help is greatly appreciated!
#include <iostream>
#include <fstream>
using namespace std;
class Resource{
string resName;
int amount;
int price;
public:
void set_values(string resName, int amount, int price){resName=resName; amount=amount; price=price;};
string get_name(){return resName;};
int get_amount(){return amount;};
int get_price(){return price;};
};
class State{
string stName;
Resource resources[5];
public:
void set_values(string stName){
stName=stName;
Resource r;
r.set_values(" ", 0, 0);
for (int i=0; i<5; i++){
resources[i] = r;
}
};
string get_name(){return stName;};
void addResource(string name, int amount, int price){
Resource r;
r.set_values(name, amount, price);
for (int i=0; i<5; i++){
if(resources[i].get_name() == " "){
resources[i] = r;
}
}
};
Resource get_resource(string resource){
for(int i=0; i<5; i++){
if (resources[i].get_name() == resource){
return resources[i];
}
}
};
bool checkForResource(string resource){
for(int i=0; i<5; i++){
if (resources[i].get_name() == resource){
return true;
}
}
}
};
class Area{
State allStates[10][10];
public:
void initialize(){
for (int i=0; i<10; i++){
for (int j=0; j<10; j++){
allStates[i][j].set_values(" ");
}
}
};
void addState(string stateName){
for (int row=0; row<10; row++){
for (int col=0; col<10; col++){
if (allStates[row][col].get_name() == " ")
allStates[row][col].set_values(stateName);
}
}
};
State get_state(string name){
for (int row=0; row<10; row++){
for (int col=0; col<10; col++){
if (allStates[row][col].get_name() == name)
return allStates[row][col];
}
}
};
void deleteState(string name){
for (int row=0; row<10; row++){
for (int col=0; col<10; col++){
if (allStates[row][col].get_name() == name)
allStates[row][col].set_values(" ");
}
}
};
void moveRowsSouth(){
for(int z=0; z<10; z++){
for(int y=10; y>=1; y--){
allStates[y][z] = allStates[y-1][z];
}
allStates[0][z].set_values(" ");
}
};
void moveColsEast(){
for(int z=0; z<10; z++){
for(int y=10; y>=1; y--){
allStates[z][y] = allStates[z][y-1];
}
allStates[z][0].set_values(" ");
}
};
void addNeighbor(string s1, string s2, string direction){
for (int row=0; row<10; row++){
for (int col=0; col<10; col++){
if (allStates[row][col].get_name() == s1)
if (direction == "North"){
if (row-1 < 0){
moveRowsSouth();
}
else {
if (allStates[row-1][col].get_name() == " "){
allStates[row-1][col] = get_state(s2);
deleteState(s2);
}
else
cout << "Unable to add this neighbor. North is occupied.";
}
}
else if (direction == "South"){
if (allStates[row+1][col].get_name() == " "){
allStates[row+1][col] = get_state(s2);
deleteState(s2);
}
else
cout << "Unable to add this neighbor. South is occupied.";
}
else if (direction == "East"){
if (allStates[row][col+1].get_name() == " "){
allStates[row][col+1] = get_state(s2);
deleteState(s2);
}
else
cout << "Unable to add this neighbor. East is occupied.";
}
else if (direction == "West"){
if (col-1 < 0){
moveColsEast();
}
else {
if (allStates[row][col-1].get_name() == " "){
allStates[row][col-1] = get_state(s2);
deleteState(s2);
}
else
cout << "Unable to add this neighbor. West is occupied.";
}
}
}
}
};
State getNeighborN(string s1){
for (int row=0; row<10; row++){
for (int col=0; col<10; col++){
if (allStates[row][col].get_name() == s1)
return allStates[row-1][col];
}
}
};
State getNeighborS(string s1){
for (int row=0; row<10; row++){
for (int col=0; col<10; col++){
if (allStates[row][col].get_name() == s1)
return allStates[row+1][col];
}
}
};
State getNeighborE(string s1){
for (int row=0; row<10; row++){
for (int col=0; col<10; col++){
if (allStates[row][col].get_name() == s1)
return allStates[row][col+1];
}
}
};
State getNeighborW(string s1){
for (int row=0; row<10; row++){
for (int col=0; col<10; col++){
if (allStates[row][col].get_name() == s1)
return allStates[row][col-1];
}
}
};
};
int main()
{
Area a;
a.initialize();
ifstream infile;
string command;
infile.open ("proj2.txt", ifstream::in);
while(!infile.eof()){
infile >> command;
if (command == "addState"){
string stateName;
infile >> stateName;
a.addState(stateName);
}
else if (command == "addNeighbor"){
string state1;
string state2;
string direction;
infile >> state1;
infile >> state2;
infile >> direction;
a.addNeighbor(state1, state2, direction);
}
else if (command == "addResource"){
string state;
string name;
int amount;
int price;
infile >> state;
infile >> name;
infile >> amount;
infile >> price;
a.get_state(state).addResource(name, amount, price);
}
else if (command == "getPrice"){
string state;
string resource;
int amount;
infile >> state;
infile >> resource;
infile >> amount;
State N = a.getNeighborN(state);
State S = a.getNeighborS(state);
State E = a.getNeighborE(state);
State W = a.getNeighborW(state);
int countOfNeigh = 0;
bool stateHas = false;
if (N.checkForResource(resource) == true) {
countOfNeigh++;
}
if (S.checkForResource(resource) == true) {
countOfNeigh++;
}
if (E.checkForResource(resource) == true) {
countOfNeigh++;
}
if (W.checkForResource(resource) == true) {
countOfNeigh++;
}
if (a.get_state(state).checkForResource(resource) == true) {
stateHas = true;
}
int price = 0;
if ((stateHas = false && countOfNeigh == 1) ||
(stateHas = true && countOfNeigh == 0)){
price = a.get_state(state).get_resource(resource).get_price();
price = price+(price*.25);
}
else if (stateHas = true && (countOfNeigh == 2 || countOfNeigh == 3)){
price = a.get_state(state).get_resource(resource).get_price();
}
else if (stateHas = true && countOfNeigh == 4){
price = a.get_state(state).get_resource(resource).get_price();
price = price-(price*.1);
}
else if (stateHas = false && countOfNeigh > 1){
price = a.get_state(state).get_resource(resource).get_price();
price = price+(price*.1);
}
cout << "The price for " << amount << " units of " << resource << " is " << price << ".";
}
}
}

You're failing to check whether the file open succeeds - http://www.cplusplus.com/reference/iostream/ifstream/open/
In case it does, your program goes in an infinite loop.
There's also no other kind of error checking. When dealing with reading from files, especially data that you expect to be formatted in some way, that's a shortcut to disaster.

Related

I don't know what is causing the segmentation fault in my code

I'm at my wit's end with this code and I am new to c++ so I don't even know where to begin to check for this error. What is causing the segmentation fault in my code and how do I fix it?
#include <iostream>
#include <string>
#include <vector>
#include <sstream>
using namespace std;
class Student
{
private:
string name;
int numClasses;
vector<string> classList;
public:
Student (string nameVal, int numClassesVal, string classListArr[]);
Student (string nameVal, int numClassesVal);
Student (string nameVal);
Student ();
void setName(string nameVal);
void setNumClasses(int numClassesVal);
void setClassList(string classListArr[]);
string getName();
int getNumClasses();
vector<string> getClassList();
void input();
void output();
void reset();
};
int main ()
{
Student user;
string answer;
int flag = 1;
while (flag == 1)
{
user.input();
user.output();
cout << "Do you want to enter the new data? (y/n)" << endl;
cin >> answer;
cin.ignore();
if (answer == "n")
{
flag == 0;
}
}
return 0;
}
Student::Student (string nameVal, int numClassesVal, string classListArr[])
: name(nameVal), numClasses(numClassesVal)
{
string test = classListArr[0];
for (int x = 0; x < 10; ++x)
{
if ( (x > 0) && (classListArr[x] == test))
break;
classListArr[x] = classList[x];
}
}
Student::Student (string nameVal, int numClassesVal)
{
name = nameVal;
numClasses = numClassesVal;
for (int x = 0; x < 10; ++x)
{
classList[x] = "";
}
}
Student::Student (string nameVal)
{
name = nameVal;
numClasses = 0;
for (int x = 0; x < 10; ++x)
{
classList[x] = "";
}
}
Student::Student ()
{
name = "";
numClasses = 0;
for (int x = 0; x < 10; ++x)
{
classList[x] = "";
}
}
void Student::setName(string nameVal) {name = nameVal;}
void Student::setNumClasses(int numClassesVal) {numClasses = numClassesVal;}
void Student::setClassList(string classListArr[])
{
string test = classListArr[0];
for (int x = 0; x < 10; ++x)
{
if ( (x > 0) && (classListArr[x] == test))
break;
classListArr[x] = classList[x];
}
}
string Student::getName() {return name;}
int Student::getNumClasses() {return numClasses;}
vector<string> Student::getClassList() {return classList;}
void Student::input()
{
string temp;
int classes;
cout << "Input Student's Name:" << endl;
getline(cin, temp);
name = temp;
cout << "Input Number of Classes:" << endl;
cin >> classes;
cin.ignore();
numClasses = classes;
for (int x = 0; x < 10; ++x)
{
if ( x == 9)
{
cout << "Input Last Class Name (Maximum of 10):";
getline(cin, temp);
classList[9] = temp;
}
else
{
cout << "Input Class Name:";
getline(cin, temp);
classList[x] = temp;
cout << "Do you have any more classes? (y/n):";
getline(cin, temp);
if ( temp == "n")
break;
}
}
}
void Student::output()
{
cout << "Student Name: " << name << "\nNumber of Classes: " << numClasses << endl;
cout << "Names of Classes: " << endl;
for (int x = 0; x < 10; ++x)
{
if ( numClasses == 0 )
break;
if ( x == 0 )
cout << "Names of Classes: \n";
if ( classList[x] == "" )
break;
cout << "(" << x << ") " << classList[x] << "\n";
}
}
void Student::reset()
{
numClasses = 0;
for (int x = 0; x < 10; ++x)
{
classList[x] = "";
}
}
I tried changing the main function from before where I had a goto statement instead of a flag, and that didn't fix it. I think it's the cin.getline() but I am not sure.
You have undefined behavior in this code (and the other constructors):
Student::Student ()
{
name = "";
numClasses = 0;
for (int x = 0; x < 10; ++x)
{
classList[x] = "";
}
}
You never allocated any elements in the classList vector, so the reference to classList[x] is out of bounds. You should use .push_back() to add new elements to the vector:
Student::Student ()
{
name = "";
numClasses = 0;
for (int x = 0; x < 10; ++x)
{
classList.push_back("");
}
}
Or before the loop you could do classList.reserve(10); to make room for 10 elements.
See C++ Tutorial: A Beginner's Guide to std::vector

LRU c++ program

I've been working on a program in one of my college classes. I have been having trouble with the implementation of my LRU code as it is not displaying any errors or anything, but compiles. There are two parts. The main that we input the values into, which we then specify which algorithm we want to use to find page faults. I know the main works, along with the FIFO algorithm, but I'm not getting anything with my LRU code (It compiles and "runs" but displays nothing as if I did not click to use the algorithm). Can anyone help me figure out what is wrong?
main.cpp
#include <iostream>
#include <string>
//#include "fifo.cpp"
#include "lru.cpp"
//#include "optimal.cpp"
using namespace std;
int main() {
// List of different variables
string pagestring;
int fs,pn[50], n;
// Prompt for page references
cout<<"Virtual Memory Simulation\nBy blah\n----------\nEnter the number of pages : " << endl;
cin >> n;
cout<<"\n-------------\nPlease enter a list of page numbers separated by commas.\n"<< endl;
cin>>pagestring;
// algorithm to use
char algo;
while (true) {
// Prompt algorithm to use
cout<<"----------\nPlease select an algorithm to use.\n\n1: First-In-First-Out (FIFO)\n2: Least-Recently-Used (LRU)\n3: Optimal\n0: Quit\n"<<endl;
cin>>algo;
if (algo == '1') {
//fifo(pagestring);
}
else if (algo == '2'){
LRU_Execute(pagestring, n);
}
else if (algo == '3'){
cout<<"Optimal Not yet coded"<<endl;
}
else if (algo == '0'){
break;
}
else {
cout<<"Invalid choice. Please try again."<<endl;
}
}
cout<<"Goodbye!!"<<endl;
};
LRU.cpp
#include <iostream>
#include <string>
using namespace std;
class pra
{
int fs,z;
int frame[50], frame1[50][2], pn[50], n, cnt, p, x;
public:
pra();
void init(string pagestring);
void getdata(string pagestring, int n);
void lru(int* pn, int n, string pagestring);
};
pra::pra()
{
int i;
for (i = 0; i < fs; i++)
{
frame[i] = -1;
}
for (i = 0; i < fs; i++)
{
frame1[i][0] = -1;
frame1[i][1] = 0;
}
p = 0;
cnt = 0;
}
void pra::init(string pagestring)
{
int i;
for (i = 0; i < fs; i++)
{
frame[i] = -1;
}
for (i = 0; i < fs; i++)
{
frame1[i][0] = -1;
frame1[i][1] = 0;
}
p = 0;
cnt = 0;
}
void pra::getdata(string pagestring, int n)
{
fs=3;
// index to loop through input string
int i = 0;
// current input string character
char z = pagestring[i];
int x = 0;
//cout << "\nEnter the page numbers : ";
while (z != '\0'){
// skip over commas and spaces
if (!(z == ',')) {
pn[x] = z;
x++;
// cout<<pn[x]<<"-This is pn[x]\n";
}
z = pagestring[++i];
}
//cout<<pn[x]<<"-This is pn[x] AGAIN\n";
this->lru(pn, n, pagestring);
}
void pra::lru(int* pn, int n, string pagestring)
{
init(pagestring);
int ind = 0, fault = 0, pi = 0, j, fn;
char i, z;
p = 0;
cnt = 0;
int min;
cout<<n<<"---"<<i<<" - "<<j<<" - "<<" - "<<fn<<" - "<<z;
for (i = 0; i < fs; i++)
{
frame1[i][0] = -1;
frame1[i][1] = 0;
}
pi = 0;
for (i = 0; i < n; i++)
{
j = 0;
if (ind > fs - 1)
ind = 0;
fault = 1;
min = 999;
while (j < fs)
{
if (frame1[j][0] = pn[pi])
{
fault = 0;
p++;
frame1[j][1] = p;
goto l2;
}
if (frame1[j][1] < min)
{
min = frame1[j][1];
fn = j;
}
j++;
}
j = 0;
while (j < fs)
{
if (frame1[j][0] = -1)
{
fault = 1;
fn = j;
goto l2;
}
j++;
}
ind++;
l2:
if (fault == 1)
{
p++;
frame1[fn][0] = pn[pi];
frame1[fn][1] = p;
cnt++;
}
cout << "\nElement: " << pn[pi];
pi++;
for (z = 0; z < fs; z++)
{
cout << "\t" << frame1[z][0];
}
if (fault == 1)
cout << "\t**Page Fault**";
else
cout << "\t--No Page Fault--";
}
cout << "\nTotal number of page faults: " << cnt;
cout << "\n";
}
void LRU_Execute(string pagestring, int n)
{
pra p;
int j, fault = 0, i, pi, z, fn, ind = 0, ans, ch;
p.getdata(pagestring, n);
//p.lru();
while (ans == 1);
//return 1;
}

c++ Function which returns data to a refrenced vector

I have a function that reads a text file and populates a vector which is referenced as an argument.
vect.push_back(TempArray);
is the line that causes my error. Any thoughts?
Error 1 error C2664: 'void std::vector<_Ty>::push_back(double *&&)' : cannot convert parameter 1 from 'std::vector<_Ty>' to 'double *&&' d:\aul_c++_12102014\aul_c++_rk_version_12182014\aul\aul\projection.h 206 1 AUL
int projection::import_inputTables(string input_file, string output_file, int dimen, vector<double*> &vect, long col_filler, long row_filler, string delim, int OptArgVar)
{
long i=0,j=0,k=0;
int total_Col = dimen;
long MaxLinesNum = 100000;
const string DELIM = delim;
string Line;
string LineCell;
long LineCounter = 0;
long LinesRead = 0;
int LineReadPoint = 0;
//Determines number of lines to be read
if (OptArgVar == 0) //Read untill the end
{
MaxLinesNum = 100000;
}
else if (OptArgVar == 1)
{
MaxLinesNum = 1;
}
else if (OptArgVar == 2)
{
MaxLinesNum = 51;
}
ifstream input_stream;
input_stream.open(input_file);
if (input_stream.is_open())
{
while( MaxLinesNum > LinesRead )
{
getline(input_stream,Line);
if (LineCounter >= col_filler)
{
vector<double> TempArray;
for (j = 0; (j < total_Col); j++) //Column Loop
{
LineCell = Line.substr(0,Line.find(DELIM));
Line.erase(0,Line.find(DELIM) + DELIM.length());
TempArray.push_back(stod(LineCell));
}
vect.push_back(TempArray);
vector<double> ().swap(TempArray);
LinesRead++;
LineCounter++;
}
else
{
LineCounter++;
}
if (MaxLinesNum == LinesRead) //Read only the needed number of lines --- Will read entire file if OptArgVar is set to 0
break;
}
}
else
{
cout << "Could Not Open File" << endl;
}
//PRINT STATEMENT DO NOT DELETE
input_stream.close();
return vect.size();
/*ofstream out(output_file);
out.precision(10);
for (j = 0; j < vect.size(); j++){
for (i = 0; i <= total_Col; i++){
out << vect.at(j)[i]<< '\t';
}
out << '\n';
}
out.close();*/
}
Looks like
vector<double*> &vect
should be
vector<vector<double>> &vect

File reading trouble

#Jason Ball this is the whole function:
std::ifstream InFile(filename);
if (!InFile)
return E_FAIL;
std::vector<Layer>Layers;
std::vector<PatternSet>Patterns;
std::vector<Mood>Moods;
Layer layer;
PatternSet ps;
Mood mood;
Theme theme;
layer.fileInfo.padding = layer.fileInfo.data = nullptr;
layer.fileInfo.len = 0;
std::string cmd;
while (true)
{
InFile >> cmd;
if (!InFile)
break;
if (cmd == "f")
{
InFile >> layer.fileInfo.filename;
}
else if (cmd == "fp")
{
int data, n; InFile >> n;
for (int a = 0; a < n; a++)
{
InFile >> data;
layer.fadePoints.push_back(data);
}
}
else if (cmd == "sp")
{
int data, n; InFile >> n;
for (int a = 0; a < n; a++)
{
InFile >> data;
layer.syncPoints.push_back(data);
}
}
else if (cmd == "v")
{
InFile >> layer.volume;
}
else if (cmd == "#layerend")
{
Layers.push_back(layer);
}
else if (cmd == "#patternset")
{
int Index;
for (int a = 0; a < 5; a++)
{
InFile >> Index;
if (Index != -1)
ps.pattern[a] = std::move(Layers[Index]);
}
Patterns.push_back(ps);
memset(ps.pattern, 0, sizeof(Layer)* 5);
}
else if (cmd == "#mood")
{
InFile >> mood.name;
int Index, n; InFile >> n;
for (int a = 0; a < n; a++)
{
InFile >> Index;
mood.data.push_back(Patterns[Index]);
}
Moods.push_back(mood);
mood.data.clear();
}
else if (cmd == "#theme")
{
InFile >> theme.name;
int Index, n; InFile >> n;
for (int a = 0; a < n; a++)
{
InFile >> Index;
theme.data.push_back(Moods[Index]);
}
m_vTheme.push_back(theme);
theme.data.clear();
}
else
{
}
}
return S_OK;
and here is a file:
#layer
f filename
fp 4 0 1998 1245 1003482
sp 3 500 1200 9500
v 0.95
#layerend
#layer
f filename2
fp 4 0 1998 1245 1003482
sp 3 500 1200 9500
v 0.75
#layerend
#patternset -1 0 -1 -1 -1
#patternset -1 1 -1 -1 -1
#mood name n 0 1
#theme name n 0
#Jason Ball here you have those structures as well:
struct node
{
union{
struct{
std::string filename;
void *padding;
};
struct{
void *data;
unsigned int len;
};
};
};
struct Theme;
struct Mood;
struct PatternSet;
struct Layer
{
node fileInfo;
std::vector<int> fadePoints;
std::vector<int> syncPoints;
float volume;
PatternSet *pUp;
};
struct PatternSet
{
union{
struct{
Layer pattern[5];
};
struct{
Layer start;
Layer main;
Layer end;
Layer rhytmic;
Layer incidental;
};
};
Mood *pUp;
};
struct Mood
{
std::vector<PatternSet> data;
std::string name;
Theme *pUp;
};
struct Theme
{
std::vector<Mood> data;
std::string name;
};
When I set breakpoints everywhere, it shows that after first if block it jumps to return line even when the file contains more than 5 000 lines.
I had the same problem a few months ago, but it somehow got to work. Any ideas what can cause this problem?
try this. Hope it helps.
{
ifstream InFile("text.txt");
if (!InFile) return 0;
string cmd;
while (InFile >> cmd)
{
cout << "\ncmd " << cmd;
if (cmd == "f")
{
string name;
if (InFile >> name) {
layer.fileInfo.filename = name;
cout << "\nfilename: " << layer.fileInfo.filename;
}
}
else if (cmd == "fp")
{
int data, n;
if (InFile >> n) {
for (int a = 0; a < n; a++)
{
if (InFile >> data) {
cout << "\nAdding " << data;
layer.fadePoints.push_back(data);
}
}
}
}
else if (cmd == "sp")
{
int data, n;
if (InFile >> n) {
for (int a = 0; a < n; a++)
{
if (InFile >> data) {
layer.syncPoints.push_back(data);
}
}
}
}
else if (cmd == "v")
{
float vol;
if (InFile >> vol) {
layer.volume = vol;
}
}
else if (cmd == "#layerend")
{
Layers.push_back(layer);
}
else if (cmd == "#patternset")
{
int Index;
for (int a = 0; a < 5; a++)
{
if (InFile >> Index) {
if (Index != -1) {
ps.pattern[a] = std::move(Layers[Index]);
}
}
}
Patterns.push_back(ps);
memset(ps.pattern, 0, sizeof(Layer)* 5);
}
else if (cmd == "#mood")
{
if (InFile >> mood.name) {
cout << "\nmood.name " << mood.name;
int Index, n;
if (InFile >> n) {
for (int a = 0; a < n; a++)
{
if (InFile >> Index) {
cout << "\nmood.data.push_back( " << Index << " )";
mood.data.push_back(Patterns[Index]);
}
}
Moods.push_back(mood);
}
}
}
else if (cmd == "#theme")
{
if (InFile >> theme.name) {
cout << "\ntheme.name " << theme.name;
int Index, n;
if (InFile >> n) {
for (int a = 0; a < n; a++)
{
if (InFile >> Index) {
cout << "\ntheme.data.push_back( " << Index << " )";
theme.data.push_back(Moods[Index]);
}
}
m_vTheme.push_back(theme);
}
}
}
else
{
//
}
}
return 1;
}

c++ code to sort text file doesn't works

A friend left me a code that should open 2 files solution.txt and priority.csv and generate a 3rd file result.txt as an output.
Files structures:
solution.txt contains an ordered list of target, names and values separated by commas, and I know how many line the file contains:
target0,name0,value0,name1,value1,name2,value2,name3,value3
target1,name4,value4,name5,value5,name6,value6,name7,value7
target2,name8,value8,name9,value9,name10,value10,name11,value11
...etc
some of solution.txt's lines contain only a target value:
target3
target4
target5
...etc.
priority.csv contains an indexed list of colornames, I know how many colornames there are:
1,colorname1
2,colorname2
3,colorname3
The code below should do the following:
ask how many lines of data solution.txt contains
ask how many colornames are contained in priority.csv
put the name(s) and associated value(s) of solution.txt in the order defined by priority.csv
create an array that contains as many columns as the number of colors, and as many lines as in solution.txt
fill this array with the value(s) associated to each line & colorname
fill the other cases with 0
The code doesn't work for some reasons I don't understand. If you have the courage to compile it, here are examples to put in solution.txt and priority.txt :
solution.txt
99985,CIN,0.624049619347,OR0,0.36925123875,K2M,0.00387491644559,gY6D,0.00282422545715
99986,CIN,0.624372658354,OR0,0.369683600811,K2M,0.00365124527159,gY6D,0.00229249556329
99987,CIN,0.624695697361,OR0,0.370115962872,K2M,0.0034275740976,gY6D,0.00176076566943
99988,CIN,0.625018736368,OR0,0.370548324933,K2M,0.0032039029236,gY6D,0.00122903577557
99989,CIN,0.625341775375,OR0,0.370980686994,K2M,0.00298023174961,gY6D,0.00069730588171
99990,CIN,0.625664814382,OR0,0.371413049055,K2M,0.00275656057561,gY6D,0.000165575987851
priority.csv
1,CIN
2,K2M
3,gY6D
4,OR0
In this example the amonut of lines is 6 and there are 4 colors
And that's the code, I listed possible errors and I get error2 and error4 printed on the console:
#include <iostream>
#include <fstream>
#include <sstream>
#include <string>
#include <stdio.h>
#include <string.h>
using namespace std;
int main() {
int COLORS = 0;
int LINES = 0;
cout << endl << "Original Data (solution.txt):" << endl << endl << "How many lines?" << endl;
cin >> LINES;
cout << "How many colors in the list?" << endl;
cin >> COLORS;
char Coul[COLORS][LINES];
//1- reading the file priority.csv
for (int i=0; i<COLORS; i++) Coul[i][0]='\0';
FILE *Read=fopen("priority.csv","rt");
if (Read == NULL) {
printf("Error 1");
return(0);
}
char line[120];
int N;
for (int i=0; i<COLORS; i++)
{
char name[8];
fgets(line,15,Read);
sscanf(line,"%d,%s",&N,name);
if (N == i) strcpy(Coul[i], name);
else {
printf("Error 2"); // Error2
break;
}
}
fclose(Read);
//2- reading the file solution.txt and writing the result.
Read=fopen("solution.txt","rt");
if (Read == NULL) {
printf("Error 3"); // Error3
return(0);
}
FILE *Write=fopen("result.txt","wt");
for (int i=1; i<LINES; i++)
{
char c[4][8]; // 4 color names
float v[4]; // 4 values
fgets(line,119,Read);
sscanf(line,"%d,%s,%f,%s,%f,%s,%f,%s,%f",
&N, c[0], &v[0], c[1], &v[1], c[2], &v[2], c[3], &v[3]);
if (N == i)
{
if (strlen(c[0]) == 0) // the line is empty
{
fprintf(Write,"%d ",i);
for (int i=0; i<COLORS; i++) fprintf(Write,"0 ");
fprintf(Write,"\n");
}
else
{
fprintf(Write,"%d ",i);
int r[4];
// we search the rang of c[ordre]
for (int order=0; order<4; order++)
{
for (int ir=0; ir<COLORS; ir++)
{
if (strcmp(c[order], Coul[ir]) == 0) r[order]=ir;
}
}
for (int ir=0; ir<r[0]; ir++) fprintf(Write,"0 ");
fprintf(Write,"%d ",v[0]);
for (int ir=r[0]+1; ir<r[1]; ir++) fprintf(Write,"0 ");
fprintf(Write,"%d ",v[1]);
for (int ir=r[1]+1; ir<r[2]; ir++) fprintf(Write,"0 ");
fprintf(Write,"%d ",v[2]);
for (int ir=r[2]+1; ir<r[3]; ir++) fprintf(Write,"0 ");
fprintf(Write,"%d ",v[3]);
for (int ir=r[3]+1; ir<57; ir++) fprintf(Write,"0 ");
fprintf(Write,"\n");
}
}
else {
printf("Error 4");
break;
} //Error4
}
fclose(Write);
fclose(Read);
}
could you please help debugging? I'm lost!
Adrien
Since you want to allocate memory dynamically you must use new and delete in c++. So instead of char Coul[COLORS][LINES]; use these lines:
char **Coul = NULL;
Coul = new char*[COLORS];
for(int i = 0; i < COLORS; i++)
Coul[i] = new char[LINES];
and at the end add these:
for(int i = 0; i < COLORS; i++)
delete [] Coul[i];
delete [] Coul;
It should compile, but I couldn't get pass the &N part, because I couldn't understand what you were trying to do.
EDIT:
Done!
EDIT2:
If I was right to assume that opening file does not load it all into RAM, then below is RAM friendly code adapted to old code, which uses temporary files as buffers (it may be a little slower and you need more disk space).
EDIT3:
Changed potentially unsafe string._Copy_s() to newly discovered string.substr()
#include <iostream>
#include <fstream>
#include <sstream>
#include <string>
#include <iomanip>
using namespace std;
class Sorter
{
private:
bool save_RAM, temp1_cleared, temp2_cleared;
string temp1, temp2;
int COLORS, LINES;
string *Color_codes, **Color_values;
bool find_codename(string line, string codename)
{
if (line.find(codename) == -1)
return 0;
else
{ //checking if there are other letters, which would make this codename not full and incorrect
char a, b;
if (line.find(codename) == 0)
{
b = line[codename.length()];
if (b == ',')
return 1;
else
return 0;
}
else
{
a = line[line.find(codename) - 1];
b = line[line.find(codename) + codename.length()];
if (a == ',' && b == ',')
return 1;
else
return 0;
}
}
}
void allocate_memory()
{
if (!save_RAM)
{
Color_codes = new string[COLORS];
Color_values = new string*[LINES];
for (int i = 0; i < LINES; i++)
Color_values[i] = new string[COLORS];
}
}
void deallocate_memory()
{
if (!save_RAM)
{
delete [] Color_codes;
for (int i = 0; i < LINES; i++)
delete [] Color_values[i];
delete [] Color_values;
}
else
{
remove(temp1.c_str());
remove(temp2.c_str());
}
}
void clear_temporary_file(const char *filename, bool &was_cleared)
{
if (was_cleared)
return;
else
was_cleared = true;
ofstream temp_file(filename);
if (temp_file == NULL)
{
cout << "Error 6";
cin.get();
exit(EXIT_FAILURE);
}
temp_file.close();
}
void write_to_temporary_file(const char *filename, string value)
{
ofstream temp_file(filename, ios::app);
if (temp_file == NULL)
{
cout << "Error 5";
cin.get();
exit(EXIT_FAILURE);
}
temp_file << value << endl;
temp_file.close();
}
string read_line(const char *filename, int line_number, bool twoD_array, int second_line_number, int line_length)
{
ifstream temp_file(filename);
string line;
if (temp_file == NULL)
{
cout << "Error 7";
cin.get();
exit(EXIT_FAILURE);
}
if (!twoD_array)
{
for (int i = 0; i < line_number; i++)
getline(temp_file, line);
getline(temp_file, line);
}
else
{
for (int j = 0; j < second_line_number + (line_length*line_number); j++)
getline(temp_file, line);
getline(temp_file, line);
}
temp_file.close();
return line;
}
void seperate_input(string line, int &N, string &Name)
{
string temp;
stringstream tempbuf;
line += ',';
stringstream ss(line);
getline(ss, temp, ',');
tempbuf << temp;
tempbuf >> N;
tempbuf = stringstream();
getline(ss, temp);
tempbuf << temp;
tempbuf >> Name;
}
void Generate_values(int line_number, string Other_stuff)
{
string temp;
if (!save_RAM)
{
for (int i = 0; i < COLORS; i++)
{
if (find_codename(Other_stuff, Color_codes[i]))
{
int j = 0;
bool search = true;
int a, b; //find comma positions
a = Other_stuff.find(Color_codes[i]) + Color_codes[i].length() + 1;
while(search)
{
j++;
char c = Other_stuff[a + j];
if (c == ',')
{
b = a + j;
search = false;
}
}
temp = Other_stuff.substr(a, b); // copy value to temporary buffer
Color_values[line_number][i] = temp;
}
else
Color_values[line_number][i] = "0";
}
}
else
{
clear_temporary_file(temp2.c_str(), temp2_cleared);
for (int i = 0; i < COLORS; i++)
{
string codename = read_line(temp1.c_str(), i, false, 0, 0);
if (find_codename(Other_stuff, codename))
{
int j = 0;
bool search = true;
int a, b; //find comma positions
a = Other_stuff.find(codename) + codename.length() + 1;
while(search)
{
j++;
char c = Other_stuff[a + j];
if (c == ',')
{
b = a + j;
search = false;
}
}
temp = Other_stuff.substr(a, b); // copy value to temporary buffer
write_to_temporary_file(temp2.c_str(), temp);
}
else
write_to_temporary_file(temp2.c_str(), "0");
}
}
}
double convert_to_double(string number)
{
double also_number = 0;
stringstream ss(number);
ss >> also_number;
return also_number;
}
public:
Sorter(bool RAM_saver)
{
COLORS = 0;
LINES = 0;
Color_codes = NULL;
Color_values = NULL;
save_RAM = RAM_saver;
temp1 = "temp_code.txt";
temp2 = "temp_values.txt";
temp1_cleared = false;
temp2_cleared = false;
}
~Sorter()
{
deallocate_memory();
}
void get_user_input()
{
cout << endl << "Original Data (solution.txt):" << endl << endl << "How many lines?" << endl;
while (!(cin >> LINES))
{
cin.clear();
cin.sync();
}
cout << "How many colors in the list?" << endl;
while (!(cin >> COLORS))
{
cin.clear();
cin.sync();
}
allocate_memory();
}
void read_priority_file(const char *filename)
{
ifstream priority_file(filename);
if (priority_file == NULL)
{
cout << "Error 1";
cin.get();
exit(EXIT_FAILURE);
}
string line;
int N;
if (!save_RAM)
{
for (int i = 0; i < COLORS; i++)
{
string Name;
getline(priority_file, line);
seperate_input(line, N, Name);
if (N == (i+1))
{
Name.pop_back(); //push last , out (I need it other function)
Color_codes[i] = Name;
}
else
{
priority_file.close();
cout << "Error 2";
cin.get();
exit(EXIT_FAILURE);
}
}
}
else
{
clear_temporary_file(temp1.c_str(), temp1_cleared);
for (int i = 0; i < COLORS; i++)
{
string Name;
getline(priority_file, line);
seperate_input(line, N, Name);
if (N == (i+1))
{
Name.pop_back(); //push last , out (I need it other function)
write_to_temporary_file(temp1.c_str(), Name);
}
else
{
priority_file.close();
cout << "Error 2";
cin.get();
exit(EXIT_FAILURE);
}
}
}
priority_file.close();
}
void read_solution_and_generate_result(const char *filename)
{
ifstream solution_file(filename);
if (solution_file == NULL)
{
cout << "Error 3";
cin.get();
exit(EXIT_FAILURE);
}
string line;
int N;
for (int i = 0; i < LINES; i++)
{
string Other_stuff;
getline(solution_file, line);
seperate_input(line, N, Other_stuff);
if (N == (i+1))
Generate_values(i, Other_stuff);
else
{
solution_file.close();
cout << "Error 4";
cin.get();
exit(EXIT_FAILURE);
}
}
solution_file.close();
}
void print_results_to_file(const char *filename)
{
ofstream result_file(filename);
if (result_file == NULL)
{
cout << "Error 5";
cin.get();
exit(EXIT_FAILURE);
}
if (!save_RAM)
{
for (int i = 0; i < COLORS; i++)
{
result_file << Color_codes[i];
if (i != COLORS-1)
result_file << ",";
}
}
else
{
for (int i = 0; i < COLORS; i++)
{
result_file << read_line(temp1.c_str(), i, false, 0, 0);
if (i != COLORS-1)
result_file << ",";
}
}
result_file << endl;
if (!save_RAM)
{
for (int i = 0; i < LINES; i++)
{
for (int j = 0; j < COLORS; j++)
{
if (Color_values[i][j] != "0")
{
result_file.setf(ios::fixed);
result_file << setprecision(9) << convert_to_double(Color_values[i][j]);
result_file.unsetf(ios::fixed);
}
else
result_file << convert_to_double(Color_values[i][j]);
if (j != COLORS-1)
result_file << ",";
}
result_file << endl;
}
}
else
{
string value;
for (int i = 0; i < LINES; i++)
{
for (int j = 0; j < COLORS; j++)
{
value = read_line(temp2.c_str(), i, true, j, COLORS);
if (value != "0")
{
result_file.setf(ios::fixed);
result_file << setprecision(9) << convert_to_double(value);
result_file.unsetf(ios::fixed);
}
else
result_file << convert_to_double(value);
if (j != COLORS-1)
result_file << ",";
}
result_file << endl;
}
}
result_file.close();
}
};
int main()
{
bool save_my_RAM = false;
Sorter sort(save_my_RAM);
sort.get_user_input();
sort.read_priority_file("priority.csv");
sort.read_solution_and_generate_result("solution.txt");
sort.print_results_to_file("results.txt");
return 0;
}
With the contents of the priority.csv file being:
1,PINK
2,Y2
3,Y4
4,Y6
5,CIN
6,K1
7,K2
8,OR0
9,PINKwA
10,PINKwB
11,MAGA
12,MAGB
13,MAGC
14,K2M
15,K1A
16,K1B
17,K1C
18,OR0A
19,OR0B
20,Y9
21,Y9A
22,gTUD
23,bTUD
24,TU
25,TUwA
26,TUwB
27,TUwC
28,REF
29,REFwA
30,REFwB
31,REFwC
32,XTwA
33,XTwB
34,XTwC
35,XTwD
36,GA
37,GB
38,GC
39,gY6A
40,gY6B
41,gY6C
42,gY6D
43,gY6E
44,gY2A
45,gY2B
46,gY2C
47,gY2D
48,gY2E
49,XTC1
50,XTC8II
51,XTC64II
52,XTC8
53,XTC64
54,XT
55,SBK
56,LBK
57,PAPER
This is the expected result:
PINK,Y2,Y4,Y6,CIN,K1,K2,OR0,PINKwA,PINKwB,MAGA,MAGB,MAGC,K2M,K1A,K1B,K1C,OR0A,OR0B,Y9,Y9A,gTUD,bTUD,TU,TUwA,TUwB,TUwC,REF,REFwA,REFwB,REFwC,XTwA,XTwB,XTwC,XTwD,GA,GB,GC,gY6A,gY6B,gY6C,gY6D,gY6E,gY2A,gY2B,gY2C,gY2D,gY2E,XTC1,XTC8II,XTC64II,XTC8,XTC64,XT,SBK,LBK,PAPER
0,0,0,0,0.624049619,0,0,0.369251239,0,0,0,0,0,0.003874916,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0.002824225,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0
0,0,0,0,0.624372658,0,0,0.369683601,0,0,0,0,0,0.003651245,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0.002292496,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0
0,0,0,0,0.624695697,0,0,0.370115963,0,0,0,0,0,0.003427574,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0.001760766,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0
0,0,0,0,0.625018736,0,0,0.370548325,0,0,0,0,0,0.003203903,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0.001229036,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0
0,0,0,0,0.625341775,0,0,0.370980687,0,0,0,0,0,0.002980232,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0.000697306,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0
0,0,0,0,0.625664814,0,0,0.371413049,0,0,0,0,0,0.002756561,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0.000165576,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0