194 lines
No EOL
6.2 KiB
Text
194 lines
No EOL
6.2 KiB
Text
[](https://classroom.github.com/a/_bYEbrbV)
|
|
:sectnums:
|
|
:nofooter:
|
|
:toc: left
|
|
:icons: font
|
|
:data-uri:
|
|
:source-highlighter: highlightjs
|
|
:stem: latexmath
|
|
|
|
= Col.03 -- Santa Claus Inc.
|
|
|
|
The Santa Claus Inc. company is preparing a very extensive delivery tour for Christmas.
|
|
Your task is to implement a tour planning software which will:
|
|
|
|
* Determine how many and which presents each child will receive
|
|
* Load & prepare the sleighs
|
|
** Due to a recent efficiency program several Santa clones are available to operate multiple sleighs
|
|
* Send the sleighs on delivery tours to the various cities
|
|
* Prints the tour logs of the sleighs
|
|
|
|
image::pics/santa.png[Santa's Sleigh]
|
|
|
|
== Implementation
|
|
|
|
.Logic
|
|
[plantuml]
|
|
----
|
|
@startuml
|
|
hide empty fields
|
|
hide empty methods
|
|
|
|
class GoodAndNaughtyList {
|
|
+GoodAndNaughtyList(List<ChildInfo>)
|
|
+List<ChildInfo> GetChildrenByCity(string)
|
|
+List<string> GetAllCities()
|
|
{static} +int CalcParcels(double)
|
|
}
|
|
class ChildInfo {
|
|
+string Name [readonly]
|
|
+int Age [readonly]
|
|
+string City [readonly]
|
|
+int HouseId [readonly]
|
|
+double GoodOrNaughty [readonly]
|
|
}
|
|
class Parcel {
|
|
+ChildInfo ForChild [readonly]
|
|
+string Description [readonly]
|
|
|
|
+string ToString() [override]
|
|
}
|
|
class Sleigh {
|
|
+string TargetCity [readonly]
|
|
|
|
+Sleigh(int, string)
|
|
+bool Load(Stack<Parcel>)
|
|
+List<string> ExecuteTour()
|
|
}
|
|
|
|
Parcel "n" -l- "1" ChildInfo
|
|
Sleigh "1" -d- "n" Parcel
|
|
GoodAndNaughtyList "1" -- "n" ChildInfo
|
|
|
|
@enduml
|
|
----
|
|
|
|
.Utility
|
|
[plantuml]
|
|
----
|
|
@startuml
|
|
hide empty fields
|
|
hide empty methods
|
|
|
|
class List<TValue> {
|
|
+int InitialCapacity [const]
|
|
+int Count [private set]
|
|
+int Capacity [readonly]
|
|
+TValue? this[int index]
|
|
|
|
+List()
|
|
+void Add(TValue)
|
|
}
|
|
class Stack<TValue> {
|
|
+int Count [private set]
|
|
|
|
+Stack()
|
|
+void Push(TValue)
|
|
+TValue? Peek()
|
|
+TValue? Pop()
|
|
}
|
|
class Preparation {
|
|
{static} +List<Sleigh> PrepareTours(GoodAndNaughtyList)
|
|
}
|
|
class RandomProvider {
|
|
{static} +Random Random
|
|
}
|
|
|
|
@enduml
|
|
----
|
|
|
|
NOTE: As usual extensive XMLDoc & Unit Tests have been provided
|
|
|
|
=== Collections
|
|
|
|
* To support the complex logic this application requires, supporting collections need to be _implemented_
|
|
* These collections have to be implemented in a _generic_ fashion
|
|
|
|
==== List
|
|
|
|
* Implement as an _array list_
|
|
* It has to be _generic_, accepting a `TValue` _type parameter_
|
|
* The initial size is `4`
|
|
* The growth factor is `1.5`
|
|
** If the calculated size is not a whole number round _up_ to the next whole number
|
|
* Provides an _indexer_
|
|
** If an invalid index is supplied the `default` value of the `TValue` type parameter is returned
|
|
|
|
TIP: You do _not_ have to implement additional methods like `Remove` or `Contains`
|
|
|
|
==== Stack
|
|
|
|
* Implement a stack based on _nodes_ and _pointers_
|
|
** You could add a _private_ node class
|
|
* It has to be generic, accepting a `TValue` type parameter
|
|
* Implement _correctly_:
|
|
** `Push`
|
|
** `Peek`
|
|
** `Pop`
|
|
* If the stack is empty `Peek` & `Pop` return the `default` value of the `TValue` type
|
|
|
|
=== Tour Planning Logic
|
|
|
|
* Read the provided XMLDoc carefully
|
|
* The following contains some additional explanations & clarifications for some parts of the implementation
|
|
|
|
CAUTION: Just in case it is not clear enough for someone: you must _not_ use framework collections, but only those you implemented yourself in this assignment
|
|
|
|
==== `GoodAndNaughtyList`
|
|
|
|
* The 'good or naughty' rating of a child is multiplied by `1.5` to determine the amount of presents which will be allocated for that child
|
|
** A _negative_ (very naughty) rating does _not_ lead to the child having to give Santa presents 😉
|
|
*** => the min. amount is `0`
|
|
** The amount of presents is rounded _down_ to the next whole number
|
|
** Only 'whole' presents are allocated -- no '0.6 presents' or something like that
|
|
* `GetAllCities` returns a _distinct_ list of city names
|
|
|
|
==== `Parcel`
|
|
|
|
* The `ToString` implementation follows the format `<Description> for <ChildName> (age <ChildAge>)`
|
|
** Example: `Watercolors for Josef (age 9)`
|
|
|
|
==== `Preparation`
|
|
|
|
* There is a defined set of possible toys which can be used in presents
|
|
* For each present one of the toys is selected by random
|
|
** Use `RandomProvider` for the selection logic
|
|
* For each city a single sleigh is prepared
|
|
** Make sure to set the capacity of the sleigh big enough to hold all parcel piles for all children who will receive at least one present in this city -- sleighs use advanced magic technology, so the size can be easily set as required
|
|
* For each child a dedicated pile of presents is prepared
|
|
** That pile has a minimal size of one, but can contain many more presents
|
|
** Each child has exactly one pile of presents
|
|
** No pile of presents contains presents of different children
|
|
** The amount of presents is determined by the 'good or naughty' value of each child
|
|
* Those piles loaded first on the sleigh will be delivered last
|
|
** Those loaded last will be removed first
|
|
|
|
TIP: A sleigh is a _stack of stacks_
|
|
|
|
==== `RandomProvider`
|
|
|
|
You don't have to implement anything here.
|
|
But you should read up on https://learn.microsoft.com/en-us/dotnet/api/system.random.shared?view=net-9.0[`Random.Shared`].
|
|
|
|
==== `Sleigh`
|
|
|
|
* Several aspects of the sleighs have already been explained in previous sections
|
|
* When the sleigh executes its tour delivering all the presents to the deserving, good children it creates a log entry for each of the steps
|
|
** First it travels to a city
|
|
** Then to the house of the first child
|
|
** Then it delivers all the presents
|
|
** Then moves to the next house
|
|
** ...
|
|
** Once all presents have been delivered it returns home to the north-pole
|
|
* Each step gets assigned a unique, incrementing step number
|
|
* Be careful with the _indentation_ of the various log messages
|
|
** 'Inner' steps are indented more than 'outer' steps
|
|
** See the sample run output for an example
|
|
* The log entries are kept in a `List`
|
|
|
|
== Program & Sample Run
|
|
|
|
A `Program` file has been provided.
|
|
Executing it after implementing all required pieces should result in an output similar to the following -- toy selection can vary due to randomized generation.
|
|
|
|
image::pics/sample_run.png[Sample Run] |