2020年6月8日 星期一

a468: 12439 - February 29 解題心得

題目來源: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;

}



}

沒有留言:

張貼留言

o079. 4. 最佳選擇

 題目描述: 給一個長度為 n 的正整數序列 a1,a2...an ,你可以執行多次操作 (包含 0 次),每次操作只能選擇這個序列的第一個或最後一個數字,再將這個數字從序列中刪除並自己搜集起來。 求滿足總和不超過 k 且搜集的數字奇數和偶數個數相同的條件下,所能搜集的數字總和最...