#include <bits/stdc++.h>
using namespace std;
long long gcd(long long a, long long b) { return b == 0 ? a : gcd(b, a % b); }
long long lcm(long long a, long long b) { return a * (b / gcd(a, b)); }
long long fact(long long n) {
  long long ret = 1;
  for (int i = 1; i <= n; i++) ret *= i;
  return ret;
}
bool is_vowel(char c) {
  if (c == 'a' || c == 'e' || c == 'i' || c == 'o' || c == 'u' || c == 'y')
    return 1;
  return 0;
}
long double getDistance(long double x1, long double y1, long double x2,
                        long double y2) {
  return sqrt((x1 - x2) * (x1 - x2) + (y1 - y2) * (y1 - y2));
}
long long mod = 1000000009;
long long power(long long base, long long p) {
  if (p == 1) return base;
  if (!p) return 1ll;
  long long ret = power(base, p / 2);
  ret *= ret;
  ret %= mod;
  if (p & 1) ret *= base;
  return ret % mod;
}
long long extended_euclidean(long long a, long long b, long long &x,
                             long long &y) {
  if (b == 0) {
    x = 1;
    y = 0;
    return a;
  }
  long long g = extended_euclidean(b, a % b, y, x);
  y -= (a / b) * x;
  return g;
}
struct triple {
  int x, r, idx;
  triple(int a, int y, int z) {
    x = a;
    r = y;
    idx = z;
  }
  triple() { ; }
};
bool operator<(triple a, triple b) {
  if (a.x != b.x) return a.x < b.x;
  if (a.r != b.r) return a.r < b.r;
  return 1;
}
const int N = 10002;
vector<triple> v[10005];
int n, k, bit[400000], counter = 1;
triple a[100005];
vector<int> rnk;
map<int, int> mp;
int sol[100005];
int get(int idx) {
  int ret = 0;
  while (idx > 0) {
    ret += bit[idx];
    idx -= idx & -idx;
  }
  return ret;
}
void update(int idx, int val) {
  while (idx <= counter) {
    bit[idx] += val;
    idx += idx & -idx;
  }
}
long long all[100001][3];
void solve(int idx) {
  if (v[idx].empty()) return;
  int l = max(0, idx - k);
  int r = min(10000, idx + k);
  vector<triple> updates;
  for (int i = (l); i <= (r); ++i) {
    for (int j = (0); j <= ((int)v[i].size() - 1); ++j) {
      int x = v[i][j].x, r = v[i][j].r, pos = v[i][j].idx;
      updates.push_back(triple(all[pos][0], 1, all[pos][1]));
      updates.push_back(triple(all[pos][2] + 1, -1, all[pos][1]));
      if (idx == i) {
        updates.push_back(triple(all[pos][1], 2, v[i][j].idx));
      }
    }
  }
  sort(updates.begin(), updates.end());
  for (int i = (0); i <= ((int)updates.size() - 1); ++i) {
    if (updates[i].r == 2) {
      int pos = updates[i].idx;
      int x = a[pos].x;
      r = a[pos].r;
      sol[pos] = get(all[pos][2]) - get(all[pos][0] - 1) - 1;
    } else {
      update(updates[i].idx, updates[i].r);
    }
  }
}
int main() {
  scanf("%d", &n);
  scanf("%d", &k);
  set<int> st;
  for (int i = (0); i <= (n - 1); ++i) {
    int f;
    scanf("%d %d %d", &a[i].x, &a[i].r, &f);
    a[i].idx = i;
    v[f].push_back(a[i]);
    st.insert(a[i].x);
    st.insert(a[i].x + a[i].r);
    st.insert(a[i].x - a[i].r);
  }
  rnk.assign(st.begin(), st.end());
  for (int i = (0); i <= (rnk.size() - 1); ++i) mp[rnk[i]] = counter++;
  for (int i = (0); i <= (n - 1); ++i) {
    all[i][0] = mp[a[i].x - a[i].r];
    all[i][1] = mp[a[i].x];
    all[i][2] = mp[a[i].x + a[i].r];
  }
  for (int i = (0); i <= (10000); ++i) {
    solve(i);
  }
  long long sum = 0;
  for (int i = (0); i <= (n - 1); ++i) {
    sum += sol[i];
  }
  cout << sum / 2;
  return 0;
}
