#include <fstream>
#include <print>
#include <string>
#include <algorithm>
#include <ranges>

// Datei mit den Aktienkursen
constexpr auto FILENAME = "../../04_Data/aktien.csv";
constexpr auto SIZE = 12;

// Feld zum Ablegen der Aktienkurse
struct Aktie
{
    std::string name;       // Aktiename
    float       aktVal;     // aktueller Kurs
    float       maxVal;     // hoechster Kurs
    std::string datum;      // Kursdatum
} aktien[SIZE];

int main()
{
    // Datei oeffnen
    std::ifstream infile(FILENAME);
    if (!infile)
    {
        std::println("Datei {} wurde nicht gefunden!", FILENAME);
        exit(1);
    }

    // Daten einlesen
    for (auto index=0; index<SIZE; index++)
    {
        std::getline(infile, aktien[index].name, ';');
        if (infile.eof())
        {
            std::println("Fehler beim Einlesen der Datei!");
            infile.close();
            exit(1);
        }
        // Niedrigsten Kurs einlesen und Semikolon ueberspringen
        infile >> aktien[index].aktVal;
        infile.ignore(1);
        // Hoechsten Kurs einlesen und Semikolon ueberspringen
        infile >> aktien[index].maxVal;
        infile.ignore(1);
        // Datum lesen (Rest der Zeile)
        getline(infile, aktien[index].datum);
    }

    // Lambda-Funktion: Aktie ausgeben
    auto PrintAktie = [](const Aktie& obj)
    {
        std::println("AG: {}, akt {:.2f}, max {:.2f} am {}",
            obj.name, obj.aktVal, obj.maxVal, obj.datum);
    };

    // Alle Aktien ausgeben
    std::println("Aktienkurse in EUR:");
        std::ranges::for_each(aktien, PrintAktie);

    // Alle Kurswerte, deren AG mit dem Buchstaben D beginnen,
    // in Dollar umrechnen (1 EUR = 1.2 $) und ausgeben
    std::println("\nAktienkurse der AGs D* in Dollar:");
    // Lambda-Funktion: Liefert true wenn Aktie mit D beginnt
    auto afilter = [](const Aktie& obj)
                    { return obj.name[0] == 'D'; };
    // Lambda-Funktion zur Umrechnung EUR in USD; Kurs als Capture
    auto atrans = [kurs=1.2f](Aktie& obj)
                    { obj.maxVal *= kurs; obj.aktVal *= kurs; return obj; };
    // Kurse der Aktien mit D* in USD ausgeben
    std::ranges::for_each(aktien | std::views::filter(afilter)
        | std::views::transform(atrans) , PrintAktie);

}
