POJ_2947

    将M条信息翻译成同余方程组后用高斯消元求解就可以了。

#include<stdio.h>
#include<string.h>
#include<iostream>
#define MAXD 310
using namespace std;
int N, M, mat[MAXD][MAXD], ans[MAXD], h[MAXD];
char a[5], b[5], day[][5] = {"MON", "TUE", "WED", "THU", "FRI", "SAT", "SUN"};
int getday(char *b)
{
    int i;
    for(i = 0; i < 7; i ++)
        if(strcmp(b, day[i]) == 0)
            break;
    return i;
}
void init()
{
    int i, j, k, n;
    for(i = 0; i < M; i ++)
    {
        scanf("%d", &n);
        scanf("%s%s", a, b);
        mat[i][N] = (getday(b) - getday(a) + 8) % 7;
        memset(h, 0, sizeof(h));
        for(j = 0; j < n; j ++)
        {
            scanf("%d", &k);
            ++ h[k - 1];
        }
        for(j = 0; j < N; j ++)
            mat[i][j] = h[j] % 7;
    }
}
int gauss()
{
    int i, j, k, x, y, a, b;
    for(i = j = 0; i < M && j < N; i ++, j ++)
    {
        if(mat[i][j] == 0)
        {
            for(k = i + 1; k < M; k ++)
                if(mat[k][j])
                    break;
            if(k == M)
            {
                -- i;
                continue;
            }
            for(y = j; y <= N; y ++)
                swap(mat[i][y], mat[k][y]);
        }
        for(x = i + 1; x < M; x ++)
            if(mat[x][j])
            {
                a = mat[i][j], b = mat[x][j];
                for(y = j; y <= N; y ++)
                    mat[x][y] = ((mat[x][y] * a - mat[i][y] * b) % 7 + 7) % 7;
            }
    }
    for(k = i; k < M; k ++)
        if(mat[k][N])
            return -1;
    if(i < N)
        return -2;
    for(i = N - 1; i >= 0; i --)
    {
        b = mat[i][N];
        for(j = i + 1; j < N; j ++)
            b -= mat[i][j] * ans[j];
        b = (b % 7 + 7) % 7;
        for(a = 3; a <= 9; a ++)
            if(((a * mat[i][i] % 7 + 7) % 7) == b)
                break;
        ans[i] = a;
    }
    return 0;
}
void solve()
{
    int i, k = gauss();
    if(k == -2)
        printf("Multiple solutions.\n");
    else if(k == -1)
        printf("Inconsistent data.\n");
    else
    {
        printf("%d", ans[0]);
        for(i = 1; i < N; i ++)
            printf(" %d", ans[i]);
        printf("\n");
    }
}
int main()
{
    for(;;)
    {
        scanf("%d%d", &N, &M);
        if(!N && !M)
            break;
        init();
        solve();
    }
    return 0;
}
posted on 2012-05-11 23:08  Staginner  阅读(241)  评论(0编辑  收藏  举报