[G_PRO] Basis Programmeren en OO Programmeren
DigitAP
  • Welkom
  • Inleiding
    • Benodigdheden
    • Afspraken code
    • Afspraken oefeningen
    • Nuttige extras
    • Dankwoord
    • Mee helpen?
  • Semester 1: Programming Principles
    • H1: Werken met Visual Studio
      • Introductie tot C#
      • Visual Studio en .NET Core installeren
      • Een C# project maken in Visual Studio
      • Fouten in je code
      • Je eerste stappen in C#
      • Input/Output: ReadLine/WriteLine
      • Kleuren in Console
      • Oefeningen
    • H2: Variabelen en datatypes
      • De syntaxis van C#
      • Datatypes
      • Variabelen
      • Expressies en operators
      • Oefeningen
    • H3: Strings en hun methoden
      • Strings
      • Strings samenvoegen
      • Omzetten van en naar strings
      • Functionaliteit van strings
      • Oefeningen
    • H4: Beslissingen
      • Beslissingen intro
      • Enkelvoudige booleaanse expressies
      • If, else, else if
      • Samengestelde booleaanse expressies
      • Scope van variabelen
      • Switch
      • Oefeningen
    • H5: Loops
      • Loops intro
      • While en Do While
      • For
      • Debuggen
      • Oefeningen
    • H6: Arrays
      • Array principes
      • Alternatieve syntax
      • Werken met arrays
      • Defaultwaarden
      • List<T>
      • Oefeningen
    • H7: Methoden
      • Methoden intro
      • Parameters
      • Return waarden
      • Geavanceerde methoden
      • Oefeningen
    • Intermezzo: TextCell
    • H8: Numerieke data
      • De Math klasse
      • Random
      • Casting en conversie
      • Oefeningen
    • H9: Meerdimensionaal werken
      • N-dimensionale arrays
      • Geneste iteratie
      • Oefeningen
    • H10: Gevorderde tekstverwerking
      • Voorstelling van tekst
      • Interpolatie met formattering
      • Werken met arrays van strings
      • Input en output van tekstbestanden
      • Oefeningen
    • Afsluiter: TextCell2D
  • Semester 2 : OOP
    • H10: Klassen en objecten
      • OOP Intro
      • Klassen en objecten aanmaken
      • DateTime: leren werken met objecten
      • Enumeraties: nog een eigen datatype
      • Klassen en objecten weergeven deel 1
      • Attributen
      • Methoden
      • Access modifiers
      • Properties
      • Oefeningen
    • H11: Objecten (al dan niet) aanmaken
      • Constructors
      • Spelen met strings
      • Oefeningen
    • H12: Geheugenmanagement bij klassen
      • value en reference met eigen objecten
      • nullable value types
      • NullReference exception
      • Oefeningen
    • H13: Datastructuren
      • Foreach en var
      • List
      • Dictionary
      • Immutable datastructuren
      • Verdere datastructuren
      • Oefeningen
    • H14: Overerving
      • Overerving intro
      • Virtual en override
      • Abstract
      • Constructors bij overerving
      • Oefeningen
    • H15: Geavanceerde overerving
      • protected access modifier
      • Base keyword
      • System.Object
      • Oefeningen
    • H16: Exception handling
      • Werken met exceptions
      • Zelf uitzonderingen maken
      • Wanneer exceptions en handling gebruiken
      • Oefeningen
    • H17: Polymorfisme en interfaces
      • Polymorfisme
      • Polymorfisme in de praktijk
      • Interfaces
      • Losse koppeling
      • Oefeningen
    • H18: Testing
      • Intro Testing
      • Wat is Unit Testing
      • Waarom Unit Testing?
      • Wanneer Unit Testing?
      • Schrijven van een unit test: AAA methode
      • Eerste voorbeeld: Sum
      • Assert
      • Oefening even of oneven getal
      • TestInitialize en DataRows
      • Oefening BMI
      • Exception testing
      • Oefening BMI exception
      • Oefening SchoolAdmin test null-waarden en TestCleanup
      • Oefening SchoolAdmin test equals
      • Oefening SchoolAdmin test cursus zoeken met id
      • Dependencies bij Unit Testing
      • Mocking
      • Oefeningen Mocking
      • Test Driven Development
      • Class Library
      • Oefeningen TDD
    • H19: SOLID
      • Single Responsibility Principle (SRP)
      • Open/Closed Principle (OCP)
      • Liskov Substitution Principle (LSP)
      • Interface Segregation Principle (ISP)
      • Dependency Inversion Principle (DIP)
  • Appendix
    • Visual Studio Tips & Tricks
    • Ea-ict coding guidelines
    • Oefeningen kerkhof
  • Semester 1 appendix
    • Nice to know stuff
      • Out en Ref parameters
      • Jagged arrays
    • All-In-Projecten
      • Overzicht
      • Console Matrix
      • Ascii filmpjes maken met loops
      • Ascii filmpjes maken met methoden
      • Fun with methods: een verhaalgenerator
      • Tekst-gebaseerd Maze game
      • Conway game of life
  • Semester 2 appendix
    • Operator overloading
    • Object Initializer Syntax
    • Compositie en aggregatie
    • Nice to know stuff
      • Klassen herbruiken
      • Expression bodied members
    • All-In-Projecten
      • Overzicht
      • OO Textbased Game
      • War Simulator
      • Map Maker
      • Magic The Gathering API
      • SchoolAdmin
  • Pro (geen leerstof en/of in opbouw)
    • Bitwise operators
    • Generics en collections
      • Generics methoden en types
      • Generic classes en constraints
      • Collections
      • Labo-oefeningen
    • Events
      • Events
      • Chat server
    • Software engineering
      • SOLID
