蔡勒公式

w=(y+[\frac{y}{4}]+[\frac{c}{4}]-2c+[\frac{26\times (m+1)}{10}]+d-1)mod7

w:指星期,對7取模,0 -> 星期一   1 -> 星期二   2 -> 星期三  3 -> 星期四  4 -> 星期五  5 -> 星期六  6 -> 星期日

c:指世紀  

y:指年份  一般情況下取後兩位,y % 100

m:指月份

d:指日

[] 代指取整,只取整數部分

蔡勒公式只適用於1582年10月15日之後的情形

蔡勒公式的模板:

int col(int year, int mon, int day){
    if(mon == 1 || mon == 2) year--, mon += 12;
    int c = year / 100;
    int y = year - c*100;
    int w = y + y/4 + c/4 - 2*c + 26*(mon+1)/10 + day - 1;
    while(w < 0) w += 7;
    return w % 7;
}

 

例題:2019牛客多校第六場Is Today Friday

題意:每組測試樣例給出n個長度爲10的字符串,該字符串由A~J的字母組成,讓你求是否有一組數字串可以使得字母字符串滿足星期五。

代碼:

#include<bits/stdc++.h>

using namespace std;
const int maxn = 1e5+5;

int n;
int a[15], v[15];
string s[maxn];
map<string, int>vis;
set<string>cun;

int mm[] = {0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};

bool pan(int x){
    if((x % 400 == 0) || (x % 4 == 0 && x % 100)) return true;
    else return false;
}

int col(int year, int mon, int day){
    if(mon == 1 || mon == 2) year--, mon += 12;
    int c = year / 100;
    int y = year - c*100;
    int w = y + y/4 + c/4 - 2*c + 26*(mon+1)/10 + day - 1;
    while(w < 0) w += 7;
    return w % 7;
}

bool check(int x[]){
    set<string>::iterator it;
    for(it = cun.begin(); it != cun.end(); it++){
        int y = x[(*it)[0] - 'A'] * 1000 + x[(*it)[1] - 'A'] * 100 + x[(*it)[2] - 'A'] * 10 + x[(*it)[3] - 'A'];
        int m = x[(*it)[5] - 'A'] * 10 + x[(*it)[6] - 'A'];
        int d = x[(*it)[8] - 'A'] * 10 + x[(*it)[9] - 'A'];

        if(y < 1600 || y > 9999) return false;
        if(m < 1 || m > 12) return false;

        int tmpm = mm[m];
        if(m == 2 && pan(y)) tmpm = 29;
        if(d < 1 || d > tmpm) return false;

        int w = col(y, m, d);
        if(w != 5) return false;
    }
    return true;
}

int main()
{
    int T;
    cin >> T;
    for(int cas = 1; cas <= T; cas++){
        cun.clear();
        cin >> n;
        for(int i = 1; i <= n; i++) cin >> s[i], cun.insert(s[i]);
        for(int i = 0; i < 10; i++) a[i] = i;

        cout << "Case #" << cas << ": ";
        int flag = 0;
        do{
            if(check(a)){
                flag = 1;
                for(int i = 0; i < 10; i++) cout << a[i];
                cout << endl;
                break;
            }
        } while(next_permutation(a, a+10));

        if(!flag){
            cout << "Impossible" << endl;
        }
    }
}



 

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章