From 2bcc319e7fdde4a584997c4a0694556ce7b405ac Mon Sep 17 00:00:00 2001
From: fsimonsen <fredersi@stud.ntnu.no>
Date: Tue, 5 Apr 2022 18:04:08 +0200
Subject: [PATCH] R E smett

---
 rute.cpp | 245 +++++++++++++++++++++++++++++++++++++------------------
 rute.h   |   1 +
 2 files changed, 168 insertions(+), 78 deletions(-)

diff --git a/rute.cpp b/rute.cpp
index 9bf0505..7963b61 100644
--- a/rute.cpp
+++ b/rute.cpp
@@ -87,6 +87,37 @@ Rute::Rute(ifstream & inn) {
     }
 }
 
+/**
+ * Sjekker om et sluttsted ifm. smetting av stopper er før på ruten
+ * enn startstedet i intervallet for hvor stopper skal smettes
+ * 
+ * @param s1 - Peker til startstopp i intervallet 
+ * @param s2 - Peker til sluttstopp i intervallet
+ * @return true s2 er tidligere på ruten enn s1
+ * @return false s1 er før s2
+ */
+bool Rute::erForst(Stopp* s1, Stopp* s2) {
+    int fPos, // første posisjon
+        aPos; // andre posisjon
+    // finner posisjon i listen for startstopp i intervallet:
+    auto it = find(stoppene.begin(), stoppene.end(), s1);
+    if (it != stoppene.end()) {
+        fPos = distance(stoppene.begin(), it);
+    }
+    // Finner posisjon i listen for stoppsted i intervallet:
+    auto it2 = find(stoppene.begin(), stoppene.end(), s2);
+    if (it2 != stoppene.end()) {
+        aPos = distance(stoppene.begin(), it2);
+    }
+    // Hvis stoppsted faktisk er før startsted i intervall:
+    if (aPos < fPos) {
+        return true;
+    }
+    // Hvis startsted faktisk er før stoppsted i intervall:
+    return false;
+
+}
+
 /**
  * Sjekker om en rute har mer enn en stopp (= gyldig rute)
  *
@@ -101,36 +132,25 @@ bool Rute::erListeGyldig() {
 }
 
 /**
- * Går gjennom et medsendt navn fra bruker, sjekker
- * alle tegn i strengen er tall eller ei
+ * Sjekker om to stopp på en rute faktisk er nabo eller ei
  *
- * @param nvn - Mulig stoppestedsnavn eller stoppestedsnr
- * @return true Hvis alle tegnene i strengen er tall
- * @return false Hvis strengen inneholder tegn som ikke er tall
- */
-bool Rute::erTall(std::string nvn) {
-    return all_of(nvn.begin(), nvn.end(), ::isdigit);
-}
-
-/**
- * @brief
- *
- * @param fStoppNr
- * @param aStoppNr
- * @return true
- * @return false
+ * @param s1 - Peker til startstopp i intervallet
+ * @param s2 - Peker til sluttstopp i intervallet
+ * @return true Hvis stoppene er naboer
+ * @return false Hvis stoppene ikke er naboer
  */
 bool Rute::erNabo(Stopp* s1, Stopp* s2) {
-    int fPos,
-        aPos,
-        temp,
-        avstand;
+    int fPos, // posisjon til første stopp i ruten
+        aPos, // posisjon til andre stopp i ruten
+        temp, // Hjelpevariabel for eventuelt bytte om fPos og aPos
+        avstand; // Avstand mellom stoppene på ruten (=1 hvis nabo)
 
+    // Finner posisjon til første stopp i intervallet
     auto it = find(stoppene.begin(), stoppene.end(), s1);
     if (it != stoppene.end()) { // Funn av stoppNr
         fPos = distance(stoppene.begin(), it);
     }
-
+    // Finner posisjon til andre stopp i intervallet
     auto it2 = find(stoppene.begin(), stoppene.end(), s2);
     if (it2 != stoppene.end()) { // Funn av stoppNr
         aPos = distance(stoppene.begin(), it2);
@@ -138,22 +158,36 @@ bool Rute::erNabo(Stopp* s1, Stopp* s2) {
 
     if (fPos < aPos) { // Hvis første er før på ruten enn andre
         avstand = aPos-fPos; // Setter avstand mellom stopp på ruten
+    // Hvis slutt stopp er før start stopp i intervallet, bytter plass:
     } else if (fPos > aPos) {
-        temp = fPos; // Gjør om slik at første stopp på ruten kommer først
+        temp = fPos;
         fPos = aPos;
         aPos = temp;
         avstand = aPos-fPos;
+    // Hvis man sjekker om samme stopp er først og sist i intervall:
     } else if (fPos == aPos) { // Skal ikke skje
         cout << "\nHer er det noe alvorlig galt.\n\n";
     }
-
-    if (avstand == 1) { // Stoppene er naboer
+    // Hvis stoppene i intervallet er naboer:
+    if (avstand == 1) {
         return true;
     }
     // Stoppene er ikke naboer:
     return false;
 }
 
+/**
+ * Går gjennom et medsendt navn fra bruker, sjekker
+ * alle tegn i strengen er tall eller ei
+ *
+ * @param nvn - Mulig stoppestedsnavn eller stoppestedsnr
+ * @return true Hvis alle tegnene i strengen er tall
+ * @return false Hvis strengen inneholder tegn som ikke er tall
+ */
+bool Rute::erTall(std::string nvn) {
+    return all_of(nvn.begin(), nvn.end(), ::isdigit);
+}
+
 /**
  * Går gjennom om alle Stopp på en rute for å sjekke om deres
  * unike nr matcher en nr som bruker mener finnes på ruten
@@ -240,10 +274,12 @@ string Rute::hentNavn(const Retning retning) {
 }
 
 /**
- * Prøver å finne en peker til et stopp på en rute
+ * Sjekker om en stopp er på en aktuell rute
  *
- * @param nr
- * @return Stopp*
+ * @param nr - Stoppens unike nr
+ * @return Stopp* - Peker til stopp ved funn (er på ruta)
+ * @return nullptr - Hvis stoppen ikke er på aktuell rute
+ * @see Stopp::hentNr()
  */
 Stopp* Rute::finnStopp(int nr) {
     int nummer;
@@ -481,35 +517,61 @@ void Rute::slettData(){
 }
 
 /**
- * TODO: smettStopp()
- * Husk her må avstanden mellom de to stoppestedene være akkurat 1 (naboer)
- * Hvis de ikke er naboer, skal man bli sendt tilbake til meny
+ * Smetter inn stoppesteder mellom et intervall hvis mulig
+ * Skal godta tall, navn så fort entydig, hoppe ut ved enter
+ * Skal sjekke at det kun går ann å smette inn mellom faktiske
+ * naboer på en rute (uavhengig av hvilken "vei" bruker har
+ * tastet inn disse) osv.
+ * 
+ * @see Stoppesteder::byttBokstaver(...)
+ * @see Rute::erTall(...)
+ * @see Stoppesteder::finnesIndeks(...)
+ * @see Stoppesteder::hentNavnVhaIndeks(...)
+ * @see Stoppesteder::finnEntydig(...)
+ * @see Stoppesteder::hentIndeksVhaNavn(...)
+ * @see Rute::finnesStopp(...)
+ * @see Stoppesteder::finnDuplikat(...)
+ * @see Rute::finnStopp(...)
+ * @see Rute::erNabo(...)
+ * @see Rute::erForst(...)
+ * @see Stoppested::finnesNabo(...)
+ * @see Stoppested::hentNaboIndeks(...)
+ * @see Stoppested::hentNaboTid(...)
+ * @see Stopp::Stopp(...)
+ * @see Stoppested::settNaboIndeks(...)
+ * @see Stoppested::settNaboTid(...)
+ * @see Rute::skrivRute(...)
  */
 void Rute::smettStopp() {
-    string navn,
-           fNavn,
-           aNavn,
-           nNavn;
-    int stoppNr,
-        fStoppNr,
-        aStoppNr,
-        nStoppNr,
-        indeks,
-        naboIndeks,
-        fIndeks,
-        aIndeks,
-        tid,
-        storrelse = stoppene.size();
-    Stopp* fStopp = nullptr;
-    Stopp* aStopp = nullptr;
-    Stopp* nStopp = nullptr;
-    Stoppested* fStoppested = nullptr;
-    Stoppested* aStoppested = nullptr;
-    Stoppested* nStoppested = nullptr;
+    string navn, // Hjelpevariabel for å lese brukerinput
+           fNavn, // Forrige stoppesteds navn
+           aNavn, // Siste stoppesteds navn i intervall
+           nNavn, // Nåværende stoppesteds navn
+           tempNavn; // Hjelpevariabel for evt. å endre rekkefølge
+    int stoppNr, // Hjelpevariabel for å lese brukerinput
+        fStoppNr, // Forrige stoppesteds unike nr
+        aStoppNr, // Siste stoppesteds unike nr i intervall
+        nStoppNr, // Nåværende stoppesteds unike nr
+        tempStoppNr, // Hjelpevariabel for evt. å endre rekkefølge
+        indeks, // Hjelpevariabel for å lese bruker input
+        naboIndeks, // Nabostopp sin indeks
+        fIndeks, // Forrige stoppested sin indeks
+        aIndeks, // Siste stoppested sin indeks i intervall
+        tempIndeks, // Hjelpevariabel for evt. å endre rekkefølge
+        tid, // antall minutter mellom stopp
+        storrelse = stoppene.size(); // Hjelpevariabel for å se om ruten har blitt lengre
+    Stopp* fStopp = nullptr; // Peker til forrige stopp-struct
+    Stopp* aStopp = nullptr; // Peker til siste stopp-struct i intervall
+    Stopp* nStopp = nullptr; // Peker til nåværende stopp-struct
+    Stopp* tempStopp = nullptr; // Hjelpevariabel for evt. å endre rekkefølge
+    Stoppested* fStoppested = nullptr; // Peker til forrige stoppested i vector
+    Stoppested* aStoppested = nullptr; // Peker til siste stoppested i vector fra intervall
+    Stoppested* nStoppested = nullptr; // Peker til nåværende stoppested i vector
+    Stoppested* tempStoppested = nullptr; // Hjelpevariabel for evt. å endre rekkefølge
 
     cout << "\n\nMellom start\n"
          << "Stoppested (entydig navn / tall / ENTER for å avslutte): ";
-    getline(cin, navn);
+    getline(cin, navn); // Leser navn fra bruker
 
     while (navn.size() > 0) { // Så lenge ikke skrevet enter:
         navn = gStoppestederBase.byttBokstaver(navn); // fjerner æøåÆØÅ
@@ -539,7 +601,7 @@ void Rute::smettStopp() {
                 // Starte på neste while for å finne andre stopp?
                 navn = ""; // Sørger for at man kommer seg ut av whilen
             } else {
-                navn = ""; // TEST
+                fNavn = ""; // Må være her hvis neste input er ENTER
                 cout << "\nStoppen finnes ikke på denne ruten.\n"
                      << "\nStoppested (entydig navn / tall / ENTER"
                      << " for å avslutte): ";
@@ -547,7 +609,7 @@ void Rute::smettStopp() {
                 //send inn i while igjen, stopp er ikke på ruta
             }
         } else {
-            navn = ""; // TEST
+            fNavn = ""; // må være her hvis neste input er ENTER
             cout << "\nIngen entydig stopp funnet.\n"
                  << "\nStoppested (entydig navn / tall / ENTER"
                  << " for å avslutte): ";
@@ -559,7 +621,7 @@ void Rute::smettStopp() {
     if (fNavn.size() > 0) { // Hvis suksessfull funn av startsted
         cout << "\n\nMellom slutt\n"
              << "Stoppested (entydig navn / tall / ENTER for å avslutte): ";
-        getline(cin, navn);
+        getline(cin, navn); // Leser navn fra bruker
 
         while (navn.size() > 0) { // Så lenge ikke skrevet enter:
             navn = gStoppestederBase.byttBokstaver(navn); // fjerner æøå
@@ -581,19 +643,41 @@ void Rute::smettStopp() {
                 aStoppNr = aIndeks+1; // Setter eget stoppNr
 
                 if (aStoppNr != fStoppNr) { // Hvis ikke samme stopp 2x på rad
-                    // Finnes stoppen på ruta?
+                    // Hvis stopp finnes på ruten:
                     if (finnesStopp(aStoppNr)) {
-                        // Sjekker om stoppene er nabo på ruta:
                         // Henter peker til egen stopp:
                         aStopp = finnStopp(aStoppNr);
+                        // Sjekker om stoppene er nabo på ruta:
                         if (erNabo(fStopp, aStopp)) {
                             // Henter peker til eget stoppested i vector
                             aStoppested = gStoppestederBase.finnDuplikat(aNavn);
-                            // Henter peker til eget stopp i ruten
-                            //aStopp = finnStopp(aStoppNr);
+                            // Hvis sluttsted er før startsted, bytt alt:
+                            if (erForst(fStopp, aStopp)) {
+                                tempNavn = fNavn;
+                                fNavn = aNavn;
+                                aNavn = tempNavn;
+                                tempIndeks = fIndeks;
+                                fIndeks = aIndeks;
+                                aIndeks = tempIndeks;
+                                tempStoppNr = fStoppNr;
+                                fStoppNr = aStoppNr;
+                                aStoppNr = tempStoppNr;
+                                tempStoppested = fStoppested;
+                                fStoppested = aStoppested;
+                                aStoppested = tempStoppested;
+                                tempStopp = fStopp;
+                                fStopp = aStopp;
+                                aStopp = tempStopp;
+
+                                tempNavn = "";
+                                tempIndeks = -1;
+                                tempStoppNr = -1;
+                                tempStoppested = nullptr;
+                                tempStopp = nullptr;
+                            }
                             navn = ""; // Sørger for at man kommer seg ut av while
                         } else {
-                            navn = ""; // TEST
+                            aNavn = ""; // må være her hvis neste input er ENTER
                             // Stoppene er ikke naboer på ruta
                             cout << "\nStoppene er ikke naboer på ruten.\n"
                                  << "\nStoppested (entydig navn / tall / "
@@ -602,7 +686,7 @@ void Rute::smettStopp() {
                         }
 
                     } else {
-                        navn = ""; // TEST
+                        aNavn = ""; // må være her hvis neste input er ENTER
                         // stoppen er ikke på ruta
                         cout << "\nStoppen er ikke på ruten.\n"
                              << "\nStoppested (entydig navn / tall / "
@@ -611,7 +695,7 @@ void Rute::smettStopp() {
                     }
 
                 } else {
-                    navn = ""; // TEST
+                    aNavn = ""; // må være her hvis neste input er ENTER
                     // andre stopp er samme som første stopp
                     cout << "\nStart- og sluttstopp kan ikke være lik.\n"
                          << "\nStoppested (entydig navn / tall / "
@@ -620,8 +704,8 @@ void Rute::smettStopp() {
                 }
 
             } else {
-                navn = ""; // TEST
-                // IKKE ENTYDIG NAVN
+                aNavn = ""; // Må være her hvis neste input er ENTER
+                // Navnet er ikke entydig:
                 cout << "\nIngen entydig stopp funnet.\n"
                      << "Stoppested (entydig navn / tall / ENTER"
                      << " for å avslutte): ";
@@ -634,7 +718,7 @@ void Rute::smettStopp() {
         cout << "\n\nNye stoppested(er) etter " << fNavn
              << " og før " << aNavn << ":\n"
              << "Stoppested (entydig navn / tall / ENTER): ";
-        getline (cin, navn);
+        getline (cin, navn); // Leser navn fra bruker
 
         while (navn.size() > 0) { // Så lenge ikke tastet enter:
             navn = gStoppestederBase.byttBokstaver(navn); // Fjerner æøå
@@ -647,7 +731,8 @@ void Rute::smettStopp() {
                     navn = gStoppestederBase.hentNavnVhaIndeks(stoppNr);
                 }
             }
-            nNavn = gStoppestederBase.finnEntydig(navn); // Sjekker for entydighet
+            // Sjekker for entydighet:
+            nNavn = gStoppestederBase.finnEntydig(navn);
 
             if (nNavn.size() > 0) { // Hvis entydig navn
             // Henter egen indeks
@@ -666,14 +751,13 @@ void Rute::smettStopp() {
                             naboIndeks = nStoppested->hentNaboIndeks(fStoppNr);
                             // Henter tid til nabo:
                             tid = nStoppested->hentNaboTid(naboIndeks);
+                            // Oppretter nytt stopp på ruten:
                             nStopp = new Stopp(nStoppNr, tid);
-                            // Hvordan får jeg satt dette i listen riktig???
-                            // Insert evt., men skjønner ikke helt hvordan det
-                            // fungerer
+                            // Sørger for at stopp blir smettet inn på rett sted:
                             auto it = find(stoppene.begin(), stoppene.end(), aStopp);
                             stoppene.insert(it, nStopp); // Settes inn foran
                                                          // slutt stopp i intervall
-                            // Oppdaterer peker og fStoppNr for videre bruk:
+                            // Oppdaterer peker, indeks og stoppNr for videre bruk:
                             fStoppNr = nStoppNr;
                             fStoppested = nStoppested;
                             fIndeks = indeks;
@@ -710,24 +794,27 @@ void Rute::smettStopp() {
                             getline(cin, navn);
                         }
                     } else {
-                        navn = ""; // TEST
+                        // Stoppen finnes allerede på ruten:
+                        nNavn = ""; // Må være her hvis neste input er ENTER
                         cout << "\nStoppet finnes allerede på ruten.\n"
                              << "\nStoppested (entydig navn / tall / "
                              << "ENTER for å avslutte): ";
                         getline(cin, navn);
-                        // Stoppen finnes allerede på ruten
+                        
                     }
                 } else {
-                    navn = ""; // TEST
+                    // Stoppen er en av de som skal smettes inn mellom:
+                    nNavn = ""; // Må være her hvis neste input er ENTER
                     cout << "\nStoppet finnes allerede på ruten.\n"
                          << "\nStoppested (entydig navn / tall / "
                          << "ENTER for å avslutte): ";
                     getline(cin, navn);
-                    // Stoppen er en av de som skal smettes inn mellom
+                    
                 }
 
             } else {
-                navn = ""; // TEST
+                // Stopp er ikke entydig:
+                nNavn = ""; // Må være her hvis neste input er ENTER
                 cout << "\nIngen entydig stopp funnet.\n"
                      << "Stoppested (entydig navn / tall / ENTER"
                      << " for å avslutte): ";
@@ -740,9 +827,10 @@ void Rute::smettStopp() {
         cout << "\n\nFra " << nNavn << " til " << aNavn << ":\n";
         // Hvis nabo finnes fra før:
         if (aStoppested->finnesNabo(nStoppNr)) {
+            // Henter nabo sin indeks og allerede registrert tid:
             naboIndeks = aStoppested->hentNaboIndeks(nStoppNr);
             tid = nStoppested->hentNaboTid(naboIndeks);
-            aStopp->nr = tid; // oppdaterer tid til forrige nabo
+            aStopp->minutter = tid; // oppdaterer tid til forrige nabo på ruten
             cout << "\nTiden mellom stoppestedene er allerede "
                  << "registrert som " << tid << " minutter.\n\n";
 
@@ -759,7 +847,8 @@ void Rute::smettStopp() {
             aStoppested->settNaboIndeks(indeks);
             // Oppdaterer egen stopps tid til nabo vektor
             aStoppested->settNaboTid(tid);
-            aStopp->nr = tid; // oppdaterer tid til forrige nabo
+            aStopp->minutter = tid; // oppdaterer tid til forrige nabo
+            cout << '\n';
             skrivRute(Fram); // skriver oppdatert rute forlengs
         }
     }
@@ -786,7 +875,7 @@ void Rute::smettStopp() {
  */
 void Rute::lesData() {
     string navn,
-           fNavn;
+           fNavn; // faktisk navn (entydig)
     int stoppNr = 0,
         indeks = 0,
         naboIndeks = 0,
diff --git a/rute.h b/rute.h
index 05868fd..faf4445 100644
--- a/rute.h
+++ b/rute.h
@@ -35,6 +35,7 @@ class Rute {
     public:
         Rute();
         Rute(std::ifstream & inn);
+        bool erForst(Stopp* s1, Stopp* s2);
         bool erListeGyldig();
         bool erNabo(Stopp* s1, Stopp* s2);
         bool erTall(std::string nvn);
-- 
GitLab