package pl.klemba.aoc.day3

import java.io.File

fun main() {
  // ----- PART 1 -----
  File(inputPath)
    .readLines()
    .let { schematic ->
      schematic.mapIndexed { lineIndex, line ->
        numberRegex.findAll(line)
          .filter { schematic.checkIfAdjacentToASymbol(it.range, lineIndex) }
          .map { it.value.toInt() }
          .sum()
      }.sum()
        .let { println(it) }
    }

  // ----- PART 2 -----
  val schematic = File(inputPath)
    .readLines()

  val numbersSchematic = schematic.mapIndexed { lineIndex, line ->
    numberRegex.findAll(line)
      .filter { schematic.checkIfAdjacentToASymbol(it.range, lineIndex) }
      .toList()
  }

  schematic.mapIndexed { lineIndex, line ->
    gearRegex.findAll(line)
      .map {
        numbersSchematic.sumGearRatio(it.range, lineIndex)
      }
      .sum()
  }.sum()
    .let { println(it) }

}

private fun List<List<MatchResult>>.sumGearRatio(range: IntRange, lineIndex: Int): Int {
  val listOfAdjacentNumbers = mutableListOf<MatchResult>()
  if (lineIndex != 0) {
    listOfAdjacentNumbers.addAll(this[lineIndex - 1].getNumbersForIndex(range, this[0].lastIndex))
  }
  if (lineIndex != this.lastIndex) {
    listOfAdjacentNumbers.addAll(this[lineIndex + 1].getNumbersForIndex(range, this[0].lastIndex))
  }

  listOfAdjacentNumbers.addAll(this[lineIndex].getNumbersForIndex(range, this[0].lastIndex))
  return if (listOfAdjacentNumbers.size == 2) {
    listOfAdjacentNumbers.map { it.value.toInt() }.reduce { acc, value -> acc * value }
  }
  else 0
}

private fun List<MatchResult>.getNumbersForIndex(range: IntRange, lastIndex: Int): List<MatchResult> {
  val rangeToCheck = getRangeToCheck(range, lastIndex)
  return this.filter { it.isAdjacentToGear(rangeToCheck) }
}

private fun MatchResult.isAdjacentToGear(rangeToCheck: IntRange) = range.intersect(rangeToCheck).isNotEmpty()

private fun List<String>.checkIfAdjacentToASymbol(numberIndices: IntRange, lineIndex: Int): Boolean {
  // check top and bottom
  if (lineIndex != 0) {
    if (this[lineIndex - 1].checkIfSymbolsExistForRange(numberIndices, this[0].lastIndex)) return true
  }
  if (lineIndex != this.lastIndex) {
    if (this[lineIndex + 1].checkIfSymbolsExistForRange(numberIndices, this[0].lastIndex)) return true
  }

  // check sides
  if (numberIndices.first != 0) {
    if (this[lineIndex][numberIndices.first - 1].isASymbol()) return true
  }
  if (numberIndices.last != this[lineIndex].lastIndex) {
    if (this[lineIndex][numberIndices.last + 1].isASymbol()) return true
  }

  return false
}

private fun String.checkIfSymbolsExistForRange(indexRange: IntRange, lineLastIndex: Int): Boolean {
  val rangeToCheck: IntRange = getRangeToCheck(indexRange, lineLastIndex)
  return substring(rangeToCheck).any { it.isASymbol() }
}

private fun getRangeToCheck(indexRange: IntRange, lineLastIndex: Int): IntRange {
  val rangeToCheck: IntRange = when {
    indexRange.first == 0 -> IntRange(0, indexRange.last + 1)
    indexRange.last == lineLastIndex -> IntRange(indexRange.first - 1, indexRange.last)
    else -> IntRange(indexRange.first - 1, indexRange.last + 1)
  }
  return rangeToCheck
}

private fun Char.isASymbol() = this.isDigit().not() && this != '.'

private const val inputPath = "src/main/kotlin/pl/klemba/aoc/day3/input.txt"

private val numberRegex = Regex("\\d+")
private val gearRegex = Regex("\\*")

Compiled from "Main.kt"
public final class pl.klemba.aoc.day3.MainKt {
  private static final java.lang.String inputPath;

  private static final kotlin.text.Regex numberRegex;

  private static final kotlin.text.Regex gearRegex;

  public static final void main();
    Code:
       0: new           #8                  // class java/io/File
       3: dup
       4: ldc           #10                 // String src/main/kotlin/pl/klemba/aoc/day3/input.txt
       6: invokespecial #14                 // Method java/io/File."<init>":(Ljava/lang/String;)V
       9: aconst_null
      10: iconst_1
      11: aconst_null
      12: invokestatic  #20                 // Method kotlin/io/FilesKt.readLines$default:(Ljava/io/File;Ljava/nio/charset/Charset;ILjava/lang/Object;)Ljava/util/List;
      15: astore_1
      16: iconst_0
      17: istore_2
      18: aload_1
      19: checkcast     #22                 // class java/lang/Iterable
      22: astore_3
      23: iconst_0
      24: istore        4
      26: aload_3
      27: astore        5
      29: new           #24                 // class java/util/ArrayList
      32: dup
      33: aload_3
      34: bipush        10
      36: invokestatic  #30                 // Method kotlin/collections/CollectionsKt.collectionSizeOrDefault:(Ljava/lang/Iterable;I)I
      39: invokespecial #33                 // Method java/util/ArrayList."<init>":(I)V
      42: checkcast     #35                 // class java/util/Collection
      45: astore        6
      47: iconst_0
      48: istore        7
      50: iconst_0
      51: istore        8
      53: aload         5
      55: invokeinterface #39,  1           // InterfaceMethod java/lang/Iterable.iterator:()Ljava/util/Iterator;
      60: astore        9
      62: aload         9
      64: invokeinterface #45,  1           // InterfaceMethod java/util/Iterator.hasNext:()Z
      69: ifeq          165
      72: aload         9
      74: invokeinterface #49,  1           // InterfaceMethod java/util/Iterator.next:()Ljava/lang/Object;
      79: astore        10
      81: aload         6
      83: iload         8
      85: iinc          8, 1
      88: istore        11
      90: iload         11
      92: ifge          98
      95: invokestatic  #52                 // Method kotlin/collections/CollectionsKt.throwIndexOverflow:()V
      98: iload         11
     100: aload         10
     102: checkcast     #54                 // class java/lang/String
     105: astore        12
     107: istore        13
     109: astore        14
     111: iconst_0
     112: istore        15
     114: getstatic     #58                 // Field numberRegex:Lkotlin/text/Regex;
     117: aload         12
     119: checkcast     #60                 // class java/lang/CharSequence
     122: iconst_0
     123: iconst_2
     124: aconst_null
     125: invokestatic  #66                 // Method kotlin/text/Regex.findAll$default:(Lkotlin/text/Regex;Ljava/lang/CharSequence;IILjava/lang/Object;)Lkotlin/sequences/Sequence;
     128: aload_1
     129: iload         13
     131: invokedynamic #86,  0             // InvokeDynamic #0:invoke:(Ljava/util/List;I)Lkotlin/jvm/functions/Function1;
     136: invokestatic  #92                 // Method kotlin/sequences/SequencesKt.filter:(Lkotlin/sequences/Sequence;Lkotlin/jvm/functions/Function1;)Lkotlin/sequences/Sequence;
     139: invokedynamic #102,  0            // InvokeDynamic #1:invoke:()Lkotlin/jvm/functions/Function1;
     144: invokestatic  #105                // Method kotlin/sequences/SequencesKt.map:(Lkotlin/sequences/Sequence;Lkotlin/jvm/functions/Function1;)Lkotlin/sequences/Sequence;
     147: invokestatic  #109                // Method kotlin/sequences/SequencesKt.sumOfInt:(Lkotlin/sequences/Sequence;)I
     150: invokestatic  #115                // Method java/lang/Integer.valueOf:(I)Ljava/lang/Integer;
     153: aload         14
     155: swap
     156: invokeinterface #119,  2          // InterfaceMethod java/util/Collection.add:(Ljava/lang/Object;)Z
     161: pop
     162: goto          62
     165: aload         6
     167: checkcast     #121                // class java/util/List
     170: nop
     171: checkcast     #22                 // class java/lang/Iterable
     174: invokestatic  #124                // Method kotlin/collections/CollectionsKt.sumOfInt:(Ljava/lang/Iterable;)I
     177: istore        4
     179: iconst_0
     180: istore        5
     182: getstatic     #130                // Field java/lang/System.out:Ljava/io/PrintStream;
     185: iload         4
     187: invokevirtual #135                // Method java/io/PrintStream.println:(I)V
     190: nop
     191: nop
     192: nop
     193: nop
     194: new           #8                  // class java/io/File
     197: dup
     198: ldc           #10                 // String src/main/kotlin/pl/klemba/aoc/day3/input.txt
     200: invokespecial #14                 // Method java/io/File."<init>":(Ljava/lang/String;)V
     203: aconst_null
     204: iconst_1
     205: aconst_null
     206: invokestatic  #20                 // Method kotlin/io/FilesKt.readLines$default:(Ljava/io/File;Ljava/nio/charset/Charset;ILjava/lang/Object;)Ljava/util/List;
     209: astore_0
     210: aload_0
     211: checkcast     #22                 // class java/lang/Iterable
     214: astore_2
     215: iconst_0
     216: istore_3
     217: aload_2
     218: astore        4
     220: new           #24                 // class java/util/ArrayList
     223: dup
     224: aload_2
     225: bipush        10
     227: invokestatic  #30                 // Method kotlin/collections/CollectionsKt.collectionSizeOrDefault:(Ljava/lang/Iterable;I)I
     230: invokespecial #33                 // Method java/util/ArrayList."<init>":(I)V
     233: checkcast     #35                 // class java/util/Collection
     236: astore        5
     238: iconst_0
     239: istore        6
     241: iconst_0
     242: istore        7
     244: aload         4
     246: invokeinterface #39,  1           // InterfaceMethod java/lang/Iterable.iterator:()Ljava/util/Iterator;
     251: astore        8
     253: aload         8
     255: invokeinterface #45,  1           // InterfaceMethod java/util/Iterator.hasNext:()Z
     260: ifeq          345
     263: aload         8
     265: invokeinterface #49,  1           // InterfaceMethod java/util/Iterator.next:()Ljava/lang/Object;
     270: astore        9
     272: aload         5
     274: iload         7
     276: iinc          7, 1
     279: istore        10
     281: iload         10
     283: ifge          289
     286: invokestatic  #52                 // Method kotlin/collections/CollectionsKt.throwIndexOverflow:()V
     289: iload         10
     291: aload         9
     293: checkcast     #54                 // class java/lang/String
     296: astore        11
     298: istore        12
     300: astore        16
     302: iconst_0
     303: istore        13
     305: getstatic     #58                 // Field numberRegex:Lkotlin/text/Regex;
     308: aload         11
     310: checkcast     #60                 // class java/lang/CharSequence
     313: iconst_0
     314: iconst_2
     315: aconst_null
     316: invokestatic  #66                 // Method kotlin/text/Regex.findAll$default:(Lkotlin/text/Regex;Ljava/lang/CharSequence;IILjava/lang/Object;)Lkotlin/sequences/Sequence;
     319: aload_0
     320: iload         12
     322: invokedynamic #140,  0            // InvokeDynamic #2:invoke:(Ljava/util/List;I)Lkotlin/jvm/functions/Function1;
     327: invokestatic  #92                 // Method kotlin/sequences/SequencesKt.filter:(Lkotlin/sequences/Sequence;Lkotlin/jvm/functions/Function1;)Lkotlin/sequences/Sequence;
     330: invokestatic  #144                // Method kotlin/sequences/SequencesKt.toList:(Lkotlin/sequences/Sequence;)Ljava/util/List;
     333: aload         16
     335: swap
     336: invokeinterface #119,  2          // InterfaceMethod java/util/Collection.add:(Ljava/lang/Object;)Z
     341: pop
     342: goto          253
     345: aload         5
     347: checkcast     #121                // class java/util/List
     350: nop
     351: astore_1
     352: aload_0
     353: checkcast     #22                 // class java/lang/Iterable
     356: astore_2
     357: iconst_0
     358: istore_3
     359: aload_2
     360: astore        4
     362: new           #24                 // class java/util/ArrayList
     365: dup
     366: aload_2
     367: bipush        10
     369: invokestatic  #30                 // Method kotlin/collections/CollectionsKt.collectionSizeOrDefault:(Ljava/lang/Iterable;I)I
     372: invokespecial #33                 // Method java/util/ArrayList."<init>":(I)V
     375: checkcast     #35                 // class java/util/Collection
     378: astore        5
     380: iconst_0
     381: istore        6
     383: iconst_0
     384: istore        7
     386: aload         4
     388: invokeinterface #39,  1           // InterfaceMethod java/lang/Iterable.iterator:()Ljava/util/Iterator;
     393: astore        8
     395: aload         8
     397: invokeinterface #45,  1           // InterfaceMethod java/util/Iterator.hasNext:()Z
     402: ifeq          490
     405: aload         8
     407: invokeinterface #49,  1           // InterfaceMethod java/util/Iterator.next:()Ljava/lang/Object;
     412: astore        9
     414: aload         5
     416: iload         7
     418: iinc          7, 1
     421: istore        10
     423: iload         10
     425: ifge          431
     428: invokestatic  #52                 // Method kotlin/collections/CollectionsKt.throwIndexOverflow:()V
     431: iload         10
     433: aload         9
     435: checkcast     #54                 // class java/lang/String
     438: astore        11
     440: istore        12
     442: astore        16
     444: iconst_0
     445: istore        13
     447: getstatic     #147                // Field gearRegex:Lkotlin/text/Regex;
     450: aload         11
     452: checkcast     #60                 // class java/lang/CharSequence
     455: iconst_0
     456: iconst_2
     457: aconst_null
     458: invokestatic  #66                 // Method kotlin/text/Regex.findAll$default:(Lkotlin/text/Regex;Ljava/lang/CharSequence;IILjava/lang/Object;)Lkotlin/sequences/Sequence;
     461: aload_1
     462: iload         12
     464: invokedynamic #153,  0            // InvokeDynamic #3:invoke:(Ljava/util/List;I)Lkotlin/jvm/functions/Function1;
     469: invokestatic  #105                // Method kotlin/sequences/SequencesKt.map:(Lkotlin/sequences/Sequence;Lkotlin/jvm/functions/Function1;)Lkotlin/sequences/Sequence;
     472: invokestatic  #109                // Method kotlin/sequences/SequencesKt.sumOfInt:(Lkotlin/sequences/Sequence;)I
     475: invokestatic  #115                // Method java/lang/Integer.valueOf:(I)Ljava/lang/Integer;
     478: aload         16
     480: swap
     481: invokeinterface #119,  2          // InterfaceMethod java/util/Collection.add:(Ljava/lang/Object;)Z
     486: pop
     487: goto          395
     490: aload         5
     492: checkcast     #121                // class java/util/List
     495: nop
     496: checkcast     #22                 // class java/lang/Iterable
     499: invokestatic  #124                // Method kotlin/collections/CollectionsKt.sumOfInt:(Ljava/lang/Iterable;)I
     502: istore_3
     503: iconst_0
     504: istore        4
     506: getstatic     #130                // Field java/lang/System.out:Ljava/io/PrintStream;
     509: iload_3
     510: invokevirtual #135                // Method java/io/PrintStream.println:(I)V
     513: nop
     514: nop
     515: return

