Hey guys,

Im trying to make a program that guesses the name of an animal in the users head by asking him or her a bunch of questions. The questions, answers, and line number for yes/no are inlcuded in the file animals.txt as follows:

Q Does it have feathers? 2 7
Q Is it a mammal? 3 4
A lizard
Q Does it have stripes? 5 6
Q Does it hop? 10 11
A tiger
Q Is it tasty to eat? 8 9
A owl
A chicken
A elephant
A kangaroo

Im using a struct to organize this information:
struct QandA
{
bool animal; // true if question is an animal
string question; // holds either a question or animal name
int yes;
int no;
};

I've only just started the program but I'm getting errors when i try to try to make codes like:
info[k].question.assign(tempstring,2,(tempstring.length()-6));

I get an error C2228: left of '.assign' must have class/struct/union.

Any advice on how to fix this problem and any additional input would be greatly appreciated.

Thanks in advance,


Code:

// Program attempts to guess the name of an animal in the user's mind by asking a series of questions which have a yes or no answer


#include <iostream>
#include <fstream> 
#include <string>

using namespace std;



void main ()
{
	struct QandA 
	{
		bool animal; // true if question is an animal
		string question; // holds either a question or animal name
		int yes;
		int no; 
	};

	string lines[200];
	QandA info[300];

	ifstream source;
	char c;
	int i = 0;
	string bigstring = "";
	string file1, tempstring;
	
	


	source.open("animals.txt");

		
while(source.fail())										//Code for validation of input file
	{
		cout<<"Error: Invalid input file name. Please make sure the file is in the default directory or provide full path."<<endl;
		cin>> file1;
		source.close();
		source.clear();
		source.open (file1.c_str());
	}

	 
	while (! source.eof())								//Loading the text from the input file into the string
	{      
		source.get(c);
		bigstring += c;
		 
		if (c == '\n')
		{
			lines[i] = bigstring ;
			bigstring = "";
			i++;
		}
			//cout<<text[i];
	}

		
		
	/*for (int j=0;j<i;j++)
		{
			cout<<"Line "<<j<<" is: "<<lines[j]<<endl;
		}*/

	for (int k=0;k<i;k++)
		{
			lines[k] = tempstring;
			if (tempstring.at(0) == 'A' && tempstring.at(1) == ' ')
			{
				info[k].animal = true;
				info[k].question.assign(tempstring,2,(tempstring.length()-6));
				
			}
			if (tempstring.at(0) == 'Q' && tempstring.at(1) == ' ')
			{
				info[k].animal = false;
				info[k].question.assign(tempstring,2,(tempstring.length()-6));
				info[k].no.assign(tempstring,(tempstring.length()-3),1);
				info[k].yes.assign(tempstring,(tempstring.length()-1),1);

			}
		}
	cout<<info[0];
}

You've got 87 lines of code. If we don't know which line has the error we can't suggest much.

When asking for help, provide all the details you can.

You've got 87 lines of code. If we don't know which line has the error we can't suggest much.

When asking for help, provide all the details you can.

Right.. my bad.

Ive modified the code. It works so far except for the part where I'm trying to update the database of animals by user input. I think the problem is on line 93: getline(cin,newquestion,'\n');
And probably the few lines after it up until line 101

// Ismail Makhlouf
// UID: 900092040
// Section 02
// CS 110 - Ismail M Assignment 3
// Program attempts to guess the name of an animal in the user's mind by asking a series of questions which have a yes or no answer


#include <iostream>
#include <fstream> 
#include <string>
using namespace std;

struct QandA 
{
	bool animal; // true if question is an animal
	string question; // holds either a question or animal name
	int yes;
	int no; 
};

