結果
| 問題 | No.3507 RangeSum RangeUpdate RangeSqrt |
| コンテスト | |
| ユーザー |
|
| 提出日時 | 2026-04-18 06:00:24 |
| 言語 | Python3 (3.14.3 + numpy 2.4.4 + scipy 1.17.1) |
| 結果 |
TLE
|
| 実行時間 | - |
| コード長 | 4,037 bytes |
| 記録 | |
| コンパイル時間 | 558 ms |
| コンパイル使用メモリ | 20,832 KB |
| 実行使用メモリ | 42,520 KB |
| 最終ジャッジ日時 | 2026-04-18 06:01:08 |
| 合計ジャッジ時間 | 10,891 ms |
|
ジャッジサーバーID (参考情報) |
judge2_0 / judge3_0 |
(要ログイン)
| ファイルパターン | 結果 |
|---|---|
| sample | -- * 1 |
| other | AC * 1 TLE * 2 -- * 26 |
ソースコード
import sys
import math
input = sys.stdin.readline
class SegTree:
def __init__(self, a):
sz = 1
while sz < len(a):
sz <<= 1
self.sz = sz
m = sz << 1
self.sm = [0] * m
self.mn = [0] * m
self.mx = [0] * m
self.lz_set = [None] * m
self.lz_add = [0] * m
for i in range(sz):
if i < len(a):
val = a[i]
else:
val = 0
p = sz + i
self.sm[p] = val
self.mn[p] = val
self.mx[p] = val
for i in range(sz - 1, 0, -1):
self.pull(i)
def pull(self, i):
lc = i << 1
rc = lc | 1
self.sm[i] = self.sm[lc] + self.sm[rc]
self.mn[i] = min(self.mn[lc], self.mn[rc])
self.mx[i] = max(self.mx[lc], self.mx[rc])
def apply_set(self, i, l, r, v):
self.sm[i] = v * (r - l)
self.mn[i] = v
self.mx[i] = v
self.lz_set[i] = v
self.lz_add[i] = 0
def apply_add(self, i, l, r, d):
if d == 0:
return
self.sm[i] += d * (r - l)
self.mn[i] += d
self.mx[i] += d
if self.lz_set[i] is not None:
self.lz_set[i] += d
else:
self.lz_add[i] += d
def push(self, i, l, r):
if r - l == 1:
self.lz_set[i] = None
self.lz_add[i] = 0
return
mid = (l + r) >> 1
lc = i << 1
rc = lc | 1
if self.lz_set[i] is not None:
v = self.lz_set[i]
self.apply_set(lc, l, mid, v)
self.apply_set(rc, mid, r, v)
self.lz_set[i] = None
if self.lz_add[i] != 0:
d = self.lz_add[i]
self.apply_add(lc, l, mid, d)
self.apply_add(rc, mid, r, d)
self.lz_add[i] = 0
def update_set(self, ql, qr, v, i=1, l=0, r=None):
if r is None:
r = self.sz
if qr <= l or r <= ql:
return
if ql <= l and r <= qr:
self.apply_set(i, l, r, v)
return
self.push(i, l, r)
mid = (l + r) >> 1
self.update_set(ql, qr, v, i << 1, l, mid)
self.update_set(ql, qr, v, i << 1 | 1, mid, r)
self.pull(i)
def query_sum(self, ql, qr, i=1, l=0, r=None):
if r is None:
r = self.sz
if qr <= l or r <= ql:
return 0
if ql <= l and r <= qr:
return self.sm[i]
self.push(i, l, r)
mid = (l + r) >> 1
left_sum = self.query_sum(ql, qr, i << 1, l, mid)
right_sum = self.query_sum(ql, qr, i << 1 | 1, mid, r)
return left_sum + right_sum
def update_sqrt(self, ql, qr, i=1, l=0, r=None):
if r is None:
r = self.sz
if qr <= l or r <= ql:
return
if self.mx[i] <= 1:
return
if ql <= l and r <= qr:
d1 = math.isqrt(self.mn[i]) - self.mn[i]
d2 = math.isqrt(self.mx[i]) - self.mx[i]
if d1 == d2:
self.apply_add(i, l, r, d1)
return
if r - l == 1:
nv = math.isqrt(self.mx[i])
self.apply_set(i, l, r, nv)
return
self.push(i, l, r)
mid = (l + r) >> 1
self.update_sqrt(ql, qr, i << 1, l, mid)
self.update_sqrt(ql, qr, i << 1 | 1, mid, r)
self.pull(i)
def main():
n, q = map(int, input().split())
a = list(map(int, input().split()))
seg = SegTree(a)
ans = []
for _ in range(q):
qry = list(map(int, input().split()))
t = qry[0]
if t == 0:
l, r = qry[1], qry[2]
ans.append(str(seg.query_sum(l, r)))
elif t == 1:
l, r, x = qry[1], qry[2], qry[3]
seg.update_set(l, r, x)
else:
l, r = qry[1], qry[2]
seg.update_sqrt(l, r)
print("\n".join(ans))
if __name__ == "__main__":
main()