  private static final int sumGearRatio(java.util.List<? extends java.util.List<? extends kotlin.text.MatchResult>>, kotlin.ranges.IntRange, int);
    Code:
       0: new           #24                 // class java/util/ArrayList
       3: dup
       4: invokespecial #182                // Method java/util/ArrayList."<init>":()V
       7: checkcast     #121                // class java/util/List
      10: astore_3
      11: iload_2
      12: ifeq          54
      15: aload_3
      16: aload_0
      17: iload_2
      18: iconst_1
      19: isub
      20: invokeinterface #186,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
      25: checkcast     #121                // class java/util/List
      28: aload_1
      29: aload_0
      30: iconst_0
      31: invokeinterface #186,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
      36: checkcast     #121                // class java/util/List
      39: invokestatic  #190                // Method kotlin/collections/CollectionsKt.getLastIndex:(Ljava/util/List;)I
      42: invokestatic  #194                // Method getNumbersForIndex:(Ljava/util/List;Lkotlin/ranges/IntRange;I)Ljava/util/List;
      45: checkcast     #35                 // class java/util/Collection
      48: invokeinterface #198,  2          // InterfaceMethod java/util/List.addAll:(Ljava/util/Collection;)Z
      53: pop
      54: iload_2
      55: aload_0
      56: invokestatic  #190                // Method kotlin/collections/CollectionsKt.getLastIndex:(Ljava/util/List;)I
      59: if_icmpeq     101
      62: aload_3
      63: aload_0
      64: iload_2
      65: iconst_1
      66: iadd
      67: invokeinterface #186,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
      72: checkcast     #121                // class java/util/List
      75: aload_1
      76: aload_0
      77: iconst_0
      78: invokeinterface #186,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
      83: checkcast     #121                // class java/util/List
      86: invokestatic  #190                // Method kotlin/collections/CollectionsKt.getLastIndex:(Ljava/util/List;)I
      89: invokestatic  #194                // Method getNumbersForIndex:(Ljava/util/List;Lkotlin/ranges/IntRange;I)Ljava/util/List;
      92: checkcast     #35                 // class java/util/Collection
      95: invokeinterface #198,  2          // InterfaceMethod java/util/List.addAll:(Ljava/util/Collection;)Z
     100: pop
     101: aload_3
     102: aload_0
     103: iload_2
     104: invokeinterface #186,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
     109: checkcast     #121                // class java/util/List
     112: aload_1
     113: aload_0
     114: iconst_0
     115: invokeinterface #186,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
     120: checkcast     #121                // class java/util/List
     123: invokestatic  #190                // Method kotlin/collections/CollectionsKt.getLastIndex:(Ljava/util/List;)I
     126: invokestatic  #194                // Method getNumbersForIndex:(Ljava/util/List;Lkotlin/ranges/IntRange;I)Ljava/util/List;
     129: checkcast     #35                 // class java/util/Collection
     132: invokeinterface #198,  2          // InterfaceMethod java/util/List.addAll:(Ljava/util/Collection;)Z
     137: pop
     138: aload_3
     139: invokeinterface #202,  1          // InterfaceMethod java/util/List.size:()I
     144: iconst_2
     145: if_icmpne     366
     148: aload_3
     149: checkcast     #22                 // class java/lang/Iterable
     152: astore        4
     154: iconst_0
     155: istore        5
     157: aload         4
     159: astore        6
     161: new           #24                 // class java/util/ArrayList
     164: dup
     165: aload         4
     167: bipush        10
     169: invokestatic  #30                 // Method kotlin/collections/CollectionsKt.collectionSizeOrDefault:(Ljava/lang/Iterable;I)I
     172: invokespecial #33                 // Method java/util/ArrayList."<init>":(I)V
     175: checkcast     #35                 // class java/util/Collection
     178: astore        7
     180: iconst_0
     181: istore        8
     183: aload         6
     185: invokeinterface #39,  1           // InterfaceMethod java/lang/Iterable.iterator:()Ljava/util/Iterator;
     190: astore        9
     192: aload         9
     194: invokeinterface #45,  1           // InterfaceMethod java/util/Iterator.hasNext:()Z
     199: ifeq          251
     202: aload         9
     204: invokeinterface #49,  1           // InterfaceMethod java/util/Iterator.next:()Ljava/lang/Object;
     209: astore        10
     211: aload         7
     213: aload         10
     215: checkcast     #204                // class kotlin/text/MatchResult
     218: astore        11
     220: astore        13
     222: iconst_0
     223: istore        12
     225: aload         11
     227: invokeinterface #208,  1          // InterfaceMethod kotlin/text/MatchResult.getValue:()Ljava/lang/String;
     232: invokestatic  #212                // Method java/lang/Integer.parseInt:(Ljava/lang/String;)I
     235: nop
     236: invokestatic  #115                // Method java/lang/Integer.valueOf:(I)Ljava/lang/Integer;
     239: aload         13
     241: swap
     242: invokeinterface #119,  2          // InterfaceMethod java/util/Collection.add:(Ljava/lang/Object;)Z
     247: pop
     248: goto          192
     251: aload         7
     253: checkcast     #121                // class java/util/List
     256: nop
     257: checkcast     #22                 // class java/lang/Iterable
     260: astore        4
     262: nop
     263: iconst_0
     264: istore        5
     266: aload         4
     268: invokeinterface #39,  1           // InterfaceMethod java/lang/Iterable.iterator:()Ljava/util/Iterator;
     273: astore        6
     275: aload         6
     277: invokeinterface #45,  1           // InterfaceMethod java/util/Iterator.hasNext:()Z
     282: ifne          295
     285: new           #214                // class java/lang/UnsupportedOperationException
     288: dup
     289: ldc           #216                // String Empty collection can\'t be reduced.
     291: invokespecial #217                // Method java/lang/UnsupportedOperationException."<init>":(Ljava/lang/String;)V
     294: athrow
     295: aload         6
     297: invokeinterface #49,  1           // InterfaceMethod java/util/Iterator.next:()Ljava/lang/Object;
     302: astore        7
     304: aload         6
     306: invokeinterface #45,  1           // InterfaceMethod java/util/Iterator.hasNext:()Z
     311: ifeq          355
     314: aload         7
     316: aload         6
     318: invokeinterface #49,  1           // InterfaceMethod java/util/Iterator.next:()Ljava/lang/Object;
     323: checkcast     #219                // class java/lang/Number
     326: invokevirtual #222                // Method java/lang/Number.intValue:()I
     329: istore        8
     331: checkcast     #219                // class java/lang/Number
     334: invokevirtual #222                // Method java/lang/Number.intValue:()I
     337: istore        9
     339: iconst_0
     340: istore        10
     342: iload         9
     344: iload         8
     346: imul
     347: invokestatic  #115                // Method java/lang/Integer.valueOf:(I)Ljava/lang/Integer;
     350: astore        7
     352: goto          304
     355: aload         7
     357: checkcast     #219                // class java/lang/Number
     360: invokevirtual #222                // Method java/lang/Number.intValue:()I
     363: goto          367
     366: iconst_0
     367: ireturn

