java线段树求调
查看原帖
java线段树求调
1110115
chronobox楼主2024/3/6 19:44

问题是数组越界,但是不知道是哪一步出了问题

import java.util.*;
import java.io.*;
import java.math.*;
public class Main{
	static PrintWriter cout = new PrintWriter(System.out);
	static FastReader cin = new FastReader();
	static final int N = 100010;
	static int [] cnt0 = new int [N*4], cnt1 = new int [N*4], max0 = new int [N*4], max1 = new int [N*4];
	static int [] lmax0 = new int [N*4], lmax1 = new int [N*4], rmax0 = new int [N*4], rmax1 = new int [N*4];
	static int [] set = new int [N*4], rev = new int [N*4];
	static int [] a = new int [N];
	static int lc(int u) {
		return u << 1;
	}
	static int rc(int u) {
		return u << 1 | 1;
	}
	static void settag(int u, int tp) {
		if(tp == 0 || tp == 1) { // 赋值
			cnt0[u] = max0[u] = lmax0[u] = rmax0[u] = tp ^ 1;
			cnt1[u] = max1[u] = lmax1[u] = rmax1[u] = tp;
			set[u] = tp;
			rev[u] = 0;
		}
		else { //反转
			rev[u] ^= 1;
			int t = cnt0[u]; cnt0[u] = cnt1[u]; cnt1[u] = t;
			t = max0[u]; max0[u] = max1[u]; max1[u] = t;
			t = lmax0[u]; lmax0[u] = lmax1[u]; lmax1[u] = t;
			t = rmax0[u]; rmax0[u] = rmax1[u]; rmax1[u] = t;
		}
		
	}
	static void pushup(int u) {
		cnt0[u] = cnt0[lc(u)] + cnt0[rc(u)];
		cnt1[u] = cnt1[lc(u)] + cnt1[rc(u)];
		max0[u] = Math.max(Math.max(max0[lc(u)], max0[rc(u)]), rmax0[lc(u)] + lmax0[rc(u)]);
		max1[u] = Math.max(Math.max(max1[lc(u)], max1[rc(u)]), rmax1[lc(u)] + lmax1[rc(u)]);
		//左区间全是1 
		if(cnt0[lc(u)] == 0) lmax1[u] = cnt1[lc(u)] + lmax1[rc(u)];
		else lmax1[u] = lmax1[lc(u)];
		//左区间全是0
		if(cnt1[lc(u)] == 0) lmax0[u] = cnt0[lc(u)] + lmax0[rc(u)];
		else lmax0[u] = lmax0[lc(u)];
		//右区间全是1
		if(cnt0[rc(u)] == 0) rmax1[u] = cnt1[rc(u)] + rmax1[lc(u)];
		else rmax1[u] = rmax1[rc(u)];
		//右区间全是0
		if(cnt1[rc(u)] == 0) rmax0[u] = cnt0[rc(u)] + rmax0[lc(u)];
		else rmax0[u] = rmax0[rc(u)];
	}
	static void pushdown(int u) {
		if(set[u] >= 0 && set[u] <= 1) {
			settag(lc(u), set[u]);
			settag(rc(u), set[u]);
			set[u] = -1;
		}
		else if (rev[u] == 1) {
			settag(lc(u), 2);
			settag(rc(u), 2);
			set[u] = -1;
			rev[u] = 0;
		}
	}
	static void build(int u, int l, int r) {
		if(l == r) {
			if(a[l] == 0) {
				cnt0[u] = max0[u] = lmax0[u] = rmax0[u] = 1;
				cnt1[u] = max1[u] = lmax1[u] = rmax1[u] = 0;
			}
			else{
				cnt0[u] = max0[u] = lmax0[u] = rmax0[u] = 0;
				cnt1[u] = max1[u] = lmax1[u] = rmax1[u] = 1;
			}
			return;
		}
		int mid = (l + r) >> 1;
		build(lc(u), l, mid);
		build(rc(u), mid + 1, r);
		pushup(u);
	}
	static void modify(int u, int l, int r, int ql, int qr, int tp) {
		if(l == ql && r == qr) {
			settag(u, tp);
			return;
		}
		pushdown(u);
		int mid = (l + r) >> 1;
		if(qr <= mid) modify(lc(u), l, mid, ql, qr, tp);
		else if(ql > mid) modify(rc(u), mid + 1, r, ql, qr, tp);
		else {
			modify(lc(u), l, mid, ql, mid, tp);
			modify(rc(u), mid + 1, r, mid + 1, qr, tp);
		}
		pushup(u);
	}
	
	static int query1(int u, int l, int r, int ql, int qr) {
		if(l == ql && r == qr) {
			return cnt1[u];
		}
		pushdown(u);
		int mid = (l + r) >> 1;
		if(qr <= mid) return query1(lc(u), l, mid, ql, qr);
		else if(ql > mid) return query1(rc(u), mid + 1, r, ql, qr);
		else return query1(lc(u), l, mid, ql, mid) + query1(rc(u), mid + 1, r, mid + 1, qr); 
	}
	static int query2(int u, int l, int r, int ql, int qr) {
		if(l == ql && r == qr) {
			return max1[u];
		}
		pushdown(u);
		int mid = (l + r) >> 1;
		if(qr <= mid) return query2(lc(u), l, mid, ql, qr);
		else if(ql > mid) return query2(rc(u), mid + 1, r, ql, qr);
		else return Math.max(Math.max(query2(lc(u), l, mid, ql, mid), query2(rc(u),mid + 1, r, mid + 1, qr)), rmax1[lc(u)] + lmax1[rc(u)]);
	}
	
	public static void main(String[] args) {
		int t = 1;
		//t = cin.nextInt();
		while(t-- > 0) {
			solve();
		}
		cout.flush();
	}
	static void solve() {
		int n = cin.nextInt(), m = cin.nextInt();
		for(int i = 1; i <= n; i++) a[i] = cin.nextInt();
		build(1, 1, n);
		while(m-- > 0) {
			int tp = cin.nextInt(), l = cin.nextInt(), r = cin.nextInt();
			if(tp <= 2) modify(1, 1, n, l, r, tp);
			else if(tp == 3) {
				int ans = query1(1, 1, n, l ,r);
				cout.println(ans);
			}
			else {
				int ans = query2(1, 1, n, l, r);
				cout.println(ans);
			}
		}
	}
}
class FastReader{
	StringTokenizer st;
	BufferedReader br;
	public FastReader() {
		br = new BufferedReader(new InputStreamReader(System.in));
	}
	String next() {
		while(st == null || !st.hasMoreElements()) {
			try {
				st = new StringTokenizer(br.readLine());
			}catch (IOException e) {
				e.getStackTrace();
			}
		}
		return st.nextToken();
	}
	int nextInt() {
		return Integer.parseInt(next());
	}
}
2024/3/6 19:44
加载中...