17 errors with cpp file

I have to write a ArrayDictionary.cpp file that follows the ArrayDictionary.h file listed below. The purpose of the h file is An array-based implementation of the ADT dictionary that organizes its data items in sorted search-key order.
Search keys in the dictionary are unique. . The code includes ArrayDictionary.h and ArrayDictionary.cpp. The ArrayDictionary.h file also includes other h files please let me know if you need them to help me.

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
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
  // Complete the implementation of the class ArrayDictionary as given in Listing 18-3.
/** An array-based implementation of the ADT dictionary
  that organizes its data items in sorted search-key order.
  Search keys in the dictionary are unique.
  @file ArrayDictionary.h */

#pragma once

  #ifndef _ARRAY_DICTIONARY
 #define _ARRAY_DICTIONARY

 #include "DictionaryInterface.h"
 #include "Entry.h"
 #include "NotFoundException.h"
#include "PrecondViolatedExcept.h"

template < class KeyType, class ValueType>
class ArrayDictionary : public DictionaryInterface < KeyType, ValueType>
{
private:
static const int DEFAULT_CAPACITY = 21; // Small capacity to test for
                                           // a full dictionary

Entry<KeyType, ValueType>* entries; // Array of dictionary entries
int entryCount                   // Maximum capacity of the dictionary
void destroyDictionary();
int findEntryIndex(int firstIndex, int lastIndex, const KeyType & searchKey) const;
int maxEntries;

public:
ArrayDictionary();
ArrayDictionary(int maxNumberOfEntries);
ArrayDictionary(const ArrayDictionary<KeyType, ValueType>&dictionary);

virtual ~ArrayDictionary();

bool isEmpty() const;
int getNumberOfEntries() const;
bool add(const KeyType& searchKey, const ValueType& newValue) throw (PrecondViolatedExcep);
bool remove(const KeyType& searchKey);
void clear();
ValueType getValue(const KeyType& searchKey) const throw (NotFoundException);
bool contains(const KeyType& searchKey) const;
	
/** Traverses the items in this dictionary in sorted search-key order
 and calls a given client function once for each item. */
void traverse(void visit(ValueType&)) const;
}; // end ArrayDictionary

#include "ArrayDictionary.cpp"
#endif






// ArrayDictionary.cpp
#include <iostream>
#include "ArrayDictionary.h"
#include "PrecondViolatedExcept.cpp"

template < class KeyType, class ValueType>
inline void destroyDictionary()
{
	delete[] items;

	items = new Entry[maxItems];

	itemsCount = 0;
}

template < class KeyType, class ValueType>
inline int findEntryIndex(int firstIndex, int lastIndex, const KeyType& searchKey)
{
	int IndexMiddle = firstIndex + (lastIndex - firstIndex) / 2;

	if (firstIndex > lastIndex)

		return -1;

	else if (searchKey == items[IndexMiddle].getKey())

		return IndexMiddle;

	else if (searchKey < items[IndexMiddle].getKey())

		return findEntryIndex(firstIndex, IndexMiddle - 1, searchKey);

	else

		return findEntryIndex(IndexMiddle + 1, lastIndex, searchKey);

}

template < class KeyType, class ValueType>
inline ArrayDictionary::ArrayDictionary() : itemCount(0), maxItems(DEFAULT_CAPACITY)
{
	items = new Entry[DEFAULT_CAPACITY];
}

template < class KeyType, class ValueType>
inline ArrayDictionary::ArrayDictionary(int maxNumberOfEntries) :
	itemCount(0), maxItems(maxNumberOfEntries)
{
	items = new Entry[maxNumberOfEntries];
}


template < class KeyType, class ValueType>
inline ArrayDictionary::ArrayDictionary(const ArrayDictionary& dictionary) :

	itemCount(dict.itemCount), maxItems(dict.maxItems)
{
	items = new Entry[dict.maxItems];

	for (int index = 0; index < dict.itemCount; index++)
	{
		items[index] = dict.items[index];
	}
}

template < class KeyType, class ValueType>

inline ArrayDictionary::~ArrayDictionary()
{
	destroyDictionary()
}

template < class KeyType, class ValueType>
inline bool isEmpty()
{
	return (itemCount == 0);

}

template < class KeyType, class ValueType>
inline int getNumberOfItems()
{
	return itemCount;
}

template < class KeyType, class ValueType>
inline void clear()
{
	destroyDictionary();
}


