1. 程式人生 > >codeforces 734F (數學)

codeforces 734F (數學)

題意:給出兩個陣列b,c,構造a陣列滿足條件.

首先需要知道一個推論:aANDb+aORb=a+b,這個按位比較很顯然是相等的. 然後把原式的bici加起來就得到了:
b.1+c1=na1+ab2+c2=na2+abn+cn=nan+a
這麼一個n元1次方程解出來也很容易,然後就是帶入按位check, 按照ai在當前位的奇偶性討論即可.

#include <cstdio>
#include <iostream>
#include <cstring>
#include <queue>
#include <cmath>
#include <algorithm> #include <stack> #define Clear(x,y) memset (x,y,sizeof(x)) #define Close() ios::sync_with_stdio(0) #define Open() freopen ("more.in", "r", stdin) #define fi first #define se second #define pii pair<int, int> #define pli pair<long long, int> #define pb push_back
#define mod 1000000007 template <class T> inline bool scan (T &ret) { char c; int sgn; if (c = getchar(), c == EOF) return 0; //EOF while (c != '-' && (c < '0' || c > '9') ) c = getchar(); sgn = (c == '-') ? -1 : 1; ret = (c == '-') ? 0 : (c - '0'); while (c = getchar(), c >= '0'
&& c <= '9') ret = ret * 10 + (c - '0'); ret *= sgn; return 1; } using namespace std; #define maxn 200005 long long b[maxn], c[maxn], f[maxn], a[maxn], ans[maxn]; int n; int main () { //Open (); Close (); cin >> n; for (int i = 1; i <= n; i++) cin >> b[i]; long long sum = 0; for (int i = 1; i <= n; i++) { cin >> c[i]; f[i] = b[i]+c[i]; sum += f[i]; } a[1] = (f[1]*2*n-sum); if (a[1]%(1LL*2*n*n) != 0) { cout << "-1" << endl; return 0; } a[1] /= (1LL*2*n*n); ans[1] = a[1]; if (a[1] < 0) { cout << -1 << endl; return 0; } for (int i = 2; i <= n; i++) { if ((f[i]-f[1])%n != 0) { cout << -1 << endl; return 0; } a[i] = a[1]+(f[i]-f[1])/n; if (a[i] < 0) { cout << -1 << endl; return 0; } ans[i] = a[i]; } for (int bit = 1; bit <= 33; bit++) { int num = 0; for (int i = 1; i <= n; i++) { num += (a[i]&1); } for (int i = 1; i <= n; i++) { if (a[i]&1) b[i] -= num, c[i] -= n; else c[i] -= num; if ((b[i]&1) || (c[i]&1)) { cout << -1 << endl; return 0; } b[i] >>= 1; c[i] >>= 1; } for (int i = 1; i <= n; i++) a[i] >>= 1; } for (int i = 1; i <= n; i++) cout << ans[i] << " "; cout <<endl; return 0; }