Típicament, l’operador ++ dels iteradors de
la classe List els desplaça una unitat cap al end de la llista, i
l’operador – dels iteradors de la classe List
els desplaça una unitat cap al begin de la llista. A més a més, executar
++ sobre un iterador que es troba al end de la
llista produeix error d’execució, i executar –
sobre un iterador que es troba al begin de la llista també produeix
error d’execució.
En aquest exercici modificarem la classe List de manera que els
errors d’execució abans esmentats ja no es produiran. En canvi, es
produirà un intercanvi en la direcció de moviment dels operadors
++ i – (efecte
rebot). Per exemple, si creem un iterador nou, el col.loquem al end de
la llista, i executem ++ sobre ell, no hi
haurà error d’execució, l’iterador no es mourà, i a partir d’aquell
moment l’operador ++ sobre ell l’anirà
desplaçant cap al begin de la llista, i l’operador
– el desplaçarà cap al end de la llista.
Fixeu-vos en el següent exemple de programa i el seu comportament descrit en els seus comentaris.
List<string> l; // l:
l.push_back("a"); // l: a
l.push_back("b"); // l: a,b
l.push_back("c"); // l: a,b,c
List<string>::iterator it = l.begin(); // l: (a),b,c
it++; // l: a,(b),c
it++; // l: a,b,(c)
it--; // l: a,(b),c
it++; // l: a,b,(c)
it++; // l: a,b,c,()
it++; // l: a,b,c,()
it++; // l: a,b,(c)
it++; // l: a,(b),c
it--; // l: a,b,(c)
it++; // l: a,(b),c
it++; // l: (a),b,c
it++; // l: (a),b,c
it++; // l: a,(b),c
it--; // l: (a),b,c
it--; // l: (a),b,c
it--; // l: a,(b),c
it--; // l: a,b,(c)
it++; // l: a,(b),c
it--; // l: a,b,(c)
it--; // l: a,b,c,()
it--; // l: a,b,c,()
it++; // l: a,b,c,()
it++; // l: a,b,(c)
D’entre els fitxers que s’adjunten en aquest exercici, trobareu
list.hh, a on hi ha una implementació de la
classe genèrica List. Caldrà que modifiqueu la
classe List per a poder recordar quina és la
direcció actual de desplaçament d’un iterador donat, i reimplementeu els
operadors ++ i –
convenientment. Més específicament, haureu de buscar les següents línies
i fer els afegits i modificacions que s’hi indiquen:
...
// Iterators mutables
class iterator {
friend class List;
private:
List *plist;
Item *pitem;
// Add an attribute to remember the orientation of the iterator:
// ...
// You can add new private methods if you wish.
public:
iterator() {
// Initialise the orientation of the iterator
// ...
}
// Adapt this function so that no error occurs and the orientation of the iterator
// is taken into account and updated accordingly.
// Preincrement
iterator operator++()
/* Pre: el p.i apunta a un element E de la llista,
que no és el end() */
/* Post: el p.i apunta a l'element següent a E
el resultat és el p.i. */
{
if (pitem == &(plist->itemsup)) {
cerr << "Error: ++ on iterator at the end of list" << endl;
exit(1);
}
pitem = pitem->next;
return *this;
}
...
// Adapt this function so that no error occurs and the orientation of the iterator
// is taken into account and updated accordingly.
// Predecrement
iterator operator--()
/* Pre: el p.i apunta a un element E de la llista que
no és el begin() */
/* Post: el p.i apunta a l'element anterior a E,
el resultat és el p.i. */
{
if (pitem == plist->iteminf.next) {
cerr << "Error: -- on iterator at the beginning of list" << endl;
exit(1);
}
pitem = pitem->prev;
return *this;
}
...
D’entre els fitxers que s’adjunten a l’exercici també hi ha
main.cc (programa principal), i el podeu
compilar directament, doncs inclou list.hh.
Només cal que pugeu list.hh al jutge.
L’entrada del programa té una seqüència d’instruccions del següent tipus que s’aniran aplicant sobre la llista i dos iteradors que se suposen situats inicialment al principi (i final) de la llista:
push_front s (s és string)
push_back s (s és string)
pop_front
pop_back
it1 = begin
it1 = end
it1 = erase it1
it1++
it1--
++it1
--it1
*it1 = s (s és string)
insert it1 s (s és string)
cout << *it1
it2 = begin
it2 = end
it2 = erase it2
it2++
it2--
++it2
--it2
*it2 = x (x és string)
insert it2 x (x és string)
cout << *it2
cout << l
Se suposa que la seqüència d’entrada serà correcta, és a dir, que no es produeixen errors d’execució si s’apliquen correctament sobre una llista i dos iteradors amb les condicions abans esmentades.
El programa principal que us oferim ja s’encarrega de llegir aquestes entrades i fer les crides als corresponents mètodes de la classe list. Només cal que implementeu les modificacions abans esmentades.
Per a cada instrucció cout << *it1 o
cout << *it2 s’escriurà el contingut
apuntat per l’iterador it1 o
it2, respectivament. Per a cada instrucció
cout << l s’escriurà el contingut de
tota la llista. El programa que us oferim ja fa això. Només cal que feu
els canvis abans esmentats.
Avaluació sobre 10 punts: (Afegiu comentaris si el vostre codi no és prou clar)
Solució lenta: 5 punts.
solució ràpida: 10 punts.
Entenem com a solució lenta una que és correcta i capaç de superar els jocs de proves públics. Entenem com a solució ràpida una que és correcta i capaç de superar els jocs de proves públics i privats.
Autoria: PRO2
Generació: 2026-01-27T18:57:24.846Z
© Jutge.org, 2006–2026.
https://jutge.org