題目來源:https://zerojudge.tw/ShowProblem?problemid=a468
這題也是2012年大學程式檢定CPE的考題。
今年 2012 年,閏年。所以今年有「二月29日」,這天稱為「閏日」。有趣的是,今年二月29日出生的嬰兒要等到下一個閏年,也就是 2016 年才過生日。閏年是每 4 年一次嗎?能被 4 整除的年份是閏年,但是能被 100 整除的年份卻不是閏年,除非它可以被 400 整除。能被 400 整除的年份則是閏年。
本題給你兩個日期,你要找出它們兩者之間有幾個「閏日」。
輸入說明
第一行有一個 T (≤ 500) 表示測資筆數。
每筆測資兩行。第一行為第一個日期,第二行則為第二個。注意,第二個日期決不會比第一個早。所給的日期格式為 - 「月 日, 年」。詳細情形請參見範例輸出。所有日期均為正確日期,年份則介於 2 * 103 和 2 * 109 之間。月份名稱及每個月的天數詳列如下以便參考。
輸出說明
對於每筆測資,印出測資編號及兩個日期之間 (含) 有幾個「閏日」。
範例輸入 #1
4
January 12, 2012
March 19, 2012
August 12, 2899
August 12, 2901
August 12, 2000
August 12, 2005
February 29, 2004
February 29, 2012
範例輸出 #1
Case 1: 1
Case 2: 0
Case 3: 1
Case 4: 3
月份的名稱為 {"January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November" 及 "December"}. 平年中每個月的天數則依序是 {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30 及 31}。閏年時,二月有 29 天,其他月份則與平年相同。
如果你乍看這題會感到不知道從何下手,我建議你習慣性的在大腦中或是紙筆上寫下流程圖。
step0.請先別管幾月幾號,請先別管幾月幾號,請先別管幾月幾號
step1.跟隨題目定義出判斷閏年的條件
if(n % 400 && (n % 4 == 0 && n % 100 != 0)) {
cout << n << "是閏年";
}
step2.根據日期調整起始與終點區間
step3.求解。一班人在這個時候會先採用FORLOOP來比對區間內的每一年是不是閏年,但這題的側資不允許你這麼做,一定會超時,所以你必須簡化流程。
小時候我們都做過數學題:10以內可以被2整除但不能被6整除的數有幾個?
1 2 3 4 5 6 7 8 9 10
先用肉眼看,恩有4個,算式怎麼列呢==>10 / 2 - 10 / 6 = 4,有感覺了嗎,下面附上此題程式碼。
#include <iostream>
#include <algorithm>
#include <string>
#include <vector>
#include <map>
using namespace std;
int main()
{
int n, y , y1;
string m , d;
cin >> n;
int testCount = 0;
while (n-- > 0) {
testCount++;
cin >> m >> d >> y;
int count = 0;
if (m != "January" && m != "February") {
y++;
}
y--;
cin >> m >> d >> y1;
if ((m == "January") || (m == "February" && d != "29,")) y1--;
count = y1 / 4 - y1 / 100 + y1 / 400 - (y / 4 - y / 100 + y / 400);
cout << "Case " << testCount << ": " << count <<endl;
}
}
沒有留言:
張貼留言