This assignment will give you experience with implementing C++ classes. Possibly motivated by the CREATE Institute at MSOE, you have decided to build a general-purpose match-making application that takes the names of two groups of students and uses an algorithm to determine perfect matches for any activity from tandem kayaking to catching a musical at the Performing Arts Center. Unfortunately, you failed to realize the effort required to build a matching application and decide to use a trivial method: two students match if their names have a letter in common or they have the same day of birth. You are going to write C++ classes to solve your problem. This is an individual assignment.
This has been broken into steps with the idea that you can just start on the first step without reading the full writeup. But feel free to read it through at the start if you want!
main.cpp
into the folder. This will overwrite
the old main.cpp
with the new version.
pool.h
and pool.cpp
. For
pool.h
, select File | New | C/C++ Header File. For
pool.cpp
, use C/C++ Source File.
pool.cpp
and see if there is a menu item Add
‘pool.cpp’ to CMake Project; if so, click on it. Note you do not do
this with pool.h
.
pool.h
: Student
and Pool
. For now,
put no data in the classes.Student
. You will need to be able to create a
Student
object with just a string (the student's name) and also
with both a string and an integer (the day of birth). You can use
default arguments if you like. You will refine these below.Student
methods:
printableDescription
which takes no arguments and
returns a string.matches
which takes a pointer to a Student
object and
returns a boolean value.*
, not &
to declare a pointer;
declaring a reference instead will create problems throughout the
assignment.Pool
. There needs to be a constructor with no
arguments and a constructor with a string argument (representing a
student's name) and an optional integer argument (representing the
day of the month the student was born). The integer argument
defaults to 0.Pool
methods:
add
that takes a string as an argument.add
that takes a string and an integer as
arguments. You could combine this with the previous one and use
default values.readStudents
that takes no arguments.printMatches
that takes a Student
pointer as an
argument.printMatches
that takes a Pool
pointer as an
argument.empty
method that takes no arguments and returns a boolean
value.Student
and Pool
methods, but
main.cpp
should have no errors in it. You will likely need to
include additional library code and make other changes. You should
not change main.cpp
.#include
for pool.h
in main.cpp
. This
will break the build. Fix it by adding the appropriate "#ifndef
magic" to pool.h
. See the phonebook
project for an example.Student
and Pool
to pool.cpp
. A
stub is either an empty body or a body that returns a constant
result (for example, always returns true).Add code to read all data. This will require adding private data in the
class definitions (in pool.h
) and appropriate implementations in
pool.cpp
.
Student
so it holds a name and the day of the month the
student was born. The day will be between 0 and 31 with 0 meaning
"no information".Student
constructors. The constructor which takes
arguments initializes the pool to contain a student with that name
and day. Recall the day defaults to 0.printableDescription
to return the name. If the day
number is greater than 0, follow this by " born on day X" where X
is the day number. Use std::to_string
to convert the number into a
string.matches
to return true
if the birth day numbers are
both greater than 0 and they match or any character in one of the
names is also in the other student's name (ignoring underscores).Pool
. The array must allow up
to 20 students. You will also need a counter of the actual number of
students in the pool. Note: this must use regular arrays; no
vector
or similar container classes.add
methods to create Student
objects and add them
to the pool.readStudents
so it reads student names and birth days
from standard input until either end-of-file is reached or the text
"END" is read; note that names are written as single words with
'_' used to separate parts of the name. Assume each name is
followed by an integer, and read that integer as the birth day. You
do not have to test for the birth day being out of range. Each of
the first 20 students is to be added to the pool. You can
assume that if there is a name in the input, it is followed by an
integer. This includes the word END. See input1.txt
for an example.readStudents
finds more than 20 students before "END", ignore
the additional students. That is, continue to read students until
you reach END, but do not add them too the pool.Student
objects in the pool with the same name.input1.txt
. It will not do
anything at this point, but it should at least run without crashing.
See the directions from assignment 1 to
set your run configuration to read from the file.When you are finished, your classes will match the structure shown in this diagram:
Note this captures just the minimal data and methods. You can add private data and private methods. In fact, it is almost necessary to add other private elements to avoid duplicating code.
This stage will lead you through printing matches for simple cases. More complex cases will be handled in later stages.
Implement empty
to return the appropriate result.
Implement the version of printMatches
that takes a Student
argument and cycles through the whole pool, printing
A perfect match for X: Y
(where X
is the name passed to printMatches
and Y
is a name in
the pool) for each matching student. The rules for whether two
students match are given below. When printing names, print a space
instead of an underscore. This likely means changing
printDescription
to handle underscores. You might find it handy to
create a printable version of the name and/or description as private
data in Student
.
Implement the second version of printMatches
so it prints all
matches between this
and the second pool. Process the students in
the current object (the one pointed to by this
) in the order they
are in the array, and for each one call printMatches
on the second
pool.
The rules for matching have a number of elements:
_
' (underscore) when matching. For example, "a_men"
and "y_xi" would not match.Note your main
is configured so if the first name is TEST
, the
program runs simple tests and exits without processing any additional
input. You can use this to do some basic testing at the start.
These should be satisfied by doing the above, but just in case...
All code you write will be in one of two files: pool.h
and pool.cpp
.
The classes will be defined in pool.h
.
pool.h
must include the #ifndef
magic to ensure the file can
be included multiple times without errors. Do not use #pragma
.
You must add method documentation in pool.h
for all Pool
methods. The Student
class is simple enough that additional
documentation is not likely to be helpful.
Implementations of all constructors and methods must be in pool.cpp
.
Since the goal of this assignment is to give you experience with
built-in arrays, declare any arrays using []
rather than some
container class such as std::vector
. For instance, if your code has
an array of integers, declare it as
constexpr int MAX_NUMBERS = 100;
int numbers[MAX_NUMBERS];
You must use std::string
(which you can write as string
if you
write using namespace std;
) to store names.
Do not add public data to either classes; all data must be private.
Use pointers for all Student
and Pool
objects (since they have
"identity"), but you do not need to use pointers for string
values.
Follow the DRY principle: do not repeat yourself. If there is a method
that is doing an operation, do not repeat the code for the operation
in another method. For example, consider calling the add
method from
readStudents
.
Do not use <algorithm>
in your solution. (Most students would never
be tempted, but it is easy to find code suggesting using this library
online. However, we want you to do this lab using more standard
programming techniques.)
Do not add public methods to class Pool other than the methods discussed above. Likewise, do not add additional constructors except the one mentioned here. You can add private or protected methods.
Note that your solution will probably use newer features of C++, so if
your compiler defaults to a newer version then add the -std=c++17
option when building.
The input files typically have a list of names followed by END
followed by another list of names. main
creates two pools, calling
readStudents
for both, so the first END marks the division between
the pools.
Given std::string x;
and cin >> x;
x
will be the next "word", a sequence of characters ending with a
space or newline. You will not need to remove any trailing newlines.
You will likely find the functions tolower
and/or toupper
useful
for this assignment. The code
char c;
cin >> c;
cout << toupper(c);
will read any type of character and print it out. If it is any non-letter, it will print the character unchanged. If it is a letter, it will print the uppercase form of the letter. You can use these in a loop to convert all of the letters in a string to either upper or lower case.
Do not use reference parameters in this assignment. A single &
should not appear in pool.h
or pool.cpp
. Note you may need a
double &&
when doing a logical and, but you will not need &
to
pass reference variables.
If you wish, you can add const
to the appropriate methods and
parameters, but this is not required and will not change your score.
You do not need to worry about memory management for this assignment.
That is, you do not need to use delete
.
Do not change main.cpp
.
pool.cpp
as
"Main" and pool.h
as an extra file - esubmit will automatically
compile the provided main.cpp
and it will include your code.
esubmit
already has! In
particular, do not submit main.cpp
for this assignment..This is not a complete list, but provides easy access to many of the tests.
input1.txt
generates output1.txt
input2.txt
generates output2.txt
-
the input is essentially ignored in this case because the "TEST"
runs all of the test code.input3.txt
generates output3.txt
input4.txt
generates output4.txt
input5.txt
generates output5.txt
input6.txt
generates output6.txt
input7.txt
generates output7.txt
input8.txt
generates output8.txt
input9.txt
generates output9.txt