  private static final java.util.List<kotlin.text.MatchResult> getNumbersForIndex(java.util.List<? extends kotlin.text.MatchResult>, kotlin.ranges.IntRange, int);
    Code:
       0: aload_1
       1: iload_2
       2: invokestatic  #247                // Method getRangeToCheck:(Lkotlin/ranges/IntRange;I)Lkotlin/ranges/IntRange;
       5: astore_3
       6: aload_0
       7: checkcast     #22                 // class java/lang/Iterable
      10: astore        4
      12: iconst_0
      13: istore        5
      15: aload         4
      17: astore        6
      19: new           #24                 // class java/util/ArrayList
      22: dup
      23: invokespecial #182                // Method java/util/ArrayList."<init>":()V
      26: checkcast     #35                 // class java/util/Collection
      29: astore        7
      31: iconst_0
      32: istore        8
      34: aload         6
      36: invokeinterface #39,  1           // InterfaceMethod java/lang/Iterable.iterator:()Ljava/util/Iterator;
      41: astore        9
      43: aload         9
      45: invokeinterface #45,  1           // InterfaceMethod java/util/Iterator.hasNext:()Z
      50: ifeq          94
      53: aload         9
      55: invokeinterface #49,  1           // InterfaceMethod java/util/Iterator.next:()Ljava/lang/Object;
      60: astore        10
      62: aload         10
      64: checkcast     #204                // class kotlin/text/MatchResult
      67: astore        11
      69: iconst_0
      70: istore        12
      72: aload         11
      74: aload_3
      75: invokestatic  #251                // Method isAdjacentToGear:(Lkotlin/text/MatchResult;Lkotlin/ranges/IntRange;)Z
      78: ifeq          43
      81: aload         7
      83: aload         10
      85: invokeinterface #119,  2          // InterfaceMethod java/util/Collection.add:(Ljava/lang/Object;)Z
      90: pop
      91: goto          43
      94: aload         7
      96: checkcast     #121                // class java/util/List
      99: nop
     100: areturn

  private static final boolean isAdjacentToGear(kotlin.text.MatchResult, kotlin.ranges.IntRange);
    Code:
       0: aload_0
       1: invokeinterface #264,  1          // InterfaceMethod kotlin/text/MatchResult.getRange:()Lkotlin/ranges/IntRange;
       6: checkcast     #22                 // class java/lang/Iterable
       9: aload_1
      10: checkcast     #22                 // class java/lang/Iterable
      13: invokestatic  #268                // Method kotlin/collections/CollectionsKt.intersect:(Ljava/lang/Iterable;Ljava/lang/Iterable;)Ljava/util/Set;
      16: checkcast     #35                 // class java/util/Collection
      19: invokeinterface #271,  1          // InterfaceMethod java/util/Collection.isEmpty:()Z
      24: ifne          31
      27: iconst_1
      28: goto          32
      31: iconst_0
      32: ireturn

  private static final boolean checkIfAdjacentToASymbol(java.util.List<java.lang.String>, kotlin.ranges.IntRange, int);
    Code:
       0: iload_2
       1: ifeq          38
       4: aload_0
       5: iload_2
       6: iconst_1
       7: isub
       8: invokeinterface #186,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
      13: checkcast     #54                 // class java/lang/String
      16: aload_1
      17: aload_0
      18: iconst_0
      19: invokeinterface #186,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
      24: checkcast     #60                 // class java/lang/CharSequence
      27: invokestatic  #280                // Method kotlin/text/StringsKt.getLastIndex:(Ljava/lang/CharSequence;)I
      30: invokestatic  #284                // Method checkIfSymbolsExistForRange:(Ljava/lang/String;Lkotlin/ranges/IntRange;I)Z
      33: ifeq          38
      36: iconst_1
      37: ireturn
      38: iload_2
      39: aload_0
      40: invokestatic  #190                // Method kotlin/collections/CollectionsKt.getLastIndex:(Ljava/util/List;)I
      43: if_icmpeq     80
      46: aload_0
      47: iload_2
      48: iconst_1
      49: iadd
      50: invokeinterface #186,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
      55: checkcast     #54                 // class java/lang/String
      58: aload_1
      59: aload_0
      60: iconst_0
      61: invokeinterface #186,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
      66: checkcast     #60                 // class java/lang/CharSequence
      69: invokestatic  #280                // Method kotlin/text/StringsKt.getLastIndex:(Ljava/lang/CharSequence;)I
      72: invokestatic  #284                // Method checkIfSymbolsExistForRange:(Ljava/lang/String;Lkotlin/ranges/IntRange;I)Z
      75: ifeq          80
      78: iconst_1
      79: ireturn
      80: aload_1
      81: invokevirtual #287                // Method kotlin/ranges/IntRange.getFirst:()I
      84: ifeq          114
      87: aload_0
      88: iload_2
      89: invokeinterface #186,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
      94: checkcast     #54                 // class java/lang/String
      97: aload_1
      98: invokevirtual #287                // Method kotlin/ranges/IntRange.getFirst:()I
     101: iconst_1
     102: isub
     103: invokevirtual #291                // Method java/lang/String.charAt:(I)C
     106: invokestatic  #295                // Method isASymbol:(C)Z
     109: ifeq          114
     112: iconst_1
     113: ireturn
     114: aload_1
     115: invokevirtual #298                // Method kotlin/ranges/IntRange.getLast:()I
     118: aload_0
     119: iload_2
     120: invokeinterface #186,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
     125: checkcast     #60                 // class java/lang/CharSequence
     128: invokestatic  #280                // Method kotlin/text/StringsKt.getLastIndex:(Ljava/lang/CharSequence;)I
     131: if_icmpeq     161
     134: aload_0
     135: iload_2
     136: invokeinterface #186,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
     141: checkcast     #54                 // class java/lang/String
     144: aload_1
     145: invokevirtual #298                // Method kotlin/ranges/IntRange.getLast:()I
     148: iconst_1
     149: iadd
     150: invokevirtual #291                // Method java/lang/String.charAt:(I)C
     153: invokestatic  #295                // Method isASymbol:(C)Z
     156: ifeq          161
     159: iconst_1
     160: ireturn
     161: iconst_0
     162: ireturn

  private static final boolean checkIfSymbolsExistForRange(java.lang.String, kotlin.ranges.IntRange, int);
    Code:
       0: aload_1
       1: iload_2
       2: invokestatic  #247                // Method getRangeToCheck:(Lkotlin/ranges/IntRange;I)Lkotlin/ranges/IntRange;
       5: astore_3
       6: aload_0
       7: aload_3
       8: invokestatic  #304                // Method kotlin/text/StringsKt.substring:(Ljava/lang/String;Lkotlin/ranges/IntRange;)Ljava/lang/String;
      11: checkcast     #60                 // class java/lang/CharSequence
      14: astore        4
      16: iconst_0
      17: istore        5
      19: iconst_0
      20: istore        6
      22: iload         6
      24: aload         4
      26: invokeinterface #307,  1          // InterfaceMethod java/lang/CharSequence.length:()I
      31: if_icmpge     70
      34: aload         4
      36: iload         6
      38: invokeinterface #308,  2          // InterfaceMethod java/lang/CharSequence.charAt:(I)C
      43: istore        7
      45: iload         7
      47: istore        8
      49: iconst_0
      50: istore        9
      52: iload         8
      54: invokestatic  #295                // Method isASymbol:(C)Z
      57: ifeq          64
      60: iconst_1
      61: goto          71
      64: iinc          6, 1
      67: goto          22
      70: iconst_0
      71: ireturn

