three times faster solve now, skipping consecutive sameface operationsoperations

This commit is contained in:
Joachim 2018-08-26 12:40:54 +02:00
parent d5a771ff14
commit 5a2131cb64

View File

@ -1,31 +1,68 @@
package be.nielandt
import kotlin.math.min
import java.util.*
/**
* Counter for X digits of a given base. Skips situations where faces are the same.
*/
class CounterSkip(size: Int) : Counter(size, 18) {
/**
* Increase the counter.
*
* @return true if the increase happened, false if we hit the ceiling.
*/
// /**
// * Increase the counter.
// *
// * @return true if the increase happened, false if we hit the ceiling.
// */
// override fun increase(): Boolean {
// var lmi = lastModifiedIndex
// var last = super.increase()
// lmi = min(lastModifiedIndex, lmi)
// // are we having an invalid situation? this would be two consecutive moves on the same face
// while (
// (containsConsecutiveSameFaceMoves() && !atMax()) ||
// (this.counter?.size > 1 && !atMax() && containsPalindrome())) {
// last = super.increase()
// lmi = min(lastModifiedIndex, lmi)
// }
// // we have to set the lastmodified index to the lowest point that it got to... otherwise we might be skipping some cases
// this.lastModifiedIndex = lmi
// return last
// }
override fun increase(): Boolean {
var lmi = lastModifiedIndex
var last = super.increase()
lmi = min(lastModifiedIndex, lmi)
// are we having an invalid situation? this would be two consecutive moves on the same face
while (
(containsConsecutiveSameFaceMoves() && !atMax()) ||
(this.counter?.size > 1 && !atMax() && containsPalindrome())) {
last = super.increase()
lmi = min(lastModifiedIndex, lmi)
if (atMax()) {
return false
}
// we have to set the lastmodified index to the lowest point that it got to... otherwise we might be skipping some cases
this.lastModifiedIndex = lmi
return last
for (i in this.counter.size - 1 downTo 0) {
this.counter[i]++
// if we've hit the maximum value on the first digit, return false
if(this.counter[i]==base && i == 0)
return false
this.lastModifiedIndex = i
// if we're overflowing, go to 0
if (this.counter[i] == base) {
this.counter[i] = 0
}
// we're not overflowing, this is the right digit. if we have a same-face situation, increase again
else if (i > 0 && this.counter[i] % 6 == this.counter[i - 1] % 6) {
// we're increasing again, this time try to get into the next 'class'
this.counter[i]++
// which potentially overflows again
if (this.counter[i] == base) {
this.counter[i] = 0
} else {
// we didn't overflow, so we have increase
return true
}
}
// didn't find a reason to inhibit this combination, break and return true
else {
// keep track of the digit index we're breaking on.
return true
}
}
return true
}
private fun containsPalindrome(): Boolean {
@ -48,4 +85,13 @@ class CounterSkip(size: Int) : Counter(size, 18) {
}
return false
}
}
fun main(args: Array<String>) {
val counterSkip = CounterSkip(4)
while (counterSkip.increase()) {
println("counterSkip.counter = ${Arrays.toString(counterSkip.counter)}")
}
}