__MACOSX/._WS03
WS03/.DS_Store
__MACOSX/WS03/._.DS_Store
__MACOSX/WS03/._part 2
WS03
eadme.md
# Workshop 3: Templates
In this workshop, you design and code several class templates and test them on different instantiations.
## Learning Outcomes
Upon successful completion of this workshop, you will have demonstrated the abilities to:
- design and code a class template
- template a class variable
- specialize a templated class variable for a particular type
- instantiate a template class
- specialize a member function of a templated class to process a particular type
- derive a templated class from another templated class
## Submission Policy
The workshop is divided into two coding parts and one non-coding part:
- *Part 1*: worth 0% of the workshop's total mark, is optional and designed to assist you in completing the second part.
- *Part 2*: worth 100% of the workshop's total mark, is due on **Sunday at 23:59:59** of the week of your scheduled lab. Submissions of *Part 2* that do not contain the *reflection* are not considered valid submissions and are ignored.
- *reflection*: non-coding part, to be submitted together with *Part 2*. The reflection does not have marks associated to it, but can incur a **penalty of max 40% of the whole workshop's mark** if your professor deems it insufficient (you make your marks from the code, but you can lose some on the reflection).
The workshop should contain ***only work done by you this term*** or provided by your professor. Work done in another term (by you or somebody else), or work done by somebody else and not **clearly identified/cited** is considered plagiarism, in violation of the Academic Integrity Policy.
Every file that you submit must contain (as a comment) at the top **your name**, **your Seneca email**, **Seneca Student ID** and the **date** when you completed the work.
- If the file contains only your work, or work provided to you by your professor, add the following message as a comment at the top of the file:
> I have done all the coding by myself and only copied the code that my professor provided to complete my workshops and assignments.
- If the file contains work that is not yours (you found it online or somebody provided it to you), **write exactly which parts of the assignment are given to you as help, who gave it to you, or which source you received it from.** By doing this you will only lose the mark for the parts you got help for, and the person helping you will be clear of any wrong doing.
## Compiling and Testing Your Program
All your code should be compiled using this command on `matrix`:
```bash
us
local/gcc/10.2.0
in/g++ -Wall -std=c++17 -g -o ws file1.cpp file2.cpp ...
```
- `-Wall`: compiler will report all warnings
- `-std=c++17`: the code will be compiled using the C++17 standard
- `-g`: the executable file will contain debugging symbols, allowing *valgrind* to create better reports
- `-o ws`: the compiled application will be named `ws`
After compiling and testing your code, run your program as following to check for possible memory leaks (assuming your executable name is `ws`):
```bash
valgrind ws
```
To check the output, use a program that can compare text files. Search online for such a program for your platform, or use *diff* available on `matrix`.
## Part 1 (0%)
This workshop consists of five modules:
- `w3` (supplied)
- `Set`
- `Pair`
- `SetSummable`
- `PairSummable`
The solution to Part 1 invokes the first three modules.
Enclose all your source code within the `sdds` namespace and include the necessary guards in each header file.
All the modules **you create** in this workshop must have only a header file. *🗎 Explain in the reflection why we do not split a module into `*.h` and `*.cpp` like you did in the previous workshops.*
In all classes that you create, you are allowed to add any **private** members that your design requires (without changing the specs)!
### `w3` Module (supplied)
**Do not modify this module!** Look at the code and make sure you understand how to instantiate a templated class.
### `Set` Module
This module represents a family of collections of elements of any data type (for example, sets of `int`s, or sets of `Student`s, etc.).
Design and code a class template named `Set`. Your template manages a statically allocated a
ay of any datatype. The template parameters in order of their specification are:
- `N`: the capacity of the collection (a non-type parameter; an integer without sign). This is the maximum number of elements that can be added to the collection
- `T`: the type of any element in the collection
Your design keeps track of the cu
ent number of elements stored in the collection (which may differ from the capacity of the collection (`N`)). Initially the collection has no elements.
**This module should not use or know the type `Pair`!!**
***Public Members***
- `size_t size() const`: returns the cu
ent number of elements in the collection
- `const T& get(size_t idx) const`: returns a reference to the element at index `idx` of the statically allocated a
ay (assume that the parameter is valid).
- `void operator+=(const T& item)`: if the collection has capacity for another element, adds a copy of `item` to the collection. Otherwise, does nothing.
Add any other **private** members that your design requires (without changing the specs above)!
### `Pair` Module
This module represents a family of *value-key* pairs.
Design and code a class template named `Pair`. Your template manages a single *value-key* pair. The template parameters (in order) identify the type of the value and the type of the key that constitute a `Pair` object:
- `V`: the type of the value
- `K`: the type of the key
**This module should not use or know the type `Set`!!**
***Public Members***
- default constructo
- `Pair(const K& key, const V& value)`: copies the values refe
ed to by the parameters into the instance variables
- `const V& value() const`: returns the **value** component of the pai
- `const K& key() const`: returns the **key** component of the pai
- `void display(std::ostream& os) const`: inserts into stream `os` the key and the value of the pair in the following format
```
KEY : VALUE
```
***Free Helper***
- `std::ostream& operato
(std::ostream& os, const Pai
V, K>& pair)`: calls the membe
function `display()` on `pair` to insert a pair into stream `os`.
Add any other **private** members that your design requires (without changing the specs above)!
### Sample Output
When the program is started with the command (the file `sales.txt` is provided):
```
ws sales.txt
```
the output should look like the one from the `sample_output.txt` file.
### Test Your Code
To test the execution of your program, use the same data as shown in the output example above.
Upload your source code to your `matrix` account. Compile and run your code using the latest version of the `g++` compiler (available at `/us
local/gcc/10.2.0
in/g++`) and make sure that everything works properly.
Then, run the following command from your account (replace `profname.proflastname` with your professor’s Seneca userid):
```
~profname.proflastname/submit 345_w3_p1
```
and follow the instructions.
***This part represents a milestone in completing the workshop and is not marked!***
## Part 2 (100%)
The second part of this workshop upgrades your Part 1 solution to
- align the key and value output in pretty columnar format
- accumulate the values stored in a `Set` object, for a specified key, which serves as the filter for selecting elements from the `Set`
To implement each upgrade, you will derive templated classes from your original templated classes (one derived class from `Set` and one derived class from `Pair`) and specialize the class derived from `Pair` as described below.
### `Pair` Module
Modify the `display()` member function in the `Pair` module to enable inclusion polymorphism on the `Pair` hierarchy.
No other changes are necessary to this module.
### `PairSummable` Module
A new module called `PairSummable` represents a `Pair` that has key alignment, compatibility and summation functionality.
Derive the `PairSummable` class template from `Pai
V, K>`. Your template receives 2 template parameters:
- `V`: the type of the value
- `K`: the type of the key
**This module should not use or know the type `Set` or `SetSummable`!!**
***Static Private Members for `PairSummable`***
- an object of type `V` that holds the *initial value* for a summation. The initial value varies with the type of the value in the value-key pair.
- a variable of type `size_t` that holds the minimum field width for pretty columnar output of key-value pairs (initialize it with 0). This is the minimum number of characters needed to display any key in a set of keys.
This value must be updated every time a new pair is constructed.
***Public Members for `PairSummable`***
- default constructo
- `PairSummable(const K& key, const V& value = initial)`: calls the base class constructor passing the two parameters to it, and updates the field width if necessary. *🗎 Explain in the reflection what `= initial` in the prototype means.*
- This function assumes that the type `K` supports a function named `size()`, which returns the number of characters required to display `key`. Use this function to determine if the field width must be updated.
- `bool isCompatibleWith(const PairSummable
& b) const`: returns *true* if the parameter has the same `key` as the cu
ent object, *false* otherwise.
- overload the `operator+=` to receive a reference to an unmodifiable `PairSummable` object. This function adds the `value` of the parameter object to the `value` of the cu
ent object and returns a reference to the cu
ent object. Assume that the cu
ent object and the parameter have the same `key`.
- ove
ide the `display()` query to set the alignment to left and the field width to the value of the static attribute (see above, in the static members section) for all `K` types, then call the base class version of `display()`, and finally restore the alignment to right.
***Specializations***
- for `V = std::string` and `K = std::string`, the function `operator+=()` should concatenate the values stored using `", "` as a separator (use operator `+` to concatenate strings), for the result shown in the sample output.
### `Set` Module
The `Set` module doesn't require any change.
### `SetSummable` Module
A new module called `SetSummable` represents a collection that is summable on a subset of the collection.
Derive the `SetSummable` class template from your `Set` template. Your new template has 2 template parameters (in order):
- `N`: the capacity of the collection (an integer without sign)
- `T`: the type of any element in the collection
Your design assumes that the type `T`:
- has a constructor that accepts an `std::string` as a parameter, which specifies the filter for identifying the elements that belong to the subset.
- has a member function named `isCompatibleWith`, which returns *true* if the object is compatible with an object of type `T`; *false* otherwise.
- supports the `operator+=` operation, which adds an object of type `T` to another object of type `T`.
**This module should