#include using namespace std; using ll = long long; const ll mod = 1e9 + 7; const int N = 200005; const ll INF = 0x3f3f3f3f3f3f3f3f; #define int long long struct Event { ll x; int y1, y2; ll d; bool operator<(Event const& o) const { if (x != o.x) return x < o.x; return d > o.d; } }; struct SegTree { struct Node { ll val, tag; }; int n; vector st; SegTree(int _n) : n(_n), st(4 * n + 4, {0, 0}) {} void gx(int u, ll v) { st[u].val += v; st[u].tag += v; } void pushdown(int u) { if (st[u].tag != 0) { gx(u << 1, st[u].tag); gx(u << 1 | 1, st[u].tag); st[u].tag = 0; } } void pushup(int u) { st[u].val = max(st[u << 1].val, st[u << 1 | 1].val); } void update(int u, int l, int r, int x, int y, ll v) { if (y <= l || r <= x) return; if (x <= l && r <= y) { gx(u, v); return; } pushdown(u); int mid = l + r >> 1; update(u << 1, l, mid, x, y, v); update(u << 1 | 1, mid, r, x, y, v); pushup(u); } ll query(int u, int l, int r, int x, int y) { if (y <= l || r <= x) return -INF; if (x <= l && r <= y) return st[u].val; pushdown(u); int mid = l + r >> 1; return max(query(u << 1, l, mid, x, y), query(u << 1 | 1, mid + 1, r, x, y)); } ll query_max() { return query(1, 0, n, 0, n); } }; signed main() { ios::sync_with_stdio(0); cin.tie(0); cout.tie(0); int n; ll A; cin >> n >> A; vector X(n), Y(n), V(n); for (int i = 0; i < n; i++) cin >> X[i] >> Y[i] >> V[i]; vector ys; ys.reserve(2 * n); for (int i = 0; i < n; i++) { ys.push_back(Y[i]); ys.push_back(Y[i] + A); } sort(ys.begin(), ys.end()); ys.erase(unique(ys.begin(), ys.end()), ys.end()); auto cal = [&](ll y) { return lower_bound(ys.begin(), ys.end(), y) - ys.begin(); }; vector ev; ev.reserve(2 * n); for (int i = 0; i < n; i++) { ll xs = X[i] - A; ll xe = X[i]; int y1 = cal(Y[i]), y2 = cal(Y[i] + A) + 1; ev.push_back({xs, y1, y2, V[i]}); ev.push_back({xe, y1, y2, -V[i]}); } sort(ev.begin(), ev.end()); SegTree st((int)ys.size() + 2); ll ans = -INF; int M = ev.size(); for (int i = 0; i < M;) { ll curX = ev[i].x; int j = i; while (j < M && ev[j].x == curX) j++; for (int k = i; k < j; k++) { if (ev[k].d > 0) st.update(1, 0, st.n, ev[k].y1, ev[k].y2, ev[k].d); } ans = max(ans, st.query_max()); for (int k = i; k < j; k++) { if (ev[k].d < 0) st.update(1, 0, st.n, ev[k].y1, ev[k].y2, ev[k].d); } i = j; } cout << ans << "\n"; return 0; }