class Solution {
public String smallestGoodBase(String n) {
long num = Long.parseLong(n);
int maxLen = (int) (Math.log(num + 1) / Math.log(2));
for (int len = maxLen; len >= 0; len--) {
long l = 2, r = (long) Math.pow(num, 1.0 / (len-1)) + 1;
while (l < r) {
long mid = l + (r-l)/2;
long sum = 0;
for (int i = 0; i < len; i++) sum = sum * mid + 1;
if (sum == num) return ""+mid;
else if (sum < num) l = mid + 1;
else r = mid;
}
}
return String.valueOf(num - 1);
}
}
/*
1) every bit is 1, the length range is [2, log(n+1)/log2], for each length do binary search, from max to min, because max lenght leads to smaller base; 2) base range: [2, pow(n, 1.0/(len-1)) + 1], don't understand why it's the upper, binary search to find the base; 2) every bit is 1, so with candidate base and bits, calculate if it equals n;
*/