void main ()
{
	QandA info[300]; //Array of structs to save questions and answers
	ifstream source; //Input file stream declaration
	char ch; //used in capturing the first character of each line in the input file
	int rows = 1; //an index to the number of rows in the array
	string inputFile = "animals.txt"; //input file name
	string yesno, newanimal, newquestion;


	source.open(inputFile.c_str()); //Input file stream initialization

	while(source.fail()) //validation code for input file stream initialization
	{
		cout<<"Error: Invalid input file name. Please make sure the file is in the default directory or provide full path."<<endl;
		cin>> inputFile;
		source.close();
		source.clear();
		source.open (inputFile.c_str());
	}

	while (!source.eof()) //inputing and saving from input file to array of structs line by line
	{
		ch = NULL; //initialization and reseting
		source>>ch; //first obtaining the first character of the line which is either 'A' or 'Q'

		if (ch == 'Q') //Conditions for 'Q'
		{
			source.get(); //skip the space after 'Q'
			getline(source,info[rows].question,'?'); //Read till you find '?' and save
			source>>info[rows].no>>info[rows].yes; //inputing the yes/no numbers
			info[rows].animal = false; //initializing animal to false because info[rows].animal is a question
			cout<<rows<<" "<<ch<<" "<<info[rows].question<<"? "<<info[rows].no<<" "<<info[rows].yes<<endl; //you should remove this after you finish testing
			rows++;
		}

		else if (ch == 'A') //Conditions for 'A'
		{
			source.get(); //skip the space after 'A'
			getline(source,info[rows].question); //Read till end of line and save
			info[rows].animal = true;//initializing animal to true because info[rows].animal is an animal
			cout<<rows<<" "<<ch<<" "<<info[rows].question<<"."<<endl; //testing the program
			rows++;
		}
	}
	
	cout<<endl;
	cout<<"Think of an animal and I will try to guess its name "<<endl;

		int i = 1;

			while (info[i].animal == false)
			{
				cout<<info[i].question<<"? "<<"[Yes/No] ";
				cin>>yesno;
				if (yesno == "no" || yesno == "n")
				{
					
					i = info[i].no;
					if (info[i].animal == true)
						break;
				}
				if (yesno == "yes" || yesno == "y")
				{
					
					i = info[i].yes;
					if (info[i].animal == true)
						break;
				}
			}
			while (info[i].animal == true)
			{
				cout<<"Is it a "<<info[i].question<<"? ";
				cin>>yesno;

				if (yesno == "no" || yesno == "n")
				{
					cout<<"I give up: what animal were you thinking of?"<<endl;
					cin >> newanimal;
					cout<<"Please type a question that has a yes answer for "<< newanimal <<" and a no answer for " << info[i].question<<endl;
					getline(cin,newquestion,'\n');
					info[rows].question = info[i].question;
					info[rows].animal = true;
					info[rows+1].question = newanimal;
					info[rows+1].animal = true;
					info[i].question = newquestion;
					info[i].no = rows+1;
					info[i].yes = rows+2;
					info[i].animal = false;
					for (int k = 1; k<rows;k++)
					{
						cout<<k<<" "<<info[k].animal<<" "<<info[k].question<<" "<<" "<<info[k].no<<" "<<info[k].yes<<" "<<endl;
					}
					break;
				}
				if (yesno == "yes" || yesno == "y")
				{
					cout<<"I WIIN!!"<<endl;
					break;
				}
			}
	


}

Edited 6 Years Ago by som3aman: Personal info accidentally included

I think the problem is on line 93: getline(cin,newquestion,'\n');

Fair enough, but in addition to pointing to where you think the problem is it also helps to explain the problem. I will assume the problem is that the code isn't putting information into newquestion. If that's correct, then the problem is probably because you are mixing >> and getline() in the same program, and particularly >> before getline(). >> doesn't remove the terminating whitespace char from the input buffer. The terminating char for >> is the newline char. The newline char is also the default terminating char for getline(), and you are making it the explicit terminating char in the call to getline() that you quoted. If there is a newline char as the first char in the input buffer when getline() is called and the terminating char for getline() is the newline char, then the first thing getline() sees is the newline char left over from the call to >> and it won't read anything into the variable indicated in the call to getline(). Never mix >> and getline() in the same program or get into the habit of clearing the input buffer before calling getline() to be sure there is no unexpected remnants in there. To do that use a large number---the largest number you can use is the safest, eventhoug it's not the easiest syntax to use, as the argument to a call to the istream method called ignore.

This article has been dead for over six months. Start a new discussion instead.