分治思想 - 数1的个数
Jon fought bravely to rescue the wildlings who were attacked by the white-walkers at Hardhome. On his arrival, Sam tells him that he wants to go to Oldtown to train at the Citadel to become a maester, so he can return and take the deceased Aemon's place as maester of Castle Black. Jon agrees to Sam's proposal and Sam sets off his journey to the Citadel. However becoming a trainee at the Citadel is not a cakewalk and hence the maesters at the Citadel gave Sam a problem to test his eligibility.
Initially Sam has a list with a single element n. Then he has to perform certain operations on this list. In each operation Sam must remove any element x, such that x > 1, from the list and insert at the same position , , sequentially. He must continue with these operations until all the elements in the list are either 0 or 1.
Now the masters want the total number of 1s in the range l to r (1-indexed). Sam wants to become a maester but unfortunately he cannot solve this problem. Can you help Sam to pass the eligibility test?
The first line contains three integers n, l, r (0 ≤ n < 250, 0 ≤ r - l ≤ 105, r ≥ 1, l ≥ 1) – initial element and the range l to r.
It is guaranteed that r is not greater than the length of the final list.
Output the total number of 1s in the range l to r in the final sequence.
7 2 5
4
10 3 10
5
Consider first example:
Elements on positions from 2-nd to 5-th in list is [1, 1, 1, 1]. The number of ones is 4.
For the second example:
Elements on positions from 3-rd to 10-th in list is [1, 1, 1, 0, 1, 0, 1, 0]. The number of ones is 5.
题目分析 : 给你一个 n ,将 n 分成 0 和 1,询问你给定区间内的 1 的个数
思路分析 : 是一个分治的思想,每次只是查询所给区间的 1 的个数
代码示例 :
#define ll long long const int maxn = 1e6+5; const double pi = acos(-1.0); const int inf = 0x3f3f3f3f; ll n, l, r; ll fun(ll x){ if (x <= 1) return 1; else return fun(x/2)*2+1; } ll dfs(ll n, ll l, ll r, ll a, ll b){ if (l > b || r < a) return 0; if (n == 0) return 0; if (n == 1) return 1; ll sum = 0; ll mid = (a + b) >> 1; sum += dfs(n/2, l, r, a, mid-1); sum += dfs(n%2, l, r, mid, mid); sum += dfs(n/2, l, r, mid+1, b); return sum; } int main() { //freopen("in.txt", "r", stdin); //freopen("out.txt", "w", stdout); cin >> n >> l >> r; ll len = fun(n); printf("%lld\n", dfs(n, l, r, 1ll, len)); return 0; }