• No results found

Rättningsmall DD2387 oktober 2008 Tal 1

N/A
N/A
Protected

Academic year: 2021

Share "Rättningsmall DD2387 oktober 2008 Tal 1"

Copied!
4
0
0

Loading.... (view fulltext now)

Full text

(1)

Rättningsmall DD2387 oktober 2008 Tal 1 lösningsförslag

01 void remove(LinkedList<T> *& p, T data) { 02 if (p != 0) {

03 if (data == p->data) {

04 LinkedList<T> * tmp = p;

05 p = p->next;

06 delete tmp;

07 remove(p, data);

08 } else {

09 remove(p->next, data);

10 } 11 } 12 }

Det går att lösa på annat sätt utan att utnyttja att p är referensdeklarerad, funktionen måste då returnera en pekare och nextpekaren sättas lika med det returnerade värdet. Det är fel att anta att remove ligger som medlemsfunktion i en klass och definiera införa egna medlemsvariabler.

FEL:

1-9-30 Missat typdeklarera listan kontrollera:

rad 01 LinkedList<T> *& p p rad 04 LinkedList<T> * tmp

1-9-50 saknas rekursivt anrop 1-9-51 felaktigt rekursivt anrop

1-9-51 Ingen else-sats med rekursivt anrop

rad 09 remove(p->next, data);

1-9-52 Buggigt rekursivt anrop (kraschar om man tagit bort sista elementet) rad 07 remove(p.next) istället för remove(p);

1-9-53 Missat kontrollera tomma listan rad 02 if (p != 0) {

1-9-54 Felaktig borttagning, t.ex. tar bort utan temporär variabel 1-1-54 Felaktig borttagning, t.ex. stavar fel på tmp vid delete rad 04 LinkedList<T> * tmp = p;

rad 05 p = p->next;

rad 06 delete tmp;

1-5-99 annat fel, okänt hur allvarligt 1-1-99 annat litet

1-9-99 annat allvarligt fel

(2)

Tal 2

Det här är en variant på tentatal där klasser hanterar dynamiskt minne där jag brukar fråga efter copy- konstruktor, operator= och destructor.

Koden är medvetet svårtytt skriven. Pekaren current pekar på nästa lediga element att stoppa in ett värdet på. I funktionen pop blir namnet current förvillande eftersom man inledningsvis tror att den pekar på nästa värde att returnera.

2a)

lösningsförslag: operator= och copy-konstruktor

Destruktorn behöver inte nämnas och det är inte fel att nämna den. Defaultkonstruktorn finns redan och ska inte nämnas. Man behöver inte precisera med parametrar och åtkomst.

FEL:

2-9-40 operator= och/eller copy-konstruktor saknas 2-1-41 defaultkonstruktorn nämns

2b)

Lösningsförslag: Stack-klassen har en intern pekare current som kommer att peka på fel minne när Stack-klassen kopieras eller tilldelas. När man använder kopian kommer man att skriva/läsa i fel minne.

FEL:

Icke allvarligt fel är att påstå att mp också kommer att peka fel. Det är fel att påstå det, mp är en array som kommer att kopieras värde för värde.

Det är inte fel att nämna att nrItems också kommer att kopieras

2-9-70 missa att pekaren current kopieras och pekar på fel minne

2-9-50 oprecist svar: enbart säga att en pekare kopieras utan att reflektera över följderna 2-9-51 oprecist svar: säger att en pekare pekar på fel minne utan att precisera vilken pekare 2-1-72 svarar rätt men tillägger att m_p också pekar på fel minne

2-1-19 påstå max kopieras, max är statisk och kopieras inte 2c)

Det intressanta i det här talet är att argumentet s inte ska vara const-deklarerad vilken den normalt brukar vara. Det går att lösa uppgiften genom att manipulera pekarna. Det kan vara svårt att rätta.

Lösningsförslag:

void operator=(Stack<T> & s) {

nrItems = 0; // initialisera som current = mp; // defaulkonsstruktorn

Stack(Stack<T> & s) : nrItems(0),

current(mp) {

put(s.pop());

put(s.pop());

} put(s.pop());

put(s.pop());

}

(3)

FEL:

2-9-11 Allvarligt fel att const-deklarera s.

