Buggy python submission (verdict: Time Limit Exceeded):
from math import ceil
from bisect import bisect_right

def update(x, v):
  while x <= N:
    fw[x] += v
    x += x & -x

def s(x):
  res = 0
  while x:
    res += fw[x]
    x -= x & -x
  return res

def change(l, r, a):
  update(l, a)
  update(r + 1, -a)


N,D,A = map(int,input().split())
monsters = sorted([list(map(int,input().split())) for _ in range(N)])

fw = [0 for _ in range(N + 1)]

ans = 0
for i in range(N):
  h = s(i + 1) - s(0)
  if monsters[i][1] + h > 0:
    num_bomb = ceil((monsters[i][1] + h) / A)
    ans += num_bomb

    k = bisect_right(monsters, [monsters[i][0] + 2*D, 10**9])
    change(i + 1, k, -(num_bomb * A))
    
print(ans)


Fixed submission:
from math import ceil
from collections import deque

N,D,A = map(int,input().split())
monsters = sorted([list(map(int,input().split())) for _ in range(N)])

q = deque([])
s = 0

ans = 0
for i in range(N):
  while len(q) > 0 and q[0][0] < monsters[i][0]:
    s -= q[0][1]
    q.popleft()

  h = monsters[i][1] - s * A
  if h > 0:
    num_bombs = ceil(h / A)

    q.append((monsters[i][0] + 2 * D, num_bombs))
    s += num_bombs
    ans += num_bombs
    
print(ans)

Buggy python submission (verdict: Time Limit Exceeded):
from math import ceil
from bisect import bisect_right

def update(x, v):
  while x <= N:
    fw[x] += v
    x += x & -x

def s(x):
  res = 0
  while x:
    res += fw[x]
    x -= x & -x
  return res


N,D,A = map(int,input().split())
monsters = sorted([list(map(int,input().split())) for _ in range(N)])

fw = [0 for _ in range(N + 1)]

nxt = []
j = 0
for i in range(N):
  while j < N and monsters[j][0] <= monsters[i][0] + 2 * D:
    j += 1
  nxt.append(j)

ans = 0
for i in range(N):
  h = s(i + 1) - s(0)
  if monsters[i][1] + h > 0:
    num_bomb = ceil((monsters[i][1] + h) / A)
    ans += num_bomb

    k = nxt[i]
    update(i + 1, -(num_bomb * A))
    update(k + 1, num_bomb * A)
    
print(ans)


Fixed submission:
from math import ceil
from collections import deque

N,D,A = map(int,input().split())
monsters = sorted([list(map(int,input().split())) for _ in range(N)])

q = deque([])
s = 0

ans = 0
for i in range(N):
  while len(q) > 0 and q[0][0] < monsters[i][0]:
    s -= q[0][1]
    q.popleft()

  h = monsters[i][1] - s * A
  if h > 0:
    num_bombs = ceil(h / A)

    q.append((monsters[i][0] + 2 * D, num_bombs))
    s += num_bombs
    ans += num_bombs
    
print(ans)

Buggy python submission (verdict: Time Limit Exceeded):
from math import ceil
from bisect import bisect_right

def update(x, v):
  while x <= N:
    fw[x] += v
    x += x & -x

def s(x):
  res = 0
  while x:
    res += fw[x]
    x -= x & -x
  return res


N,D,A = map(int,input().split())
monsters = sorted([list(map(int,input().split())) for _ in range(N)])

fw = [0 for _ in range(N + 1)]

ans = 0
for i in range(N):
  h = s(i + 1) - s(0)
  if monsters[i][1] + h > 0:
    num_bomb = ceil((monsters[i][1] + h) / A)
    ans += num_bomb

    k = bisect_right(monsters, [monsters[i][0] + 2*D, 10**9])
    update(i + 1, -(num_bomb * A))
    update(k + 1, num_bomb * A)
    
print(ans)


Fixed submission:
from math import ceil
from collections import deque

N,D,A = map(int,input().split())
monsters = sorted([list(map(int,input().split())) for _ in range(N)])

q = deque([])
s = 0

ans = 0
for i in range(N):
  while len(q) > 0 and q[0][0] < monsters[i][0]:
    s -= q[0][1]
    q.popleft()

  h = monsters[i][1] - s * A
  if h > 0:
    num_bombs = ceil(h / A)

    q.append((monsters[i][0] + 2 * D, num_bombs))
    s += num_bombs
    ans += num_bombs
    
print(ans)