faecher:informatik:oberstufe:java:aoc:aco2023:day7:start

Unterschiede

Hier werden die Unterschiede zwischen zwei Versionen der Seite angezeigt.

Link zu der Vergleichsansicht

Beide Seiten, vorherige Überarbeitung Vorherige Überarbeitung
Nächste Überarbeitung
Vorherige Überarbeitung
faecher:informatik:oberstufe:java:aoc:aco2023:day7:start [07.12.2023 14:26] – [Hilfestellung Teil 1] Marco Kuemmelfaecher:informatik:oberstufe:java:aoc:aco2023:day7:start [07.12.2023 19:43] (aktuell) – [Variante 2: Objekte] Frank Schiebel
Zeile 1: Zeile 1:
 +
 +~~NOTOC~~
 <tabs> <tabs>
   * [[#variante1|Variante 1]]   * [[#variante1|Variante 1]]
 +  * [[#variante2|Variante 2: Objekte und Comparable]]
  
 <pane id="variante1">  <pane id="variante1"> 
Zeile 129: Zeile 132:
 </code> </code>
 ++++ ++++
 +
 +====== Hilfestellung Teil 2 ======
 +Für Teil 2 benötigt man an zwei Stellen kleinere Anpassungen.
 +  - Bei der Erfassung der Types muss anders vorgegangen werden. Man kann die Methode ''getType()'' so umprogrammieren, dass sie nun die Joker ''J'' zunächst bewusst ignoriert. Anschließend nimmt man den errechneten Karten-Typ und korrigiert ihn pro vorhandenen Joker 'nach oben'. Beispiel: ''4JJKQ'' wird zunächst exklusive der zwei J als 'High Card' klassifiziert. Nimmt man im ersten Durchlauf einen Joker hinzu, so **muss** aus einer 'High Card' immer Päärchen werden. Nimmt man im zweiten Durchlauf den zweiten Joker hinzu, so **muss** aus einem Päärchen ein Drilling werden. Das ist damit die finale Kategorie dieser Karte.
 +  - Der Comparator muss minimal umgeschrieben werden, indem man die Reihenfolge der Zeichen ändert.
 +
 +
 +++++ Lösungsvorschlag |
 +<code java>
 +private int getType2(String hand) {
 +    boolean fiveOfAKind = false;
 +    boolean fourOfAKind = false;
 +    boolean threeOfAKind = false;
 +    int pairs = 0;
 +
 +    char[] chars = hand.toCharArray();
 +    Arrays.sort(chars);
 +
 +    char lastChar = chars[0];
 +    int counter = 1;
 +    for (int i = 1; i < chars.length; i++) {
 +        if (chars[i] == 'J') {
 +            continue;
 +        }
 +        
 +        if (chars[i] != lastChar) {
 +
 +            if (counter == 4) {
 +                fourOfAKind = true;
 +            } else if (counter == 3) {
 +                threeOfAKind = true;
 +            } else if (counter == 2) {
 +                pairs++;
 +            }
 +            lastChar = chars[i];
 +            counter = 1;
 +            continue;
 +        }
 +
 +        counter++;
 +    }
 +    if (counter == 5) {
 +        fiveOfAKind = true;
 +    } else if (counter == 4) {
 +        fourOfAKind = true;
 +    } else if (counter == 3) {
 +        threeOfAKind = true;
 +    } else if (counter == 2) {
 +        pairs++;
 +    }
 +
 +    if (fiveOfAKind) {
 +        return 0;
 +    } else if (fourOfAKind) {
 +        return 1;
 +    } else if (threeOfAKind && pairs == 1) {
 +        return 2;
 +    } else if (threeOfAKind && pairs == 0) {
 +        return 3;
 +    } else if (pairs == 2) {
 +        return 4;
 +    } else if (pairs == 1) {
 +        return 5;
 +    } else {
 +        return 6;
 +    }
 +}
 +
 +private int pimpType(int type, String card) {
 +    int amountOfJ = 0;
 +    for (int i = 0; i < card.length(); i++) {
 +        if (card.charAt(i) == 'J') {
 +            amountOfJ++;
 +        }
 +    }
 +
 +    int result = type;
 +    for (int i = 0; i < amountOfJ; i++) {
 +        if (type == 0 || type == 1) {
 +            type = 0;
 +        } else if (type == 2 || type == 3) {
 +            type = 1;
 +        } else if (type == 4) {
 +            type = 2;
 +        } else if (type == 5) {
 +            type = 3;
 +        } else {
 +            type = 5;
 +        }
 +    }
 +
 +    return type;
 +}
 +
 +public long partTwo() {
 +    ArrayList<String[]> lines = new ArrayList<String[]>();
 +
 +    for (String line: inputLines) {
 +        lines.add(line.split(" "));
 +    }
 +
 +    // Die folgende Datenstruktur enthält 7 ArrayLists für String[] (die einzelnen Zeilen).  
 +    // In der ersten ArrayList werden die stärksten Kartentypen gespeichert und in den darauffolgenden die schwächeren.
 +    ArrayList<ArrayList<String[]>> ranks = new ArrayList<ArrayList<String[]>>();
 +    for (int i = 0; i < 7; i++) {
 +        ranks.add(new ArrayList<String[]>());
 +    }
 +
 +    // sortiere die einzelnen Zeilen nach Karten-Typ-Rang. Es ist noch NICHT nach Kartenwert innerhalb eines Kartentyps sortiert.
 +    for (String[] line: lines) {
 +        int type = getType2(line[0]);
 +        type = pimpType(type, line[0]);
 +        ranks.get(type).add(line);
 +    }
 +
 +    long result = 0;
 +    int rankCounter = 1;
 +    for (int r = ranks.size() - 1 ; r >= 0; r--) {
 +        ArrayList<String[]> rank = ranks.get(r);
 +
 +        rank.sort(cardComparator2);
 +        for (int l = rank.size() - 1; l >= 0; l--) {
 +            String line = rank.get(l)[1];
 +            result += rankCounter * Integer.parseInt(line);
 +            rankCounter++;
 +        }
 +    }
 +
 +    return result;
 +}
 +</code>
 +++++
 +</pane>
 +<pane id="variante2"> 
 +====== Variante 2: Objekte ======
 +
 +Variante zwei wieder mit Objekten:
 +
 +{{ :faecher:informatik:oberstufe:java:aoc:aco2023:day7:2023-12-07_20-31.png?nolink&600 |}}
 +
 +Wie bei den Sortieralgorithmen  [[faecher:informatik:oberstufe:algorithmen:sorting:problemstellung:start|hier]] erläutert, kann man bei Java-Klassen das "Comparable"-Interface implementieren, damit ist es möglich, in der Methode ''compareTo'' eigene Regeln festzulegen, nach denen die Objekte dieser Klasse sortiert werden sollen. Genau das benötigen wir hier:
 +
 +  * Wir erzeugen für jede Zeile in der Eingabe ein ''Hand''-Objekt, für den wir den Typ bestimmen und in einem Attribut ablegen.
 +  * Dann wollen wir die Objekte sortieren - allerdings reicht der Vergleich der Typen nicht aus, weil man bei zwei "Hands" desselben Typs die einzelnen Karten vergleichen soll.
 +  * Also implementieren wir in der Klasse Hand die Methode ''compareTo'', die genau das macht.
 +
 +Die Lösung für Teil 1 und Teil 2 findet sich im selben Code, ich habe versucht das verständlich zu kommentieren. Wenn du nicht viel Programmiererfahrung hast, musst du wahrscheinlich auch an anderer Stelle noch nachlesen:
 +
 +  * Teil 1: [[https://codeberg.org/qg-info-unterricht/aoc-bluej-2023/src/commit/a897fdacc8c6ad31785a9eb3c7bb682192a925c9/Hand.java|Hand.java]], [[https://codeberg.org/qg-info-unterricht/aoc-bluej-2023/src/commit/a897fdacc8c6ad31785a9eb3c7bb682192a925c9/day7.java|day7.java]]
 +  * Teil 1&2: [[https://codeberg.org/qg-info-unterricht/aoc-bluej-2023/src/branch/main/Hand.java|Hand.java]]  [[https://codeberg.org/qg-info-unterricht/aoc-bluej-2023/src/branch/main/day7.java|day7.java]]
 +
  
 </pane> </pane>
 </tabs> </tabs>
  • faecher/informatik/oberstufe/java/aoc/aco2023/day7/start.1701959178.txt.gz
  • Zuletzt geändert: 07.12.2023 14:26
  • von Marco Kuemmel