Need help with pointers

My problem is my TaskList, where my function addToList(Task* t) points to the address and I am unable to think of a way to dereference that pointer so I can get the data. TaskList is a underlying data structure that I will use for another class to implement completed and incomplete tasks. My logic behind TaskList is by making a vector of Task pointers point to the address of the Task created. Then I can iterate through the vector to output the data stored in the address. Later on, in another class, I will implement 2 TaskList objects incomplete and completed and be able to use TaskList functions to remove tasks from complete / incomplete, have the data stored in incomplete.at(index) point to completed, store the data and then remove the data at incomplete.

Task.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
class Task{

public:
	Task();
	~Task(){}
	void setType(string t){ type = t; }
	string getType(){ return type; }
	void setDeadline(int dl){ deadline = dl; }
	int getDeadline(){ return deadline; }
	void setDescription(string des){ description = des; }
	string getDescription(){ return description; }
	friend bool operator<(Task& lhs, Task& rhs){ return lhs.getDeadline()<rhs.getDeadline(); }
	virtual void print();

protected:
	int deadline;
	string description;
	string type;
};

#endif 


Task.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
Task::Task() {
	
	deadline = 0;
	description = "";
	type = "Generic";
}

void Task::print(){

	cout << "( " << getDeadline() << " days from now )     " <<  getDescription() << endl;  
}

#endif 


TaskList.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
class TaskList{
	
	public:
		TaskList(){}
		~TaskList(){}
		void addToList(Task* t);
		void removeFromList(unsigned int num);
		void setATaskG(int dl, string des);
		void setATaskE(string location, string tim);
		void setATaskH(string hw);
		void setATaskS(string it);
		bool operator()(Task* left, Task* right){ return (*left) < (*right); }
		void printAllTasks();
		bool isEmpty();
		Task* getTask(unsigned int num);

	private:
		SortedVector<Task*>someTask;
};

#endif 


TaskList.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
//This is my problem. It inserts the address, but i don't know how to dereference later on
void TaskList::addToList(Task* t){

	someTask.insert(t);
}

void TaskList::removeFromList(unsigned int num){

	someTask.remove(num-1);
}

bool TaskList::isEmpty(){

	if(someTask.empty() == true){
		return true;
	}
	return false;
}

void TaskList::setATaskG(int dl, string des){

	Task* aGenericTask = new Task;
	aGenericTask->setDeadline(dl);
	aGenericTask->setDescription(des);
	cout << "Task added successfully." << endl;

	addToList(aGenericTask);
}

void TaskList::setATaskE(string location, string tim){

	EventTask* anEventTask = new EventTask;
	anEventTask->setLocation(location);
	anEventTask->setTime(tim);
	cout << "Task added successfully." << endl;

	addToList(anEventTask);
}

void TaskList::setATaskH(string hw){

	HomeworkTask* aHomeworkTask = new HomeworkTask;
	aHomeworkTask->setHomework(hw);
	cout << "Task added successfully." << endl;

	addToList(aHomeworkTask);
}

// User is able to enter more than 1 item.
//Not sure how to implement this and then later use it in the print() in the ShoppingTask class
void TaskList::setATaskS(string it){

	ShoppingTask* aShoppingTask = new ShoppingTask;
	//vector<string>anItem;
	//cout << "What item(s) do you need to buy? " << endl <<
	//"[Type your item and press ENTER to add another item. Type DONE to complete the list.]" << endl; 
	//getline(cin,it);
	//while(it != "DONE"){
	aShoppingTask->setItem(it);
	//	anItem.push_back(it);
	//	getline(cin,it);
	//}
	cout << "Task added successfully." << endl;

	addToList(aShoppingTask);
}

void TaskList::printAllTasks(){

	for(unsigned int index=0; index < someTask.size(); index++){
		cout << someTask.at(index) << endl;
	}
}

Task* TaskList::getTask(unsigned int num){

	return someTask.at(num);
}

#endif 


Last edited on
Why not overload << ?

If not make a copy constructor and call that on an object you want to dereference.
Last edited on
So essentially for the copy constructor I make it in TaskList and call it
1
2
3
4
TaskList(const TaskList& object){
Task = new Task;
*Task = *object;
}

I never used a copy constructor before and this seems to be the syntax, so I'm not sure if this is correct or not. I need a way for my program to iterate through the SortedVector of type Task* and return the data. So would the copy constructor allow me to store the data into each element of the vector?

