For problem statement at 0-999/900-999/930-939/935/problemF.txt this is a correct solution, but verifier at 0-999/900-999/930-939/935/verifierF.go ends with All tests passed can you fix the verifier? package main
import (
"bufio"
"fmt"
"os"
)
type Node struct {
lmax bool
hasU bool
mBU int64
hasD bool
mAD int64
hasM bool
mSum int64
mAM int64
mBM int64
}
const INF int64 = 1<<60
func abs64(x int64) int64 {
if x < 0 {
return -x
}
return x
}
func min64(a, b int64) int64 {
if a < b {
return a
}
return b
}
func max64(a, b int64) int64 {
if a > b {
return a
}
return b
}
type SegTree struct {
n int
t []Node
d []int64
nv int
idn Node
}
func (st *SegTree) init(d []int64) {
st.d = d
st.nv = len(d) - 1 // number of leaves = n-2 if len(a)=n
if st.nv <= 0 {
st.nv = 0
}
st.t = make([]Node, 4*maxInt(1, st.nv))
st.idn = Node{false, false, INF, false, INF, false, INF, INF, INF}
if st.nv > 0 {
st.build(1, 0, st.nv-1)
}
}
func (st *SegTree) leafFromIndex(idx int) Node {
A := st.d[idx]
B := st.d[idx+1]
var nd Node
if A >= 0 && B <= 0 {
nd.lmax = true
}
if A >= 0 && B > 0 {
nd.hasU = true
nd.mBU = B
} else {
nd.mBU = INF
}
if A < 0 && B <= 0 {
nd.hasD = true
nd.mAD = -A
} else {
nd.mAD = INF
}
if A < 0 && B > 0 {
nd.hasM = true
nd.mSum = -A + B
nd.mAM = -A
nd.mBM = B
} else {
nd.mSum = INF
nd.mAM = INF
nd.mBM = INF
}
return nd
}
func (st *SegTree) merge(a, b Node) Node {
var r Node
r.lmax = a.lmax || b.lmax
r.hasU = a.hasU || b.hasU
r.mBU = min64(a.mBU, b.mBU)
r.hasD = a.hasD || b.hasD
r.mAD = min64(a.mAD, b.mAD)
r.hasM = a.hasM || b.hasM
r.mSum = min64(a.mSum, b.mSum)
r.mAM = min64(a.mAM, b.mAM)
r.mBM = min64(a.mBM, b.mBM)
return r
}
func (st *SegTree) build(v, l, r int) {
if l == r {
st.t[v] = st.leafFromIndex(l)
return
}
m := (l + r) >> 1
st.build(v<<1, l, m)
st.build(v<<1|1, m+1, r)
st.t[v] = st.merge(st.t[v<<1], st.t[v<<1|1])
}
func (st *SegTree) update(pos int) {
if st.nv == 0 {
return
}
st._update(1, 0, st.nv-1, pos, st.leafFromIndex(pos))
}
func (st *SegTree) _update(v, l, r, pos int, val Node) {
if l == r {
st.t[v] = val
return
}
m := (l + r) >> 1
if pos <= m {
st._update(v<<1, l, m, pos, val)
} else {
st._update(v<<1|1, m+1, r, pos, val)
}
st.t[v] = st.merge(st.t[v<<1], st.t[v<<1|1])
}
func (st *SegTree) query(ql, qr int) Node {
if st.nv == 0 {
return st.idn
}
return st._query(1, 0, st.nv-1, ql, qr)
}
func (st *SegTree) _query(v, l, r, ql, qr int) Node {
if ql <= l && r <= qr {
return st.t[v]
}
if r < ql || qr < l {
return st.idn
}
m := (l + r) >> 1
ln := st._query(v<<1, l, m, ql, qr)
rn := st._query(v<<1|1, m+1, r, ql, qr)
return st.merge(ln, rn)
}
func maxInt(a, b int) int {
if a > b {
return a
}
return b
}
type FastScanner struct {
r *bufio.Reader
}
func NewFastScanner() *FastScanner {
return &FastScanner{r: bufio.NewReaderSize(os.Stdin, 1<<20)}
}
func (fs *FastScanner) nextInt64() int64 {
var sign int64 = 1
var val int64 = 0
c, err := fs.r.ReadByte()
for (c < '0' || c > '9') && c != '-' {
c, err = fs.r.ReadByte()
if err != nil {
return 0
}
}
if c == '-' {
sign = -1
c, _ = fs.r.ReadByte()
}
for c >= '0' && c <= '9' {
val = val*10 + int64(c-'0')
c, err = fs.r.ReadByte()
if err != nil {
break
}
}
return sign * val
}
func main() {
fs := NewFastScanner()
out := bufio.NewWriterSize(os.Stdout, 1<<20)
defer out.Flush()
n := int(fs.nextInt64())
a := make([]int64, n)
for i := 0; i < n; i++ {
a[i] = fs.nextInt64()
}
d := make([]int64, n-1)
var S int64 = 0
for i := 0; i < n-1; i++ {
d[i] = a[i+1] - a[i]
S += abs64(d[i])
}
seg := &SegTree{}
seg.init(d)
q := int(fs.nextInt64())
for ; q > 0; q-- {
t := int(fs.nextInt64())
l := int(fs.nextInt64())
r := int(fs.nextInt64())
x := fs.nextInt64()
if t == 1 {
L := l - 2
R := r - 2
res := seg.query(L, R)
gain := int64(-1 << 62)
twoX := 2 * x
if res.lmax {
gain = max64(gain, twoX)
}
if res.hasU {
gain = max64(gain, twoX-2*res.mBU)
}
if res.hasD {
gain = max64(gain, twoX-2*res.mAD)
}
if res.hasM {
gain = max64(gain, twoX-2*res.mSum)
gain = max64(gain, -twoX)
mm := res.mAM
if res.mBM < mm {
mm = res.mBM
}
gain = max64(gain, -2*mm)
}
if res.hasU || res.hasD {
gain = max64(gain, 0)
}
fmt.Fprintln(out, S+gain)
} else {
j1 := l - 1
k1 := j1 - 1
old1 := d[k1]
d[k1] = old1 + x
S += abs64(d[k1]) - abs64(old1)
j2 := r
k2 := j2 - 1
old2 := d[k2]
d[k2] = old2 - x
S += abs64(d[k2]) - abs64(old2)
// update leaves for i = j1, j1+1, j2, j2+1 where 2 <= i <= n-1
if j1 >= 2 && j1 <= n-1 {
seg.update(j1 - 2)
}
if j1+1 >= 2 && j1+1 <= n-1 {
seg.update(j1 - 1)
}
if j2 >= 2 && j2 <= n-1 {
seg.update(j2 - 2)
}
if j2+1 >= 2 && j2+1 <= n-1 {
seg.update(j2 - 1)
}
}
}
}