  private static final kotlin.ranges.IntRange getRangeToCheck(kotlin.ranges.IntRange, int);
    Code:
       0: nop
       1: aload_0
       2: invokevirtual #287                // Method kotlin/ranges/IntRange.getFirst:()I
       5: ifne          25
       8: new           #242                // class kotlin/ranges/IntRange
      11: dup
      12: iconst_0
      13: aload_0
      14: invokevirtual #298                // Method kotlin/ranges/IntRange.getLast:()I
      17: iconst_1
      18: iadd
      19: invokespecial #320                // Method kotlin/ranges/IntRange."<init>":(II)V
      22: goto          72
      25: aload_0
      26: invokevirtual #298                // Method kotlin/ranges/IntRange.getLast:()I
      29: iload_1
      30: if_icmpne     53
      33: new           #242                // class kotlin/ranges/IntRange
      36: dup
      37: aload_0
      38: invokevirtual #287                // Method kotlin/ranges/IntRange.getFirst:()I
      41: iconst_1
      42: isub
      43: aload_0
      44: invokevirtual #298                // Method kotlin/ranges/IntRange.getLast:()I
      47: invokespecial #320                // Method kotlin/ranges/IntRange."<init>":(II)V
      50: goto          72
      53: new           #242                // class kotlin/ranges/IntRange
      56: dup
      57: aload_0
      58: invokevirtual #287                // Method kotlin/ranges/IntRange.getFirst:()I
      61: iconst_1
      62: isub
      63: aload_0
      64: invokevirtual #298                // Method kotlin/ranges/IntRange.getLast:()I
      67: iconst_1
      68: iadd
      69: invokespecial #320                // Method kotlin/ranges/IntRange."<init>":(II)V
      72: astore_2
      73: aload_2
      74: areturn

  private static final boolean isASymbol(char);
    Code:
       0: iload_0
       1: invokestatic  #325                // Method java/lang/Character.isDigit:(C)Z
       4: ifne          17
       7: iload_0
       8: bipush        46
      10: if_icmpeq     17
      13: iconst_1
      14: goto          18
      17: iconst_0
      18: ireturn

  public static void main(java.lang.String[]);
    Code:
       0: invokestatic  #329                // Method main:()V
       3: return

  private static final boolean main$lambda$4$lambda$2$lambda$0(java.util.List, int, kotlin.text.MatchResult);
    Code:
       0: aload_2
       1: ldc_w         #332                // String it
       4: invokestatic  #338                // Method kotlin/jvm/internal/Intrinsics.checkNotNullParameter:(Ljava/lang/Object;Ljava/lang/String;)V
       7: aload_0
       8: aload_2
       9: invokeinterface #264,  1          // InterfaceMethod kotlin/text/MatchResult.getRange:()Lkotlin/ranges/IntRange;
      14: iload_1
      15: invokestatic  #340                // Method checkIfAdjacentToASymbol:(Ljava/util/List;Lkotlin/ranges/IntRange;I)Z
      18: ireturn

  private static final int main$lambda$4$lambda$2$lambda$1(kotlin.text.MatchResult);
    Code:
       0: aload_0
       1: ldc_w         #332                // String it
       4: invokestatic  #338                // Method kotlin/jvm/internal/Intrinsics.checkNotNullParameter:(Ljava/lang/Object;Ljava/lang/String;)V
       7: aload_0
       8: invokeinterface #208,  1          // InterfaceMethod kotlin/text/MatchResult.getValue:()Ljava/lang/String;
      13: invokestatic  #212                // Method java/lang/Integer.parseInt:(Ljava/lang/String;)I
      16: ireturn

  private static final boolean main$lambda$6$lambda$5(java.util.List, int, kotlin.text.MatchResult);
    Code:
       0: aload_2
       1: ldc_w         #332                // String it
       4: invokestatic  #338                // Method kotlin/jvm/internal/Intrinsics.checkNotNullParameter:(Ljava/lang/Object;Ljava/lang/String;)V
       7: aload_0
       8: aload_2
       9: invokeinterface #264,  1          // InterfaceMethod kotlin/text/MatchResult.getRange:()Lkotlin/ranges/IntRange;
      14: iload_1
      15: invokestatic  #340                // Method checkIfAdjacentToASymbol:(Ljava/util/List;Lkotlin/ranges/IntRange;I)Z
      18: ireturn

  private static final int main$lambda$8$lambda$7(java.util.List, int, kotlin.text.MatchResult);
    Code:
       0: aload_2
       1: ldc_w         #332                // String it
       4: invokestatic  #338                // Method kotlin/jvm/internal/Intrinsics.checkNotNullParameter:(Ljava/lang/Object;Ljava/lang/String;)V
       7: aload_0
       8: aload_2
       9: invokeinterface #264,  1          // InterfaceMethod kotlin/text/MatchResult.getRange:()Lkotlin/ranges/IntRange;
      14: iload_1
      15: invokestatic  #344                // Method sumGearRatio:(Ljava/util/List;Lkotlin/ranges/IntRange;I)I
      18: ireturn

  static {};
    Code:
       0: new           #62                 // class kotlin/text/Regex
       3: dup
       4: ldc_w         #348                // String \\d+
       7: invokespecial #349                // Method kotlin/text/Regex."<init>":(Ljava/lang/String;)V
      10: putstatic     #58                 // Field numberRegex:Lkotlin/text/Regex;
      13: new           #62                 // class kotlin/text/Regex
      16: dup
      17: ldc_w         #351                // String \\*
      20: invokespecial #349                // Method kotlin/text/Regex."<init>":(Ljava/lang/String;)V
      23: putstatic     #147                // Field gearRegex:Lkotlin/text/Regex;
      26: return
}


package pl.klemba.aoc.day2

import java.io.File

fun main() {
  // ----- PART 1 -----
  File(inputPath)
    .readLines()
    .foldIndexed(0) { index, acc, line -> if (line.meetsRequirements) acc + index + 1 else acc }
    .let { println(it) }

  // ----- PART 2 -----
  File(inputPath)
    .readLines()
    .map { it.maxRgb }
    .sumOf { it.red * it.green * it.blue }
    .let { println(it) }
}

private val String.maxRgb: Rgb
  get() = Rgb(
    red = highestCubeNumber(this, redRegex),
    green = highestCubeNumber(this, greenRegex),
    blue = highestCubeNumber(this, blueRegex)
  )

data class Rgb(var red: Int, var green: Int, var blue: Int)

private val String.meetsRequirements: Boolean
  get() {
    if (highestCubeNumber(this, redRegex) > MAX_RED) return false
    if (highestCubeNumber(this, greenRegex) > MAX_GREEN) return false
    if (highestCubeNumber(this, blueRegex) > MAX_BLUE) return false
    return true
  }

private fun highestCubeNumber(rawLine: String, regex: Regex): Int =
  regex
    .findAll(rawLine)
    .map { it.destructured.component1().toInt() }
    .sortedDescending()
    .firstOrNull()
    ?: 0

private val redRegex = Regex(" (\\d*) red")
private val greenRegex = Regex(" (\\d*) green")
private val blueRegex = Regex(" (\\d*) blue")

private const val inputPath = "src/main/kotlin/pl/klemba/aoc/day2/input.txt"

private const val MAX_RED = 12
private const val MAX_GREEN = 13
private const val MAX_BLUE = 14

Compiled from "Main.kt"
public final class pl.klemba.aoc.day2.MainKt {
  private static final kotlin.text.Regex redRegex;

  private static final kotlin.text.Regex greenRegex;

  private static final kotlin.text.Regex blueRegex;

  private static final java.lang.String inputPath;

  private static final int MAX_RED;

  private static final int MAX_GREEN;

  private static final int MAX_BLUE;

