2013-team2
从 Trac 迁移的文章
这是从旧校内 Wiki 迁移的文章,可能存在一些样式问题,您可以向 memset0 反馈。
原文章内容如下:
多Case的题注意清0
{{{
#include <iostream>
#include <cstdio>
#include <vector>
using namespace std;
long long x[300000], y[300000], sumx[300000], sumy[300000];
bool check(int i, int j, int k)
{
return ((x[k] - x[i]) * (y[j] - y[i]) - (y[k] - y[i]) * (x[j] - x[i])) < 0;
}
long long calc(int i, int j)
{
return sumx[j] * y[i] - sumy[j] * x[i];
}
int b[400000];
long long f[300000], g[300000];
int main()
{
int n, i, w, tmp, j, k;
vector<int> ans;
while (cin >> n) {
if (n == 0) break;
for (i = 1; i <= n; i ++) {
scanf("%d%d", &j, &k);
x[i] = k; y[i] = j;
}
sumx[n + 1] = sumy[n + 1] = 0;
for (i = n; i >= 1; i --) {
sumx[i] = sumx[i + 1] + x[i];
sumy[i] = sumy[i + 1] + y[i];
}
w = 0; tmp = 1;
for (i = 1; i <= n - 1; i ++) {
while (w > 1 && check(b[w - 1], b[w], i)) w --;
b[++w] = i;
if (tmp > w) tmp = w;
while (tmp < w && calc(b[tmp + 1], i + 1) > calc(b[tmp], i + 1)) tmp ++;
while (tmp > 1 && calc(b[tmp - 1], i + 1) > calc(b[tmp], i + 1)) tmp --;
f[i] = calc(b[tmp], i + 1);
}
w = 0; tmp = 1;
for (i = n; i > 1; i --) {
while (w > 1 && check(b[w - 1], b[w], i)) w --;
b[++w] = i;
if (tmp > w) tmp = w;
while (tmp < w && calc(b[tmp + 1], i) < calc(b[tmp], i)) tmp ++;
while (tmp > 1 && calc(b[tmp - 1], i) < calc(b[tmp], i)) tmp --;
g[i] = calc(b[tmp], i);
}
ans.clear();
for (i = 1; i <= n - 1; i ++)
if (g[i + 1] < f[i]) ans.push_back(i);
printf("%d\n", ans.size());
for (i = 0; i < ans.size(); i ++)
printf("%d\n", ans[i]);
}
return 0;
}
}}}
{{{
#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;
int mo = 1000000007;
int tims[110000], sum[110000], sum1[110000];
char a[110000], b[110000];
int ansi, n;
bool ansf;
int work(int i, bool flag)
{
int ret;
// cout << i << " " << flag << endl;
if (a[i] != '?' && b[i] != '?' && a[i] == b[i]) return 0;
if (a[i] == '?' && b[i] == '?') {ansi = i; ansf = flag; return tims[sum[i - 1]]; }
else {
if (a[i] == '1' || b[i] == '0') flag = !flag;
if (sum[i - 1] > 0) { ansi = i; ansf = flag; return tims[sum[i - 1] - 1]; }
else if ((sum1[i - 1] & 1) == flag) { ansi = i; ansf = flag; return 1; }
}
return 0;
}
bool print()
{
bool flag = ansf;
int tt, i;
a[ansi + 1] = '1';
for (i = ansi + 2; i < n; i ++) a[i] = '0';
if (a[i] == '1' || b[i] == '0') flag = !flag;
tt = 0;
if (sum1[ansi - 1] != flag) tt = 1;
if (tt && sum[ansi - 1] == 0) return 0;
for (i = 0; i < ansi; i ++)
if (a[i] == '?' && b[i] == '?') { a[i] = tt; if (tt) tt --; }
else if (a[i] == '?') a[i] = b[i];
for (i = 0; i < n; i ++) printf("%c", a[i]);
cout << endl;
for (i = 0; i < n; i ++)
if (i != ansi) printf("%c", a[i]);
else if (a[i] == '1') printf("0");
else printf("1");
printf("\n");
return 1;
}
int main()
{
int tt, i, l, n1, tmp, cas = 0;
long long ans;
tims[0] = 1;
for (i = 1; i <= 110000; i ++) tims[i] = 2 * tims[i - 1] % mo;
cin >> tt;
while (tt --) {
scanf("%s", a);
scanf("%s", b);
printf("Case #%d:\n", ++cas);
n = strlen(a);
sum[0] = 0; n1 = 0; sum1[0] = 0;
for (i = 0; i < n; i ++) {
if (i > 0) sum[i] = sum[i - 1];
if (i > 0) sum1[i] = sum1[i - 1];
if (a[i] == '?' && b[i] == '?') sum[i] ++;
else if (a[i] == '?') sum1[i] += b[i] == '1';
else if (b[i] == '?') sum1[i] += a[i] == '1';
else if (a[i] != b[i]) { n1 ++; l = i; }
else sum1[i] += a[i] == '1';
// cout << "#" << sum[i] << " " << sum1[i] << endl;
}
ans = 0; //cout << l << endl;
if (n1 > 1) { printf("Impossible\n"); continue; }
if (n1 == 1) {
if (l < n - 1) {
if (a[l + 1] == '?' && b[l + 1] == '?') tmp = 0;
else {
if (a[l + 1] == '0' || b[l + 1] == '0') { printf("Impossible\n"); continue; }
tmp = 1;
}
for (i = l + 2; i < n; i ++) if (sum1[i] != sum1[l] + tmp) break;
if (i != n) { printf("Impossible\n"); continue; }
}
//if (i != n) { printf("Impossible\n"); continue; }
if (l == n - 1) ans += work(n - 1, 0);
else ans += work(l, 0);
}
else {
if (a[n - 1] == '?' || b[n - 1] == '?') ans += work(n - 1, 0);
//cout <<n - 1 << " " << ans << endl;
for (i = n - 1; i > 0; i--) {
if (sum[i] != sum[n - 1]) break;
else if (a[i] == '?' && b[i] == '?' || sum[i] - sum[i - 1] == 1) ans += work(i - 1, 0);
// cout << i << " " << ans << endl;
}
}
ans %= mo;
if (ans != 1) cout <<"Ambiguous " << ans << endl;
else {
if (a[ansi] == '?' && b[ansi] == '?') {
a[ansi] = '0'; if (print()) continue;
a[ansi] = '1'; print();
}
else print();
}
}
return 0;
}
}}}
多Case的题注意清0
#include <iostream>
#include <cstdio>
#include <vector>
using namespace std;
long long x[300000], y[300000], sumx[300000], sumy[300000];
bool check(int i, int j, int k)
{
return ((x[k] - x[i]) * (y[j] - y[i]) - (y[k] - y[i]) * (x[j] - x[i])) < 0;
}
long long calc(int i, int j)
{
return sumx[j] * y[i] - sumy[j] * x[i];
}
int b[400000];
long long f[300000], g[300000];
int main()
{
int n, i, w, tmp, j, k;
vector<int> ans;
while (cin >> n) {
if (n == 0) break;
for (i = 1; i <= n; i ++) {
scanf("%d%d", &j, &k);
x[i] = k; y[i] = j;
}
sumx[n + 1] = sumy[n + 1] = 0;
for (i = n; i >= 1; i --) {
sumx[i] = sumx[i + 1] + x[i];
sumy[i] = sumy[i + 1] + y[i];
}
w = 0; tmp = 1;
for (i = 1; i <= n - 1; i ++) {
while (w > 1 && check(b[w - 1], b[w], i)) w --;
b[++w] = i;
if (tmp > w) tmp = w;
while (tmp < w && calc(b[tmp + 1], i + 1) > calc(b[tmp], i + 1)) tmp ++;
while (tmp > 1 && calc(b[tmp - 1], i + 1) > calc(b[tmp], i + 1)) tmp --;
f[i] = calc(b[tmp], i + 1);
}
w = 0; tmp = 1;
for (i = n; i > 1; i --) {
while (w > 1 && check(b[w - 1], b[w], i)) w --;
b[++w] = i;
if (tmp > w) tmp = w;
while (tmp < w && calc(b[tmp + 1], i) < calc(b[tmp], i)) tmp ++;
while (tmp > 1 && calc(b[tmp - 1], i) < calc(b[tmp], i)) tmp --;
g[i] = calc(b[tmp], i);
}
ans.clear();
for (i = 1; i <= n - 1; i ++)
if (g[i + 1] < f[i]) ans.push_back(i);
printf("%d\n", ans.size());
for (i = 0; i < ans.size(); i ++)
printf("%d\n", ans[i]);
}
return 0;
}
#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;
int mo = 1000000007;
int tims[110000], sum[110000], sum1[110000];
char a[110000], b[110000];
int ansi, n;
bool ansf;
int work(int i, bool flag)
{
int ret;
// cout << i << " " << flag << endl;
if (a[i] != '?' && b[i] != '?' && a[i] == b[i]) return 0;
if (a[i] == '?' && b[i] == '?') {ansi = i; ansf = flag; return tims[sum[i - 1]]; }
else {
if (a[i] == '1' || b[i] == '0') flag = !flag;
if (sum[i - 1] > 0) { ansi = i; ansf = flag; return tims[sum[i - 1] - 1]; }
else if ((sum1[i - 1] & 1) == flag) { ansi = i; ansf = flag; return 1; }
}
return 0;
}
bool print()
{
bool flag = ansf;
int tt, i;
a[ansi + 1] = '1';
for (i = ansi + 2; i < n; i ++) a[i] = '0';
if (a[i] == '1' || b[i] == '0') flag = !flag;
tt = 0;
if (sum1[ansi - 1] != flag) tt = 1;
if (tt && sum[ansi - 1] == 0) return 0;
for (i = 0; i < ansi; i ++)
if (a[i] == '?' && b[i] == '?') { a[i] = tt; if (tt) tt --; }
else if (a[i] == '?') a[i] = b[i];
for (i = 0; i < n; i ++) printf("%c", a[i]);
cout << endl;
for (i = 0; i < n; i ++)
if (i != ansi) printf("%c", a[i]);
else if (a[i] == '1') printf("0");
else printf("1");
printf("\n");
return 1;
}
int main()
{
int tt, i, l, n1, tmp, cas = 0;
long long ans;
tims[0] = 1;
for (i = 1; i <= 110000; i ++) tims[i] = 2 * tims[i - 1] % mo;
cin >> tt;
while (tt --) {
scanf("%s", a);
scanf("%s", b);
printf("Case #%d:\n", ++cas);
n = strlen(a);
sum[0] = 0; n1 = 0; sum1[0] = 0;
for (i = 0; i < n; i ++) {
if (i > 0) sum[i] = sum[i - 1];
if (i > 0) sum1[i] = sum1[i - 1];
if (a[i] == '?' && b[i] == '?') sum[i] ++;
else if (a[i] == '?') sum1[i] += b[i] == '1';
else if (b[i] == '?') sum1[i] += a[i] == '1';
else if (a[i] != b[i]) { n1 ++; l = i; }
else sum1[i] += a[i] == '1';
// cout << "#" << sum[i] << " " << sum1[i] << endl;
}
ans = 0; //cout << l << endl;
if (n1 > 1) { printf("Impossible\n"); continue; }
if (n1 == 1) {
if (l < n - 1) {
if (a[l + 1] == '?' && b[l + 1] == '?') tmp = 0;
else {
if (a[l + 1] == '0' || b[l + 1] == '0') { printf("Impossible\n"); continue; }
tmp = 1;
}
for (i = l + 2; i < n; i ++) if (sum1[i] != sum1[l] + tmp) break;
if (i != n) { printf("Impossible\n"); continue; }
}
//if (i != n) { printf("Impossible\n"); continue; }
if (l == n - 1) ans += work(n - 1, 0);
else ans += work(l, 0);
}
else {
if (a[n - 1] == '?' || b[n - 1] == '?') ans += work(n - 1, 0);
//cout <<n - 1 << " " << ans << endl;
for (i = n - 1; i > 0; i--) {
if (sum[i] != sum[n - 1]) break;
else if (a[i] == '?' && b[i] == '?' || sum[i] - sum[i - 1] == 1) ans += work(i - 1, 0);
// cout << i << " " << ans << endl;
}
}
ans %= mo;
if (ans != 1) cout <<"Ambiguous " << ans << endl;
else {
if (a[ansi] == '?' && b[ansi] == '?') {
a[ansi] = '0'; if (print()) continue;
a[ansi] = '1'; print();
}
else print();
}
}
return 0;
}