We only want the number of ways not the actual solutions. So we can try DP.
Single Sequence DP
Step 1 Define optimal subproblem
fence(i, 0) = max number of ways to apply the same color at the ith post
fence(i, 1) = max # ways to apply different colors at the ith post
Step 2 Recurrence
fence(i, 0) = fence(i-1, 1)
fence(i, 1) = fence(i-1, 0) * (k-1) + fence(i-1, 1) * (k-1)
Step 3 Base cases
fence(0, 0) = 0
fence(0, 1) = 0
fence(1, 0) = k
fence(1, 1) = 0
fence(2, 0) = k
fence(2, 1) = k * (k - 1)
fence(3, 0) = fence(2, 1)
fence(3, 1) = fence(2, 0) * (k - 1) + fence(2, 1) * (k - 1)
Step 4 Topo Order
for i from 3 to n
Stet 5 Final Answer
fence(n, 0) + fence(n, 1)
Code
public int numWays(int n, int k) {
// create memo table
int adjN = n < 2 ? 2 : n;
int[][] fence = new int[adjN + 1][2];
// init base case
fence[0][0] = 0;
fence[0][1] = 0;
fence[1][0] = k;
fence[1][1] = 0;
fence[2][0] = k;
fence[2][1] = k * (k - 1);
// topo order
for (int i = 3; i <= n; i++) {
fence[i][0] = fence[i-1][1];
fence[i][1] = fence[i-1][0] * (k - 1) + fence[i-1][1] * (k - 1);
}
// final answer
return fence[n][0] + fence[n][1];
}
There is only one layer of dependencies so we can compress the active states.
Code w/ State Compression
public int numWays(int n, int k) {
// create memo table
int[][] fence = new int[3][2];
// init base case
fence[0][0] = 0;
fence[0][1] = 0;
fence[1][0] = k;
fence[1][1] = 0;
fence[2][0] = k;
fence[2][1] = k * (k - 1);
// topo order
for (int i = 3; i <= n; i++) {
fence[i%3][0] = fence[(i-1)%3][1];
fence[i%3][1] = fence[(i-1)%3][0] * (k - 1) + fence[(i-1)%3][1] * (k - 1);
}
// final answer
return fence[n%3][0] + fence[n%3][1];
}