  public static final void main();
    Code:
       0: new           #8                  // class java/io/File
       3: dup
       4: ldc           #10                 // String src/main/kotlin/pl/klemba/aoc/day2/input.txt
       6: invokespecial #14                 // Method java/io/File."<init>":(Ljava/lang/String;)V
       9: aconst_null
      10: iconst_1
      11: aconst_null
      12: invokestatic  #20                 // Method kotlin/io/FilesKt.readLines$default:(Ljava/io/File;Ljava/nio/charset/Charset;ILjava/lang/Object;)Ljava/util/List;
      15: checkcast     #22                 // class java/lang/Iterable
      18: astore_0
      19: iconst_0
      20: istore_1
      21: iconst_0
      22: istore_2
      23: iconst_0
      24: istore_3
      25: iload_1
      26: istore        4
      28: aload_0
      29: invokeinterface #26,  1           // InterfaceMethod java/lang/Iterable.iterator:()Ljava/util/Iterator;
      34: astore        5
      36: aload         5
      38: invokeinterface #32,  1           // InterfaceMethod java/util/Iterator.hasNext:()Z
      43: ifeq          112
      46: aload         5
      48: invokeinterface #36,  1           // InterfaceMethod java/util/Iterator.next:()Ljava/lang/Object;
      53: astore        6
      55: iload_3
      56: iinc          3, 1
      59: istore        7
      61: iload         7
      63: ifge          69
      66: invokestatic  #41                 // Method kotlin/collections/CollectionsKt.throwIndexOverflow:()V
      69: iload         7
      71: iload         4
      73: aload         6
      75: checkcast     #43                 // class java/lang/String
      78: astore        8
      80: istore        9
      82: istore        10
      84: iconst_0
      85: istore        11
      87: aload         8
      89: invokestatic  #47                 // Method getMeetsRequirements:(Ljava/lang/String;)Z
      92: ifeq          105
      95: iload         9
      97: iload         10
      99: iadd
     100: iconst_1
     101: iadd
     102: goto          107
     105: iload         9
     107: istore        4
     109: goto          36
     112: iload         4
     114: istore_1
     115: iconst_0
     116: istore_2
     117: getstatic     #53                 // Field java/lang/System.out:Ljava/io/PrintStream;
     120: iload_1
     121: invokevirtual #59                 // Method java/io/PrintStream.println:(I)V
     124: nop
     125: nop
     126: new           #8                  // class java/io/File
     129: dup
     130: ldc           #10                 // String src/main/kotlin/pl/klemba/aoc/day2/input.txt
     132: invokespecial #14                 // Method java/io/File."<init>":(Ljava/lang/String;)V
     135: aconst_null
     136: iconst_1
     137: aconst_null
     138: invokestatic  #20                 // Method kotlin/io/FilesKt.readLines$default:(Ljava/io/File;Ljava/nio/charset/Charset;ILjava/lang/Object;)Ljava/util/List;
     141: checkcast     #22                 // class java/lang/Iterable
     144: astore_0
     145: nop
     146: iconst_0
     147: istore_1
     148: aload_0
     149: astore_2
     150: new           #61                 // class java/util/ArrayList
     153: dup
     154: aload_0
     155: bipush        10
     157: invokestatic  #65                 // Method kotlin/collections/CollectionsKt.collectionSizeOrDefault:(Ljava/lang/Iterable;I)I
     160: invokespecial #67                 // Method java/util/ArrayList."<init>":(I)V
     163: checkcast     #69                 // class java/util/Collection
     166: astore_3
     167: iconst_0
     168: istore        4
     170: aload_2
     171: invokeinterface #26,  1           // InterfaceMethod java/lang/Iterable.iterator:()Ljava/util/Iterator;
     176: astore        5
     178: aload         5
     180: invokeinterface #32,  1           // InterfaceMethod java/util/Iterator.hasNext:()Z
     185: ifeq          227
     188: aload         5
     190: invokeinterface #36,  1           // InterfaceMethod java/util/Iterator.next:()Ljava/lang/Object;
     195: astore        6
     197: aload_3
     198: aload         6
     200: checkcast     #43                 // class java/lang/String
     203: astore        7
     205: astore        12
     207: iconst_0
     208: istore        8
     210: aload         7
     212: invokestatic  #73                 // Method getMaxRgb:(Ljava/lang/String;)Lpl/klemba/aoc/day2/Rgb;
     215: aload         12
     217: swap
     218: invokeinterface #77,  2           // InterfaceMethod java/util/Collection.add:(Ljava/lang/Object;)Z
     223: pop
     224: goto          178
     227: aload_3
     228: checkcast     #79                 // class java/util/List
     231: nop
     232: checkcast     #22                 // class java/lang/Iterable
     235: astore_0
     236: iconst_0
     237: istore_1
     238: aload_0
     239: invokeinterface #26,  1           // InterfaceMethod java/lang/Iterable.iterator:()Ljava/util/Iterator;
     244: astore_2
     245: aload_2
     246: invokeinterface #32,  1           // InterfaceMethod java/util/Iterator.hasNext:()Z
     251: ifeq          301
     254: aload_2
     255: invokeinterface #36,  1           // InterfaceMethod java/util/Iterator.next:()Ljava/lang/Object;
     260: astore_3
     261: iload_1
     262: aload_3
     263: checkcast     #81                 // class pl/klemba/aoc/day2/Rgb
     266: astore        4
     268: istore        12
     270: iconst_0
     271: istore        5
     273: aload         4
     275: invokevirtual #85                 // Method pl/klemba/aoc/day2/Rgb.getRed:()I
     278: aload         4
     280: invokevirtual #88                 // Method pl/klemba/aoc/day2/Rgb.getGreen:()I
     283: imul
     284: aload         4
     286: invokevirtual #91                 // Method pl/klemba/aoc/day2/Rgb.getBlue:()I
     289: imul
     290: istore        13
     292: iload         12
     294: iload         13
     296: iadd
     297: istore_1
     298: goto          245
     301: iload_1
     302: istore_1
     303: iconst_0
     304: istore_2
     305: getstatic     #53                 // Field java/lang/System.out:Ljava/io/PrintStream;
     308: iload_1
     309: invokevirtual #59                 // Method java/io/PrintStream.println:(I)V
     312: nop
     313: nop
     314: return

  private static final pl.klemba.aoc.day2.Rgb getMaxRgb(java.lang.String);
    Code:
       0: new           #81                 // class pl/klemba/aoc/day2/Rgb
       3: dup
       4: aload_0
       5: getstatic     #122                // Field redRegex:Lkotlin/text/Regex;
       8: invokestatic  #126                // Method highestCubeNumber:(Ljava/lang/String;Lkotlin/text/Regex;)I
      11: aload_0
      12: getstatic     #129                // Field greenRegex:Lkotlin/text/Regex;
      15: invokestatic  #126                // Method highestCubeNumber:(Ljava/lang/String;Lkotlin/text/Regex;)I
      18: aload_0
      19: getstatic     #132                // Field blueRegex:Lkotlin/text/Regex;
      22: invokestatic  #126                // Method highestCubeNumber:(Ljava/lang/String;Lkotlin/text/Regex;)I
      25: invokespecial #135                // Method pl/klemba/aoc/day2/Rgb."<init>":(III)V
      28: areturn

  private static final boolean getMeetsRequirements(java.lang.String);
    Code:
       0: aload_0
       1: getstatic     #122                // Field redRegex:Lkotlin/text/Regex;
       4: invokestatic  #126                // Method highestCubeNumber:(Ljava/lang/String;Lkotlin/text/Regex;)I
       7: bipush        12
       9: if_icmple     14
      12: iconst_0
      13: ireturn
      14: aload_0
      15: getstatic     #129                // Field greenRegex:Lkotlin/text/Regex;
      18: invokestatic  #126                // Method highestCubeNumber:(Ljava/lang/String;Lkotlin/text/Regex;)I
      21: bipush        13
      23: if_icmple     28
      26: iconst_0
      27: ireturn
      28: aload_0
      29: getstatic     #132                // Field blueRegex:Lkotlin/text/Regex;
      32: invokestatic  #126                // Method highestCubeNumber:(Ljava/lang/String;Lkotlin/text/Regex;)I
      35: bipush        14
      37: if_icmple     42
      40: iconst_0
      41: ireturn
      42: iconst_1
      43: ireturn

  private static final int highestCubeNumber(java.lang.String, kotlin.text.Regex);
    Code:
       0: aload_1
       1: aload_0
       2: checkcast     #139                // class java/lang/CharSequence
       5: iconst_0
       6: iconst_2
       7: aconst_null
       8: invokestatic  #145                // Method kotlin/text/Regex.findAll$default:(Lkotlin/text/Regex;Ljava/lang/CharSequence;IILjava/lang/Object;)Lkotlin/sequences/Sequence;
      11: invokedynamic #165,  0            // InvokeDynamic #0:invoke:()Lkotlin/jvm/functions/Function1;
      16: invokestatic  #171                // Method kotlin/sequences/SequencesKt.map:(Lkotlin/sequences/Sequence;Lkotlin/jvm/functions/Function1;)Lkotlin/sequences/Sequence;
      19: invokestatic  #175                // Method kotlin/sequences/SequencesKt.sortedDescending:(Lkotlin/sequences/Sequence;)Lkotlin/sequences/Sequence;
      22: invokestatic  #179                // Method kotlin/sequences/SequencesKt.firstOrNull:(Lkotlin/sequences/Sequence;)Ljava/lang/Object;
      25: checkcast     #181                // class java/lang/Integer
      28: dup
      29: ifnull        38
      32: invokevirtual #184                // Method java/lang/Integer.intValue:()I
      35: goto          40
      38: pop
      39: iconst_0
      40: ireturn

  public static void main(java.lang.String[]);
    Code:
       0: invokestatic  #189                // Method main:()V
       3: return

  private static final int highestCubeNumber$lambda$5(kotlin.text.MatchResult);
    Code:
       0: aload_0
       1: ldc           #192                // String it
       3: invokestatic  #198                // Method kotlin/jvm/internal/Intrinsics.checkNotNullParameter:(Ljava/lang/Object;Ljava/lang/String;)V
       6: nop
       7: aload_0
       8: invokeinterface #204,  1          // InterfaceMethod kotlin/text/MatchResult.getDestructured:()Lkotlin/text/MatchResult$Destructured;
      13: invokevirtual #210                // Method kotlin/text/MatchResult$Destructured.getMatch:()Lkotlin/text/MatchResult;
      16: invokeinterface #214,  1          // InterfaceMethod kotlin/text/MatchResult.getGroupValues:()Ljava/util/List;
      21: iconst_1
      22: invokeinterface #218,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
      27: checkcast     #43                 // class java/lang/String
      30: invokestatic  #222                // Method java/lang/Integer.parseInt:(Ljava/lang/String;)I
      33: ireturn

  static {};
    Code:
       0: new           #141                // class kotlin/text/Regex
       3: dup
       4: ldc           #226                // String  (\\d*) red
       6: invokespecial #227                // Method kotlin/text/Regex."<init>":(Ljava/lang/String;)V
       9: putstatic     #122                // Field redRegex:Lkotlin/text/Regex;
      12: new           #141                // class kotlin/text/Regex
      15: dup
      16: ldc           #229                // String  (\\d*) green
      18: invokespecial #227                // Method kotlin/text/Regex."<init>":(Ljava/lang/String;)V
      21: putstatic     #129                // Field greenRegex:Lkotlin/text/Regex;
      24: new           #141                // class kotlin/text/Regex
      27: dup
      28: ldc           #231                // String  (\\d*) blue
      30: invokespecial #227                // Method kotlin/text/Regex."<init>":(Ljava/lang/String;)V
      33: putstatic     #132                // Field blueRegex:Lkotlin/text/Regex;
      36: return
}


package pl.klemba.aoc.day5

import java.io.File

fun main() {
  // ----- PART 1 -----
  val almanac = File(inputPath)
    .readLines()

  val seeds: List<Long> = getSeeds(almanac)
  println("Seeds: $seeds")

  val mappings = getMappings(almanac)

  mappings
    .forEach { println(it) }
  seeds
    .map { seed -> seed.mapToLocation(mappings) }
    .let {
      println("Resultlist: $it")
      println(it.min())
    }

  // ----- PART 2 -----
  val almanac2 = File(inputPath)
    .readLines()

  val seedRanges: List<LongRange> = getSeedRangesPart2(almanac2)

  val mappings2 = getMappings(almanac2)

  seedRanges
    .fold(Long.MAX_VALUE) { acc, longRange -> findMinLocationOf(longRange, mappings2).let { location -> if (location < acc) location else acc } }
    .let { println(it) }
}

fun getMappings(almanac: List<String>): ArrayList<ArrayList<MappingPattern>> {
  val mappings = ArrayList<ArrayList<MappingPattern>>()
  return almanac
    .fold(mappings) { acc, line -> addToMappingsList(line, acc) }
}

private fun String.hasThreeNumbers() = getMappingLine() != null

private fun String.getMappingLine() = mappingLineRegex.matchEntire(this)

