Expand | |||||||||||||||||||||||||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| |||||||||||||||||||||||||||||||||||
Oppgave a) - Konstruktører (8 poeng)Skriv kode for de to konstruktørene (merk forskjellen i argumenttype), slik at valueCounters blir riktig initialisert. Du SKAL IKKE innføre andre felt. Du kan lage hjelpemetoder om du ønsker. For begge konstruktørene er argumentet en sekvens med terningverdier (altså ikke tellere) som den nyinitialiserte instansen skal representere. Merk at det er lov å lage ekstra konstruktører for å gjøre andre metoder, f.eks. add og remove, enklere å skrive.
Oppgave b) - Terningverdier (8 poeng)Skriv metodene getDieCount, getDieValueog getValueCountiht. forklaringen og koden gitt tidligere (API-beskrivelsen).
Oppgave c) - Flere metoder (8 poeng)Skriv metodene contains, isSame, add og remove, som alle tar et Dice-objekt som eneste argument. Merk at ingen av disse endrer på verken this-objektet eller argumentet. Her er noen eksempler på bruken av disse metodene, hvor [t1, t2, t3, ... tn] brukes som pseudo-synaks for et Dice-objekt som representerer terningverdiene t1-tn: [1, 2, 2, 4].contains([1, 4]) returnerer true, mens [1, 2, 4].contains([2, 2]) returnerer false. [1, 2, 2, 4].isSame([1, 2, 2, 4]) returnerer true, mens [1, 2, 2, 4].isSame([1, 2, 4]) returnerer false [1, 2].add([1, 4]) returnerer [1, 1, 2, 4] [1, 1, 2].remove([1, 4]) returnerer [1, 2] Merk at removei kke har samme logikk som Collectionsin removeAll-metode.
Oppgave d) - DiceIterator (6 poeng)Lag en implementasjon av Iterator<Integer>kalt DiceIterator, slik at den kan brukes slik det er vist i Dice sin iterator()-metode. Du kan anta at valueCounters-feltet i Dice er synlig i DiceIterator-klassen.
| |||||||||||||||||||||||||||||||||||
Expand | |||||||||||||||||||||||||||||||||||
|
Expand | ||||
---|---|---|---|---|
| ||||
Denne deloppgaven handler om representasjon av poeng og poengberegning basert på et sett terningverdier. Felles for mange terningspill er at man kaster terninger og så finner ut hvor mange poeng en får basert på terningverdiene. Visse kombinasjoner gir mer eller mindre poeng, og noen gir ingen. I Yatzy har en mange poenggivende kombinasjoner, f.eks. ett par (to like), to par, tre og fire like, liten (1-5) og stor (2-6) straight, hus (ett par og tre like) og Yatzy (fem like), og poengene en får er stort sett summen av terningverdiene som inngår i kombinasjonen. I Farkle er det andre regler, og her begrenser vi oss til å implementere tre regler (se nedenfor). DiceScore-klassen innføres (se kode nedenfor) for å knytte poeng til et sett poenggivende terninger. Et DiceScore-objekt har data om:
Eksempel: Et Dice-objekt representerer terningverdiene 1, 2, 2, 2, 3, og en får 200 poeng for de tre toerne. Dette representeres av et DiceScore-objekt med:
Selve beregningen av poeng, og dermed opprettelsen av DiceScore-objekter, gjøres av implementasjoner av DiceScorer-grensesnittet. DiceScorer-grensesnittet representerer altså en poengregel generelt, og det er én implementasjonsklasse for hver (type) regel. DiceScorer-grensesnittet har kun én metode, getScore, som tar inn et Dice-objekt med alle terningverdiene som skal vurderes samlet og returnerer et nytt DiceScore-objekt med poengene en får og de av terningene som ga poeng, som beskrevet over.
Vi begrenser oss som nevnt til tre poengregler, representert ved tre DiceScorer-implementasjoner:
|
Oppgave a) - DiceScore-klassen (6 poeng)
Skriv ferdig DiceScore-klassen, med egnede felt, konstruktørkode og tilgangsmetoder, med utgangspunkt at DiceScore-objekter ikke skal kunne endres etter at de er opprettet.
Expand | ||
---|---|---|
| ||
Vanlige feil/svakheter:
|
Oppgave b) - SingleValue-klassen (6 poeng)
Skriv kode for klassen SingleValue(enkeltverdi), som implementerer DiceScorermed følgende logikk:
For et Dice-argument som ikke inneholder den spesifikke verdien returneres null. Ellers returneres et (nytt) DiceScore-objekt med riktige verdier satt.
Merk at klassen bare gir poeng for én av den angitte verdien, selv om Dice-objektet inneholder flere av denne verdien.
Eksempel:
Et SingleValue-objekt opprettet med new SingleValue(5, 50), vil gi 50 poeng for et Diceobjekt med én eller flere femmere. DiceScore-objektet som returneres skal inneholde et Dice-objekt med bare én femmer og (poeng)tallet 50.
Code Block |
---|
/**
* Implementation of DiceScorer that gives a specific score til a specific die value.
* In Farkle it is used for giving 50 to fives and 100 to ones.
*/
public class SingleValue implements DiceScorer {
???
/**
* Initializes this SingleValue object with the (die) value and the corresponding score.
* In Farkle you will typically create two of these, with
* new SingleValue(5, 50) and new SingleValue(1, 100)
* @param value
* @param score
*/
public SingleValue(int value, int score) {
???
}
/**
* Looks for at least one of the specific value and
* if found, returns a DiceScore object with a Dice object
* with the value contributing to the score and
* the corresponding score.
*/
@Override
public DiceScore getScore(Dice dice) {
???
}
} |
Expand | ||
---|---|---|
| ||
Vanlige feil/svakheter:
|
Oppgave c) - Straight-klassen (8 poeng)
Skriv kode for klassen Straight(alle terningene utgjør en serie), som implementerer DiceScorermed følgende logikk:
For et Dice-argument uten straightreturneres null. Ellers returneres et (nytt) DiceScore-objekt med riktige verdier satt. Poengene som gis er en spesifikk verdi (konstant) som settes når Straight-objektet opprettes.
Merk at koden skal virke selv om det er (mange) færre eller flere terninger enn mulige terningverdier (1-6). Et Dice-objekt med bare én terningverdi vil f.eks. alltid gi straight, mens et Dice-objekt med flere enn 6 terningverdier aldri kan gi straight.
Code Block |
---|
/**
* Implementation of DiceScorer that gives a specific score til a so-called straight,
* which is when all values give a series of consecutive values, e.g. 1, 2, 3.
* All the die values must be used, so with six dice, the only possibility is 1, 2, 3, 4, 5, 6.
* With five dice, there are two possibilities, 1, 2, 3, 4, 5 and 2, 3, 4, 5, 6.
*/
public class Straight implements DiceScorer {
???
/**
* Initializes this Straight object with the specific score.
* @param score
*/
public Straight(int score) {
???
}
/**
* Checks that all die values in the provided Dice form a series of consecutive values.
* If this is the case returns a DiceScore object with a Dice with
* the die values contributing to the score (necessarily all of them) and
* the corresponding score.
*/
@Override
public DiceScore getScore(Dice dice) {
???
}
} |
Expand | ||
---|---|---|
| ||
|
Oppgave d) - Nothing-klassen (8 poeng)
Skriv kode for klassen Nothing, som implementerer DiceScorer med følgende logikk:
Et spesifikt antall poeng gis hvis ingen (andre) poengregler gir poeng. De andre reglene representeres av et sett DiceScore-objekter som gis inn når Nothing-objektet opprettes. Dette gjør at Nothing-klassen ikke trenger å duplisere logikk som er spesifikke for andre regler. Bestem selv typen til diceScorers-argumentet som gis inn.
Merk at denne regelen bare gjelder hvis Dice-argumentet til getScore-metoden inneholder minst et visst antall terninger, typisk like mange som brukes i spillet. Dette minsteantallet gis også inn ved opprettelse av Nothing-objektet.
Code Block |
---|
/**
* Implementation of DiceScorer that gives a specific score
* when no other DiceScore object applies.
* Requires that a certain number of dice have been thrown.
*/
public class Nothing implements DiceScorer {
??? fields
/**
* Initializes this Nothing object with the minimum required number of dice,
* the specific score given and the other DiceScorer objects.
* @param numDice the min. number of dice required for this rule to apply
* @param score the specific score to give
* @param diceScorers the (other) rules to check
*/
public Nothing(int numDice, int score, ??? diceScorers) {
???
}
/**
* Checks that no (other) DiceScore object apply,
* in case a specific score is given.
*/
@Override
public DiceScore getScore(Dice dice) {
???
}
} |
Expand | ||
---|---|---|
| ||
|
Oppgave e) - Mer om Nothing-klassen (4 poeng)
Hva kalles implementasjonsteknikken som det legges opp til at Nothingskal bruke? Begrunn svaret, f.eks. ved å forklare (kort) hva som er karakteristisk for denne teknikken.
Expand | ||
---|---|---|
| ||
|
Oppgave f) - DiceScorer-deklarasjon (4 poeng)
Når en lager en instans av et DiceScorer-objekt og lagrer (referansen til) det i en variabel, så kreves det at variablen er deklarert med en egnet type. Anta at en har følgende deklarasjon med initialisering:
??? aSingleValueObject = new SingleValue(1, 100);
Hvilke (tre) mulige typer er det lov å skrive der det står ???, hva er avgjørende for valget og hva vil man typisk bruke?
Expand | ||
---|---|---|
| ||
|
Oppgave g) - Arv med AbstractScorer (6 poeng)
De tre implementasjonene av DiceScorer(SingleValue, Straight og Nothing) har én ting felles. Forklar med tekst og/eller kode hvordan du vil utforme en felles superklasse (f.eks. kalt AbstractScorer) for disse tre, og hvordan de tre implementasjonene vil måtte endres for å fungere som subklasser.
Expand | ||
---|---|---|
| ||
|
Expand | |||||||||||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| |||||||||||||||||||||
Det finnes flere måter å implementere Dice-klassen og alle dens metoder, med ulike fordeler og ulemper. En måte å tillate bruk av flere implementasjoner er å gjøre om Dice til et grensesnitt og så ha en eller flere implementasjonsklasser, hvor den eksisterende Dice-klassen blir en av disse: public interface Dice { ... } public class DiceImpl1 implements Dice { ... tilsvarer løsningen i deloppgavene 1-6 ... } public class DiceImpl2 implements Dice { ... alternativ løsning ... }
Navnene på implementasjonsklassene kan selvsagt være mer forklarende. Oppgave a) - Dice-grensesnittet (4 poeng)Dette var en flervalgsoppgave med to spørsmål og valg av ett av flere alternativer.
Spørsmål 1: Tre alternative grensesnitt er foreslått, basert på den nåværende Dice-klassen:
Spørsmål 2: Den opprinnelige Dice-klassen implementerer Iterable<Integer>. Spørsmålet er hvordan dette skal håndteres ved overgangen til et Dice-grensesnitt.
Oppgave b) - Arv (6 poeng)Hvis en har flere implementasjoner av det nye Dice-grensesnittet, så kan en regne med at visse deler av disse vil bli nokså eller helt like. Ett aspekt som typisk vil bli (nokså) likt er håndtering av poengene (score). Forklar med tekst og/eller kode hvordan du vil håndtere det vha. arvingsmekanismen, slik at løsningen tillater stor grad av gjenbruk av kode i subklasser og blir ren og ryddig.
Oppgave c) - Delegering (10 poeng)Dice sin add-metode skal lage en ny Dice-instans (altså instans av en klasse som implementerer Dice) som kombinerer terningverdier fra to andre Dice-instanser (this og argumentet). En kan tenke seg at metoden returnerer en instans av en ny Dice-implementasjon kalt DiceAdder, som bruker delegering. Den vil ha to Dice-felt og en konstruktør som tar inn to Dice-instanser: DiceAdder(Dice dice1, Dice dice2) { ... feltene settes her ... } Hver Dice-metode kan da bruke/delegere til disse to Dice-instansene i sin løsning, f.eks. vil getDieCount() returnere summen av getDieCount() for hver av de to Dice-instansene: public int getDieCount() { return dice1.getDieCount() + dice2.getDieCount(); } Forklar med tekst og/eller kode hvordan delegeringsteknikken vil bli brukt i følgende metoder i en slik DiceAdder-klasse: getDieValue, getValueCount, contains, add og remove. Kommenter spesielt hvis delegeringsteknikken ikke passer for en spesifikk metode!
|
Oppgave b) - Terningverdier (8 poeng)Skriv metodene getDieCount, getDieValue og getValueCount iht. forklaringen og koden gitt tidligere (API-beskrivelsen).
Oppgave c) - Flere metoder (8 poeng)Skriv metodene contains, isSame, add og remove, som alle tar et Dice-objekt som eneste argument. Merk at ingen av disse endrer på verken this-objektet eller argumentet. Her er noen eksempler på bruken av disse metodene, hvor [t1, t2, t3, ... tn] brukes som pseudo-synaks for et Dice-objekt som representerer terningverdiene t1-tn: [1, 2, 2, 4].contains([1, 4]) returnerer true, mens [1, 2, 4].contains([2, 2]) returnerer false. [1, 2, 2, 4].isSame([1, 2, 2, 4]) returnerer true, mens [1, 2, 2, 4].isSame([1, 2, 4]) returnerer false [1, 2].add([1, 4]) returnerer [1, 1, 2, 4] [1, 1, 2].remove([1, 4]) returnerer [1, 2] Merk at removei kke har samme logikk som Collectionsin removeAll-metode.
Oppgave d) - DiceIterator (6 poeng)Lag en implementasjon av Iterator<Integer>kalt DiceIterator, slik at den kan brukes slik det er vist i Dice sin iterator()-metode. Du kan anta at valueCounters-feltet i Dice er synlig i DiceIterator-klassen.
|
Expand | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
Oppgave a) - DiceScore-klassen (6 poeng)Skriv ferdig DiceScore-klassen, med egnede felt, konstruktørkode og tilgangsmetoder, med utgangspunkt at DiceScore-objekter ikke skal kunne endres etter at de er opprettet.
Oppgave b) - SingleValue-klassen (6 poeng)Skriv kode for klassen SingleValue(enkeltverdi), som implementerer DiceScorermed følgende logikk: For et Dice-argument som ikke inneholder den spesifikke verdien returneres null. Ellers returneres et (nytt) DiceScore-objekt med riktige verdier satt. Merk at klassen bare gir poeng for én av den angitte verdien, selv om Dice-objektet inneholder flere av denne verdien. Eksempel: Et SingleValue-objekt opprettet med new SingleValue(5, 50), vil gi 50 poeng for et Diceobjekt med én eller flere femmere. DiceScore-objektet som returneres skal inneholde et Dice-objekt med bare én femmer og (poeng)tallet 50.
Oppgave c) - Straight-klassen (8 poeng)Skriv kode for klassen Straight(alle terningene utgjør en serie), som implementerer DiceScorermed følgende logikk: For et Dice-argument uten straightreturneres null. Ellers returneres et (nytt) DiceScore-objekt med riktige verdier satt. Poengene som gis er en spesifikk verdi (konstant) som settes når Straight-objektet opprettes. Merk at koden skal virke selv om det er (mange) færre eller flere terninger enn mulige terningverdier (1-6). Et Dice-objekt med bare én terningverdi vil f.eks. alltid gi straight, mens et Dice-objekt med flere enn 6 terningverdier aldri kan gi straight.
Oppgave d) - Nothing-klassen (8 poeng)Skriv kode for klassen Nothing, som implementerer DiceScorer med følgende logikk: Et spesifikt antall poeng gis hvis ingen (andre) poengregler gir poeng. De andre reglene representeres av et sett DiceScore-objekter som gis inn når Nothing-objektet opprettes. Dette gjør at Nothing-klassen ikke trenger å duplisere logikk som er spesifikke for andre regler. Bestem selv typen til diceScorers-argumentet som gis inn. Merk at denne regelen bare gjelder hvis Dice-argumentet til getScore-metoden inneholder minst et visst antall terninger, typisk like mange som brukes i spillet. Dette minsteantallet gis også inn ved opprettelse av Nothing-objektet.
Oppgave e) - Mer om Nothing-klassen (4 poeng)Hva kalles implementasjonsteknikken som det legges opp til at Nothingskal bruke? Begrunn svaret, f.eks. ved å forklare (kort) hva som er karakteristisk for denne teknikken.
Oppgave f) - DiceScorer-deklarasjon (4 poeng) Når en lager en instans av et DiceScorer-objekt og lagrer (referansen til) det i en variabel, så kreves det at variablen er deklarert med en egnet type. Anta at en har følgende deklarasjon med initialisering: ??? aSingleValueObject = new SingleValue(1, 100); Hvilke (tre) mulige typer er det lov å skrive der det står ???, hva er avgjørende for valget og hva vil man typisk bruke?
Oppgave g) - Arv med AbstractScorer (6 poeng) De tre implementasjonene av DiceScorer(SingleValue, Straight og Nothing) har én ting felles. Forklar med tekst og/eller kode hvordan du vil utforme en felles superklasse (f.eks. kalt AbstractScorer) for disse tre, og hvordan de tre implementasjonene vil måtte endres for å fungere som subklasser.
|
Expand | ||||||||||||||||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| ||||||||||||||||||||||||||
Oppgave a) - Iterasjon (6 poeng)Du ønsker å skrive ut (med System.out.print(...)) alle terningverdiene som et Dice-objekt representerer, men oppdager at den ikke har en egen toString()-metode som kan brukes. Skriv vanlig iterativ løkkekode som skriver ut alle terningverdiene til et Dice-objekt med mellomrom mellom (det gjør ikke noe om det kommer et ekstra mellomrom bakerst): Dice dice = new Dice(...); ??? Hva skal stå her for å få skrevet ut alle terningverdiene i dice?
Skriv kode som har samme effekt, men som utnytter et funksjonelt grensesnitt (se ressurs med Java-API) og Java 8 sin lambda-syntaks: dice. ??? Hva skal stå her for å få skrevet ut alle terningverdiene i dice?
Oppgave b) - Testing av Dice-klassen (6 poeng)Skriv en eller flere test-metoder for Dice sin contains-metode. Tenk spesielt på å teste grensetilfeller, som det kan tenkes ikke håndteres riktig!
Oppgave c) - Diagramtyper (4 poeng)Hva er forskjellen (hensikt og innhold) mellom objektdiagrammer og objekttilstandsdiagrammer?
Oppgave d) - Observerbarhet (6 poeng)Hva er hensikten med observert-observatør-teknikken? Hva vil det si at et objekt er observerbart? Du blir bedt om å gjøre Dice-objekter observerbare. Forklar med tekst og evt. kode hva du vil gjøre for å møte dette kravet.
|
Expand | |||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|
| |||||||||||
Du skal lage en liten JavaFX-app for å teste DiceScorer-implementasjonene dine, altså SingleValue-, Straight- og Nothing-klassene. Følgende oppførsel skal støttes:
Illustrasjonen for oppgaven viser resultatet etter at knappen tilsvarende Straight er trykket. Følgende FXML er skrevet for appen:
Skriv en JavaFX-kontroller som implementerer ønsket oppførsel, basert på kodeskjelettet nedenfor. Den skal passe til den oppgitte FXML-en og bruke klasser og metoder beskrevet tidligere i oppgavesettet. Du kan anta at Dice har en passende toString()-metode.
Hvis det er detaljer du er usikker på, så forklar med tekstkommentarer i koden.
| |||||||||||
Expand | |||||||||||
|
Expand | ||
---|---|---|
Så langt har koden vært relativt uavhengig av typen terningspill. I denne deloppgaven handler det om en runde i Farkle-spillet. I en slik runde så akkumuleres det poeng ved at en gjentatte ganger kaster terninger, og sparer på en eller flere poenggivende terningkombinasjoner. Reglene for hvilke kombinasjoner som gir poeng varierer noe mellom ulike varianter av Farkle, men en får typisk poeng for tre eller flere like, og for femmere (50 poeng pr. stk) og enere (100 poeng pr. stk). En tenker seg at dette beregnes av en metode tilsvarende computeDiceScores fra deloppgave 8 om totalpoengberegning. Etter hvert kast har en tre tilfeller/muligheter:
For hvert kast så får en de samme tre mulighetene. Avveiningen i spillet er altså om en skal beholde poengene en har fått så langt, eller kaste på nytt for å få flere poeng, men risikere å miste alle. Her er noen eksempler som illustrerer reglene:
Et forslag til realisering av en klasse som håndterer en Farkle-runde, er vist under. Noen deler er imidlertid utelatt...
|
Oppgave a) - final (2 poeng)
Dette var en flervalgsoppgave med ett spørsmål og to korrekte alternativer og ett galt et.
Spørsmål: Hvilke, om noen, av feltene øverst i FarkleRound-klassen kan ha modifikatoren final?
- dieCount
- kept
- currentDice
Expand | ||
---|---|---|
| ||
Her er 1 og 2 riktig og 3 er gal, siden 1 og 2 bare settes én gang (i initialiseringsdel av deklarasjon eller i konstruktør). Riktignok endres innholdet i kept-lista, men det er det samme objektet som endres hele tiden. |
Oppgave b) - Kode i bank (2 poeng)
Dette er en tekstinnfyllingsoppgave som vurderes automatisk.
Spørsmål: Nederst i bank-metoden er en kodelinje erstattet med "... put this object in a state that indicates this round is finished ...". Skriv inn den korrekte kodelinjen. Koden må være korrekt, komplett og konsis, uten kommentarer, siden den sjekkes automatisk.
Expand | ||
---|---|---|
| ||
Her er poenget å skjønne at isFinished-metoden i FarkleRound sjekker om currentDice er null, så koden må sette dette feltet til null. Alternativene som ble godkjent var currentDice = null med eller uten this foran og ; bak. Mellomrom rundt = ignoreres.
|
Oppgave c) - Unntakstyper (3 poeng)
Dette er en flervalgsoppgave med tre spørsmål.
I keepAndRoll-metoden utløses unntak i tre tilfeller.
Spørsmål 1: Hvilken av disse unntakstypene passer i det første tilfellet?
- Exception
- RuntimeException
- IllegalArgumentException
- IllegalStateException
Spørsmål 2: Hvilken av disse unntakstypene passer i det andre tilfellet?
- Exception
- RuntimeException
- IllegalArgumentException
- IllegalStateException
Spørsmål 3: I det tredje tilfellet bruker vi unntakstypen SomeKindOfException, som er tenkt som en egendefinert unntakstype. Hvilken unntakstype bør brukes som superklassen til SomeKindOfException?
- Exception
- RuntimeException
- IllegalArgumentException
- IllegalStateException
Expand | ||
---|---|---|
| ||
Svaret på det første spørsmålet er IllegalStateException, fordi metoden skal ikke kalles (uansett hva argumentet er) når runden er ferdig. Svaret på de to neste IllegalArgumentException, fordi metoden det (primært) handler om validering av argumentet.
|
Oppgave d) - Kode i keepAndRoll (2 poeng)
Nederst i keepAndRoll-metoden er én eller flere kodelinjer erstattet med "... what code needs to be here ? ...". Skrive linjen(e) som mangler. Koden vil bli lest av sensor.
Expand | ||
---|---|---|
| ||
Her er poenget at vi må avslutte metoden med å kalle roll, og må finne ut om vi skal kaste de som er igjen (hvis det er noen terninger igjen) eller alle.
Vanlige feil/mangler:
|
Oppgave e) - FarkleRound-objektdiagram (6 poeng)
Underveis i og etter en Farkle-runde vil tilstanden til runden være representert ved hjelp av flere objekter, inkludert et FarkleRound-objekt. Tegn objektdiagram for tilstanden etter runden som er beskrevet i det tredje eksemplet (fremhevet med fet skrift) for Farkle-reglene.
Bruk blyantikonet til høyre på verktøylinja for tekstfeltet, for å aktivere tegneverktøyet. Det kan være lurt å kladde på forhånd, siden tegneverktøyet er litt begrenset...
Expand | ||
---|---|---|
| ||
|
title | Del 5 - Dice-konstruktør og Supplier-argument |
---|
Dice-klassen har en konstruktør som initialiserer den med tilfeldige terningverdier, og det gjør den vanskelig å teste, fordi en jo ikke vet hvilke verdier random-metoden genererer. Et alternativ er en konstruktør som henter verdier fra en Supplier<Integer>(se nedenfor). Til vanlig kan en bruke en Supplier-implementasjon som leverer tilfeldige tall vha. Math.random(), mens til testing kan en lage en som gir ut bestemte verdier:
Code Block |
---|
/**
* Initializes this Dice with n die values provided by the supplier argument.
* @param dieCount the number of dice to "throw"
* @param supplier provides the die values
*/
public Dice(int dieCount, Supplier<Integer> supplier) { ... } |
Supplierer deklarert som følger:
Code Block |
---|
public interface Supplier<T> {
/**
* Gets a result.
* @return a result of the type T
*/
T get();
} |
Oppgave a) - Funksjonelt grensesnitt (3 poeng)
Er DiceScorer et funksjonelt grensesnitt? Forklar hvorfor/hvorfor ikke!
Expand | ||
---|---|---|
| ||
DiceScorer-grensesnittet er funksjonelt fordi det 1) har kun én abstrakt metode og 2) er ment å være primærtfunksjonen til klassen som implementerer den. |
Oppgave b) - Alternativ Dice-konstruktør (3 poeng)
Implementer den alternative Dice-konstruktøren.
Expand | ||
---|---|---|
| ||
Her er koden nokså lik den i randomDieValues, vi bare bytter ut uttrykket med Math.random med supplier.get(). Her bryr vi oss heller ikke om poeng (score).
|
Oppgave c) - Testing av Dice-klassen (5 poeng)
Skriv en eller flere test-metoder for Dice sin valueOf-metode. Du kan anta det finnes en metode kalt assertDieValuessom sjekker terningverdiene til en Dice:
assertDieValues(dice, 1, 2, 3) // utløser assert-unntak hvis dice ikke har terningverdiene 1, 2, 3 og bare disse.
Expand | ||
---|---|---|
| ||
Her bør det testes med og uten = score og i hvertfall for én feil syntaks.
Vanlige feil/mangler:
|
title | Del 6 - JavaFX og FXML (6 poeng) |
---|
Du skal lage en liten JavaFX-app for terningspill basert på Dice-klassen. I første omgang skal du støtte terningkast og poengberegning:
- Brukeren skal kunne fylle inn et tall ni et tekstfelt (TextField)
- Når en knapp (Button) trykkes, så skal det lages et Dice-objekt med ntilfeldige tall.
- Poengverdien til Dice-objektet settes vha. metoden void computeFarkleScore(Dice), som du kan anta finnes.
- Den tekstlige representasjonen til Dice-objektet skal så vises som en tekst (Label)
Følgende FXML er skrevet for appen:
Code Block |
---|
<HBoxxmlns:fx="http://javafx.com/fxml/1" fx:controller="ord2018.farkle.fx.DiceController">
<!-- text field for inputing the die count -->
<TextField fx:id="dieCountInput" promptText="Die count"/>
<!-- button for throwing the dice, i.e. create a Dice object and computing the score -->
<Button onAction="#handleThrowDice" text="Throw dice"/>
<!-- label for outputing the textual representation of the Dice object -->
<Label fx:id="diceOutput" text="No dice thrown, yet"/>
</HBox> |
Skriv en JavaFX-kontroller som implementerer ønsket oppførsel. Den skal passe til den oppgitte FXML-en og bruke klasser og metoder beskrevet tidligere i oppgavesettet.
Hvis det er detaljer du er usikker på, så forklar med tekstkommentarer i koden.
Expand | ||
---|---|---|
| ||
Her er vi mest opptatt av:
|