uva10655

Given the value of a+b and ab you will have to find the value of a n + b n Input The input file contains several lines of inputs. Each line except the last line contains 3 non-negative integers p, q and n. Here p denotes the value of a+b and q denotes the value of ab. Input is terminated by a line containing only two zeroes. This line should not be processed. Each number in the input file fits in a signed 32-bit integer. There will be no such input so that you have to find the value of 00 . Output For each line of input except the last one produce one line of output. This line contains the value of a n + b n. You can always assume that a n + b n fits in a signed 64-bit integer. Sample Input 10 16 2 7 12 3 0 0 Sample Output 68 91

矩阵快速幂。。。

很明显,要把a和b解出来很困难,因为还有虚数,讨论很烦

那么我们就要转化一下 用p和q解决问题

我们先用a^(n-1)+b^(n-1)推出a^n+b^n

要想升幂,还是生一次 只能乘a+b,但是会多出来两项(在纸上写一下,这里不方便打公式)

中间的两项提出一个a*b,变成了a^(n-2)+b^(n-2) 那么我们就可以递推了

但是太慢了,就用矩阵快速幂。。。

构造矩阵就行了

注意特判n==0

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
struct mat {
    ll a[3][3];
} A, B;
ll p, q, n;
mat operator * (mat A, mat B)
{
    mat ret; memset(ret.a, 0, sizeof(ret.a));
    for(int i = 1; i < 3; ++i)
        for(int j = 1; j < 3; ++j)
            for(int k = 1; k < 3; ++k) ret.a[i][j] = ret.a[i][j] + A.a[i][k] * B.a[k][j];
    return ret;
}
mat power(mat A, ll t)
{
    mat ret; memset(ret.a, 0, sizeof(ret.a));
    for(int i = 1; i < 3; ++i) ret.a[i][i] = 1;
    for(; t; t >>= 1, A = A * A) if(t & 1) ret = ret * A;
    return ret;
}
int main()
{
    while(scanf("%lld%lld%lld", &p, &q, &n) == 3)
    {
        if(n == 0) { puts("2"); continue; }
        if(n == 1) { printf("%lld\n", p); continue; }
        if(n == 2) { printf("%lld\n", p * p - 2 * q); continue; }
        A.a[1][1] = p; A.a[1][2] = -q;
        A.a[2][1] = 1; A.a[2][2] = 0;
        B.a[1][1] = p * p - 2 * q; B.a[2][1] = p;
        B = power(A, n - 2) * B;
        printf("%lld\n", B.a[1][1]);
    }
    return 0;
}

时间: 2024-10-01 07:26:35

uva10655的相关文章

【UVA10655】 Contemplation! Algebra

题目 给定 \(p = a + b\) 和 \(q = ab\) 和 \(n\),求 \(a ^ n + b ^ n\). $0\le n\lt 2^{63} $ 分析 大水题. 先考虑 \(n\) 较小的情况,可以很容易的想到递推: \[ \begin{array}{} \text{令} F(i) & = a ^ n + b ^ n \ & = (a + b)(a ^ {n - 1} + b ^ {n - 1}) - (ab ^ {n - 1} + a^{n - 1}b) \ &

Contemplation! Algebra(矩阵快速幂,uva10655)

Problem EContemplation! AlgebraInput: Standard Input Output: Standard Output Time Limit: 1 Second Given the value of a+b and ab you will have to find the value of an+bn Input The input file contains several lines of inputs. Each line except the last

UVA-10655 Contemplation! Algebra (矩阵)

题目大意:给出a+b的值和ab的值,求a^n+b^n的值. 题目分析:有种错误的方法是这样的:利用已知的两个方程联立,求解出a和b,进而求出答案.这种方法之所以错,是因为这种方法有局限性.联立之后会得到一个二元一次方程,只有当该方程有实数解确切的说是当某个数据满足该方程有实数解时,这种方法得到的结果才有可能正确.显然,题中数据不可能这么片面.正确的方法是这样的: 令a+b=A,ab=B,S(n)=an+bn.则S(n)=an+bn=(a+b)(an-1+bn-1)-abn-1-an-1b=(a+

《算法竞赛入门经典——训练指南》第二章题库

UVa特别题库 UVa网站专门为本书设立的分类题库配合,方便读者提交: http://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&category=442 注意,下面注有"extra"的习题并没有在书中出现,但在上面的特别题库中有,属于附加习题. 基础练习 (Basic Problems) UVa11388 GCD LCM UVa11889 Benefit UVa10943 How do y

矩阵小结

1.矩阵快速幂,用倍增来加速(O(n^3*logk)) 2.矩阵求解递推关系第n项(n很大)可以构造矩阵,用矩阵快速幂迅速求出. 3.给定起点和终点求从起点到终点恰好进过k步的方案数可以直接对可达矩阵相乘k次得到结果 4.矩阵乘法的顺序对时间影响比较大(提高Cache命中率),kij最快而且还可以进行稀疏矩阵加速(当a[i][k]为0时没必要进行运算). 因为最近在搞矩阵,所以准备写一个矩阵模板类.结果遇到不少坑,毕竟平时没怎么使用动态分配内存,只好先用静态数组水过,搞完之后调试很久才写出矩阵的