组询问

每组询问给你一个日期要求你输出在这个日期之后最近的一次父亲节或者母亲节按照题目要求的格式输出

模拟题

难点大概在找出年的所有父亲节/母亲节的日期 和 按格式输出

复杂度赛时代码没有优化直接

#include <bits/stdc++.h>
using namespace std;
template <typename T> void read(T &x){
    x = 0; int f = 1; char ch = getchar();
    while (!isdigit(ch)) {if (ch == '-') f = -1; ch = getchar();}
    while (isdigit(ch)) {x = x * 10 + ch - '0'; ch = getchar();}
    x *= f;
}
inline void write(int x){if (x > 9) write(x/10); putchar(x%10+'0'); }
inline int gety(int x){ return x / 10000 ;}
inline int getm(int x){ return x / 100 % 100; }
inline int getd(int x){ return x % 100; }
inline void printMonth(int m){
    if (m == 5) cout << "May";
    if (m == 6) cout << "June";
    cout << " ";
}
inline void printst(int d){
    if (11 <= d && d <= 20) cout << "th";
    else{
        if (d%10==1) cout << "st";
        else if (d%10==2) cout << "nd";
        else if (d%10==3) cout << "rd";
        else cout << "th";
    }
}
inline void print(bool isM,int date){
    int y,m,d;
    if (isM) cout << "Mother's Day: "; else cout << "Father's Day: ";
    y = gety(date),m = getm(date),d = getd(date);
    printMonth(m);
    cout << d;
    printst(d);
    cout << ", " << y << '\n';
}
inline bool cmp(int x,int y){ //x<y
    if (gety(x) != gety(y)) return gety(x) < gety(y);
    if (getm(x) != getm(y)) return getm(x) < getm(y);
    return getd(x) < getd(y);
}
int cnt[] = {0,31,-1,31,30,31,30,31,31,30,31,30,31};
inline int calc(int y,int m){
    if (cnt[m] > 0) return cnt[m];
    //2nd month
    if (y%400==0 || (y%100!=0&&y%4==0)) return 29;
    return 28;
}
int Fa[10000],Ma[10000];
int date,x;
inline void solve(){
    int isM = 0,ans = 99999999;
    cin >> date; date *= 100; cin >> x; date += x,date *= 100; cin >> x; date += x;
    for (int i = 2101; i >= 2000; --i){
        if (cmp(Fa[i],ans) && cmp(date,Fa[i])) isM = 0,ans = Fa[i];
        if (cmp(Ma[i],ans) && cmp(date,Ma[i])) isM = 1,ans = Ma[i];
    }
    print(isM,ans);
}
inline void init(){
    Fa[2000] = 20000618;
    Ma[2000] = 20000514;
    int s,now,i,y,m,d,k;
    y = 2000,m = 6,d = 18;
    for (now = 0,i = 2001; i <= 2101; ++i){
        s = 30 - d;
        d += s,now = (now+s)%7;
        while (m < 12){
            ++m;
            s = calc(y,m);
            now = (now+s)%7;
            d = calc(y,m);
        }
        //xxxx.12.31
        ++y,m=1,d=31,now=(now+31)%7;
        //xxxx_.1.31
        while (m < 5){
            ++m;
            s = calc(y,m);
            now = (now+s)%7;
            d = calc(y,m);
        }
        //xxxx.5.30
        ++m,d=1,now = (now+1)%7;
        //xxxx.6.1
        k = 3;
        while (k){
            if (now==0){ --k; if (!k) break; }
            ++d,now = (now+1)%7;
        }
        Fa[i] = y*10000+m*100+d;
    }
    y = 2000,m = 5,d = 14;
    for (now = 0,i = 2001; i <= 2100; ++i){
        s = 31 - d;
        d += s,now = (now+s)%7;
        while (m < 12){
            ++m;
            s = calc(y,m);
            now = (now+s)%7;
            d = calc(y,m);
        }
        //xxxx.12.31
        ++y,m=1,d=31,now=(now+31)%7;
        //xxxx_.1.31
        while (m < 4){
            ++m;
            s = calc(y,m);
            now = (now+s)%7;
            d = calc(y,m);
        }
        //xxxx.4.31
        ++m,d=1,now = (now+1)%7;
        //xxxx.5.1
        k = 2;
        while (k){
            if (now==0){ --k; if (!k) break; }
            ++d,now = (now+1)%7;
        }
        Ma[i] = y*10000+m*100+d;
    }
}
int main(){
    init();
    int T; cin >> T;
    while (T--) solve();
    return 0;
}