fun addToMappingsList(line: String, acc: ArrayList<ArrayList<MappingPattern>>): java.util.ArrayList<java.util.ArrayList<MappingPattern>> {
  when {
    line.endsWith("map:") -> {
      acc.add(ArrayList())
    }
    line.hasThreeNumbers() -> {
      acc.last().add(getMappingPattern(line))
    }
  }
  return acc
}

fun getMappingPattern(line: String) =
  line.getMappingLine()
    ?.destructured
    ?.let { (destinationValue, sourceValue, rangeValue ) -> mapToMappingPattern(destinationValue.toLong(), sourceValue.toLong(), rangeValue.toLong()) }
    ?: throw IllegalStateException("Mapping pattern not found! Wierd since it has been checked before!")

fun mapToMappingPattern(destinationValue: Long, sourceValue: Long, rangeValue: Long) =
  MappingPattern(LongRange(sourceValue, sourceValue + rangeValue), destinationValue - sourceValue)

fun getSeeds(almanac: List<String>): List<Long> =
  numberRegex.findAll(almanac[0])
    .map { it.destructured.component1().toLong() }
    .toList()

fun getSeedRangesPart2(almanac: List<String>): List<LongRange> =
  getSeeds(almanac)
    .chunked(2)
    .map { LongRange(it[0], it[0] + it[1]) }

private fun Long.mapToLocation(mappings: java.util.ArrayList<java.util.ArrayList<MappingPattern>>) =
  mappings
    .fold(this) { acc, mappingPatterns ->
      mappingPatterns.find { it.sourceRange.contains(acc) }
        ?.let { pattern -> pattern.valueShift + acc }
        ?: acc
    }

fun findMinLocationOf(longRange: LongRange, almanac2: ArrayList<ArrayList<MappingPattern>>) =
  longRange
    .fold(Long.MAX_VALUE) { acc, seed -> seed.mapToLocation(almanac2).let { location -> if (location < acc) location else acc } }

/**
 * @param sourceRange range of IDs which can be mapped by this pattern
 * @param valueShift parameter indicating needed value shift (addition of the value to source ID) to achieve the mapping result
 */
data class MappingPattern(val sourceRange: LongRange, val valueShift: Long)

private val numberRegex = Regex(""" (\d+)""")

private val mappingLineRegex = Regex("""(\d+) (\d+) (\d+)""")
private const val inputPath = "src/main/kotlin/pl/klemba/aoc/day5/input.txt"

Compiled from "Main.kt"
public final class pl.klemba.aoc.day5.MainKt {
  private static final kotlin.text.Regex numberRegex;

  private static final kotlin.text.Regex mappingLineRegex;

  private static final java.lang.String inputPath;

  public static final void main();
    Code:
       0: new           #8                  // class java/io/File
       3: dup
       4: ldc           #10                 // String src/main/kotlin/pl/klemba/aoc/day5/input.txt
       6: invokespecial #14                 // Method java/io/File."<init>":(Ljava/lang/String;)V
       9: aconst_null
      10: iconst_1
      11: aconst_null
      12: invokestatic  #20                 // Method kotlin/io/FilesKt.readLines$default:(Ljava/io/File;Ljava/nio/charset/Charset;ILjava/lang/Object;)Ljava/util/List;
      15: astore_0
      16: aload_0
      17: invokestatic  #24                 // Method getSeeds:(Ljava/util/List;)Ljava/util/List;
      20: astore_1
      21: new           #26                 // class java/lang/StringBuilder
      24: dup
      25: invokespecial #28                 // Method java/lang/StringBuilder."<init>":()V
      28: ldc           #30                 // String Seeds:
      30: invokevirtual #34                 // Method java/lang/StringBuilder.append:(Ljava/lang/String;)Ljava/lang/StringBuilder;
      33: aload_1
      34: invokevirtual #37                 // Method java/lang/StringBuilder.append:(Ljava/lang/Object;)Ljava/lang/StringBuilder;
      37: invokevirtual #41                 // Method java/lang/StringBuilder.toString:()Ljava/lang/String;
      40: getstatic     #47                 // Field java/lang/System.out:Ljava/io/PrintStream;
      43: swap
      44: invokevirtual #53                 // Method java/io/PrintStream.println:(Ljava/lang/Object;)V
      47: aload_0
      48: invokestatic  #57                 // Method getMappings:(Ljava/util/List;)Ljava/util/ArrayList;
      51: astore_2
      52: aload_2
      53: checkcast     #59                 // class java/lang/Iterable
      56: astore_3
      57: nop
      58: iconst_0
      59: istore        4
      61: aload_3
      62: invokeinterface #63,  1           // InterfaceMethod java/lang/Iterable.iterator:()Ljava/util/Iterator;
      67: astore        5
      69: aload         5
      71: invokeinterface #69,  1           // InterfaceMethod java/util/Iterator.hasNext:()Z
      76: ifeq          111
      79: aload         5
      81: invokeinterface #73,  1           // InterfaceMethod java/util/Iterator.next:()Ljava/lang/Object;
      86: astore        6
      88: aload         6
      90: checkcast     #75                 // class java/util/ArrayList
      93: astore        8
      95: iconst_0
      96: istore        10
      98: getstatic     #47                 // Field java/lang/System.out:Ljava/io/PrintStream;
     101: aload         8
     103: invokevirtual #53                 // Method java/io/PrintStream.println:(Ljava/lang/Object;)V
     106: nop
     107: nop
     108: goto          69
     111: nop
     112: aload_1
     113: checkcast     #59                 // class java/lang/Iterable
     116: astore_3
     117: nop
     118: iconst_0
     119: istore        4
     121: aload_3
     122: astore        5
     124: new           #75                 // class java/util/ArrayList
     127: dup
     128: aload_3
     129: bipush        10
     131: invokestatic  #81                 // Method kotlin/collections/CollectionsKt.collectionSizeOrDefault:(Ljava/lang/Iterable;I)I
     134: invokespecial #84                 // Method java/util/ArrayList."<init>":(I)V
     137: checkcast     #86                 // class java/util/Collection
     140: astore        6
     142: iconst_0
     143: istore        8
     145: aload         5
     147: invokeinterface #63,  1           // InterfaceMethod java/lang/Iterable.iterator:()Ljava/util/Iterator;
     152: astore        10
     154: aload         10
     156: invokeinterface #69,  1           // InterfaceMethod java/util/Iterator.hasNext:()Z
     161: ifeq          211
     164: aload         10
     166: invokeinterface #73,  1           // InterfaceMethod java/util/Iterator.next:()Ljava/lang/Object;
     171: astore        11
     173: aload         6
     175: aload         11
     177: checkcast     #88                 // class java/lang/Number
     180: invokevirtual #92                 // Method java/lang/Number.longValue:()J
     183: lstore        13
     185: astore        22
     187: iconst_0
     188: istore        15
     190: lload         13
     192: aload_2
     193: invokestatic  #96                 // Method mapToLocation:(JLjava/util/ArrayList;)J
     196: invokestatic  #102                // Method java/lang/Long.valueOf:(J)Ljava/lang/Long;
     199: aload         22
     201: swap
     202: invokeinterface #106,  2          // InterfaceMethod java/util/Collection.add:(Ljava/lang/Object;)Z
     207: pop
     208: goto          154
     211: aload         6
     213: checkcast     #108                // class java/util/List
     216: nop
     217: astore        4
     219: iconst_0
     220: istore        5
     222: new           #26                 // class java/lang/StringBuilder
     225: dup
     226: invokespecial #28                 // Method java/lang/StringBuilder."<init>":()V
     229: ldc           #110                // String Resultlist:
     231: invokevirtual #34                 // Method java/lang/StringBuilder.append:(Ljava/lang/String;)Ljava/lang/StringBuilder;
     234: aload         4
     236: invokevirtual #37                 // Method java/lang/StringBuilder.append:(Ljava/lang/Object;)Ljava/lang/StringBuilder;
     239: invokevirtual #41                 // Method java/lang/StringBuilder.toString:()Ljava/lang/String;
     242: getstatic     #47                 // Field java/lang/System.out:Ljava/io/PrintStream;
     245: swap
     246: invokevirtual #53                 // Method java/io/PrintStream.println:(Ljava/lang/Object;)V
     249: aload         4
     251: checkcast     #59                 // class java/lang/Iterable
     254: invokestatic  #114                // Method kotlin/collections/CollectionsKt.minOrThrow:(Ljava/lang/Iterable;)Ljava/lang/Comparable;
     257: checkcast     #88                 // class java/lang/Number
     260: invokevirtual #92                 // Method java/lang/Number.longValue:()J
     263: lstore        6
     265: getstatic     #47                 // Field java/lang/System.out:Ljava/io/PrintStream;
     268: lload         6
     270: invokevirtual #117                // Method java/io/PrintStream.println:(J)V
     273: nop
     274: nop
     275: new           #8                  // class java/io/File
     278: dup
     279: ldc           #10                 // String src/main/kotlin/pl/klemba/aoc/day5/input.txt
     281: invokespecial #14                 // Method java/io/File."<init>":(Ljava/lang/String;)V
     284: aconst_null
     285: iconst_1
     286: aconst_null
     287: invokestatic  #20                 // Method kotlin/io/FilesKt.readLines$default:(Ljava/io/File;Ljava/nio/charset/Charset;ILjava/lang/Object;)Ljava/util/List;
     290: astore_3
     291: aload_3
     292: invokestatic  #120                // Method getSeedRangesPart2:(Ljava/util/List;)Ljava/util/List;
     295: astore        4
     297: aload_3
     298: invokestatic  #57                 // Method getMappings:(Ljava/util/List;)Ljava/util/ArrayList;
     301: astore        5
     303: aload         4
     305: checkcast     #59                 // class java/lang/Iterable
     308: astore        6
     310: ldc2_w        #121                // long 9223372036854775807l
     313: lstore        8
     315: iconst_0
     316: istore        10
     318: lload         8
     320: lstore        11
     322: aload         6
     324: invokeinterface #63,  1           // InterfaceMethod java/lang/Iterable.iterator:()Ljava/util/Iterator;
     329: astore        13
     331: aload         13
     333: invokeinterface #69,  1           // InterfaceMethod java/util/Iterator.hasNext:()Z
     338: ifeq          398
     341: aload         13
     343: invokeinterface #73,  1           // InterfaceMethod java/util/Iterator.next:()Ljava/lang/Object;
     348: astore        14
     350: lload         11
     352: aload         14
     354: checkcast     #124                // class kotlin/ranges/LongRange
     357: astore        15
     359: lstore        16
     361: iconst_0
     362: istore        18
     364: aload         15
     366: aload         5
     368: invokestatic  #128                // Method findMinLocationOf:(Lkotlin/ranges/LongRange;Ljava/util/ArrayList;)J
     371: lstore        19
     373: iconst_0
     374: istore        21
     376: lload         19
     378: lload         16
     380: lcmp
     381: ifge          389
     384: lload         19
     386: goto          391
     389: lload         16
     391: nop
     392: nop
     393: lstore        11
     395: goto          331
     398: lload         11
     400: lstore        8
     402: iconst_0
     403: istore        11
     405: getstatic     #47                 // Field java/lang/System.out:Ljava/io/PrintStream;
     408: lload         8
     410: invokevirtual #117                // Method java/io/PrintStream.println:(J)V
     413: nop
     414: nop
     415: return

