답안 #468940

# 제출 시각 아이디 문제 언어 결과 실행 시간 메모리
468940 2021-08-30T09:01:00 Z sinamhdv ZIGZAG (INOI20_zigzag) C++11
100 / 100
1313 ms 60976 KB
#include <bits/stdc++.h>
using namespace std;

typedef long long ll;
typedef pair<int, int> pii;
typedef pair<ll, ll> pll;
const int mod = 1000 * 1000 * 1000 + 7;
const int INF = 1e9 + 100;
const ll LINF = 1e18 + 100;

#pragma GCC optimize("Ofast,unroll-loops")
#pragma GCC target("avx2")

#ifdef DEBUG
#define dbg(x) cout << #x << " = " << (x) << endl << flush;
#define dbgr(s, f) { cout << #s << ": "; for (auto _ = (s); _ != (f); _++) cout << *_ << ' '; cout << endl << flush; }
#else
#define dbg(x) ;
#define dbgr(s, f) ;
#endif
#define fast_io ios::sync_with_stdio(0); cin.tie(0);
#define FOR(i, a, b) for (int i = (a); i < (b); i++)
#define all(x) (x).begin(), (x).end()
#define pb push_back
#define fr first
#define sc second
#define endl '\n'

const int MAXN = 300100;

int n, q;
int a[MAXN];

inline int getsgn(ll x, ll y)
{
	if (x == y) return 0;
	return (x < y ? 1 : 2);
}

struct ADDSEG
{
	ll seg[4 * MAXN];
	ll lz[4 * MAXN];
	bool neglz[4 * MAXN];
	inline void build(int v = 1, int l = 0, int r = n - 1)
	{
		if (l == r)
		{
			seg[v] = a[l];
			return;
		}
		int mid = (r + l) / 2;
		build(2 * v, l, mid);
		build(2 * v + 1, mid + 1, r);
		seg[v] = min(seg[2 * v], seg[2 * v + 1]);
	}

	inline void pushdown(int v)
	{
		if (neglz[v])
		{
			FOR(t, 2 * v , 2 * v + 2)
			{
				neglz[t] ^= 1;
				lz[t] *= -1;
				seg[t] *= -1;
			}
			neglz[v] = 0;
		}
		if (lz[v])
		{
			FOR(t, 2* v, 2* v + 2)
			{
				seg[t] += lz[v];
				lz[t] += lz[v];
			}
			lz[v] = 0;
		}
	}

	inline void add(int L, int R, int x, int v = 1, int l = 0, int r = n - 1)
	{
		if (l > R || r < L) return;
		if (l >= L && r <= R)
		{
			seg[v] += x;
			lz[v] += x;
			return;
		}
		int mid = (r + l) / 2;
		pushdown(v);
		add(L, R, x, 2* v, l, mid);
		add(L, R, x, 2 * v + 1, mid + 1, r);
		seg[v] = min(seg[2 * v], seg[2 * v + 1]);
	}

	inline void neg(int L, int R, int v = 1, int l = 0, int r = n - 1)
	{
		if (l > R || r < L) return;
		if (l >= L && r <= R)
		{
			seg[v] *= -1;
			lz[v] *= -1;
			neglz[v] ^= 1;
			return;
		}
		int mid = (r + l) / 2;
		pushdown(v);
		neg(L, R, 2 * v, l, mid);
		neg(L, R, 2 * v + 1, mid + 1, r);
		seg[v] = min(seg[2 * v], seg[2 * v  + 1]);
	}

	inline ll getind(int i, int v = 1, int l = 0, int r = n - 1)
	{
		if (l == r) return seg[v];
		int mid = (r + l) / 2;
		pushdown(v);
		if (i <= mid) return getind(i,2 * v, l, mid);
		else return getind(i, 2 * v + 1, mid + 1, r);
	}
} addseg;

struct node
{
	int al, ar;
	ll val;
	int pref, suf;
	bool lz;
	int len;
};

node seg[4 * MAXN];

inline void pushdown(int v)
{
	if (!seg[v].lz) return;
	FOR(t, 2 * v, 2 * v + 2)
	{
		seg[t].lz ^= 1;
		if (seg[t].al) seg[t].al = 3 - seg[t].al;
		if (seg[t].ar) seg[t].ar = 3 - seg[t].ar;
	}
	seg[v].lz = 0;
}

inline node mrg(const node &lc, const node &rc)
{
	if (lc.al == -1) return rc;
	if (rc.al == -1) return lc;
	node res = {};
	res.al = lc.al;
	res.ar = rc.ar;
	res.len = lc.len + rc.len;
	if (lc.ar && rc.al && lc.ar != rc.al)	// can join
	{
		res.val = rc.val + lc.val + (ll)lc.suf * rc.pref;
		res.pref = (lc.pref == lc.len ? rc.pref + lc.pref : lc.pref);
		res.suf = (rc.suf == rc.len ? rc.suf + lc.suf : rc.suf);
	}
	else	// no join
	{
		res.val = lc.val + rc.val;
		res.pref = lc.pref;
		res.suf = rc.suf;
	}

	return res;
}

