Laden...
M
Benutzerbeschreibung
~ 8 Jahre C++ mit Borland und VCL; ~ 2 Jahre JavaScript mit Grease-/Tamper-Monkey; ~ 2 Jahre grundlegendes Verständnis von Assembler durch reverse engineering; Seit 30.10.2014 nun Visual Studio 2013 und C# .NET

Forenbeiträge von Max89 Ingesamt 2 Beiträge

05.11.2014 - 12:50 Uhr

Vielen lieben Dank für die zahlreichen Antworten und Lösungsansätze.
Nachdem ich jetzt Eure Vorschläge gesehen habe, frage ich mich echt warum ich das so kompliziert gelöst habe. 8o
Manchmal denke ich halt viel zu kompliziert und "sehe den Wald vor lauter Bäumen nicht".

Da ich die Distanz auch über die Geschwindigkeit berechne, werde ich wohl zur Berechnung der Durchschnittsgeschwindigkeit die Summengeschwindigkeit/SummandenZahl verwenden.
-> Das ist ja auch genau das, was ich aktuell mache - nur das mein Weg halt unnötig kompliziert ist.
-> An dieser Stelle möchte ich noch erwähnen, dass ich die Zwischenwerte nicht benötige und somit der Weg mit Array ja Blödsinn ist.

Was bedeutet die Wertigkeit? Ist das die Zeitspanne in der der selbe Geschwindigkeitswert gilt? Ich verstehe den Code nicht ganz.

Die Wertigkeit steht in meinem Code für die Anzahl der gespeicherten Geschwindigkeit.
Wenn also 120 km/h 2x gemessen wird, steht im Array: 120|2
Das funktioniert natürlich, ist aber - wie erwähnt - einfach nur umständlich.

beachte bitte
>
Punkt 4a) "Bittet nicht um Code-Reviews von längerem oder gar kompletten Quellcode."

Ich hatte diesen Punkt zwar gelesen und auch verstanden, aber scheinbar hatte ich das "längerem Quellcode" falsch gedeutet.
Ich war der Meinung man sollte halt nicht den gesamten Quelltext von etlichen Funktionen posten.
Ich entschuldige mich dafür und werde dies in Zukunft vermeiden!

Liebe Grüße
Max

05.11.2014 - 01:43 Uhr

Hallo, liebe Community.

Mein Name ist Max und dies ist mein erster Beitrag hier im Forum. 🙂
Die :rtfm: Foren-Regeln habe ich natürlich gelesen!

Ich programmiere rein aus Interesse und habe vor ca. 8 Jahren mit Borland C++ und der VCL begonnen.
Seit ein paar Tagen bin ich nun (endlich) auf Visual Studio 2013 Express und C# .NET umgestiegen.

Soweit erstmal zu mir - falls noch jemand Fragen hat, immer her damit!
Nun aber erstmal zu meinem aktuellen Projekt:

Ich habe mir ein Programm mit folgenden Funktionen geschrieben:

  • Auslesen der aktuellen Geschwindigkeit aus dem Speicher von einem Spiel
    -> Timer (10 ms), OpenProcess, ReadProcessMemory, convert byte[] to float
  • Auswertung der Geschwindigkeit, Beschleunigung, zurückgelegten Distanz und durchschnittlichen Geschwindigkeit
    -> Timer (250 ms), Anzeige der Daten in einem ListView
  • Auswertung startet automatisch, sobald die Geschwindigkeit 2 km/h übersteigt
    -> Es wird jeweils eine neue Zeile im ListView angelegt und die Werte werden aller 250 ms aktualisiert

Dieses Projekt habe ich letzte Woche noch mit Borland C++ programmiert und zu Übungszwecken
nun nochmals mit Visual Studio 2013 und C# .NET nachprogrammiert.
Die Umstellung hat zwar etwas gedauert und war teilweise auch (erstmal) verwirrend, aber ich denke
ich konnte mich nun doch recht gut mit Visual Studio und C# einarbeiten. 🙂

