BZOJ 4558 方[LNOI2016 Day1]

不知道在干什么

#pragma optimize("-O2")
#include<bits/stdc++.h>
#define LL long long
#define int LL
#define N 2007
#define mo 100000007
#define sight(c) ('0'<=c&&c<='9')
#define min(a,b) ((a)<(b)?(a):(b))
using namespace std;
LL n,m,k;
struct Point {
    int x, y;
    Point(int a = 0, int b = 0) : x(a), y(b) { }
    bool operator< (const Point &b) const& { return x < b.x || x == b.x && y < b.y; }
    bool operator== (const Point &b) const& { return x == b.x && y == b.y; }
    inline bool in(){ return 0<=x&&x<=n&&0<=y&&y<= m; }
}pt[N];
set<Point> mp;
inline void read(LL &x){
    static char c;
    for (c=getchar();!sight(c);c=getchar());
    for (x=0;sight(c);c=getchar()) x=x*10+c-48;
}
//inline void read(int &x){
//  static char c;
//  for (c=getchar();!sight(c);c=getchar());
//  for (x=0;sight(c);c=getchar()) x=x*10+c-48;
//}
void write(int x){
    if (x<10) { putchar('0'+x);return;} write(x/10),putchar('0'+x%10);
}
inline void writeln(int x){
    if (x<0) putchar('-'),x*=-1; write(x); putchar('\n');
} 
LL NO() {
    int k=min(n, m); LL ans = 0;
    for (int i=1;i<=k;++i) (ans+=(n-i+1)*(m-i+1)%mo*i)%=mo;
    return ans;
}
LL COP(int l, int r, int h) {
    int z=min(l+r,h);
    if (z==0) return 0;
    LL ans=z*(z+3)>>1;
    if (z>l) ans-=(z-l)*(z-l+1)>>1;
    if (z>r) ans-=(z-r)*(z-r+1)>>1;
    return ans;
}
LL OOO(int x, int y) {
    int t = x, b = n - x, l = y, r = m - y;
    LL tog=(COP(t,b,l)+COP(t,b,r)+COP(l,r,t) + COP(l, r, b)
            -min(l,t)-min(t,r)-min(r,b)-min(b,l))%mo;
    return tog;
}
void CN(Point a, Point b, int &cnt2, int &cnt3, int &cnt4) {
    if (a.in()&&b.in()) {
        int t = mp.count(a) + mp.count(b); ++cnt2;
        if (t>0) ++cnt3; if (t>1) ++cnt4, ++cnt3;
    }
}
LL dx,dy,x,y;
signed main() {
//  freopen("BB.in","r",stdin);
    read(n); read(m); read(k);
    LL ans=NO();
    for (int i=0;i<k;i++) {
        read(pt[i].x); read(pt[i].y);
        mp.insert(pt[i]);
        (ans-=OOO(pt[i].x, pt[i].y))%=mo;
    }
    int cnt2=0,cnt3=0,cnt4=0;
    for (int i=0;i<k;i++) {
        Point p=pt[i];
        for (int j=i+1;j<k;j++) {
            Point q=pt[j];
            dx=p.x-q.x,dy=p.y-q.y;
            CN(Point(p.x+dy,p.y-dx),Point(q.x+dy,q.y-dx),cnt2,cnt3,cnt4);
            CN(Point(p.x-dy,p.y+dx),Point(q.x-dy,q.y+dx),cnt2,cnt3,cnt4);
            if ((abs(dx)+abs(dy))&1) continue;
            x=dx-dy>>1,y=dx+dy>>1;
            CN(Point(p.x-x,p.y-y),Point(q.x+x,q.y+y),cnt2,cnt3,cnt4);
        }
    }
    ans=(ans+cnt2-cnt3/3+cnt4/6)%mo;
    if (ans<0) ans+=mo;
    writeln(ans);
}

 

posted @ 2018-01-06 20:20  泪寒之雪  阅读(203)  评论(0编辑  收藏  举报