Binary-Decimal
We are given a binary string S of length n, in which each character is either '1' or '0'.
And we are asked to perform several queries on the string.
In each query we are given integers L and R. And we have to tell the value of sub-string S[l..r], in decimal representation.
Sample testcase:
Input:
1011 (string S)
5 (number of queries)
1 1 (l, r)
2 2
1 2
2 4
1 4
Output:
1 (1 * 2^0 == 1)
0
2
3 (0 * 2^2 + 1 * 2^1 + 1 * 2^0)
11 (1 * 2^3 + 0 * 2^2 + 1 * 2^1 + 1 * 2^0 = 11)
Constraints
1 < N < 10^5
1 < Q < 10^5
As the number can be very large, we are required to print it modulo 10^9 + 7.
Approach
So basically we need to convert binary representation sub-string S[l..r] in it's decimal.
I pre-computed the results of S[i...n-1] for all i:[0, n-1] in array B. So now B[i] represents the decimal number representation of sub-string S[i..n-1].
vector<int> pow(1e5, 1);
for(int i = 1; i < 1e5; i++) {
pow[i] = (pow[i - 1] * 2) % mod;
}
string s;
getline(cin, s);
vector<int> B(n, 0);
int prev = 0;
for(int i = 0; i < n; i++) {
B[(n - 1) - i] = (prev + (s[(n - 1) - i] == '1' ? pow[i] : 0)) % mod;
prev = B[(n - 1) - i];
}
while(q--) {
int l, r;
cin >> l >> r;
cout << ((B[l] - (r + 1 < n ? B[r + 1] : 0) + mod) % mod) / pow[n - (r + 1)]<< "\n";
}
return 0;
With the above approach only sample testcase got passed and all other cases are giving the wrong answers(WA).
I even tried using Segment tree for this problem but that is also not working.
What is the correct approach to solve this problem ?
Define
V[k]to be the value of the digits ofSstarting with thekth one.Then the value of the substring
S[l..r] = (V[l] - V[r+1]) / 2^(n - r - 1). (Something like that, I may have an off by one error. Play with small examples.)Now the useful fact about
10^9 + 7is that it is a prime. (The first 10 digit prime.) Which means that dividing by 2 is the same as multiplying by2^(10^9 + 5). Which is a constant that you can figure out with repeated squaring. And raising that constant to a high power can be done very efficiently using repeated squaring.With this you can create a lookup table for
V, and then do your queries in timeO(log(n)).