\documentclass[uebung]{../../../lecture}

\title{IPI: Übungsblatt 10}
\author{Samuel Weidemaier, Christian Merten}

\begin{document}

\begin{tabular}{|c|m{1cm}|m{1cm}|m{1cm}|m{1cm}|@{}m{0cm}@{}}
    \hline
    Aufgabe & \centering A1 & \centering A2 & \centering A3 & \centering $\sum$ & \\[5mm] \hline
    Punkte & & & & & \\[5mm] \hline
\end{tabular}

\begin{aufgabe} Lesen und Schreiben von Dateien
    \begin{lstlisting}[language=C++, title=readfiles.cpp, captionpos=b]
#include <fstream>
#include <iostream>
#include <string>

using namespace std;

int main(int argc, char* argv[]) {
    // check if correct argument count
    if (argc < 2) {
        printf("Dateiname erwartet\n");
        return 1;
    }

    // get filename from argument list
    string filename = argv[1];
    // open input file
    ifstream fileIn;
    fileIn.open(filename + ".txt");
    // open output file
    ofstream fileOut;
    fileOut.open(filename + "-a.txt");
    // check if we could open the files
    if (!fileIn.good() || !fileOut.good()) {
        // could not open files
        cout << "Konnte Datei " + filename + ".txt nicht lesen" << endl;
        return 1;
    }
    string input; // variable containing line
    int lineNo = 1; // count lines
    while(getline(fileIn, input)) { // while there is still a line left
        // write out line with prepended line number to output file
        fileOut << to_string(lineNo) + ": " + input << endl;
        // increment line counter
        lineNo += 1;
    }
    // close files
    fileIn.close();
    fileOut.close();
}\end{lstlisting}
\end{aufgabe}

\begin{aufgabe} Fehler sind im Quellcode markiert
    \begin{lstlisting}[language=C++, title=Fehlersuche, captionpos=b]
#include <iostream>
class A
{
    public:
        int ap;
        void X();
    private:
        int aq;
        void aX();
};

class B : public A
{
    public:
        int bp;
        void Y();
    private:
        int bq;
        void bY();
};

class C : public B
{
    public:
        int cp;
        void Z();
    private:
        int cq;
        void cZ();
};

void A::X() { };
void A::aX() { };
void B::bY() { };
void C::Z() { };

void B::Y()
{
    bq = bp;
    aq = ap; // Fehler: A::aq ist privat, also in B nicht sichtbar
    bY();
}

void C::cZ()
{
    ap = 1;
    bp = 2;
    cq = 3;
    X();
    Y();
    aX(); // Fehler: A::aX() ist privat, also in C nicht sichtbar
}

int main()
{
    A a;  B b;  C c;

    a.X();
    b.bY(); // Fehler: B::bY() ist privat, also hier nicht sichtbar
    c.cp = 4;
    c.bp = 1;
    c.ap = 2;
    c.aq = 5; // Fehler: A::aq ist privat, in C nicht sichtbar und erst recht nicht hier

    b.ap = c.ap;

    return 0;
}\end{lstlisting}
\end{aufgabe}

\begin{aufgabe}
    Fehler wurden wegkommentiert mit Begründung dahinter, hinter den
    korrekten Aufrufen steht jeweils, welche Implementation aufgerufen wird.
    \begin{lstlisting}[language=C++, title=Virtuelle Methoden, captionpos=b]
// A a; A abstrakte Klasse
B b;
C c;
A* pa=&b;
B* pb=&c;
float x = 1.2;
pa->a(); // A::a()
pa->va(); // B::va()
pa->a(1); // B::a(int)
// pa->c(); A::c() private, hier nicht sichtbar
// pa->b(); pa ist vom Typ A* und kennt deswegen b() nicht
// pa->vb(); pa ist vom Typ A* und kennt deswegen vb() nicht
pa->a(x); // B::a(int), hier wird double x implizit zu int gecastet
// pb->a(); pb ist vom Typ B*, hier ist A::a() ueberladen durch
// entweder B::a(double) bzw. B::a(int), deswegen existiert B::a() nicht
pb->va(); // C::va()
pb->a(1); // B::a(int)
// pb->c(); A::c() private, deswegen hier nicht sichtbar
pb->b(); // B::b()
pb->vb(); // B::vb()
pb->a(x); // B::a(double)
pa = &c;
pa->a(); // A::a()
pa->va(); // C::va()
pa->a(1); // B::a(int)
// pa->c(); A::c() private, hier nicht sichtbar
// pa->b(); pa ist vom Typ A*, kennt deswegen b() nicht
// pa->vb(); pa ist vom Typ A*, kennt deswegen vb() nicht
pa->a(x); // B::a(int), hier wird double x implizit zu int gecastet\end{lstlisting}
\end{aufgabe}

\end{document}
