QOJ.ac

QOJ

IDProblemSubmitterResultTimeMemoryLanguageFile sizeSubmit timeJudge time
#48101#4654. TreeUESTC_Guest_WiFiAC ✓2513ms8584kbC++176.9kb2022-09-11 16:40:002022-09-11 16:40:02

Judging History

你现在查看的是最新测评结果

  • [2023-08-10 23:21:45]
  • System Update: QOJ starts to keep a history of the judgings of all the submissions.
  • [2022-09-11 16:40:02]
  • 评测
  • 测评结果:AC
  • 用时:2513ms
  • 内存:8584kb
  • [2022-09-11 16:40:00]
  • 提交

answer

#include <bits/stdc++.h>

#define ll long long
#define ls id << 1
#define rs id << 1 | 1
#define mem(array, value, size) memset(array, value, ((size) + 5) * sizeof(decltype(array[0])))
#define memarray(array, value) memset(array, value, sizeof(array))
#define fillarray(array, value, begin, end) fill((array) + (begin), (array) + (end) + 1, value)
#define fillvector(v, value) fill((v).begin(), (v).end(), value)
#define pb(x) push_back(x)
#define st(x) (1LL << (x))
#define pii pair<int, int>
#define pll pair<ll,ll>
#define pil pair<int,ll>
#define pli pair<ll,int>
#define mp(a, b) make_pair((a), (b))
#define Flush fflush(stdout)
#define vecfirst (*vec.begin())
#define veclast (*vec.rbegin())
#define vecall(v) (v).begin(), (v).end()
#define vecupsort(v) (sort((v).begin(), (v).end()))
#define vecdownsort(v) (sort(vecall(v), greater<decltype(v.back())>()))
#define veccmpsort(v, cmp) (sort(vecall(v), cmp))
#define vecunique(v) ((v).resize(unique(vecall(v))-(v).begin())
using namespace std;
using db = long double;
const int N = 1000050;
const int inf = 0x3f3f3f3f;
const ll llinf = 0x3f3f3f3f3f3f3f3f;
const int mod = 1e9 + 7;
const int MOD = 1e9 + 7;
const db PI = acos(-1.0L);
#define MULTIPLE_CASE
#define CLOSE_IOS

int ksm(long long a, long long b) {
    long long ret = 1;
    while (b) {
        if (b & 1) ret = ret * a % mod;
        a = a * a % mod;
        b >>= 1;
    }
    return ret;
}

int inv(int a) { return ksm(a, mod - 2); }

int add(int a, int b) { return (a + b) >= mod ? a + b - mod : a + b; }

int sub(int a, int b) { return (a - b) < 0 ? a - b + mod : a - b; }

int mul(long long a, long long b) { return add(a * b % mod, mod); }

const int MAXN = 505;
int id[MAXN];

//Guass消元
int Guass(int a[][MAXN], int l[], int ans[], int n) {//l, ans储存解, l[]表示是否是自由元
    int res = 0, r = 0;
    for (int i = 0; i < n; i++) l[i] = false, id[i] = i;
    for (int i = 0; i < n; i++) {
        for (int j = r; j < n; j++)
            if (a[j][i]) {
                for (int k = i; k <= n; k++)
                    swap(a[j][k], a[r][k]);
//                swap(id[i], id[j]);
                break;
            }
        if (a[r][i] == 0) {
            ++res;
            continue;
        }
        for (int j = 0; j < n; j++)
            if (j != r && a[j][i]) {
                int tmp = mul(a[j][i], inv(a[r][i]));
                for (int k = i; k <= n; k++)
                    a[j][k] = sub(a[j][k], mul(tmp, a[r][k]));
            }
        l[i] = true;
        ++r;
    }
    for (int i = 0; i < n; i++)
        if (l[i])
            for (int j = 0; j < n; j++)
                if (a[j][i])
                    ans[i] = mul(a[j][n], inv(a[j][i]));
    return res;//返回解空间的维数
}


const int M = 505;
int n, m;
int L[M][M], L2[M][M], L3[M][M], ans[M], LL[M][M], LT[M][M];
int x[M], y[M];

//#define DEBUG

void print(const int A[M][M], int size, const string &name = "") {
#ifdef DEBUG
    if (!name.empty()) cerr << name << endl;
    for (int i = 0; i < size; ++i, cerr << endl)
        for (int j = 0; j <= size; ++j)cerr << setw(10) << A[i][j] << " ";
    cerr << endl;
#endif
}

void print(const int A[M], int size, const string &name = "") {
#ifdef DEBUG
    if (!name.empty()) cerr << name << endl;
    for (int i = 0; i < size; ++i)
        cerr << setw(10) << A[i] << " ";
    cerr << endl << endl;
#endif
}

void copy_mat(int to[M][M], const int from[M][M], int size) {
    for (int i = 0; i <= size; ++i)for (int j = 0; j <= size; ++j)to[i][j] = from[i][j];
}

