bc第八场Reading comprehension(快速幂,数模公式)

来源:互联网 发布:c语言合法关键字 编辑:程序博客网 时间:2024/05/29 18:06

题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=4990

题意:给定一个代码,用其他时间复杂度小的方法来实现这个代码功能

思路:打表发现有一定的规律,奇数位是一个类等比数列,或者可以换成前n项等比数列求和的形式,然后得到一个通项公式,或者求和公式,容易发现需要用快速幂来求,或者矩阵快速幂(这个不会),同时需要处理取模的情况,最后的公式会有一个除以3,然后再取模,经验告诉我需要用乘法逆元来处理,也就是乘以3的逆元,百度又学到了一个新的处理方法:数模公式:a/b mod m=a mod(b*m)/b

代码:
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <cmath>
#include <ctime>
#include <iostream>
#include <algorithm>
#include <string>
#include <vector>
#include <deque>
#include <list>
#include <set>
#include <map>
#include <stack>
#include <queue>
#include <cctype>
#include <numeric>
#include <iomanip>
#include <bitset>
#include <sstream>
#include <fstream>
#define debug "output for debug\n"
#define pi (acos(-1.0))
#define eps (1e-8)
#define inf 0x3f3f3f3f
#define ll long long
using namespace std;
const int maxn = 100005;
 ll n,m;
ll ans;
ll pow_mod(ll a, ll n,ll m)
{
    ll res = 1;
    while(n) {
        if (n & 1)
            res = res * a%m;
        a = a * a%m;
        n >>= 1;

    }
    return res;
}


int main()
{

    while(scanf("%I64d%I64d",&n,&m)!=EOF)
    {

        if(n&1)
        {
           ans=(pow_mod(2,(n+1),3*m)-1)/3;
        }
        else
        {
           ans=(pow_mod(2,n+1,3*m)-2)/3;
           
        }
        printf("%I64d\n",ans);

    }
    return 0;
}

 

0 0
原创粉丝点击