2222. Number of Ways to Select Buildings | 1657
wrong interpretation & wrong result:
1class Solution:
2 def numberOfWays(self, s: str) -> int:
3 # either 0101... or 1010...
4 # if 0, find how many 1s until another 0
5 # if 1, find how many 0s until another 1
6 # [count(continuous 0 or 1s), count(continuous 0 or 1s), ...]
7 # "001101" -> [2,2,1,1]
8 # 2*2*1 + 2*1*1 = 6
9 # can go with a length == 3 running product, result += each time
10
11 if not s:
12 return 0
13
14 consecutive = []
15 prev = s[0]
16 combo = 0
17
18 for c in s:
19 if c == prev:
20 combo += 1
21 else:
22 consecutive.append(combo)
23 prev = c
24 combo = 1
25
26 consecutive.append(combo)
27
28 # print(consecutive)
29
30 if len(consecutive) < 3:
31 return 0
32
33 n = len(consecutive)
34 running_product = consecutive[0] * consecutive[1] * consecutive[2]
35 result = running_product
36 # print(result, running_product)
37
38 for i in range(3, n):
39 running_product *= consecutive[i]
40 running_product = running_product // consecutive[i - 3]
41 result += running_product
42 # print(result, running_product)
43
44 return result
thinking in another perspective - prefix sum - works:
1class Solution:
2 def numberOfWays(self, s: str) -> int:
3 # we focus on the second building.
4 # for each char
5 # if 0, then the possibilities of involving this 0 as the second building is
6 # (number of 1s before this 0) * 1 * (number of 1s after this 0)
7
8 n = len(s)
9 num_zeros = s.count("0")
10 num_ones = n - num_zeros
11 zeros_to_the_left = ones_to_the_left = result = 0
12
13 for c in s:
14 if c == "0":
15 result += ones_to_the_left * (num_ones - ones_to_the_left)
16 zeros_to_the_left += 1
17 else: # c == "1"
18 result += zeros_to_the_left * (num_zeros - zeros_to_the_left)
19 ones_to_the_left += 1
20
21 return result
takeaways:
- brought prefix sum out of my toolbox so that I know I have this tool