Powered by GitBook
On this page
  • h15-Orders-bugfix
  • Functionele analyse
  • Technische analyse
  • Voorbeeldinteractie
  • h15-Pizza
  • Functionele analyse
  • Technische analyse
  • Voorbeeldinteractie
  • h15-Menu
  • Functionele analyse
  • Technische analyse
  • Voorbeeldinteractie
  • Uitbreidingen SchoolAdmin
  • H15_1 SchoolAdmin: Vergelijkbare objecten
  • H15_2 SchoolAdmin: ToString
  • H15_3 SchoolAdmin: Eenmaking statische lijsten personen
  • H15_4 SchoolAdmin: Tweerichtingsverkeer voor CourseRegistration
  • H15_5 SchoolAdmin: Cursussen in semesters
  • H15_6 SchoolAdmin: Manueel data invoeren
Export as PDF
  1. Semester 2 : OOP
  2. H15: Geavanceerde overerving

Oefeningen

h15-Orders-bugfix

Functionele analyse

We schrijven een bestelsysteem. We kunnen gewone bestellingen en internationale bestellingen plaatsen. Voor internationale bestellingen wordt een extra kost van 10% aangerekend, maar is er wel korting voor grote bestellingen. We willen de prijzen van onze producten niet publiek zichtbaar maken, want dat verhindert prijsafspraken.

Technische analyse

Schrijf een klasse 0rder met een uint property Numberen een double privé-attribuut unitPrice. Voorzie ook een overschrijfbare computed property TotalPrice, namelijk het aantal maal de basisprijs. Voeg een constructor toe met het aantal en de basisprijs als parameters.

Schrijf daarna een subklasse InternationalOrder die de totaalprijs bepaalt door de basisprijs met 10% te verhogen, maar vanaf 100 stuks een vlakke korting van 1000 euro toepast. Dit zal niet meteen werken! Doe een zo klein mogelijke aanpassing om het toch te doen werken.

Schrijf een methode DemoOrdersin de klasse Inheritance. Hierin vraag je of de gebruiker een gewone of internationale bestelling wil plaatsen, vraag je om het aantal en de basisprijs en toon je dan de totaalprijs.

Voorbeeldinteractie

Aantal stuks?
> 150
Basisprijs?
> 200
Gewone bestelling (1) of internationale bestelling (2)?
> 2
Totaalprijs: 32000,00 

h15-Pizza

Functionele analyse

We schrijven software om bestellingen van pizza's op te volgen. Deze software spreekt met andere software, bijvoorbeeld van Deliveroo of Uber Eats. We willen niet dat die diensten iets kunnen aanpassen aan de ingrediënten van onze pizza's, maar we willen wel zelf allerlei pizza's kunnen samenstellen.

Technische analyse

Je krijgt volgende klasse Pizza:

internal abstract class Pizza
    {
        private List<string> Ingredients;

        public Pizza(string[] extraToppings)
        {
            this.Ingredients = new List<string> { "deeg", "tomatensaus", "kaas" };
            foreach (var topping in extraToppings)
            {
                this.Ingredients.Add(topping);
            }
        }

        public abstract double UnitPrice
        {
            get;
        }

        public double Price
        {
            get
            {
                return this.UnitPrice + (this.Ingredients.Count * 0.5);
            }
        }

        public void ShowIngredients()
        {
            foreach (var ingredient in Ingredients)
            {
                Console.WriteLine(ingredient);
            }
        }

    }