2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
class TaskList{

public:
TaskList(){}
~TaskList(){}
void addToList(Task* t);
void removeFromList(unsigned int num);
void setATaskG(int dl, string des);
void setATaskE(string location, string tim);
void setATaskH(string hw);
void setATaskS(string it);
bool operator()(Task* left, Task* right){ return (*left) < (*right); }
void printAllTasks();
bool isEmpty();
Task* getTask(unsigned int num);

private:
//I don't know what you are trying to do here. Have you initialized a vector??
//vector<Task*> someTask;
SortedVector<Task*>someTask; };




void TaskList::addToList(Task* t){
//to insert items into a vector it is done with push_back.
//someTask.push_back(t);
someTask.insert(t);
}

*******************************************************
Review vector functions.. it will help you. http://www.cplusplus.com/reference/vector/vector/

If you are thinking of working with a container of Task pointers overloading the extraction operator (<<) may not be most efficient because when you dereference the base class pointer you're essentially left with a base class object that will only pick up the overloaded extraction operator related to the base class. I saw some posts about getting around this with typeid().name() etc but I did not find any of the solutions entirely satisfactory. Instead, I found it better to declare a virtual print function() method in the base class and then augment it for the derived classes that can be better indirected by the base class pointer pointing to derived class objects. The general on-line opinion also seems to be that polymorphism is better achived via pointers than objects. The program below uses smart pointers (std::unique_ptr) and so the managed objects are automatically deleted at the appropriate time.

TaskList should not be a separate class but rather a container of Tasks in the main() function that the user uses to create a collection of Tasks and then they can be printed out. You mention using a vector at one point and also later wished to have the facility to remove Tasks depending on whether or not they're completed. For that reason I'd suggest using a List<Task> instead of vector<Task> as it's far more efficient to insert/delete List at any point. And you can use can of the List class methods or STL algorithms for additional functionality.

You do not need separate classes for complete/incomplete Task but instead a bool data member for each Task member, say isComplete, that is initialized "false" upon instantiation and you can have a method that deletes an item from List<Task> when isComplete == "true".

Event, Homework and Shopping tasks should be derived from Generic Task (here just Task) since each is a type of task.

Finally, and this is a VERY important point, the program has a lot of user input of int data type (since your deadline data member is type int) and this is a nightmare in case user inputs a char by mistake and presses Enter, so you need to add strict input validation around any cin>> that accepts int's.

Program uses C++11 features.

Header file: http://pastie.org/10956967
Implementation file: http://pastie.org/10956968
Main(): http://pastie.org/10956969

Sample Output

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
1.Generic Task 2.Event Task 3.Homework Task 4.Shopping Task 5.Quit
1
Enter Generic task description:
laundry
Enter task deadline:
1107
1.Generic Task 2.Event Task 3.Homework Task 4.Shopping Task 5.Quit
2
Enter Event task description:
doc appt
Enter task deadline:
1108
Enter event location:
gen hosp
1.Generic Task 2.Event Task 3.Homework Task 4.Shopping Task 5.Quit
3
Enter Homework task description:
programming h/w
Enter task deadline:
1109
Enter homework subject:
c++ quiz
1.Generic Task 2.Event Task 3.Homework Task 4.Shopping Task 5.Quit
4
Enter Shopping task description:
online amazon
Enter task deadline:
1110
1.Add to shopping list
2. Quit
1
Enter item:
c++ books
1.Add to shopping list
2. Quit
1
Enter item:
laptop
1.Add to shopping list
2. Quit
2
No further orders, thank you
1.Generic Task 2.Event Task 3.Homework Task 4.Shopping Task 5.Quit
5
TaskList updated
Task description: laundry       Deadline: 1107

Task description: doc appt      Deadline: 1108
Event location: gen hosp

Task description: programming h/w       Deadline: 1109
Homework subject: c++ quiz

Task description: online amazon Deadline: 1110
The shop list includes:
c++ books
laptop
@tibrado I used implemented my own SortedVector that uses vector as the underlying data structure. It has it own functionality, such as inserting the data into the vector based on deadline date.

@gunnerfunner As per my specs I need 1 base class Task and 3 derived classes ShoppingTask, EventTask& Homework. My TaskList would be an underlying data structure for another class that has to deal with 2 TaskList objects complete & incomplete, where I would be able to call the functions of TaskList to manipulate the two lists. An example would be removing an element on outstanding. I would use outstanding.removeFromList(2), would remove the element at index 1. My command outstanding.addToList(anEventTask) would return the address of the task, but would not display the actual data of the of that address. I was originally thinking about using lists as my original design proposal, but due to time constraints i opt to use vectors since I am more familiar with it than linked list. After the project, I plan on rewriting the code using lists to familiar myself with the list data structure. My program will not have any error checking, for I can assume the user would input correct values.
Topic archived. No new replies allowed.