【BNU】33943 Super Rooks on Chessboard 【FFT】

来源:互联网 发布:宏业软件最新版本 编辑:程序博客网 时间:2024/05/21 03:19

【BNU】33943 Super Rooks on Chessboard

UVA上的题,然而我怎么会蠢到去UVA呢!(其实是百度首先跳出来的是BNU_

题目分析:

numxN个车没有覆盖的行数,numyN个车没有覆盖的列数。
首先我们考虑没有主对角线覆盖这一条件时,总共的没有被覆盖的面积就是numxnumy
现在我们考虑主对角线影响。
考虑没有被车覆盖的行的集合R={r1,r2,r3...rm}
考虑没有被车覆盖的列的集合C={c1,c2,c3...cn}
考虑被车覆盖的对角线的集合D={d1,d2,d3...ds}
那么对角线dk覆盖的还未被覆盖的格子数量即ricj=dk
考虑FFT,我们将行集合,列集合转化成多项式:R=xriC=xci
做一遍FFT答案就出来了。

心得:FFT时,首元素可以为任意阶。

my code:

#include <stdio.h>#include <string.h>#include <math.h>#include <algorithm>using namespace std ;typedef long long LL ;#define clr( a , x ) memset ( a , x , sizeof a )#define cpy( a , x ) memcpy ( a , x , sizeof a )const int MAXN = 100005 ;const double pi = acos ( -1.0 ) ;struct Complex {    double r , i ;    Complex () {}    Complex ( double r , double i ) : r ( r ) , i ( i ) {}    Complex operator + ( const Complex& t ) const {        return Complex ( r + t.r , i + t.i ) ;    }    Complex operator - ( const Complex& t ) const {        return Complex ( r - t.r , i - t.i ) ;    }    Complex operator * ( const Complex& t ) const {        return Complex ( r * t.r - i * t.i , r * t.i + i * t.r ) ;    }} ;void FFT ( Complex y[] , int n , int rev ) {    for ( int i = 1 , j , k , t ; i < n ; ++ i ) {        for ( j = 0 , k = n >> 1 , t = i ; k ; k >>= 1 , t >>= 1 ) j = j << 1 | t & 1 ;        if ( i < j ) swap ( y[i] , y[j] ) ;    }    for ( int s = 2 , ds = 1 ; s <= n ; ds = s , s <<= 1 ) {        Complex wn ( cos ( rev * 2 * pi / s ) , sin ( rev * 2 * pi / s ) ) , w ( 1 , 0 ) , t ;        for ( int k = 0 ; k < ds ; ++ k , w = w * wn ) {            for ( int i = k ; i < n ; i += s ) {                y[i + ds] = y[i] - ( t = w * y[i + ds] ) ;                y[i] = y[i] + t ;            }        }    }    if ( rev == -1 ) for ( int i = 0 ; i < n ; ++ i ) y[i].r /= n ;}bool visx[MAXN] , visy[MAXN] , visd[MAXN << 2] ;Complex x1[MAXN << 2] , x2[MAXN << 2] ;int r , c , q , n ;void solve ( int T ) {    int x , y , numx = 0 , numy = 0 ;    clr ( visx , 0 ) ;    clr ( visy , 0 ) ;    clr ( visd , 0 ) ;    scanf ( "%d%d%d" , &r , &c , &q ) ;    for ( int i = 0 ; i < q ; ++ i ) {        scanf ( "%d%d" , &x , &y ) ;        visx[x] = 1 ;        visy[y] = 1 ;        visd[x - y + c] = 1 ;    }    int n = 1 ;    while ( n < r + c + 1 ) n <<= 1 ;    for ( int i = 1 ; i <= r ; ++ i ) numx += visx[i] == 0 ;    for ( int i = 1 ; i <= c ; ++ i ) numy += visy[i] == 0 ;    for ( int i = 1 ; i <= r ; ++ i ) x1[i - 1] = Complex ( visx[i] == 0 , 0 ) ;    for ( int i = r ; i < n ; ++ i ) x1[i] = Complex ( 0 , 0 ) ;    for ( int i = 1 ; i <= c ; ++ i ) x2[c - i] = Complex ( visy[i] == 0 , 0 ) ;    for ( int i = c ; i < n ; ++ i ) x2[i] = Complex ( 0 , 0 ) ;    FFT ( x1 , n , 1 ) ;    FFT ( x2 , n , 1 ) ;    for ( int i = 0 ; i < n ; ++ i ) x1[i] = x1[i] * x2[i] ;    FFT ( x1 , n , -1 ) ;    LL ans = ( LL ) numx * numy ;    for ( int i = 0 ; i < n ; ++ i ) ans -= ( LL ) ( x1[i].r + 0.5 ) * visd[i + 1] ;    printf ( "Case %d: %lld\n" , T , ans ) ;}int main () {    int T ;    scanf ( "%d" , &T ) ;    for ( int i = 1 ; i <= T ; ++ i ) solve ( i ) ;    return 0 ;}
1 0
原创粉丝点击
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 金立手机导航信号弱怎么办 手机导航时gps信号弱怎么办 三星手机导航gps信号弱怎么办 小米5导航信号弱怎么办 华为手机导航gps信号弱怎么办 手机屏玻璃裂了怎么办 oppo音量键坏了怎么办 魅蓝手机屏幕碎了怎么办 手机钢化膜边缘有气泡怎么办 手机贴钢化膜边缘有气泡怎么办 苹果手机钢化膜边缘有气泡怎么办 手机膜里的水泡怎么办 膜贴好了有气泡怎么办 后档玻璃膜气泡怎么办 贴膜里面有灰尘怎么办 贴膜边缘不粘怎么办 贴膜时候的气泡怎么办 贴手机膜起泡了怎么办 手机膜起泡泡了怎么办 手机膜鼓起来了怎么办 贴膜中间有气泡怎么办 新车贴膜有气泡怎么办 贴手机膜进灰尘怎么办 贴手机膜有灰尘怎么办 华为mate10后机壳碎了怎么办 手机屏和壳分开了怎么办 oppoa33手机开不了机怎么办 7p背面刮花了怎么办 oppo手机左右两键失灵怎么办 苹果5s屏幕翘起怎么办 0pp0手机有点卡怎么办 手机用久有点卡怎么办 手机有点卡怎么办魅蓝 苹果6排线接反了怎么办 oppo手机解锁密码忘了怎么办 魅蓝5音量小怎么办 魅蓝5密码忘记了怎么办 魅蓝note3锁定了怎么办 魅族mx5系统铃声没有了怎么办 魅族主板坏了怎么办 魅族mx5螺丝滑丝怎么办