  public static final java.util.ArrayList<java.util.ArrayList<pl.klemba.aoc.day5.MappingPattern>> getMappings(java.util.List<java.lang.String>);
    Code:
       0: aload_0
       1: ldc           #169                // String almanac
       3: invokestatic  #175                // Method kotlin/jvm/internal/Intrinsics.checkNotNullParameter:(Ljava/lang/Object;Ljava/lang/String;)V
       6: new           #75                 // class java/util/ArrayList
       9: dup
      10: invokespecial #176                // Method java/util/ArrayList."<init>":()V
      13: astore_1
      14: aload_0
      15: checkcast     #59                 // class java/lang/Iterable
      18: astore_2
      19: nop
      20: iconst_0
      21: istore_3
      22: aload_1
      23: astore        4
      25: aload_2
      26: invokeinterface #63,  1           // InterfaceMethod java/lang/Iterable.iterator:()Ljava/util/Iterator;
      31: astore        5
      33: aload         5
      35: invokeinterface #69,  1           // InterfaceMethod java/util/Iterator.hasNext:()Z
      40: ifeq          78
      43: aload         5
      45: invokeinterface #73,  1           // InterfaceMethod java/util/Iterator.next:()Ljava/lang/Object;
      50: astore        6
      52: aload         4
      54: aload         6
      56: checkcast     #178                // class java/lang/String
      59: astore        7
      61: astore        8
      63: iconst_0
      64: istore        9
      66: aload         7
      68: aload         8
      70: invokestatic  #182                // Method addToMappingsList:(Ljava/lang/String;Ljava/util/ArrayList;)Ljava/util/ArrayList;
      73: astore        4
      75: goto          33
      78: aload         4
      80: areturn

  private static final boolean hasThreeNumbers(java.lang.String);
    Code:
       0: aload_0
       1: invokestatic  #191                // Method getMappingLine:(Ljava/lang/String;)Lkotlin/text/MatchResult;
       4: ifnull        11
       7: iconst_1
       8: goto          12
      11: iconst_0
      12: ireturn

  private static final kotlin.text.MatchResult getMappingLine(java.lang.String);
    Code:
       0: getstatic     #196                // Field mappingLineRegex:Lkotlin/text/Regex;
       3: aload_0
       4: checkcast     #198                // class java/lang/CharSequence
       7: invokevirtual #204                // Method kotlin/text/Regex.matchEntire:(Ljava/lang/CharSequence;)Lkotlin/text/MatchResult;
      10: areturn

  public static final java.util.ArrayList<java.util.ArrayList<pl.klemba.aoc.day5.MappingPattern>> addToMappingsList(java.lang.String, java.util.ArrayList<java.util.ArrayList<pl.klemba.aoc.day5.MappingPattern>>);
    Code:
       0: aload_0
       1: ldc           #207                // String line
       3: invokestatic  #175                // Method kotlin/jvm/internal/Intrinsics.checkNotNullParameter:(Ljava/lang/Object;Ljava/lang/String;)V
       6: aload_1
       7: ldc           #208                // String acc
       9: invokestatic  #175                // Method kotlin/jvm/internal/Intrinsics.checkNotNullParameter:(Ljava/lang/Object;Ljava/lang/String;)V
      12: nop
      13: aload_0
      14: ldc           #210                // String map:
      16: iconst_0
      17: iconst_2
      18: aconst_null
      19: invokestatic  #216                // Method kotlin/text/StringsKt.endsWith$default:(Ljava/lang/String;Ljava/lang/String;ZILjava/lang/Object;)Z
      22: ifeq          40
      25: aload_1
      26: new           #75                 // class java/util/ArrayList
      29: dup
      30: invokespecial #176                // Method java/util/ArrayList."<init>":()V
      33: invokevirtual #217                // Method java/util/ArrayList.add:(Ljava/lang/Object;)Z
      36: pop
      37: goto          65
      40: aload_0
      41: invokestatic  #219                // Method hasThreeNumbers:(Ljava/lang/String;)Z
      44: ifeq          65
      47: aload_1
      48: checkcast     #108                // class java/util/List
      51: invokestatic  #223                // Method kotlin/collections/CollectionsKt.last:(Ljava/util/List;)Ljava/lang/Object;
      54: checkcast     #75                 // class java/util/ArrayList
      57: aload_0
      58: invokestatic  #227                // Method getMappingPattern:(Ljava/lang/String;)Lpl/klemba/aoc/day5/MappingPattern;
      61: invokevirtual #217                // Method java/util/ArrayList.add:(Ljava/lang/Object;)Z
      64: pop
      65: aload_1
      66: areturn

  public static final pl.klemba.aoc.day5.MappingPattern getMappingPattern(java.lang.String);
    Code:
       0: aload_0
       1: ldc           #207                // String line
       3: invokestatic  #175                // Method kotlin/jvm/internal/Intrinsics.checkNotNullParameter:(Ljava/lang/Object;Ljava/lang/String;)V
       6: aload_0
       7: invokestatic  #191                // Method getMappingLine:(Ljava/lang/String;)Lkotlin/text/MatchResult;
      10: astore_1
      11: aload_1
      12: ifnull        123
      15: aload_1
      16: invokeinterface #233,  1          // InterfaceMethod kotlin/text/MatchResult.getDestructured:()Lkotlin/text/MatchResult$Destructured;
      21: astore_2
      22: aload_2
      23: ifnull        123
      26: aload_2
      27: astore        4
      29: iconst_0
      30: istore        5
      32: aload         4
      34: invokevirtual #239                // Method kotlin/text/MatchResult$Destructured.getMatch:()Lkotlin/text/MatchResult;
      37: invokeinterface #243,  1          // InterfaceMethod kotlin/text/MatchResult.getGroupValues:()Ljava/util/List;
      42: iconst_1
      43: invokeinterface #247,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
      48: checkcast     #178                // class java/lang/String
      51: astore        6
      53: aload         4
      55: invokevirtual #239                // Method kotlin/text/MatchResult$Destructured.getMatch:()Lkotlin/text/MatchResult;
      58: invokeinterface #243,  1          // InterfaceMethod kotlin/text/MatchResult.getGroupValues:()Ljava/util/List;
      63: iconst_2
      64: invokeinterface #247,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
      69: checkcast     #178                // class java/lang/String
      72: astore        7
      74: aload         4
      76: invokevirtual #239                // Method kotlin/text/MatchResult$Destructured.getMatch:()Lkotlin/text/MatchResult;
      79: invokeinterface #243,  1          // InterfaceMethod kotlin/text/MatchResult.getGroupValues:()Ljava/util/List;
      84: iconst_3
      85: invokeinterface #247,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
      90: checkcast     #178                // class java/lang/String
      93: astore        8
      95: aload         6
      97: invokestatic  #251                // Method java/lang/Long.parseLong:(Ljava/lang/String;)J
     100: aload         7
     102: invokestatic  #251                // Method java/lang/Long.parseLong:(Ljava/lang/String;)J
     105: aload         8
     107: invokestatic  #251                // Method java/lang/Long.parseLong:(Ljava/lang/String;)J
     110: invokestatic  #255                // Method mapToMappingPattern:(JJJ)Lpl/klemba/aoc/day5/MappingPattern;
     113: nop
     114: astore_3
     115: aload_3
     116: ifnull        123
     119: aload_3
     120: goto          134
     123: new           #257                // class java/lang/IllegalStateException
     126: dup
     127: ldc_w         #259                // String Mapping pattern not found! Wierd since it has been checked before!
     130: invokespecial #260                // Method java/lang/IllegalStateException."<init>":(Ljava/lang/String;)V
     133: athrow
     134: areturn

  public static final pl.klemba.aoc.day5.MappingPattern mapToMappingPattern(long, long, long);
    Code:
       0: new           #266                // class pl/klemba/aoc/day5/MappingPattern
       3: dup
       4: new           #124                // class kotlin/ranges/LongRange
       7: dup
       8: lload_2
       9: lload_2
      10: lload         4
      12: ladd
      13: invokespecial #269                // Method kotlin/ranges/LongRange."<init>":(JJ)V
      16: lload_0
      17: lload_2
      18: lsub
      19: invokespecial #272                // Method pl/klemba/aoc/day5/MappingPattern."<init>":(Lkotlin/ranges/LongRange;J)V
      22: areturn

  public static final java.util.List<java.lang.Long> getSeeds(java.util.List<java.lang.String>);
    Code:
       0: aload_0
       1: ldc           #169                // String almanac
       3: invokestatic  #175                // Method kotlin/jvm/internal/Intrinsics.checkNotNullParameter:(Ljava/lang/Object;Ljava/lang/String;)V
       6: getstatic     #276                // Field numberRegex:Lkotlin/text/Regex;
       9: aload_0
      10: iconst_0
      11: invokeinterface #247,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
      16: checkcast     #198                // class java/lang/CharSequence
      19: iconst_0
      20: iconst_2
      21: aconst_null
      22: invokestatic  #280                // Method kotlin/text/Regex.findAll$default:(Lkotlin/text/Regex;Ljava/lang/CharSequence;IILjava/lang/Object;)Lkotlin/sequences/Sequence;
      25: invokedynamic #300,  0            // InvokeDynamic #0:invoke:()Lkotlin/jvm/functions/Function1;
      30: invokestatic  #306                // Method kotlin/sequences/SequencesKt.map:(Lkotlin/sequences/Sequence;Lkotlin/jvm/functions/Function1;)Lkotlin/sequences/Sequence;
      33: invokestatic  #310                // Method kotlin/sequences/SequencesKt.toList:(Lkotlin/sequences/Sequence;)Ljava/util/List;
      36: areturn

