F 日期小助手
题目描述
作为一个关心父母的孩子,Compute 会在每年的母亲节和父亲节为父母准备礼物。可是粗心的他却不记得它们的具体日期了。
已知:母亲节在每年 5 月的第 2 个周日;父亲节在每年 6 月的第 3 个周日。
现在你需要告诉他,下一个(不包括当天)母亲节或父亲节是在什么时候。
输入描述:
第一行包含一个整数
T
(
T
≤
100
)
T (T \leq 100)
T(T≤100),表示测试数据的组数。
对于每组数据,包含三个整数 y, m, d,中间以空格分隔,分别表示今天的年、月、日。
输入保证是一个在公元 2000 年 1 月 1 日 到 2100 年 12 月 31 日间的合法日期。
输出描述:
对于每组数据,在一行输出下一个需要准备礼物的节日和日期。格式参考样例输出。
输入
7
2000 1 1
2001 1 1
2002 1 1
2003 1 1
2020 1 1
2020 5 10
2020 6 21
输出
Mother's Day: May 14th, 2000
Mother's Day: May 13th, 2001
Mother's Day: May 12th, 2002
Mother's Day: May 11th, 2003
Mother's Day: May 10th, 2020
Father's Day: June 21st, 2020
Mother's Day: May 9th, 2021
备注:
注意在冒号和逗号后面有一个空格。
思路:
从2000年到2100年底,还要加上2102年一年,一共
365
×
102
=
37230
365 \times 102 = 37230
365×102=37230 天左右,
T
=
100
T=100
T=100 ,总的时间复杂度也才
O
(
3723000
)
O(3723000)
O(3723000),所以我们可以对每个日期暴力一遍。
Code:
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
const int N = 40005;
int months[13] = {0, 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
string s[10] = {"", "st", "nd", "rd"};
string deal(int x)
{
int m = x % 10;
if (x == 11 || x == 12 || x == 13)
return "th";
if (m == 1 || m == 2 || m == 3)
return s[m];
return "th";
}
struct node
{
int Y, M, D, W;
} a[N];
bool judge_run(int Year)
{
if (Year % 400 == 0 || (Year % 4 == 0 && Year % 100 != 0))
return true;
else
return false;
}
int main()
{
#ifdef LOCAL_LIUZHIHAN
freopen("in.in", "r", stdin);
// freopen("out.out", "w", stdout);
#endif
int i, yy = 2000, mm = 1, dd = 1, ww = 6;
for (i = 1; i < N; i++) //从 2000.1.1 开始往后预处理 40000 天,记下每天的 年 月 日 星期
{
a[i].Y = yy;
a[i].M = mm;
a[i].D = dd;
a[i].W = ww;
ww = ww % 7 + 1;
dd++;
if (dd == months[mm] + 1)
{
dd = 1;
mm++;
if (mm == 13)
{
mm = 1;
yy++;
if (judge_run(yy))
{
months[2] = 29;
}
else
{
months[2] = 28;
}
}
}
}
int T, y, m, d;
cin >> T;
while (T--)
{
cin >> y >> m >> d;
int r5 = 0, r6 = 0;
bool f = false;
int c5 = 0, c6 = 0;
for (i = 1; i < N; i++)
{
if (a[i].M == 5 && a[i].W == 7)
{
c5++;
if (c5 == 2) //这是五月的第 2 个星期天
{
if (f) //并且在给出的日期之后
{
r5 = i;
break;
}
}
}
if (a[i].M == 6 && a[i].W == 7)
{
c6++;
if (c6 == 3) //这是六月的第 3 个星期天
{
if (f) //并且在给出的日期之后
{
r6 = i;
break;
}
}
}
if (a[i].M == 6) //出了五月,到下一年去,要置 0
c5 = 0;
if (a[i].M == 7) //同上
c6 = 0;
if (!f && y == a[i].Y && m == a[i].M && d == a[i].D) //如果找到这一天了,f=true
{
// cout << "riqi:" << a[i].Y << " " << a[i].M << " " << a[i].D << " " << a[i].W << endl;
f = true;
}
}
if (r5)
{
cout << "Mother's Day: May " << a[r5].D << deal(a[r5].D) << ", " << a[r5].Y << endl;
}
if (r6)
{
cout << "Father's Day: June " << a[r6].D << deal(a[r6].D) << ", " << a[r6].Y << endl;
}
}
return 0;
}