inline void solve() {
    cin >> n >> m;
    for (int i = 0; i <= n; i++)for (int j = 0; j <= n; ++j)L[i][j] = L2[i][j] = L3[i][j] = 0;
    for (int i = 1; i <= m; ++i) {
        int u, v;
        cin >> u >> v;
        u--, v--;
        L[v][v] = add(L[v][v], 1);
        L[u][v] = sub(L[u][v], 1);
    }
    int flag = 0;
    int idx = 0;
    int idy = 0;
    for (int i = 0; i < n; i++) {
        if (L[i][i] == 0) {
            flag = 1, idx = idy = i;
            break;
        }
    }
    print(L, n, "L");

    copy_mat(LL, L, n);
    int l[M] = {0};
    int rank = n - Guass(LL, l, ans, n);

    print(LL, n, "LL");

    if (rank < n - 1) {
        for (int i = 1; i <= n; ++i)cout << 0 << " \n"[i == n];
        return;
    }

    // solve vertical vectors
    print(l, n, "l_y_before");
    if (!flag)
        for (int i = 0; i < n; ++i) {
            if (!l[i]) {
                idx = id[i];
                break;
            }
        }
    for (int i = 0, i2 = 0; i < n - 1; ++i) {
        for (int j = 0, j2 = 0; j < n; j++) {
            if (j == idx) {
                L2[i2][n - 1] = sub(0, L[i][j]);
                continue;
            }
            L2[i2][j2] = L[i][j], j2++;
        }
        i2++;
    }
    print(L2, n - 1, "L2_x_before");
    fill(l, l + n, false);
    Guass(L2, l, x, n - 1);

    print(L2, n - 1, "L2_x");

    // solve horizon vectors
    for (int i = 0; i < n; i++)
        for (int j = 0; j < n; j++)
            L2[i][j] = L[j][i];
    copy_mat(LT, L2, n);
    fill(l, l + n, false);
    Guass(L2, l, ans, n);

    print(L2, n - 1, "L2_H");
    if (!flag)
        for (int i = 0; i < n; ++i) {
            if (!l[i]) {
                idy = id[i];
                break;
            }
        }
    for (int i = 0, i2 = 0; i < n - 1; ++i) {
        for (int j = 0, j2 = 0; j < n; j++) {
            if (j == idy) {
                L3[i2][n - 1] = sub(0, LT[i][j]);
                continue;
            }
            L3[i2][j2] = LT[i][j], j2++;
        }
        i2++;
    }
    fill(l, l + n, false);
    Guass(L3, l, y, n - 1);

    print(L3, n - 1, "L3_y");

    // solve
    for (int i = 0, i2 = 0; i < n; ++i) {
        if (i == idx) continue;
        for (int j = 0, j2 = 0; j < n; j++) {
            if (j == idy) {
                continue;
            }
            LL[i2][j2] = L[i][j], j2++;
        }
        i2++;
    }
    print(LL, n - 1, "LL_ANS");
    Guass(LL, l, ans, n - 1);
    int ori_det = 1;
    for (int i = 0; i < n - 1; i++)
        ori_det = mul(ori_det, LL[i][i]);
    ori_det = mul(ori_det, (idx + idy) % 2 ? mod - 1 : 1);

    cerr << "idx: " << idx << ", idy: " << idy << " ori_det: " << ori_det << endl;
    print(x, n - 1, "x");
    print(y, n - 1, "y");
    cerr << "print ans" << endl;
    for (int i = 0; i < n; i++) {
        int res = mul(i == idx ? 1 : x[i - (i > idx)], i == idy ? 1 : y[i - (i > idy)]);
        res = mul(res, ori_det);
        cout << res << " \n"[i + 1 == n];
    }
}

int main() {
    int Test = 1;
#ifdef MULTIPLE_CASE
#ifdef CLOSE_IOS
    ios::sync_with_stdio(false), cin.tie(nullptr), cout.tie(nullptr);
    cin >> Test;
#else
    scanf("%d", &Test);
#endif
#endif
    while (Test--) {
        solve();
        // if (Test)
        //     putchar('\n');
    }
    return 0;
}

Details

Tip: Click on the bar to expand more detailed information

Test #1:

score: 100
Accepted
time: 2513ms
memory: 8584kb

input:

100
7 12
1 3
2 1
1 4
5 1
4 7
6 5
2 3
4 6
3 1
6 4
7 1
1 2
2 2
2 1
1 2
50 49
49 29
41 33
41 48
27 46
41 36
9 1
41 7
17 12
23 10
8 15
32 6
21 45
18 40
49 21
41 17
41 8
2 35
17 16
38 31
13 5
32 20
36 3
25 18
29 47
29 37
15 23
11 13
29 9
47 44
29 39
41 27
25 28
36 25
19 42
27 38
45 34
15 19
14 24
11 43
1...

output:

2 3 1 4 2 6 2
1 1
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0
1
1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
1 0
850518977 850518977 850518977 850518977 850518977 850518977 850518977 850518...

result:

ok 100 lines