牛客寒假算法基礎集訓營4 - E Applese 塗顏色 數論

題目鏈接

題意:給一個 nnmm 列的方陣上色,只能上黑色或者白色,且必須滿足左右相鄰的格子顏色不能相同,問有多少種上色的方法。

思路:可以得出一行只有兩種上色方法,而相鄰兩行之間互不影響,所以答案就是 2n2^n

解法一:

由於 nn 範圍過大,可以通過歐拉降冪來減小時間複雜度。
歐拉降冪: xnxn mod φ(m) + φ(m) (mod m)x^n≡x^{n \ mod \ \varphi(m) \ + \ \varphi(m)} \ (mod \ m)
由於 m=109+7m = 10^9+7 ,所以 mm 爲質數,質數 mm 的歐拉函數 φ(m)\varphi(m)m1m-1。降冪後再通過快速冪即可求解。

#-*-coding:utf-8 -*-
n ,m = map(int ,input().split(" "))
p = 1000000007
n = n % (p - 1) + p - 1
a = [0]*12
b = [1, 2, 4, 8, 16, 32, 64, 128, 256, 512]
len = -1
while n > 0:
    len += 1
    a[len] = n % 10
    n = n // 10
ans = 1
for i in range(len):
    ans = ans * b[a[len - i]] % p
    ans = pow(ans ,10) % p
ans = ans * b[a[0]] % p
print(ans)
解法二:

因爲是模數 mm 是質數,所以也可以用費馬小定理來進行降冪。
費馬小定理: ap11 (mod p)a^{p-1}≡1 \ (mod \ p) ( pp 爲質數)
代碼同解法一是一樣的

解法三:

c++直接用十進制快速冪
十進制快速冪:
n=i=0dai10in=\sum_{i=0}^{d}a_i*10^i
mn=((((mad)10mad1)10mad2)10...)10ma0m^n = ((((m^{a_d})^{10}*m^{a_{d-1}})^{10}*m^{a_{d-2}})^{10}...)^{10}*m^{a_0}

#include<cstdio>
#include<iostream>
#include<string>
#include<cstring>
using namespace std;
const long long p = 1e9 + 7;
string a, b;
int num[10] = {1, 2, 4, 8, 16, 32, 64, 128, 256, 512};
long long ans, x;
int main()
{
    cin >> a >> b;
    ans = 1;
    int len = a.size() - 1;
    for (int i = 0; i < len; ++i)
    {
        (ans *= num[a[i] - '0']) %= p;
        x = ans;
        for (int j = 2; j <= 10; ++j)
            (ans *= x) %= p;
    }
    (ans *= num[a[len] - '0']) %= p;
    printf("%lld\n", ans);
    return 0;
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章