Diesen Code verwende ich momentan zur Berechnung der durchschnittlichen Geschwindigkeit:


        // durchschnittliche Geschwindigkeit als Array 150x2 Werte
        // -> 450 km/h geteilt durch 3 km/h = 150 Items für mögliche Geschwindigkeiten
        // Wertepaare = Geschwindigkeit und Wertigkeit
        private float[,] fSpeedAverage = new float[150, 2];

        /// <summary>
        /// Berechnet die durchschnittliche Geschwindigkeit.
        /// - Es werden 150 Wertepaare (Geschwindigkeit, Wertigkeit) gespeichert.
        /// - Geschwindigkeit wird bei jeder Berechnung mit der Wertigkeit multipliziert.
        /// - ähnliche Werte werden zusammengefasst (3 km/h Toleranz)
        /// </summary>
        /// <param name="fSpeed">(float) Geschwindigkeit in km/h</param>
        private void LogAverage(float fSpeed)
        {
            // Zähler für die Anzahl der gespeicherten Werte
            int iCounter = 0;

            // wurde ein neuer Wert gespeichert bzw. ein alter Wert aktualisiert?
            bool bChanged = false;

            // gesamte Liste durchlaufen und prüfen ob die aktuelle Geschwindigkeit bereits gespeichert wurde
            for (int i = 0; i < fSpeedAverage.GetLength(0); ++i)
            {
                // aktuellen Wert mit der aktuellen Geschwindigkeit vergleichen
                // Toleranz liegt bei 3 km/h, dies entspricht +/- 1.5f
                if (!bChanged && fSpeedAverage[i, 0] != 0 && Math.Abs((float)(fSpeedAverage[i, 0] - fSpeed)) <= 1.5f)
                {
                    // nur die Wertigkeit erhöhen
                    fSpeedAverage[i, 1]++;

                    // Zähler erhöhen und Änderung speichern
                    iCounter++; bChanged = true;
                }

                // aktueller Wert ist leer (0)
                else if (!bChanged && fSpeedAverage[i, 0] == 0)
                {
                    // aktuelle Geschwindigkeit und Wertigkeit '1' eintragen
                    fSpeedAverage[i, 0] = fSpeed;
                    fSpeedAverage[i, 1] = 1;

                    // Zähler erhöhen und Änderung speichern
                    iCounter++; bChanged = true;
                }

                // Wert ist nicht 0 und liegt nicht innerhalb der Toleranz - Zähler erhöhen
                else if (fSpeedAverage[i, 0] != 0) iCounter++;

                // Wert ist 0 und es wurde bereits ein Wert gespeichert - Schleife verlassen
                else if (bChanged && fSpeedAverage[i, 0] == 0) break;
            }

            // --------------------------------------------------------------
            // Durchschnitt berechnen

            // durchschnittliche Geschwindigkeit
            float fSpeedAvg = 0.0f;

            // Anzahl der Werte (Wertigkeit)
            int iAnzahl = 0;
                
            // Alle Werte addieren und Wertigkeit beachten
            // (Counter wird vorsichtshalber nochmal mit dem maximalen Index verglichen)
            for (int i = 0; i < iCounter && iCounter <= fSpeedAverage.GetLength(0); ++i)
            {
                // Speed (gesamt) += (speed * wertigkeit)
                fSpeedAvg += ((float)fSpeedAverage[i, 0] * fSpeedAverage[i, 1]);

                // Anzahl der Werte (Wertigkeit) addieren
                iAnzahl += (int)fSpeedAverage[i, 1];
            }

            // Debug:
            // Text = "iCounter = " + iCounter.ToString() + " | iAnzahl = " + iAnzahl.ToString();

            // Wert durch die Anzahl der Werte (Summe aller Wertigkeiten) teilen
            fSpeedAvg = (float)(fSpeedAvg / iAnzahl);

            // durchschnittliche Geschwindigkeit in der Liste anzeigen
            // Parameter = float <Wert>, String <Format>, int <SubItem-Index der aktuellen Zeile>
            WerteAnzeigen(fSpeedAvg, "km/h", 11);
        }

Der Code wird aller 250 ms aufgerufen und macht auch genau das was er machen soll. 🙂_(Die Funktion 'WerteAnzeigen()' ist außerhalb deklariert und ist für das Zeichnen der Liste zuständig.)_

Meine Frage(n) wäre(n) nun:

  • Gibt es eine elegantere Lösung um die Durchschnittsgeschwindigkeit zu berechnen?
    -> Ich musste bisher noch nie den Durchschnitt einer unbestimmten Anzahl von Werten über einen unbestimmten Zeitraum berechnen.
    -> Daher war dies mein (2.) Versuch eine Lösung für dieses Problemchen zu finden.
  • Gibt es allgemeine Vorschläge oder Kritik zu meinem Code?
    -> Vorschläge und Tipps sind immer gern gesehen. Ich lerne gern etwas dazu!

Anmerkung:
Ich habe mich für die 3 km/h Toleranz entschieden um die Anzahl der Werte zumindest auf ein Maximum von 150 begrenzen zu können.

Liebe Grüße
Max