void build(int v = 1, int l = 0, int r = n - 2)
{
	if (l == r)
	{
		int x = getsgn(a[l], a[l + 1]);
		seg[v].al = seg[v].ar = x;
		seg[v].val = seg[v].pref = seg[v].suf = (x != 0);
		seg[v].len = 1;
		// lz not set
		return;
	}
	int mid = (r + l) / 2;
	build(2 * v, l, mid);
	build(2 * v + 1, mid + 1, r);
	seg[v] = mrg(seg[2 * v], seg[2 * v + 1]);
}

inline void tgl(int L, int R, int v = 1, int l = 0, int r = n - 2)
{
	if (l > R || r < L) return;
	if (l >= L && r <= R)
	{
		seg[v].lz ^= 1;
		if (seg[v].al) seg[v].al = 3 - seg[v].al;
		if (seg[v].ar) seg[v].ar = 3 - seg[v].ar;
		return;
	}
	int mid = (r + l) / 2;
	pushdown(v);
	tgl(L, R, 2 * v, l, mid);
	tgl(L, R, 2 * v + 1, mid + 1, r);
	seg[v] = mrg(seg[2 * v], seg[2 * v+  1]);
}

inline node get(int L, int R, int v = 1, int l = 0, int r = n - 2)
{
	if (l > R || r < L) return {-1, -1, 0, 0, 0, 0, 0};
	if (l >= L && r <= R) return seg[v];
	int mid = (r + l) / 2;
	pushdown(v);
	return mrg(get(L, R, 2 * v, l, mid), get(L, R, 2 * v + 1, mid + 1, r));
}

inline void setind(int i, int v = 1, int l = 0, int r  = n - 2)
{
	if (l == r)
	{
		int x = getsgn(addseg.getind(l), addseg.getind(l + 1));
		seg[v].al = seg[v].ar = x;
		seg[v].val = seg[v].pref = seg[v].suf = (x != 0);
		// lz not set
		return;
	}
	int mid = (r + l) / 2;
	pushdown(v);
	if (i <= mid) setind(i, 2* v, l, mid);
	else setind(i, 2 * v + 1, mid + 1, r);
	seg[v] = mrg(seg[2 * v], seg[2 * v + 1]);
}

int32_t main(void)
{
//	fast_io;
	scanf("%d %d", &n, &q);

	FOR(i, 0, n) scanf("%d", a + i);

	if (n == 1)
	{
		while (q--)
		{
			char op; int l, r , x;
			scanf(" %c %d %d", &op, &l, &r);
			if (op == '+') scanf("%d", &x);
			if (op == '?') putchar('1'), putchar('\n');
		}
		return 0;
	}

	addseg.build();
	build();

	while (q--)
	{
		char op;
		int l, r;
		scanf(" %c %d %d ", &op, &l, &r);
		l--; r--;
		if (op == '+')
		{
			int x;
			scanf("%d", &x);
			addseg.add(l, r, x);
			if (l > 0) setind(l - 1);
			if (r < n - 1) setind(r);
		}
		else if (op == '*')
		{
			addseg.neg(l, r);
			if (l < r) tgl(l, r - 1);
			if (l > 0) setind(l - 1);
			if (r < n - 1) setind(r);
		}
		else	// ask
		{
			node res = get(l, r - 1);
			printf("%lld\n", res.val + (r - l + 1));
		}
	}

	return 0;
}


Compilation message

Main.cpp: In function 'int32_t main()':
Main.cpp:234:7: warning: ignoring return value of 'int scanf(const char*, ...)' declared with attribute 'warn_unused_result' [-Wunused-result]
  234 |  scanf("%d %d", &n, &q);
      |  ~~~~~^~~~~~~~~~~~~~~~~
Main.cpp:236:20: warning: ignoring return value of 'int scanf(const char*, ...)' declared with attribute 'warn_unused_result' [-Wunused-result]
  236 |  FOR(i, 0, n) scanf("%d", a + i);
      |               ~~~~~^~~~~~~~~~~~~
Main.cpp:243:9: warning: ignoring return value of 'int scanf(const char*, ...)' declared with attribute 'warn_unused_result' [-Wunused-result]
  243 |    scanf(" %c %d %d", &op, &l, &r);
      |    ~~~~~^~~~~~~~~~~~~~~~~~~~~~~~~~
Main.cpp:244:24: warning: ignoring return value of 'int scanf(const char*, ...)' declared with attribute 'warn_unused_result' [-Wunused-result]
  244 |    if (op == '+') scanf("%d", &x);
      |                   ~~~~~^~~~~~~~~~
Main.cpp:257:8: warning: ignoring return value of 'int scanf(const char*, ...)' declared with attribute 'warn_unused_result' [-Wunused-result]
  257 |   scanf(" %c %d %d ", &op, &l, &r);
      |   ~~~~~^~~~~~~~~~~~~~~~~~~~~~~~~~~
