Problem p03989 (C++)

Buggy submission (status: Time Limit Exceeded):
#include <bits/stdc++.h>
using namespace std;

typedef long long lint;
typedef long double louble;

template <typename T1, typename T2> inline T1 max(T1 a, T2 b) {
  return a < b ? b : a;
}
template <typename T1, typename T2> inline T1 min(T1 a, T2 b) {
  return a < b ? a : b;
}

namespace ae86 {
const int bufl = 1 << 15;

char buf[bufl], *s = buf, *t = buf;

inline int fetch() {
  if (s == t) {
    t = (s = buf) + fread(buf, 1, bufl, stdin);
    if (s == t)
      return EOF;
  }
  return *s++;
}

inline int ty() {
  int a = 0, b = 1, c = fetch();
  while (!isdigit(c))
    b ^= c == '-', c = fetch();
  while (isdigit(c))
    a = a * 10 + c - 48, c = fetch();
  return b ? a : -a;
}
} // namespace ae86
using ae86::ty;

const int _ = 2003, mo = 924844033;

inline lint powa(lint a, lint t) {
  lint b = 1;
  while (t) {
    if (t & 1)
      b = b * a % mo;
    a = a * a % mo, t >>= 1;
  }
  return b;
}

inline lint inva(lint a) { return powa(a, mo - 2); }

lint jc[_], rjc[_];

inline void fuck(int n = _ - 1) {
  jc[0] = jc[1] = rjc[0] = 1;
  for (int i = 2; i <= n; i++)
    jc[i] = jc[i - 1] * i % mo;
  rjc[n] = inva(jc[n]);
  for (int i = n - 1; i >= 1; i--)
    rjc[i] = rjc[i + 1] * (1ll + i) % mo;
}

inline lint C(int n, int m) {
  if (n < m || n < 0 || m < 0)
    return 0;
  return jc[n] * rjc[m] % mo * rjc[n - m] % mo;
}

int n, lim, llim;
lint f[_] = {0};

int main() {
  n = ty(), lim = ty(), llim = lim + lim;
  fuck();

  f[0] = 1;
  for (int i = 1; i <= llim && i <= n; i++) {
    int j = i;
    while (j + llim <= n)
      j += llim;
    int cnt = (j - i) / lim + (i > lim) + (j + lim <= n);
    for (int k = n; k >= 1; k--)
      for (int a = 1; a <= k; a++)
        f[k] = (f[k] + f[k - a] * C(cnt - a + 1, a) % mo) % mo;
  }

  lint ans = 0;
  for (int i = 0; i <= n; i++)
    ans = (ans + f[i] * jc[n - i] % mo * (i & 1 ? -1 : 1) + mo) % mo;
  printf("%lld\n", ans);

  return 0;
}


Fixed submission:
#include <bits/stdc++.h>
using namespace std;

typedef long long lint;
typedef long double louble;

template <typename T1, typename T2> inline T1 max(T1 a, T2 b) {
  return a < b ? b : a;
}
template <typename T1, typename T2> inline T1 min(T1 a, T2 b) {
  return a < b ? a : b;
}

namespace ae86 {
const int bufl = 1 << 15;

char buf[bufl], *s = buf, *t = buf;

inline int fetch() {
  if (s == t) {
    t = (s = buf) + fread(buf, 1, bufl, stdin);
    if (s == t)
      return EOF;
  }
  return *s++;
}

inline int ty() {
  int a = 0, b = 1, c = fetch();
  while (!isdigit(c))
    b ^= c == '-', c = fetch();
  while (isdigit(c))
    a = a * 10 + c - 48, c = fetch();
  return b ? a : -a;
}
} // namespace ae86
using ae86::ty;

const int _ = 2003, mo = 924844033;

inline lint powa(lint a, lint t) {
  lint b = 1;
  while (t) {
    if (t & 1)
      b = b * a % mo;
    a = a * a % mo, t >>= 1;
  }
  return b;
}

inline lint inva(lint a) { return powa(a, mo - 2); }

lint jc[_], rjc[_];

inline void fuck(int n = _ - 1) {
  jc[0] = jc[1] = rjc[0] = 1;
  for (int i = 2; i <= n; i++)
    jc[i] = jc[i - 1] * i % mo;
  rjc[n] = inva(jc[n]);
  for (int i = n - 1; i >= 1; i--)
    rjc[i] = rjc[i + 1] * (1ll + i) % mo;
}

inline lint C(int n, int m) {
  if (n < m || n < 0 || m < 0)
    return 0;
  return jc[n] * rjc[m] % mo * rjc[n - m] % mo;
}

int n, lim, llim;
lint f[_] = {0};

int main() {
  n = ty(), lim = ty(), llim = lim + lim;
  fuck();

  f[0] = 1;
  for (int i = 1; i <= llim && i <= n; i++) {
    int j = i;
    while (j + llim <= n)
      j += llim;
    int cnt = (j - i) / lim + (i > lim) + (j + lim <= n);
    for (int k = n; k >= 1; k--)
      for (int a = 1; a <= k && a + a - 1 <= cnt; a++)
        f[k] = (f[k] + f[k - a] * C(cnt - a + 1, a) % mo) % mo;
  }

  lint ans = 0;
  for (int i = 0; i <= n; i++)
    ans = (ans + f[i] * jc[n - i] % mo * (i & 1 ? -1 : 1) + mo) % mo;
  printf("%lld\n", ans);

  return 0;
}