Problem p00618 (C++) — buggy submission, verdict: Time Limit Exceeded

#include <algorithm>
#include <bitset>
#include <cmath>
#include <complex>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <iostream>
#include <map>
#include <queue>
#include <set>
#include <string>
#include <vector>
using namespace std;

#define REP(i, n) for (int i = 0; i < (int)n; ++i)
#define FOR(i, c)                                                              \\
  for (__typeof((c).begin()) i = (c).begin(); i != (c).end(); ++i)
#define ALL(c) (c).begin(), (c).end()
const int INF = 1 << 29;

bool visited[20];
int bitmask[20];
int memo[1 << 20];
int c[20];
int n, U;
int S, sum;
int solve() {
  if (memo[S] >= 0)
    return memo[S];
  //  cout <<bitset<4>(S) << " "  << sum << endl;
  if (sum >= U)
    return 0;
  int res = INF;
  REP(i, n) {
    if (!(S >> i & 1)) {
      if ((S & bitmask[i]) == bitmask[i]) {
        if (sum + c[i] >= U)
          return memo[S] = 1;
        else {
          S |= 1 << i;
          if (memo[S] >= 0)
            res = min(res, memo[S] + 1);
          else {
            sum += c[i];
            res = min(res, solve() + 1);
            sum -= c[i];
          }
          S ^= 1 << i;
        }
      }
    }
  }
  return memo[S] = res;
}

int main() {
  while (cin >> n >> U, n || U) {
    memset(bitmask, 0, sizeof(bitmask));
    REP(i, n) {
      int k;
      cin >> c[i] >> k;
      REP(j, k) {
        int r;
        cin >> r;
        bitmask[i] |= 1 << r;
      }
    }
    if (U == 0) { // ツつ「ツづゥツつゥツ不ツ鳴セ
      cout << 0 << endl;
      continue;
    }

    memset(visited, 0, sizeof(visited));
    memset(memo, -1, sizeof(memo));
    S = 0;
    sum = 0;
    cout << solve() << endl;
  }
}

Error: TLE

Fixed submission:

#include <algorithm>
#include <bitset>
#include <cmath>
#include <complex>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <iostream>
#include <map>
#include <queue>
#include <set>
#include <string>
#include <vector>
using namespace std;

#define REP(i, n) for (int i = 0; i < (int)n; ++i)
#define FOR(i, c)                                                              \\
  for (__typeof((c).begin()) i = (c).begin(); i != (c).end(); ++i)
#define ALL(c) (c).begin(), (c).end()
const int INF = 1 << 29;

bool visited[20];
int bitmask[20];
int memo[1 << 20];
int c[20];
int n, U;
int S, sum;
int solve() {
  if (memo[S] >= 0)
    return memo[S];
  //  cout <<bitset<4>(S) << " "  << sum << endl;
  if (sum >= U)
    return 0;
  int res = INF;
  REP(i, n) {
    if (!(S >> i & 1)) {
      if ((S & bitmask[i]) == bitmask[i]) {
        if (sum + c[i] >= U)
          return 1;
        else {
          S |= 1 << i;
          if (memo[S] >= 0)
            res = min(res, memo[S] + 1);
          else {
            sum += c[i];
            res = min(res, solve() + 1);
            sum -= c[i];
          }
          S ^= 1 << i;
        }
      }
    }
  }
  return memo[S] = res;
}

int main() {
  while (cin >> n >> U, n || U) {
    memset(bitmask, 0, sizeof(bitmask));
    REP(i, n) {
      int k;
      cin >> c[i] >> k;
      REP(j, k) {
        int r;
        cin >> r;
        bitmask[i] |= 1 << r;
      }
    }

    memset(visited, 0, sizeof(visited));
    memset(memo, -1, sizeof(memo));
    S = 0;
    sum = 0;
    cout << solve() << endl;
  }
}