/** * This is the hardest problem to understand. I am still not sure if what I solved was actually the question. * I find the diagrams very confusing, and it took me 3 hours just to get an idea of what the problem is. * It might be cleared up to explain which algorithm of example 2 can't be used and why(I asumed the green one, but * that might be wrong). * * What I figured is that you have to find overlap in hyperspace. There is one exception where the lower bounds match * exactly the upper bound of to hyperspaces. I then create a new hyperspace of the matches of the origin and check if * others overlap. * * I'm not sure about this solution. Please be aware that using coloured illustrations can break the problemset, since * they are usually not printed in colour since it costs 10x as much unfortunately. Be sure to add a warning about this * to the organizers. */ fun main() { val input = System.`in`.bufferedReader() val (algo, params) = input.readLine().split(" ").take(2).map { it.toInt() } var algorithms = (0 until algo).map { val low = input.readLine().split(" ").take(params).map { it.toInt() } val high = input.readLine().split(" ").take(params).map { it.toInt() } Dimension(low, high) }.toList() val origin = Dimension( (0 until params).map { 0 }.toList(), (0 until params).map { 0 }.toList() ) val queue = mutableListOf(origin) var matches = 0 while (queue.isNotEmpty()) { val coverage = queue.removeLast() val matched = algorithms.filter { it in coverage } algorithms = algorithms.filter { it !in matched } if (matched.isNotEmpty()) { matched.map { origin + it.also { matches++ } }.toCollection(queue) } } println(matches) } data class Dimension( val low: List, val high: List ) { operator fun contains(other: Dimension): Boolean = high.zip(other.low).all { (a, b) -> b < a } || high == other.low operator fun plus(other: Dimension): Dimension = Dimension( low.zip(other.low).map { (a, b) -> a.coerceAtMost(a) }, high.zip(other.high).map { (a, b) -> b.coerceAtLeast(a) } ) }