  public static final java.util.List<kotlin.ranges.LongRange> getSeedRangesPart2(java.util.List<java.lang.String>);
    Code:
       0: aload_0
       1: ldc           #169                // String almanac
       3: invokestatic  #175                // Method kotlin/jvm/internal/Intrinsics.checkNotNullParameter:(Ljava/lang/Object;Ljava/lang/String;)V
       6: aload_0
       7: invokestatic  #24                 // Method getSeeds:(Ljava/util/List;)Ljava/util/List;
      10: checkcast     #59                 // class java/lang/Iterable
      13: iconst_2
      14: invokestatic  #315                // Method kotlin/collections/CollectionsKt.chunked:(Ljava/lang/Iterable;I)Ljava/util/List;
      17: checkcast     #59                 // class java/lang/Iterable
      20: astore_1
      21: nop
      22: iconst_0
      23: istore_2
      24: aload_1
      25: astore_3
      26: new           #75                 // class java/util/ArrayList
      29: dup
      30: aload_1
      31: bipush        10
      33: invokestatic  #81                 // Method kotlin/collections/CollectionsKt.collectionSizeOrDefault:(Ljava/lang/Iterable;I)I
      36: invokespecial #84                 // Method java/util/ArrayList."<init>":(I)V
      39: checkcast     #86                 // class java/util/Collection
      42: astore        4
      44: iconst_0
      45: istore        5
      47: aload_3
      48: invokeinterface #63,  1           // InterfaceMethod java/lang/Iterable.iterator:()Ljava/util/Iterator;
      53: astore        6
      55: aload         6
      57: invokeinterface #69,  1           // InterfaceMethod java/util/Iterator.hasNext:()Z
      62: ifeq          150
      65: aload         6
      67: invokeinterface #73,  1           // InterfaceMethod java/util/Iterator.next:()Ljava/lang/Object;
      72: astore        7
      74: aload         4
      76: aload         7
      78: checkcast     #108                // class java/util/List
      81: astore        8
      83: astore        10
      85: iconst_0
      86: istore        9
      88: new           #124                // class kotlin/ranges/LongRange
      91: dup
      92: aload         8
      94: iconst_0
      95: invokeinterface #247,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
     100: checkcast     #88                 // class java/lang/Number
     103: invokevirtual #92                 // Method java/lang/Number.longValue:()J
     106: aload         8
     108: iconst_0
     109: invokeinterface #247,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
     114: checkcast     #88                 // class java/lang/Number
     117: invokevirtual #92                 // Method java/lang/Number.longValue:()J
     120: aload         8
     122: iconst_1
     123: invokeinterface #247,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
     128: checkcast     #88                 // class java/lang/Number
     131: invokevirtual #92                 // Method java/lang/Number.longValue:()J
     134: ladd
     135: invokespecial #269                // Method kotlin/ranges/LongRange."<init>":(JJ)V
     138: aload         10
     140: swap
     141: invokeinterface #106,  2          // InterfaceMethod java/util/Collection.add:(Ljava/lang/Object;)Z
     146: pop
     147: goto          55
     150: aload         4
     152: checkcast     #108                // class java/util/List
     155: nop
     156: areturn

  private static final long mapToLocation(long, java.util.ArrayList<java.util.ArrayList<pl.klemba.aoc.day5.MappingPattern>>);
    Code:
       0: aload_2
       1: checkcast     #59                 // class java/lang/Iterable
       4: astore_3
       5: lload_0
       6: lstore        4
       8: nop
       9: iconst_0
      10: istore        6
      12: lload         4
      14: lstore        7
      16: aload_3
      17: invokeinterface #63,  1           // InterfaceMethod java/lang/Iterable.iterator:()Ljava/util/Iterator;
      22: astore        9
      24: aload         9
      26: invokeinterface #69,  1           // InterfaceMethod java/util/Iterator.hasNext:()Z
      31: ifeq          157
      34: aload         9
      36: invokeinterface #73,  1           // InterfaceMethod java/util/Iterator.next:()Ljava/lang/Object;
      41: astore        10
      43: lload         7
      45: aload         10
      47: checkcast     #75                 // class java/util/ArrayList
      50: astore        11
      52: lstore        12
      54: iconst_0
      55: istore        14
      57: aload         11
      59: checkcast     #59                 // class java/lang/Iterable
      62: astore        15
      64: aload         15
      66: invokeinterface #63,  1           // InterfaceMethod java/lang/Iterable.iterator:()Ljava/util/Iterator;
      71: astore        16
      73: aload         16
      75: invokeinterface #69,  1           // InterfaceMethod java/util/Iterator.hasNext:()Z
      80: ifeq          120
      83: aload         16
      85: invokeinterface #73,  1           // InterfaceMethod java/util/Iterator.next:()Ljava/lang/Object;
      90: astore        17
      92: aload         17
      94: checkcast     #266                // class pl/klemba/aoc/day5/MappingPattern
      97: astore        18
      99: iconst_0
     100: istore        19
     102: aload         18
     104: invokevirtual #321                // Method pl/klemba/aoc/day5/MappingPattern.getSourceRange:()Lkotlin/ranges/LongRange;
     107: lload         12
     109: invokevirtual #325                // Method kotlin/ranges/LongRange.contains:(J)Z
     112: ifeq          73
     115: aload         17
     117: goto          121
     120: aconst_null
     121: checkcast     #266                // class pl/klemba/aoc/day5/MappingPattern
     124: astore        20
     126: aload         20
     128: ifnull        150
     131: aload         20
     133: astore        17
     135: iconst_0
     136: istore        18
     138: aload         17
     140: invokevirtual #328                // Method pl/klemba/aoc/day5/MappingPattern.getValueShift:()J
     143: lload         12
     145: ladd
     146: nop
     147: goto          152
     150: lload         12
     152: lstore        7
     154: goto          24
     157: lload         7
     159: lreturn

  public static final long findMinLocationOf(kotlin.ranges.LongRange, java.util.ArrayList<java.util.ArrayList<pl.klemba.aoc.day5.MappingPattern>>);
    Code:
       0: aload_0
       1: ldc_w         #337                // String longRange
       4: invokestatic  #175                // Method kotlin/jvm/internal/Intrinsics.checkNotNullParameter:(Ljava/lang/Object;Ljava/lang/String;)V
       7: aload_1
       8: ldc_w         #338                // String almanac2
      11: invokestatic  #175                // Method kotlin/jvm/internal/Intrinsics.checkNotNullParameter:(Ljava/lang/Object;Ljava/lang/String;)V
      14: aload_0
      15: checkcast     #59                 // class java/lang/Iterable
      18: astore_2
      19: ldc2_w        #121                // long 9223372036854775807l
      22: lstore_3
      23: iconst_0
      24: istore        5
      26: lload_3
      27: lstore        6
      29: aload_2
      30: invokeinterface #63,  1           // InterfaceMethod java/lang/Iterable.iterator:()Ljava/util/Iterator;
      35: astore        8
      37: aload         8
      39: invokeinterface #69,  1           // InterfaceMethod java/util/Iterator.hasNext:()Z
      44: ifeq          101
      47: aload         8
      49: checkcast     #340                // class kotlin/collections/LongIterator
      52: invokevirtual #343                // Method kotlin/collections/LongIterator.nextLong:()J
      55: lstore        9
      57: lload         6
      59: lload         9
      61: lstore        11
      63: lstore        13
      65: iconst_0
      66: istore        15
      68: lload         11
      70: aload_1
      71: invokestatic  #96                 // Method mapToLocation:(JLjava/util/ArrayList;)J
      74: lstore        16
      76: iconst_0
      77: istore        18
      79: lload         16
      81: lload         13
      83: lcmp
      84: ifge          92
      87: lload         16
      89: goto          94
      92: lload         13
      94: nop
      95: nop
      96: lstore        6
      98: goto          37
     101: lload         6
     103: lreturn

  public static void main(java.lang.String[]);
    Code:
       0: invokestatic  #348                // Method main:()V
       3: return

  private static final long getSeeds$lambda$8(kotlin.text.MatchResult);
    Code:
       0: aload_0
       1: ldc_w         #351                // String it
       4: invokestatic  #175                // Method kotlin/jvm/internal/Intrinsics.checkNotNullParameter:(Ljava/lang/Object;Ljava/lang/String;)V
       7: nop
       8: aload_0
       9: invokeinterface #233,  1          // InterfaceMethod kotlin/text/MatchResult.getDestructured:()Lkotlin/text/MatchResult$Destructured;
      14: invokevirtual #239                // Method kotlin/text/MatchResult$Destructured.getMatch:()Lkotlin/text/MatchResult;
      17: invokeinterface #243,  1          // InterfaceMethod kotlin/text/MatchResult.getGroupValues:()Ljava/util/List;
      22: iconst_1
      23: invokeinterface #247,  2          // InterfaceMethod java/util/List.get:(I)Ljava/lang/Object;
      28: checkcast     #178                // class java/lang/String
      31: invokestatic  #251                // Method java/lang/Long.parseLong:(Ljava/lang/String;)J
      34: lreturn

  static {};
    Code:
       0: new           #200                // class kotlin/text/Regex
       3: dup
       4: ldc_w         #355                // String  (\\d+)
       7: invokespecial #356                // Method kotlin/text/Regex."<init>":(Ljava/lang/String;)V
      10: putstatic     #276                // Field numberRegex:Lkotlin/text/Regex;
      13: new           #200                // class kotlin/text/Regex
      16: dup
      17: ldc_w         #358                // String (\\d+) (\\d+) (\\d+)
      20: invokespecial #356                // Method kotlin/text/Regex."<init>":(Ljava/lang/String;)V
      23: putstatic     #196                // Field mappingLineRegex:Lkotlin/text/Regex;
      26: return
}