Language: C++

#include<bits/stdc++.h>

using namespace std;

struct Mo_3D
{
  vector< int > left, right, index, order;
  vector< bool > v;
  int width;
  int nl, nr, time, ptr;

  Mo_3D(int n) : width((int) pow(n, 2.0 / 3.0)), nl(0), nr(0), ptr(0), time(0), v(n) {}

  void insert(int idx, int l, int r) /* [l, r) */
  {
    left.push_back(l);
    right.push_back(r);
    index.push_back(idx);
  }

  void build()
  {
    order.resize(left.size());
    iota(begin(order), end(order), 0);
    sort(begin(order), end(order), [&](int a, int b)
    {
      if(left[a] / width != left[b] / width) return left[a] < left[b];
      if(right[a] / width != right[b] / width) return bool((right[a] < right[b]) ^ (left[a] / width % 2));
      return bool((index[a] < index[b]) ^ (right[a] / width % 2));
    });
  }

  int process()
  {
    if(ptr == order.size()) return (-1);
    const auto id = order[ptr];
    while(nl > left[id]) distribute(--nl);
    while(nr < right[id]) distribute(nr++);
    while(nl < left[id]) distribute(nl++);
    while(nr > right[id]) distribute(--nr);

    while(time < index[id]) addquery(time++);
    while(time > index[id]) delquery(--time);
    return (index[order[ptr++]]);
  }

  inline void distribute(int idx);

  void addquery(int idx);

  void delquery(int idx);
};

struct edge
{
  int to, cost;
};

#define int long long

int N, K, Q;
vector< edge > g[100000];
int A[100000], B[100000], C[100000];
int T[100000], X[100000], Y[100000];
char buff[10];

vector< int > vs;
int in[100000], par[100000], cost[100000], add[100000];
int ans[100000], ret;

void dfs(int idx, int p = -1)
{
  in[idx] = (int) vs.size();
  par[idx] = p;
  vs.push_back(idx);
  for(auto &e : g[idx]) {
    dfs(e.to, idx);
    vs.push_back(idx);
    cost[e.to] += e.cost;
  }
}

inline void Mo_3D::distribute(int idx)
{
  auto p = minmax(vs[idx], vs[idx + 1]);
  v[p.second].flip();
  int beet = cost[p.second] + add[p.first] + add[p.second];
  if(v[p.second]) {
    if(beet % K) ret += beet;
  } else {
    if(beet % K) ret -= beet;
  }
}

void Mo_3D::addquery(int idx)
{
  if(T[idx]) return;
  if(v[X[idx]]) {
    int beet = cost[X[idx]] + add[X[idx]] + add[par[X[idx]]];
    if(beet % K) ret -= beet;
    beet = cost[X[idx]] + add[X[idx]] + add[par[X[idx]]] + Y[idx];
    if(beet % K) ret += beet;

  }

  for(auto &e : g[X[idx]]) {
    if(v[e.to]) {
      int beet = cost[e.to] + add[X[idx]] + add[e.to];
      if(beet % K) ret -= beet;
      beet = cost[e.to] + add[X[idx]] + add[e.to] + Y[idx];
      if(beet % K) ret += beet;
    }
  }

  add[X[idx]] += Y[idx];
}

void Mo_3D::delquery(int idx)
{
  if(T[idx]) return;
  if(v[X[idx]]) {
    int beet = cost[X[idx]] + add[X[idx]] + add[par[X[idx]]];
    if(beet % K) ret -= beet;
    beet = cost[X[idx]] + add[X[idx]] + add[par[X[idx]]] - Y[idx];
    if(beet % K) ret += beet;

  }


  for(auto &e : g[X[idx]]) {
    if(v[e.to]) {
      int beet = cost[e.to] + add[X[idx]] + add[e.to];
      if(beet % K) ret -= beet;
      beet = cost[e.to] + add[X[idx]] + add[e.to] - Y[idx];
      if(beet % K) ret += beet;
    }
  }

  add[X[idx]] -= Y[idx];
}

signed main()
{
  scanf("%lld %lld", &N, &K);
  for(int i = 1; i < N; i++) {
    scanf("%lld %lld %lld", &A[i], &B[i], &C[i]);
    g[A[i]].push_back((edge) {B[i], C[i]});
  }
  scanf("%lld", &Q);
  for(int i = 0; i < Q; i++) {
    scanf("%s %lld %lld", buff, &X[i], &Y[i]);
    T[i] = buff[0] == 's';
  }
  dfs(0);
  Mo_3D mo(vs.size());
  for(int i = 0; i < Q; i++) {
    if(T[i]) {
      auto p = minmax(in[X[i]], in[Y[i]]);
      mo.insert(i, p.first, p.second);
    }
  }
  mo.build();
  int idx;
  while((idx = mo.process()) != -1) ans[idx] = ret;
  for(int i = 0; i < Q; i++) {
    if(T[i]) printf("%lld\n", ans[i]);
  }
}

Compiler output:
a.cc:83:13: error: no declaration matches 'void Mo_3D::distribute(long long int)'
   83 | inline void Mo_3D::distribute(int idx)
      |             ^~~~~
a.cc:47:15: note: candidate is: 'void Mo_3D::distribute(int)'
   47 |   inline void distribute(int idx);
      |               ^~~~~~~~~~
a.cc:5:8: note: 'struct Mo_3D' defined here
    5 | struct Mo_3D
      |        ^~~~~
a.cc:95:6: error: no declaration matches 'void Mo_3D::addquery(long long int)'
   95 | void Mo_3D::addquery(int idx)
      |      ^~~~~
a.cc:49:8: note: candidate is: 'void Mo_3D::addquery(int)'
   49 |   void addquery(int idx);
      |        ^~~~~~~~
a.cc:5:8: note: 'struct Mo_3D' defined here
    5 | struct Mo_3D
      |        ^~~~~
a.cc:118:6: error: no declaration matches 'void Mo_3D::delquery(long long int)'
  118 | void Mo_3D::delquery(int idx)
      |      ^~~~~
a.cc:51:8: note: candidate is: 'void Mo_3D::delquery(int)'
   51 |   void delquery(int idx);
      |        ^~~~~~~~
a.cc:5:8: note: 'struct Mo_3D' defined here
    5 | struct Mo_3D
      |        ^~~~~
a.cc: In function 'int main()':
a.cc:147:34: warning: narrowing conversion of 'B[i]' from 'long long int' to 'int' [-Wnarrowing]
  147 |     g[A[i]].push_back((edge) {B[i], C[i]});
      |                               ~~~^
a.cc:147:40: warning: narrowing conversion of 'C[i]' from 'long long int' to 'int' [-Wnarrowing]
  147 |     g[A[i]].push_back((edge) {B[i], C[i]});
      |                                     ~~~^
a.cc: At global scope:
a.cc:47:15: warning: inline function 'void Mo_3D::distribute(int)' used but never defined
   47 |   inline void distribute(int idx);
      |               ^~~~~~~~~~