template < class KeyType, class ValueType>
inline bool ArrayDictionary<KeyType, ValueType>::add(const KeyType& searchKey, const ValueType& newValue) throw (PrecondViolatedExcep)
{
	bool ableToInsert = (itemCount < maxItems);

	if (ableToInsert)
	{
		// Make room for new entry by shifting all entries at
		// positions >= newPosition toward the end of the array
		// (no shift if newPosition == itemCount + 1). Performing
		// a binary search doesn’t help here, because we need to
		// shift the entries while looking for the insertion location.

		int index = itemCount;

		// Short-circuit evaluation is important

		while ((index > 0) && (searchKey < items[index - 1].getKey()))
		{
			items[index] = items[index - 1];
			index--;
		}  // end while

		if (searchKey != items[index - 1].getKey())
		{
			items[index] = Entry<KeyType, ValueType>(searchKey, newValue);
			itemCount++;

		}
		else
		{
			auto message = "Attempt to add entry whose search key exits in dictionary.";
			throw (PrecondViolatedExcep(message);
		}

		return ableToInsert;
	}  // end add

}

template < class KeyType, class ValueType>
inline bool remove(const const KeyType& itemKey)
{
	int currentIndex = findEntryIndex(0, itemCount - 1, itemKey);

	bool deletable = !isEmpty() && (currentIndex >= 0);

	if (deletable)
	{
		while (currentIndex < itemCount - 1)
		{
			items[currentIndex] = items[currentIndex + 1];

			currentIndex++;
		}
		itemCount--;
	}
	return deletable;
}

template < class KeyType, class ValueType>
inline ValueType getValue(const KeyType& searchKey) throw(NotFoundException)
{
	int currentIndex = findEntryIndex(0, itemCount - 1, searchKey);

	if (currentIndex < 0)
		throw NotFoundException("nnItemis not in the Dictionary!nn");

	return items[currentIndex].getItem();
}

template < class KeyType, class ValueType>
inline bool contains(const KeyType& searchKey)
{
	return (findEntryIndex(0, itemCount - 1, itemKey) >= 0)
}

template < class KeyType, class ValueType>
inline void traverse(void visit(ValueType&))
{
	for (int itr = 0; itr < itemCount; itr++)
	{
		ValueType currentItem = items[itr].getItem();

		visit(currentItem);
	}
}


Last edited on
The errors include:
name followed by "::" must be a class or namespace name on lines 97, 111, 103, 125
Also for the four lines listed it also gives an error saying ArrayDictionary:: ArrayDictionary
unable to match function definition to existing declaration

argument list for class template "ArrayDictionary" is missing on line 111

any time the variable items is uses says identifier not found

also when maxItems and itemsCount says identifier not found

destroyDictionary no matching overload function on line 146

On line 146 void destroyDictionary (void) cannot deduce template agrument for KeyType or ValueType

On line 182 '{" no matching token found





Take the first one at L97. You're trying to define the function body for ArrayDictionary default constructor. You're said that ArrayDictionary() is in the scope of the class ArrayDictionary. But class ArrayDictionary is templated. So which instance of ArrayDictionary scope are you referring?

 
inline ArrayDictionary<KeyType, ValueType>::ArrayDictionary() : itemCount(0), maxItems(DEFAULT_CAPACITY)



This is a reason why with templated classes, it's a pain to separate the class definition from the class implementation.

Also note that for a templated class, the class definition and the implementation have to be in the same file. You can't have ArrayDictionary.h and a compileable unit called ArrayDictionary.cpp
Thanks @seeplus was able to fix my code now I have 17 errors. I have posted my new code below. I' still having trouble with the variables items, maxItems, and itemsCount identifier not found. Also on line 94 it says 'typename' is not a 'class'. Then the last error I get is on line 180 saying unexpected end of file found
Last edited on
Here is my new code for ArrayDictionary.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
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
 
#include <iostream>
#include "ArrayDictionary.h"
#include "PrecondViolatedExcept.h"

template < class KeyType, class ValueType>
inline void destroyDictionary()
{
	delete[] items;

	items = new Entry[maxItems];

	itemsCount = 0;
}

template < class KeyType, class ValueType>
inline int findEntryIndex(int firstIndex, int lastIndex, const KeyType& searchKey)
{
	int IndexMiddle = firstIndex + (lastIndex - firstIndex) / 2;

	if (firstIndex > lastIndex)

		return -1;

	else if (searchKey == items[IndexMiddle].getKey())

		return IndexMiddle;

	else if (searchKey < items[IndexMiddle].getKey())

		return findEntryIndex(firstIndex, IndexMiddle - 1, searchKey);

	else

		return findEntryIndex(IndexMiddle + 1, lastIndex, searchKey);

}

template < class KeyType, class ValueType>
inline ArrayDictionary< class KeyType, class ValueType>::ArrayDictionary() : itemCount(0), maxItems(DEFAULT_CAPACITY)
{
	items = new Entry[DEFAULT_CAPACITY];
}

template < class KeyType, class ValueType>
inline ArrayDictionary< class KeyType, class ValueType>::ArrayDictionary(int maxNumberOfEntries) :
	itemCount(0), maxItems(maxNumberOfEntries)
{
	items = new Entry[maxNumberOfEntries];
}


template < class KeyType, class ValueType>
inline ArrayDictionary< class KeyType, class ValueType>::ArrayDictionary(const ArrayDictionary& dictionary) :

	itemCount(dict.itemCount), maxItems(dict.maxItems)
{
	items = new Entry[dict.maxItems];

	for (int index = 0; index < dict.itemCount; index++)
	{
		items[index] = dict.items[index];
	}
}

template < class KeyType, class ValueType>

inline ArrayDictionary< class KeyType, class ValueType>::~ArrayDictionary()
{
	destroyDictionary()
}

template < class KeyType, class ValueType>
inline bool isEmpty()
{
	return (itemCount == 0);

}

template < class KeyType, class ValueType>
inline int getNumberOfItems()
{
	return itemCount;
}

template < class KeyType, class ValueType>
inline void clear()
{
	destroyDictionary();
}


template < class KeyType, class ValueType>
inline bool ArrayDictionary<KeyType, ValueType>::add(const KeyType& searchKey, const ValueType& newValue) throw (PrecondViolatedExcep)
{
	bool ableToInsert = (itemCount < maxItems);

	if (ableToInsert)
	{
		// Make room for new entry by shifting all entries at
		// positions >= newPosition toward the end of the array
		// (no shift if newPosition == itemCount + 1). Performing
		// a binary search doesn’t help here, because we need to
		// shift the entries while looking for the insertion location.

		int index = itemCount;

		// Short-circuit evaluation is important

		while ((index > 0) && (searchKey < items[index - 1].getKey()))
		{
			items[index] = items[index - 1];
			index--;
		}  // end while

		if (searchKey != items[index - 1].getKey())
		{
			items[index] = Entry<KeyType, ValueType>(searchKey, newValue);
			itemCount++;

		}
		else
		{
			auto message = "Attempt to add entry whose search key exits in dictionary.";
			throw (PrecondViolatedExcep(message);
		}

		return ableToInsert;
	}  // end add

}

template < class KeyType, class ValueType>
inline bool remove(const const KeyType& itemKey)
{
	int currentIndex = findEntryIndex(0, itemCount - 1, itemKey);

	bool deletable = !isEmpty() && (currentIndex >= 0);

	if (deletable)
	{
		while (currentIndex < itemCount - 1)
		{
			items[currentIndex] = items[currentIndex + 1];

			currentIndex++;
		}
		itemCount--;
	}
	return deletable;
}

template < class KeyType, class ValueType>
inline ValueType getValue(const KeyType& searchKey) throw(NotFoundException)
{
	int currentIndex = findEntryIndex(0, itemCount - 1, searchKey);

	if (currentIndex < 0)
		throw NotFoundException("nnItemis not in the Dictionary!nn");

	return items[currentIndex].getItem();
}

template < class KeyType, class ValueType>
inline bool contains(const KeyType& searchKey)
{
	return (findEntryIndex(0, itemCount - 1, itemKey) >= 0)
}

template < class KeyType, class ValueType>
inline void traverse(void visit(ValueType&))
{
	for (int itr = 0; itr < itemCount; itr++)
	{
		ValueType currentItem = items[itr].getItem();

		visit(currentItem);
	}
}
Last edited on
You normally shouldn't be #including .cpp files, and you can't have template code in a .cpp (in its own compilation unit).

Just put all template definitions you have in the header file (to be #included by other files), and then we'll go from there.
You normally shouldn't be #including .cpp files

It is a management nightmare if you can't easily differentiate source files (which are given to compiler to be compiled into object files) and header files (that are merely included by one or more source files).

The filename suffix is the common way to differentiate. The .cpp are assumed to be source files. Some IDE/build systems assume that too. It is easier to name files than to write exceptions.
I taken the suggestion the only file now included are only h files. Could someone please help with the errors I had talked about above.
Have fixed some errors with my code however, the items and itemCount both say identifier not found/ undeclared variables. How do I fix there errors. Here is my new code for ArrayDictionary.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
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
#include <iostream>
#include "ArrayDictionary.h"
#include "PrecondViolatedExcept.h"

template < class KeyType, class ValueType>
void ArrayDictionary<KeyType, ValueType>::destroyDictionary()
{
	delete[] items;

	items = new Entry[maxItems];

	itemsCount = 0;
}

template < class KeyType, class ValueType>
inline int findEntryIndex(int firstIndex, int lastIndex, const KeyType& searchKey)
{
	int IndexMiddle = firstIndex + (lastIndex - firstIndex) / 2;

	if (firstIndex > lastIndex)

		return -1;

	else if (searchKey == items[IndexMiddle].getKey())

		return IndexMiddle;

	else if (searchKey < items[IndexMiddle].getKey())

		return findEntryIndex(firstIndex, IndexMiddle - 1, searchKey);

	else

		return findEntryIndex(IndexMiddle + 1, lastIndex, searchKey);

}

template < class KeyType, class ValueType>
inline ArrayDictionary<KeyType, ValueType>::ArrayDictionary() : itemCount(0), maxItems(DEFAULT_CAPACITY)
{
	items = new Entry[DEFAULT_CAPACITY];
}

template < class KeyType, class ValueType>
inline ArrayDictionary<KeyType,ValueType>::ArrayDictionary(int maxNumberOfEntries) :
	itemCount(0), maxItems(maxNumberOfEntries)
{
	items = new Entry[maxNumberOfEntries];
}


template < class KeyType, class ValueType>
inline ArrayDictionary<KeyType,ValueType>::ArrayDictionary(const ArrayDictionary& dictionary) :

	itemCount(dictionary.itemCount), maxItems(dictionary.maxItems)
{
	items = new Entry[dictionary.maxItems];

	for (int index = 0; index < dictionary.itemCount; index++)
	{
		items[index] = dictionary.items[index];
	}
}

template < class KeyType, class ValueType>

inline ArrayDictionary<KeyType, ValueType>::~ArrayDictionary()
{
	destroyDictionary();
}

template < class KeyType, class ValueType>
inline bool isEmpty()
{
	return (itemCount == 0);

}

template < class KeyType, class ValueType>
inline int getNumberOfItems()
{
	return itemCount;
}

template < class KeyType, class ValueType>
inline void ArrayDictionary<KeyType, ValueType>:: clear()
{
	destroyDictionary();
}


template < class KeyType, class ValueType>
inline bool ArrayDictionary<KeyType, ValueType>::add(const KeyType& searchKey, const ValueType& newValue) throw (PrecondViolatedExcep)
{
	bool ableToInsert = (itemCount < maxItems);

	if (ableToInsert)
	{
		// Make room for new entry by shifting all entries at
		// positions >= newPosition toward the end of the array
		// (no shift if newPosition == itemCount + 1). Performing
		// a binary search doesn’t help here, because we need to
		// shift the entries while looking for the insertion location.

		int index = itemCount;

		// Short-circuit evaluation is important

		while ((index > 0) && (searchKey < items[index - 1].getKey()))
		{
			items[index] = items[index - 1];
			index--;
		}  // end while

		if (searchKey != items[index - 1].getKey())
		{
			items[index] = Entry<KeyType, ValueType>(searchKey, newValue);
			itemCount++;

		}
		else
		{
			auto message = "Attempt to add entry whose search key exits in dictionary.";
			throw (PrecondViolatedExcep(message);
		}

		return ableToInsert;
	}  // end add

}

template < class KeyType, class ValueType>
inline bool ArrayDictionary<KeyType, ValueType>:: remove(const const KeyType& itemKey)
{
	int currentIndex = findEntryIndex(0, itemCount - 1, itemKey);

	bool deletable = !isEmpty() && (currentIndex >= 0);

	if (deletable)
	{
		while (currentIndex < itemCount - 1)
		{
			items[currentIndex] = items[currentIndex + 1];

			currentIndex++;
		}
		itemCount--;
	}
	return deletable;
}

template < class KeyType, class ValueType>
inline ValueType getValue(const KeyType& searchKey) throw(NotFoundException)
{
	int currentIndex = findEntryIndex(0, itemCount - 1, searchKey);

	if (currentIndex < 0)
		throw NotFoundException("nnItemis not in the Dictionary!nn");

	return items[currentIndex].getItem();
}

template < class KeyType, class ValueType>
inline bool contains(const KeyType& searchKey)
{
	return (findEntryIndex(0, itemCount - 1, itemKey) >= 0)
}

template < class KeyType, class ValueType>
inline void traverse(void visit(ValueType&))
{
	for (int itr = 0; itr < itemCount; itr++)
	{
		ValueType currentItem = items[itr].getItem();

		visit(currentItem);
	}
}

You still have const errors on
isEmpty()
findEntryIndex()
getValue()
contains()
traverse()

If your declaration says the function is const, the definition must also be const.

Topic archived. No new replies allowed.