```

Schrijf nu twee klassen Margherita en Veggie die overerven van Pizza, met basisprijs (UnitPrice) 5 en 6. Bij constructie krijgt een Margherita sowieso "mozzarella" toegevoegd aan de lijst met ingrediënten en krijgt een Veggie sowieso "tofu" en "spinazie", maar geen "kaas". Je moet hierbij een aanpassing doen aan Pizza, maar hou ze zo klein mogelijk. Het blijft de bedoeling dat een pizza standaard ook kaas bevat, dus schrijf je code zodat de veggie pizza dit ingrediënt verwijdert. Schrijf een demonstratiemethode DemoPizzas in de klasse Inheritance.

Voorbeeldinteractie

h15-Menu

Functionele analyse

We willen een digitale menukaart tonen in een online restaurant. Op deze kaart verschijnen gerechten in een standaardformaat. Kindergerechten volgen hetzelfde formaat, maar verschijnen in kleur.

Technische analyse

  • Schrijf een klasse Mealmet:

    • properties Nameen Price(deze laatste van type double).

    • een constructor met de naam en de prijs.

    • methode ShowTheMenu: dezeprint de naam, gevolgd door 3 tabs, gevolgd door de prijs

  • Schrijf een kindklasse ChildrenMeal

    • Dit werkt hetzelfde als een gewoon gerecht, maar de weergave op het menu gebruikt een willekeurige kleur. Als we bijvoorbeeld het aantal tabs aanpassen naar 5, moet ChildrenMeal zonder aanpassingen mee volgen. Je kan een willekeurige kleur krijgen door een willekeurig getal tussen 1 en 15 te bepalen en dat dan te casten naar een waarde van de enum ConsoleColor.

  • Maak een methode DemoMeals in de klasse Inheritance. Hierin maak je een lijst met minstens 4 gerechten (waarvan minstens 2 kindergerechten) naar keuze en doorloop je de lijst zodat elk gerecht getoond wordt op het menu.

Voorbeeldinteractie

Tabs zijn eigenlijk niet ideaal. Zoek, als je sneller klaar bent, uit hoe je stringformattering kan gebruiken om de naam van elk gerecht met exact 35 tekens weer te geven.

Uitbreidingen SchoolAdmin

In de volgende stappen, zullen we SchoolAdmin verder uitbouwen. Volgend diagram toont het hele project na al deze wijzigingen:

H15_1 SchoolAdmin: Vergelijkbare objecten

Functionele analyse

We willen kunnen nagaan of een van de objecten niet dubbel voorkomt in de lijst met geregistreerde objecten.

Technische analyse

Voorzie Person en Course van een eigen versie van Equals.

Een persoon is gelijk aan een andere persoon met hetzelfde ID. Je hoeft hier niet na te gaan dat de objecten van exact hetzelfde type zijn. In plaats daarvan kan je schrijven: if (obj is Person) { ... } Test ook op de null-waarde.

Een cursus is gelijk aan een andere cursus met hetzelfde ID.

Voorzie ook overal een hash code volgens de vuistregel in de cursus (gebruik het Id).

H15_2 SchoolAdmin: ToString

Functionele analyse

We willen van alle personen een tekstje met info over de persoon kunnen tonen.

Technische analyse

Voorzie Person van een ToString methode die een resultaat van volgende vorm toont:

Zorg dat de concrete klassen hier ook het statuut van de persoon aan koppelen, bijvoorbeeld:

Doe dit niet met GetType, want dan is de schrijfwijze anders. Schrijf het statuut letterlijk in de code per klasse.

H15_3 SchoolAdmin: Eenmaking statische lijsten personen

Functionele analyse

Je hebt momenteel volgende statische properties voor (immutable) lijsten met personen:

  • AllPersons

  • AllLecturers

  • AlleStudents

  • AllEmployees

  • AllAdministrativePersonnel

Het is niet ideaal om al deze lijsten te hebben. Elke persoon wordt nu op twee of drie plaatsen bijgehouden, dus als je het systeem zou aanpassen om personen te verwijderen, moet je er aan denken dat op twee of drie plaatsen te doen. Als je klassen zoals GuestLecturer, ExchangeStudentof ScheduleManagerzou toevoegen, zou je dat zelfs op nog meer plaatsen moeten doen.

Technische analyse

Vervang daarom de lijsten voor de subklassen van Person zodat er geen achterliggend attribuut wordt bijgehouden. In plaats daarvan, moet de lijst met personen "on-the-fly" berekend worden. Met andere woorden, je moet nog steeds een getter AllLecturersenzovoort voorzien, maar deze verzamelt alle lectoren door AllPersonste doorlopen. Gebruik hier opnieuw het woordje is dat we bij Equals hebben gebruikt.

Vergeet niet om voor de gewijzigde klassen de constructor aan te passen.

H15_4 SchoolAdmin: Tweerichtingsverkeer voor CourseRegistration

Functionele analyse

In je huidige code heeft de klasse Student een lijst courseRegistrations. Zo wordt een student gelinkt aan de cursussen die hij of zij volgt. Dit is niet ideaal, want in werkelijkheid willen we ook vaak te weten komen welke studenten in een bepaalde cursus zijn ingeschreven. We moeten dus in twee richtingen kunnen gaan.

Technische analyse

De oplossing die hier voorgesteld wordt, verreist wel wat aanpassingen. We zullen er stap voor stap doorgaan:

  • klasse CourseRegistration:

    • voorzie de klasse van een (immutable) lijst AllCourseRegistrations. Zo hoef je geen data dubbel bij te houden en kan je toch de functionaliteit verder uitbreiden.

  • klasse Student:

    • Schrap de huidige lijst met courseRegistrations.

  • klasse CourseRegistration:

    • Voorzie ter vervanging daarvan een property (read only) Student die bijhoudt welke student bij de inschrijving hoort.

    • Pas de constructor aan met een extra parameter Student. Zorg er ook voor dat de nieuwe inschrijving toegevoegd wordt aan AllCourseRegistrations.

  • klasse Student:

    • Voorzie een property (immutable list) CourseRegistrationsdie "on-the-fly" berekent welke inschrijvingen bij de student in kwestie horen. Overloop alle inschrijvingen in AllCourseRegistrations en elke inschrijving van de desbetreffende student, voeg je toe aan de lijst. Maak gebruik van een builder.

    • Verander de naam courseRegistrations in CourseRegistrations in de andere methoden van Student.

    • In de methode RegisterCourseResult moeten we de inschrijving niet meer toevoegen aan de lijst van CourseRegistrations maar enkel nog een nieuwe CourseRegistration maken.

    • Voorzie ook een property (immutable list)Courses. Hierin plaats je al de cursussen van de student door CourseRegistrations te overlopen. Maak ook hier gebruik van een builder.

  • klasse Course:

    • Voorzie een property (immutable list)CourseRegistrations. Hierin zet je elke inschrijving die gebeurd is voor de desbetreffende cursus door de lijst van AllCourseRegistrations te overlopen. Gebruik een builder.

    • Wis het bestaande attribuut Students en vervang die door een immutable list Students. Overloop hiervoor de lijst CourseRegistrations van de cursus en voeg de studenten toe die ingeschreven zijn voor deze cursus. Gebruik ook hier een builder.

    • In de constructors wordt nog gebruikt gemaakt van een parameter students. Die parameter halen we er uit want het toevoegen van studenten aan een cursus verloopt nu via CourseRegistration. Wijzig constructor 1 en 2 en verwijder 3 want deze wordt overbodig.

  • klasse Program:

    • DemoCourses:

      • verwijder de lijst saidEnMieke bij het maken van de Course-instanties.

      • verwijder het toevoegen van studenten aan een cursus

H15_5 SchoolAdmin: Cursussen in semesters

Functionele analyse

Momenteel bestaat een studieprogramma gewoon uit een vlakke lijst cursussen. Dat stemt niet goed overeen met de werkelijkheid. In werkelijkheid wordt een cursus in een bepaald semester ingepland.

Technische analyse

We zullen het opdelen in semesters mogelijk maken door de vlakke lijst met cursussen te vervangen door een Dictionary met cursussen als keys en semesters (byte) als values. Doe deze aanpassing in je code.

Pas de code van ShowOverview aan zodat er gebruik gemaakt wordt van de nieuwe Dictionary en zodat je de cursussen toont, geordend per semester.

Voorbeeld:

Daarna pas je de demonstratiecode aan. Zorg dat communicatie bij de opleiding programmeren in het eerste semester staat, maar bij de opleiding systeem- en netwerkbeheer in het tweede semester. Alle andere vakken staan overal in het eerste semester.

Het veranderen van de titel van een cursus naar "Scripting" zal niet meer werken. Herschrijf de code zodat deze wijziging nog steeds gebeurt.

H15_6 SchoolAdmin: Manueel data invoeren

Functionele analyse

De demonstratiemethodes hebben bijna overal objecten aangemaakt door ze te "hard coden". Dat wil zeggen dat de instructies C# code zijn en niet gewijzigd kunnen worden eens je programma gecompileerd is. In een echte systeem voor schoolbeheer zou het administratief personeel voortdurend nieuwe entiteiten kunnen toevoegen aan het systeem.

Technische analyse

We voorzien hiervoor vier nieuwe mogelijkheden in het keuzemenu: "student toevoegen" (AddStudent), "cursus toevoegen" (AddCourse), "vakinschrijving toevoegen" ( AddCourseRegistration) en "inschrijvingsgegevens tonen" 'ShowCourseRegistrations).

De eerste drie vragen om de nodige gegevens om een object van een van deze klassen aan te maken. De laatste toont eerst alle studenten in het systeem, dan alle cursussen, dan alle inschrijvingen.

Let op, er kan maar een vakinschrijving toegevoegd worden als er minstens één student geregistreerd is en minstens één cursus.

Voorbeeldinteracties:

PreviousSystem.ObjectNextH16: Exception handling

Last updated 8 months ago