• K-QAQ(打表)


    题目链接:http://acm.csust.edu.cn/problem/3033

    Description

     

    定义,即1到i的j次方的异或和

    的值

    Input

     

    一行三个整数k,x,y

    1k1e5

    1xy1e9

    Output

     

    一个整数,表示答案

    Sample Input 1 

    1 2 7

    Sample Output 1

    6

    此题看起来复杂,但打个表就会发现是个一眼题... 公式由于(i%2)的存在,所以我们只需要计算i为奇数的情况就好了。 那么打个奇数的表就会发现:

    那么此题就结束了。

    证明如下:

    记 f(x, y) 为x到y的所有整数的异或值。对 f(2^k, 2^(k+1) -1) (注意文章中的 ^ 表示的是“幂”,xor 表示“异或”,or 表示“或”): 2^k 到 2^(k+1) -1 这2^k个数,最高位(+k位)的1个数为2^k, 若 k >= 1,则2^k为偶数,将这2^k个数的最高位(+k位)去掉,异或值不变。

    因而f(2^k, 2^(k+1) -1) = f(2^k - 2^k, 2^(k+1) -1 -2^k) = f(0, 2^k -1)

    因而 f(0, 2^(k+1) -1) = f(0, 2^k -1) xor f(2^k, 2^(k+1) -1) = 0 (k >= 1) 即 f(0, 2^k - 1) = 0 (k >= 2)

    对 f(0, n)  (n >= 4) 设n的最高位1是在+k位(k >= 2), f(0, n) = f(0, 2^k - 1) xor f(2^k, n) = f(2^k, n) 对2^k到n这n+1-2^k个数,最高位(+k位)共有 m = n+1-2^k 个1,去除最高位的1 当n为奇数时,m是偶数,

    因而 f(0, n) = f(2^k, n) = f(0, n - 2^k) 由于n - 2^k 与 n同奇偶,递推上面的公式,可得:

    f(0, n) = f(0, n % 4)

    当 n % 4 == 1 时, f(0, n) = f(0, 1) = 1

    当 n % 4 == 3 时, f(0, n) = f(0, 3) = 0

    以下是打表的程序以及打表的结果:

    #include <bits/stdc++.h>
    using namespace std;
    
    int work(int i,int j)
    {
        int ans=0;
        for (int k=1; k<=pow(i,j); k++)
            ans^=k;
        return ans;
    }
    
    void en(int i,int j)
    {
        printf ("f(%d,%d)=%d
    ",i,j,work(i,j));
        
    }
    
    int main()
    {
        int n;
        n=11;
        int ans=0;
        for (int i=1; i<=n; i+=2){
            for (int j=1; j<=5; j++){
                en(i,j);
            }
            printf ("
    ");
        }
        return 0;
    }
    
    /*
    f(1,1)=1
    f(1,2)=1
    f(1,3)=1
    f(1,4)=1
    f(1,5)=1
    
    f(3,1)=0
    f(3,2)=1
    f(3,3)=0
    f(3,4)=1
    f(3,5)=0
    
    f(5,1)=1
    f(5,2)=1
    f(5,3)=1
    f(5,4)=1
    f(5,5)=1
    
    f(7,1)=0
    f(7,2)=1
    f(7,3)=0
    f(7,4)=1
    f(7,5)=0
    
    f(9,1)=1
    f(9,2)=1
    f(9,3)=1
    f(9,4)=1
    f(9,5)=1
    
    f(11,1)=0
    f(11,2)=1
    f(11,3)=0
    f(11,4)=1
    f(11,5)=0
    */
    View Code

    以下是AC代码:

    #include <bits/stdc++.h>
    using namespace std;
    
    const int mod=1e9+7;
    
    int main()
    {
        int n,x,y;
        scanf ("%d%d%d",&n,&x,&y);
        int ans=0;
        int mark=0;
        for (int i=1; i<=n; i+=2){
            if (!mark) ans=(ans+y-x+1)%mod;
            else ans=(ans+y/2-(x-1)/2)%mod;
            mark^=1;
        }
        printf ("%d
    ",ans);
        
        return 0;
    }
    路漫漫兮
  • 相关阅读:
    一文了解网络编程之走进TCP三次握手和HTTP那些你不知道的事
    并发编程面试必备之ConcurrentHashMap源码解析
    java延迟队列DelayQueue及底层优先队列PriorityQueue实现原理源码详解
    聊一聊面试中常问的延时队列
    面试必备HashMap源码解析
    synchronized解锁源码分析
    synchronized的jvm源码加锁流程分析聊锁的意义
    jvm源码解析java对象头
    从ReentrantLock源码入手看锁的实现
    从synchronized和lock区别入手聊聊java锁机制
  • 原文地址:https://www.cnblogs.com/lonely-wind-/p/12003956.html
Copyright © 2020-2023  润新知