void operator=(const Stack<T> & s) { 2-1-50 litet fel om koden nästan gör rätt.

2-9-51 fel om koden inte gör vad den ska 2-5-99 oförutsett fel

Tal 3

Kommentar till talet: Eftersom index()-metoderna i lösningen inte är virtual får man olika resultat med referenserna även om de refererar till samma instans. Man har fog att tycka att det är dålig

objektorienterad programmering eftersom man inte uppfyller "is a " relationen.

En alternativ lösning är att ha en medlemsvariabel som ändras vid varje anrop och dessutom påverkar resultatet.

Lösningsförslag:

01 struct OldWay { 02 float index() { 03 return 3.7;

04 } 05 };

06

07 struct NewDeal : OldWay { FEL

3-9-20 virtual deklarerade metoder, koden skriver inte ut why 3-9-50 Logiskt fel. Koden skriver inte ut WHY

3-9-15 Koden deklarerad private så att exemplet inte fungerar 3-9-16 inget arv

3-5-99 oförutsett fel

08 float index() { 09 return 5.6;

10 } 11 };

Tal 4

Lösningsförslag:

struct Bank {

bool nogood() const {return true};

FEL

4-9-10 Allvarligt fel om Banks metoder inte är const-deklarerade 4-9-40 Allvarligt fel om operator[] inte returnerar en

referens (l-value)

4-9-50 Allvarligt fel om operator[] och in_depth returtyper inte matchar

4-9-51 Allvarligt fel om operator[]-argumentet inte tar en typ man kan göra ++ på.

4-5-99 oförutsett fel int in_depth() const {return 4;};

};

struct State { int next;

int & operator[](int & x) { return next;

} };

(4)

Tal 5a

FEL:

5-9-30 Fel om koden inte kompilerar 5-9-31 Fel om koden inte fungerar 5-5-99 oförutsett fel

Lösningsförslag

const & T max(const T & x, const T & y) { if (x < y) return y;

else return x;

} // alternativ till if-sats return x < y ? y : x;

Det spelar ingen roll om man skickar/returnerar kopia i 5a) men det måste motiveras i 5c)

5b)

Lösningen kräver operator<

Det går att implementera med operator> operator<= operator>=

Även metoder (less, greater_...) godkänns om man är konsekvent i a och b

5-9-32 Fel om man inte identiferar krav på typparametern.

5-5-99 oförutsett fel

5c)

Det är mer användbart att returnera en referens. T.ex. när man vill förändra det största av två objekt.

Returnerar man en kopia så förändrar man kopian.

En någorlunda vettig förklaring på att man returnerar en kopia är också godkänd.

5-1-33 Fel är att inte inse att man har ett val att returnera en kopia eller en referens.

5-1-34 Fel om man returnerar något helt annat.

5-1-60 Otydligt svar 5-5-99 oförutsett fel

5d)

Lösningsförslag: Man kan bara deklarera en och endast en returtyp

FEL

5-9-90 Alla andra svar.

5-5-60 Otydligt svar - kanske rätt.

6

FEL

6-9-20 Grovt fel om utskriften fel.

6-1-91 Missat endl svarat c a d e d c a

d e d

Mellanslag räknas inte som fel.

References

Related documents

Där anropade vi defaultkonstruktorn (den automatiskt genererade) när vi skapade objekt, samt så hade vi en funktion skriv_in_data( ) som vi använde för att lägga in ”värden”

MEN OM dESSA föRHåLLANdEN vore permanenta och man ofta kom för sent, när färden till jobbet inte blir en rolig utan en jobbig historia. Hur skulle man då bli betraktad av

Något som kan förstås utifrån kunskapen om våldets utbredning i det svenska samhället där 46 % av alla kvinnor någon gång utsätts för våld under sin livstid (NCK 2014).

En kreativ journalist ger sig ut på spaning med helikopter för att spana på de sven- ska båtarna som spanar efter det oidentifierade dykande föremålet. En annan skribent spekulerar

Implementera A och B så att följande kod kompilerar. Det är mycket allvarligt att göra fel på const. Observera att parametern till operator+= antingen är en kopia eller

• För klasser som använder medlemspekare till dynamiskt allokerat minne blir det fel...

net av Isak Gustaf Clason, skaparen av museets stolta byggnad och under ett kvarts århundrade ordförande i dess nämnd, är det för museet en stor glädje att detta får ske i

Leta i rutan och fyll i diagrammet. Där är En