codeforces 959E Mahmoud and Ehab and the xor-MST

E. Mahmoud and Ehab and the xor-MST

Ehab is interested in the bitwise-xor operation and the special graphs. Mahmoud gave him a problem that combines both. He has a complete graph consisting of n vertices numbered from 0 to n - 1. For all 0 ≤ u < v < n, vertex u and vertex v are connected with an undirected edge that has weight  (where  is the bitwise-xor operation). Can you find the weight of the minimum spanning tree of that graph?

You can read about complete graphs in https://en.wikipedia.org/wiki/Complete_graph

You can read about the minimum spanning tree in https://en.wikipedia.org/wiki/Minimum_spanning_tree

The weight of the minimum spanning tree is the sum of the weights on the edges included in it.

Input

The only line contains an integer n (2 ≤ n ≤ 1012), the number of vertices in the graph.

Output

The only line contains an integer x, the weight of the graph's minimum spanning tree.

Example
input
Copy
4
output
Copy
4

发现找规律 很重要,

#include<iostream>
#include<stdio.h>
#include<algorithm>
#include<string.h>
using namespace std;
typedef long long ll;
const int maxn = 100000;
ll n,ans;
/*
发现奇数 n 就与前面的那个偶数 n-1 异或是最好的情况( n^(n-1) == 1)
偶数 n 就与 n^(n^(1<<L)) / L为n二进制中的最低为1的位 / 这个数 异或 取最好的情况 ( n ^ (n^(1<<L)) == (1<<L) )

所以对整数 N
奇数贡献 N/2+N%2
偶数贡献 枚举最低为1的位 求贡献

比如 n = 1001001000
枚举最低为1的位:
     n = 1001001000
                 10
                100
               1000
               ....
    ans =:
    小于等于 1000000000 的偶数贡献
    小于等于 1000000 的偶数贡献
    小于等于 1000 的偶数贡献
*/
int main()
{
    while(~scanf("%lld",&n))
    {
        n--;
        int l = 0;
        for(int i=0; i<50; i++) if((1ll<<i)&n) l = i;
        ans = n/2+n%2;//奇数的贡献
        int f = l;
        for(; f>0; f--)//小于等于n的偶数贡献,枚举偶数为1的最低
        {
            if((1ll<<f)&n)//为1的位
            {
                int k = f;
                ans+=(1ll<<f);//等于 (1<<k)的贡献
                for(int i=1; i<k; i++)// 小于 (1<<k)的贡献
                {
                    ans+=(1ll<<i)*(1ll<<(k-1-i));//此位贡献 (1<<i) 有(k-1-i)个这样的偶数情况
                }
            }
        }
        printf("%lld\n",ans);
    }
    return 0;
}
/*
1025
6144

158
653

99
371

98
369

1001
5060

11111
79227

123
439

321
1536

2000
11104

56
172
*/


猜你喜欢

转载自blog.csdn.net/qq_32944513/article/details/80163890