Main.cpp:262:9: warning: ignoring return value of 'int scanf(const char*, ...)' declared with attribute 'warn_unused_result' [-Wunused-result]
  262 |    scanf("%d", &x);
      |    ~~~~~^~~~~~~~~~
# 결과 실행 시간 메모리 Grader output
1 Correct 11 ms 1100 KB Output is correct
2 Correct 10 ms 1128 KB Output is correct
3 Correct 11 ms 1136 KB Output is correct
4 Correct 11 ms 1144 KB Output is correct
5 Correct 10 ms 1100 KB Output is correct
6 Correct 2 ms 204 KB Output is correct
7 Correct 10 ms 972 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 1170 ms 52412 KB Output is correct
2 Correct 105 ms 2508 KB Output is correct
3 Correct 866 ms 60796 KB Output is correct
4 Correct 1064 ms 60680 KB Output is correct
5 Correct 989 ms 60672 KB Output is correct
6 Correct 1000 ms 60672 KB Output is correct
7 Correct 1057 ms 57588 KB Output is correct
8 Correct 1099 ms 60680 KB Output is correct
9 Correct 1032 ms 60764 KB Output is correct
10 Correct 732 ms 60652 KB Output is correct
11 Correct 913 ms 60784 KB Output is correct
12 Correct 1096 ms 60776 KB Output is correct
13 Correct 460 ms 58336 KB Output is correct
14 Correct 458 ms 58276 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 11 ms 1100 KB Output is correct
2 Correct 10 ms 1128 KB Output is correct
3 Correct 11 ms 1136 KB Output is correct
4 Correct 11 ms 1144 KB Output is correct
5 Correct 10 ms 1100 KB Output is correct
6 Correct 2 ms 204 KB Output is correct
7 Correct 10 ms 972 KB Output is correct
8 Correct 372 ms 13476 KB Output is correct
9 Correct 326 ms 13368 KB Output is correct
10 Correct 336 ms 13476 KB Output is correct
11 Correct 178 ms 11204 KB Output is correct
12 Correct 326 ms 13372 KB Output is correct
13 Correct 330 ms 13552 KB Output is correct
14 Correct 329 ms 13448 KB Output is correct
15 Correct 330 ms 13472 KB Output is correct
16 Correct 349 ms 13464 KB Output is correct
17 Correct 293 ms 13456 KB Output is correct
18 Correct 131 ms 13208 KB Output is correct
19 Correct 138 ms 13124 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 11 ms 1100 KB Output is correct
2 Correct 10 ms 1128 KB Output is correct
3 Correct 11 ms 1136 KB Output is correct
4 Correct 11 ms 1144 KB Output is correct
5 Correct 10 ms 1100 KB Output is correct
6 Correct 2 ms 204 KB Output is correct
7 Correct 10 ms 972 KB Output is correct
8 Correct 1170 ms 52412 KB Output is correct
9 Correct 105 ms 2508 KB Output is correct
10 Correct 866 ms 60796 KB Output is correct
11 Correct 1064 ms 60680 KB Output is correct
12 Correct 989 ms 60672 KB Output is correct
13 Correct 1000 ms 60672 KB Output is correct
14 Correct 1057 ms 57588 KB Output is correct
15 Correct 1099 ms 60680 KB Output is correct
16 Correct 1032 ms 60764 KB Output is correct
17 Correct 732 ms 60652 KB Output is correct
18 Correct 913 ms 60784 KB Output is correct
19 Correct 1096 ms 60776 KB Output is correct
20 Correct 460 ms 58336 KB Output is correct
21 Correct 458 ms 58276 KB Output is correct
22 Correct 372 ms 13476 KB Output is correct
23 Correct 326 ms 13368 KB Output is correct
24 Correct 336 ms 13476 KB Output is correct
25 Correct 178 ms 11204 KB Output is correct
26 Correct 326 ms 13372 KB Output is correct
27 Correct 330 ms 13552 KB Output is correct
28 Correct 329 ms 13448 KB Output is correct
29 Correct 330 ms 13472 KB Output is correct
30 Correct 349 ms 13464 KB Output is correct
31 Correct 293 ms 13456 KB Output is correct
32 Correct 131 ms 13208 KB Output is correct
33 Correct 138 ms 13124 KB Output is correct
34 Correct 1 ms 332 KB Output is correct
35 Correct 1 ms 332 KB Output is correct
36 Correct 1313 ms 57832 KB Output is correct
37 Correct 1254 ms 60884 KB Output is correct
38 Correct 568 ms 50756 KB Output is correct
39 Correct 1239 ms 60848 KB Output is correct
40 Correct 1253 ms 57792 KB Output is correct
41 Correct 1057 ms 60864 KB Output is correct
42 Correct 1100 ms 57924 KB Output is correct
43 Correct 1203 ms 60820 KB Output is correct
44 Correct 1175 ms 60812 KB Output is correct
45 Correct 1256 ms 60976 KB Output is correct
46 Correct 1048 ms 60968 KB Output is correct
47 Correct 619 ms 58712 KB Output is correct