#include <bits/stdc++.h>
using namespace std;
long long gcd(long long a, long long b) { return b == 0 ? a : gcd(b, a % b); }
const int MAXN = 100000;
const int MAXSIGN = 5;
typedef struct Road {
  int A, B, C, idx;
} Road;
typedef struct F {
  long long num, den;
  F() { num = 0, den = 1; }
  F(long long n, long long d) {
    long long g = gcd(abs(n), abs(d));
    if (d < 0) n = -n, d = -d;
    num = n / g, den = d / g;
  }
} F;
typedef struct P {
  F x, y;
} P;
bool operator<(const F &a, const F &b) { return a.num * b.den < b.num * a.den; }
bool operator==(const F &a, const F &b) {
  return a.num == b.num && a.den == b.den;
}
bool operator<(const P &a, const P &b) {
  return a.x < b.x || a.x == b.x && a.y < b.y;
}
bool operator==(const P &a, const P &b) { return a.x == b.x && a.y == b.y; }
bool online(const P &p, const Road &u) {
  long long g = gcd(p.x.den, p.y.den);
  return u.A * p.x.num * (p.y.den / g) + u.B * p.y.num * (p.x.den / g) ==
         u.C * p.y.den * (p.x.den / g);
}
void print(const F &a) {
  printf("%lld", a.num);
  if (a.den != 1) printf("/%lld", a.den);
}
void print(const P &p) {
  printf("(");
  print(p.x);
  printf(",");
  print(p.y);
  printf(")");
}
void print(const Road &u) { printf("[%d,%d,%d]", u.A, u.B, u.C); }
bool intersect(const Road &u, const Road &v, P &p) {
  long long numx = (long long)v.C * u.B - (long long)v.B * u.C;
  long long numy = (long long)u.C * v.A - (long long)u.A * v.C;
  long long den = (long long)v.A * u.B - (long long)v.B * u.A;
  if (den == 0) {
    return false;
  } else {
    p.x = F(numx, den);
    p.y = F(numy, den);
    return true;
  }
}
vector<vector<int> > ans;
bool solve(vector<Road> road, int k) {
  int n = ((int)(road).size());
  if (n <= k) {
    for (int i = (0); i < (n); ++i) ans.push_back(vector<int>(1, road[i].idx));
    return true;
  }
  if (k == 0) return false;
  int ntest = n >= k * k + 1 ? k * k + 1 : n;
  int nwant = n >= k * k + 1 ? k + 1 : (n + k - 1) / k;
  vector<P> p;
  p.reserve(ntest * (ntest - 1) / 2);
  for (int i = (0); i < (ntest); ++i)
    for (int j = (i + 1); j < (ntest); ++j) {
      P cur;
      if (!intersect(road[i], road[j], cur)) continue;
      p.push_back(cur);
    }
  sort(p.begin(), p.end());
  p.erase(unique(p.begin(), p.end()), p.end());
  for (int i = (0); i < (((int)(p).size())); ++i) {
    int cnt = 0;
    for (int j = (0); j < (ntest); ++j)
      if (online(p[i], road[j])) ++cnt;
    if (cnt < nwant) continue;
    vector<Road> nroad;
    nroad.reserve(n);
    vector<int> onroad;
    onroad.reserve(n);
    for (int j = (0); j < (n); ++j)
      if (online(p[i], road[j]))
        onroad.push_back(road[j].idx);
      else
        nroad.push_back(road[j]);
    if (solve(nroad, k - 1)) {
      ans.push_back(onroad);
      return true;
    }
    if (n >= k * k + 1) break;
  }
  return false;
}
int n, k;
vector<Road> road;
void run() {
  scanf("%d%d", &n, &k);
  road.resize(n);
  for (int i = (0); i < (n); ++i)
    scanf("%d%d%d", &road[i].A, &road[i].B, &road[i].C), road[i].idx = i + 1;
  if (!solve(road, k)) {
    printf("NO\n");
    return;
  }
  printf("YES\n");
  printf("%d\n", ((int)(ans).size()));
  for (int i = (0); i < (((int)(ans).size())); ++i)
    if (((int)(ans[i]).size()) == 1)
      printf("%d -1\n", ans[i][0]);
    else
      printf("%d %d\n", ans[i][0], ans[i][1]);
}
int main() {
  run();
  return 0;
}
