Problem:
上司のおごり
会津太郎さんの会社には、割り切れない事が大嫌いな上司がいます。太郎さんがその上司と食事に行くときは、割り勘で会計をしているのですが、支払金額が参加人数で割り切れないときは、いつも上司がおごってくれています。
ある日、太郎さんは食事会の幹事になりました。お金の少ない太郎さんは、その上司を誘ってなんとかおごってもらえるように出来ないか考えました。もう料理屋に注文をしなければならないのですが、まだ何人参加するかは分からないので、どんな人数が参加してもおごってもらえるような注文をしておきたいようです。太郎さんの同期で、同じく食事会に参加する予定のあなたは、太郎さんに協力して、予算額以下で最大のどんな人数でも割り切れない金額を算出することにしました。
料理の種類、各料理の料金、予算額を入力とし、予算額以下で最大のどんな数字でも割り切れない合計金額(ただし、 1 と合計金額は除く)を出力するプログラムを作成してください。なお、各種類の料理は複数個注文できますが、全種類の料理を注文する必要はありません。ただし、このような合計金額がない場合は、 NA と出力してください。
Input
複数のデータセットの並びが入力として与えられます。  入力の終わりはゼロふたつの行で示されます。
各データセットは以下の形式で与えられます。
n
x
v
1
v
2
:
v
n
1 行目に料理の種類
n
(1 ≤
n
≤ 30) と予算額
x
(1 ≤
x
≤ 1000000) が空白区切りで与えられます。続く
n
行に
i
種類目の料理の金額を表す整数
v
i
(1 ≤
v
i
≤ 1000000) が与えられます。
データセットの数は 100 を超えません。
Output
入力データセットごとに、予算額に最も近い合計金額、または NA を１行に出力します。
Sample Input
4 15000
305
260
129
500
3 400
10
20
30
3 200909
5
9
12
0 0
Output for the Sample Input
14983
NA
200909

Submitted solutions:

code_snippet: #pragma GCC optimize("Ofast")
#include <bits/stdc++.h>
using namespace std;
typedef long long int ll;
typedef unsigned long long int ull;

mt19937_64 rng(chrono::steady_clock::now().time_since_epoch().count());
ll myRand(ll B) { return (ull)rng() % B; }

const int N = 10000000;
bool f[N];

int main() {
    ios::sync_with_stdio(false);
    cin.tie(nullptr);
    f[0] = f[1] = true;
    for (int i = 2; i < N; i++) {
        if (f[i]) continue;
        for (int j = i + i; j < N; j += i) {
            f[j] = true;
        }
    }
    int n, x;
    while (cin >> n >> x, n) {
        vector<int> a(n);
        for (int i = 0; i < n; i++) {
            cin >> a[i];
        }
        vector<bool> dp(x + 1, false);
        dp[0] = true;
        for (int i = 0; i < n; i++) {
            for (int j = 0; j <= x - a[i]; j++) {
                if (dp[j]) dp[j + a[i]] = true;
            }
        }
        int res = -1;
        for (int i = x; i >= 0; i--) {
            if (dp[i] and !f[i]) {
                res = i;
                break;
            }
        }
        if (res == -1) {
            cout << "NA" << endl;
        } else {
            cout << res << endl;
        }
    }
}
accuracy: 1
time_ms: 570
memory_kb: 13268
final_rank: 17

code_snippet: #include <iostream>
#include <algorithm>
#include <vector>
using namespace std;
int n, x;
vector<int> a(30);
vector<bool> dp(1000001), prime(1000001);

void generate_primes() {
  prime[0] = true, prime[2] = true;
  for (int i = 3; i <= 1000000; i += 2)
    prime[i] = true;
  for (int i = 3; i <= 1000; i++) {
    if (!prime[i])
      continue;
    for (int j = i; i * j <= 1000000; j += 2)
      prime[i * j] = false;
  }
}

int main() {
  generate_primes();
  while (cin >> n >> x, n) {
    for (int i = 0; i < n; i++)
      cin >> a[i];
    sort(a.begin(), a.begin() + n);
    if (x >= dp.size()) dp.resize(x+1);
    fill(dp.begin(), dp.begin() + x + 1, false);
    dp[0] = true;
    for (int i = 1; i <= x; i++) {
      for (int j = 0; j < n && i >= a[j]; j++) {
        if (dp[i - a[j]]) {
          dp[i] = true;
          break;
        }
      }
    }
    for (int i = x; i >= 0; i--) {
      if (dp[i] && prime[i]) {
        cout << (i ? to_string(i) : "NA") << '\n';
        break;
      }
    }
  }
}
accuracy: 1
time_ms: 310
memory_kb: 3736
final_rank: 9

code_snippet: #include <algorithm>
#include <stdio.h>
using namespace std;

int n, x, a[30];
bool dp[1000001], prime[1000001];

// Function to calculate prime numbers
void calculate_primes() {
  prime[0] = true, prime[2] = true;
  for (int i = 3; i <= 1000000; i += 2)
    prime[i] = true;
  for (int i = 3; i <= 1000; i++) {
    if (!prime[i])
      continue;
    for (int j = i; i * j <= 1000000; j += 2)
      prime[i * j] = false;
  }
}

int main() {
  calculate_primes(); // Calculate primes once
  while (scanf("%d%d", &n, &x), n) {
    for (int i = 0; i < n; i++)
      scanf("%d", &a[i]);
    sort(a, a + n);
    for (int i = 0; i < x; i++)
      dp[i + 1] = false;
    dp[0] = true;
    for (int i = 1; i <= x; i++) {
      for (int j = 0; j < n && i >= a[j]; j++) {
        if (dp[i - a[j]]) {
          dp[i] = true;
          break;
        }
      }
    }
    for (int i = x; i >= 0; i--) {
      if (dp[i] && prime[i]) {
        printf(i ? "%d\n" : "NA\n", i);
        break;
      }
    }
  }
}
accuracy: 1
time_ms: 290
memory_kb: 4924
final_rank: 10

code_snippet: #include <algorithm>
#include <bitset>
#include <stdio.h>
using namespace std;
int n, x, a[30];
bitset<1000001> prime;
bool dp[1000001];
int main() {
  prime[0] = true, prime[2] = true;
  for (int i = 3; i <= 1000000; i += 2)
    prime[i] = true;
  for (int i = 3; i <= 1000; i++) {
    if (!prime[i])
      continue;
    for (int j = i; i * j <= 1000000; j += 2)
      prime[i * j] = false;
  }
  while (scanf("%d%d", &n, &x), n) {
    for (int i = 0; i < n; i++)
      scanf("%d", &a[i]);
    sort(a, a + n);
    for (int i = 0; i < x; i++)
      dp[i + 1] = false;
    dp[0] = true;
    for (int i = 1; i <= x; i++) {
      for (int j = 0; j < n && i >= a[j]; j++) {
        if (dp[i - a[j]]) {
          dp[i] = true;
          break;
        }
      }
    }
    for (int i = x; i >= 0; i--) {
      if (dp[i] && prime[i]) {
        printf(i ? "%d\n" : "NA\n", i);
        break;
      }
    }
  }
}
accuracy: 1
time_ms: 290
memory_kb: 3892
final_rank: 4

code_snippet: #include <algorithm>
#include <stdio.h>
#include <string.h>
using namespace std;
int n, x, a[30];
bool dp[1000001], prime[1000001];
int main() {
  memset(prime, false, sizeof(prime));
  prime[0] = true, prime[2] = true;
  for (int i = 3; i <= 1000000; i += 2)
    prime[i] = true;
  for (int i = 3; i * i <= 1000000; i += 2) {
    if (!prime[i])
      continue;
    for (int j = i * i; j <= 1000000; j += i * 2)
      prime[j] = false;
  }
  while (scanf("%d%d", &n, &x), n) {
    for (int i = 0; i < n; i++)
      scanf("%d", &a[i]);
    sort(a, a + n);
    memset(dp, false, sizeof(dp));
    dp[0] = true;
    for (int i = 1; i <= x; i++) {
      for (int j = 0; j < n && i >= a[j]; j++) {
        if (dp[i - a[j]]) {
          dp[i] = true;
          break;
        }
      }
    }
    for (int i = x; i >= 0; i--) {
      if (prime[i] && dp[i]) {
        printf(i ? "%d\n" : "NA\n", i);
        break;
      }
    }
  }
}
accuracy: 1
time_ms: 250
memory_kb: 4896
final_rank: 1

code_snippet: #include <bits/stdc++.h>

using namespace std;

using LL = long long;
using VI = vector<int>;
using VVI = vector<VI>;
using VL = vector<LL>;

vector<bool> GetPrimes(const int N) {
    vector<bool> is_p(N + 1, true);  // 素数表

    is_p[0] = is_p[1] = false;
    for (int i = 2; i * i <= N; ++i) {
        if (is_p[i]) {
            for (int j = 2; i * j <= N; ++j) {
                is_p[i * j] = false;
            }
        }
    }
    return is_p;
}

int main() {
    vector<bool> p = GetPrimes(1000000);
    int n, x;
    while (true) {
        cin >> n >> x;
        if (n == 0 && x == 0) break;
        VI items(n);
        for (int i = 0; i < n; ++i) cin >> items[i];
        VVI dp(n, VI(x + 1, 0));
        for (int i = items[0]; i <= x; i += items[0]) dp[0][i] = 1;
        for (int i = 0; i < n; ++i) dp[i][0] = 1;
        for (int i = 1; i < n; ++i) {
            for (int j = 1; j <= x; ++j) {
                if (j < items[i]) {
                    dp[i][j] = dp[i - 1][j];
                } else {
                    dp[i][j] = (dp[i - 1][j] | dp[i][j - items[i]]);
                }
            }
        }
        bool flg = false;
        for (int i = x; i >= 2; --i) {
            if (p[i] && dp[n - 1][i]) {
                cout << i << endl;
                flg = true;
                break;
            }
        }
        if (!flg) cout << "NA" << endl;
    }
    return 0;
}
accuracy: 1
time_ms: 1750
memory_kb: 124008
final_rank: 19

code_snippet: #include <bits/stdc++.h>

using namespace std;

using LL = long long;
using VI = vector<int>;
using VVI = vector<VI>;
using VL = vector<LL>;

vector<bool> GetPrimes(const int N) {
    vector<bool> is_p(N + 1, true);  // 素数表

    is_p[0] = is_p[1] = false;
    for (int i = 2; i * i <= N; ++i) {
        if (is_p[i]) {
            for (int j = 2; i * j <= N; ++j) {
                is_p[i * j] = false;
            }
        }
    }
    return is_p;
}

int main() {
    vector<bool> p = GetPrimes(1000000);
    int n, x;
    while (true) {
        cin >> n >> x;
        if (n == 0 && x == 0) break;
        VI items(n);
        for (int i = 0; i < n; ++i) cin >> items[i];
        VVI dp(n, VI(x + 1, 0));
        for (int i = items[0]; i <= x; i += items[0]) dp[0][i] = 1;
        for (int i = 0; i < n; ++i) dp[i][0] = 1;
        for (int i = 1; i < n; ++i) {
            for (int j = 1; j <= x; ++j) {
                if (j < items[i]) {
                    dp[i][j] = dp[i - 1][j];
                } else {
                    dp[i][j] = (dp[i - 1][j] || dp[i][j - items[i]]);
                }
            }
        }
        bool flg = false;
        for (int i = x; i >= 2; --i) {
            if (p[i] && dp[n - 1][i] == 1) {
                cout << i << endl;
                flg = true;
                break;
            }
        }
        if (!flg) cout << "NA" << endl;
    }
    return 0;
}
accuracy: 1
time_ms: 2300
memory_kb: 124120
final_rank: 20

code_snippet: #include <algorithm>
#include <stdio.h>
using namespace std;
int n, x, a[30];
bool dp[1000001], prime[1000001];
int main() {
  fill(prime, prime+1000001, true);
  prime[0] = prime[1] = false;
  for (int i = 2; i*i <= 1000000; i++) {
    if (prime[i]) {
      for (int j = i*i; j <= 1000000; j += i)
        prime[j] = false;
    }
  }
  while (scanf("%d%d", &n, &x), n) {
    for (int i = 0; i < n; i++)
      scanf("%d", &a[i]);
    sort(a, a + n);
    fill(dp, dp+x+1, false);
    dp[0] = true;
    for (int i = 0; i < n; i++)
      for (int j = a[i]; j <= x; j++)
        dp[j] = dp[j] || dp[j - a[i]];

    int i = x;
    while (i > 0 && (!dp[i] || !prime[i])) i--;
    printf(i ? "%d\n" : "NA\n", i);
  }
}
accuracy: 1
time_ms: 460
memory_kb: 4876
final_rank: 15

code_snippet: #include <algorithm>
#include <stdio.h>
#define MAX_NUM 1000001
using namespace std;
int n, x, a[30];
bool dp[MAX_NUM], prime[MAX_NUM];
int main() {
  fill_n(prime, MAX_NUM, true);
  prime[0] = prime[1] = false;
  for (int i = 2; i * i <= MAX_NUM; i++) {
    if (!prime[i]) continue;
    for (int j = i * i; j <= MAX_NUM; j += i)
      prime[j] = false;
  }
  while (scanf("%d%d", &n, &x), n) {
    for (int i = 0; i < n; i++)
      scanf("%d", &a[i]);
    sort(a, a + n);
    fill_n(dp, x+1, false);
    dp[0] = true;
    for (int i = 1; i <= x; i++) {
      for (int j = 0; j < n && i >= a[j]; j++) {
        if (dp[i - a[j]]) {
          dp[i] = true;
          break;
        }
      }
    }
    int i;
    for (i = x; i >= 0; i--) {
      if (dp[i] && prime[i]) {
        printf("%d\n", i);
        break;
      }
    }
    if(i < 0) printf("NA\n");
  }
}
accuracy: 1
time_ms: 310
memory_kb: 4680
final_rank: 14

code_snippet: #include <algorithm>
#include <stdio.h>
using namespace std;
int n, x, a[30];
bool dp[1000001], prime[1000001];
void sieve() {
    fill(prime, prime+1000001, true);
    prime[0] = prime[1] = false;
    for (int p=2; p*p<=1000000; p++) {
        if (prime[p]) {
            for (int i=p*p; i<=1000000; i += p)
                prime[i] = false;
        }
    }
}
int main() {
    sieve();
    while (scanf("%d%d", &n, &x), n) {
        for (int i = 0; i < n; i++)
            scanf("%d", &a[i]);
        sort(a, a + n);
        fill(dp, dp+x+1, false);
        dp[0] = true;
        for (int i = 1; i <= x; i++) {
            for (int j = 0; j < n && a[j] <= i; j++) {
                if (dp[i - a[j]]) {
                    dp[i] = true;
                    break;
                }
            }
        }
        for (int i = x; i >= 0; i--) {
            if (dp[i] && prime[i]) {
                printf("%d\n", i);
                break;
            }
            else if (i == 0)
                printf("NA\n");
        }
    }
}
accuracy: 1
time_ms: 300
memory_kb: 4960
final_rank: 13

code_snippet: #include <algorithm>
#include <stdio.h>
using namespace std;
int n, x, a[30];
bool dp[1000001], prime[1000001];
int main() {
  prime[0] = true, prime[2] = true;
  for (int i = 3; i <= 1000000; i += 2)
    prime[i] = true;
  for (int i = 3; i <= 1000; i++) {
    if (!prime[i])
      continue;
    for (int j = i; i * j <= 1000000; j++)
      prime[i * j] = false;
  }
  while (scanf("%d%d", &n, &x), n) {
    for (int i = 0; i < n; i++)
      scanf("%d", &a[i]);
    sort(a, a + n);
    for (int i = 0; i < x; i++)
      dp[i + 1] = false;
    dp[0] = true;
    for (int i = 1; i <= x; i++) {
      for (int j = 0; j < n && i >= a[j]; j++) {
        if (dp[i - a[j]]) {
          dp[i] = true;
          break;
        }
      }
    }
    for (int i = x; i >= 0; i--) {
      if (dp[i] && prime[i]) {
        printf(i ? "%d\n" : "NA\n", i);
        break;
      }
    }
  }
}
accuracy: 1
time_ms: 290
memory_kb: 4904
final_rank: 8

code_snippet: #include <algorithm>
#include <stdio.h>
using namespace std;
int n, x, a[30];
bool dp[1000001], prime[1000001];
int main() {
  prime[0] = true, prime[2] = true;
  for (int i = 3; i <= 1000000; i += 2)
    prime[i] = true;
  for (int i = 3; i <= 1000; i++) {
    if (!prime[i])
      continue;
    for (int j = i; i * j <= 1000000; j += 2)
      prime[i * j] = false;
  }
  while (scanf("%d%d", &n, &x), n) {
    for (int i = 0; i < n; i++)
      scanf("%d", &a[i]);
    sort(a, a + n);
    for (int i = 0; i < x; i++)
      dp[i + 1] = false;
    dp[0] = true;
    for (int i = 1; i <= x; i++) {
      for (int j = 0; j < n && i >= a[j]; j++) {
        if (dp[i - a[j]]) {
          dp[i] = true;
          break;
        }
      }
    }
    for (int i = x; i >= 0; i--) {
      if (dp[i] && prime[i]) {
        printf(i ? "%d\n" : "NA\n", i);
        break;
      }
    }
  }
}
accuracy: 1
time_ms: 280
memory_kb: 4756
final_rank: 5

code_snippet: #include <algorithm>
#include <stdio.h>
using namespace std;
int n, x, a[30];
bool dp[1000001], prime[1000001];
int main() {
  prime[0] = true;
  for (int i = 3; i <= 1000000; i += 2)
    prime[i] = true;
  for (int i = 3; i <= 1000; i++) {
    if (!prime[i])
      continue;
    for (int j = i; i * j <= 1000000; j += 2)
      prime[i * j] = false;
  }
  while (scanf("%d%d", &n, &x), n) {
    for (int i = 0; i < n; i++)
      scanf("%d", &a[i]);
    sort(a, a + n);
    for (int i = 0; i < x; i++)
      dp[i + 1] = false;
    dp[0] = true;
    for (int i = 1; i <= x; i++) {
      for (int j = 0; j < n && i >= a[j]; j++) {
        if (dp[i - a[j]]) {
          dp[i] = true;
          break;
        }
      }
    }
    for (int i = x; i >= 0; i--) {
      if (dp[i] && prime[i]) {
        printf(i ? "%d\n" : "NA\n", i);
        break;
      }
    }
  }
}
accuracy: 1
time_ms: 290
memory_kb: 4896
final_rank: 7

code_snippet: #include <algorithm>
#include <stdio.h>
using namespace std;
int n, x, a[30];
bool dp[1000001], prime[1000001];
int main() {
  prime[0] = true, prime[2] = true;
  for (int i = 3; i <= 1000000; i += 2)
    prime[i] = true;
  for (int i = 3; i <= 1000; i += 2) { // Only check odd numbers
    if (prime[i]) {
      for (int j = i * i; j <= 1000000; j += i * 2) // Start from i^2 instead of i and increment by i * 2
        prime[j] = false;
    }
  }
  while (scanf("%d%d", &n, &x), n) {
    for (int i = 0; i < n; i++)
      scanf("%d", &a[i]);
    sort(a, a + n);
    for (int i = 0; i < x; i++)
      dp[i + 1] = false;
    dp[0] = true;
    for (int i = 1; i <= x; i++) {
      for (int j = 0; j < n && i >= a[j]; j++) {
        if (dp[i - a[j]]) {
          dp[i] = true;
          break;
        }
      }
    }
    for (int i = x; i >= 0; i--) {
      if (dp[i] && prime[i]) {
        printf(i ? "%d\n" : "NA\n", i);
        break;
      }
    }
  }
}
accuracy: 1
time_ms: 290
memory_kb: 4668
final_rank: 6

code_snippet: #include <algorithm>
#include <stdio.h>
#include <bitset>
using namespace std;
int n, x, a[30];
bitset<1000001> dp, prime;
int main() {
  prime[0] = prime[1] = true;
  for (int i = 3; i <= 1000000; i += 2)
    prime[i] = true;
  for (int i = 3; i <= 1000; i += 2) {
    if (prime[i])
      for (int j = i * i; j <= 1000000; j += i)
        prime[j] = false;
  }
  while (scanf("%d%d", &n, &x), n) {
    for (int i = 0; i < n; i++)
      scanf("%d", &a[i]);
    sort(a, a + n);
    dp.reset();
    dp[0] = true;
    for (int i = 0; i < n; i++) {
      for (int j = a[i]; j <= x; j++) {
        dp[j] = dp[j] || dp[j - a[i]];
      }
    }
    for (int i = x; i >= 0; i--) {
      if (dp[i] && prime[i]) {
        printf(i ? "%d\n" : "NA\n", i);
        break;
      }
    }
  }
}
accuracy: 1
time_ms: 810
memory_kb: 3012
final_rank: 18

code_snippet: #include <algorithm>
#include <cstdio>
using namespace std;
int n, x, a[30];
bool dp[1000001], prime[1000001];
int main() {
  prime[0] = true, prime[2] = true;
  for (int i = 3; i <= 1000000; i += 2)
    prime[i] = true;
  for (int i = 3; i <= 1000; i += 2) {
    if (!prime[i])
      continue;
    for (int j = i * i; j <= 1000000; j += i << 1)
      prime[j] = false;
  }
  while (scanf("%d%d", &n, &x), n) {
    for (int i = 0; i < n; i++)
      scanf("%d", &a[i]);
    sort(a, a + n);
    for (int i = 0; i <= x; i++)
      dp[i] = false;
    dp[0] = true;
    for (int i = 0; i < n; i++) {
      for (int j = a[i]; j <= x; j++) {
        dp[j] |= dp[j - a[i]];
      }
    }
    for (int i = x; i >= 0; i--) {
      if (dp[i] && prime[i]) {
        printf(i ? "%d\n" : "NA\n", i);
        break;
      }
    }
  }
  return 0;
}
accuracy: 1
time_ms: 290
memory_kb: 4924
final_rank: 10

code_snippet: #include <algorithm>
#include <stdio.h>
using namespace std;
const int MAXN = 30, MAXX = 1e6 + 1;
int n, x, a[MAXN];
bool dp[MAXX], prime[MAXX];
int main() {
  prime[0] = true, prime[2] = true;
  for (int i = 3; i <= MAXX - 1; i += 2)
    prime[i] = true;
  for (int i = 3; i <= 1000; i += 2) {
    if (!prime[i])
      continue;
    for (int j = i; i * j <= MAXX - 1; j += 2)
      prime[i * j] = false;
  }
  while (scanf("%d%d", &n, &x), n) {
    for (int i = 0; i < n; i++)
      scanf("%d", &a[i]);
    sort(a, a + n);
    for (int i = 0; i <= x; i++)
      dp[i] = false;
    dp[0] = true;
    for (int i = 1; i <= x; i++) {
      if (!dp[i]) {
        for (int j = 0; j < n && a[j] <= i; j++) {
          dp[i] |= dp[i - a[j]];
        }
      }
    }
    for (int i = x; i >= 0; i--) {
      if (dp[i] && prime[i]) {
        printf(i ? "%d\n" : "NA\n", i);
        break;
      }
    }
  }
}
accuracy: 1
time_ms: 470
memory_kb: 4884
final_rank: 16

code_snippet: #include <algorithm>
#include <cstdio>
using namespace std;
const int MAX_N = 30;
const int MAX_X = 1e6;
bool dp[MAX_X + 1], prime[MAX_X + 1];
int n, x, a[MAX_N];
int main() {
  prime[0] = true, prime[2] = true;
  for (int i = 3; i <= MAX_X; i += 2)
    prime[i] = true;
  for (int i = 3; i * i <= MAX_X; i += 2) {
    if (!prime[i])
      continue;
    for (int j = i * i; j <= MAX_X; j += 2 * i)
      prime[j] = false;
  }
  while (scanf("%d%d", &n, &x), n) {
    for (int i = 0; i < n; i++)
      scanf("%d", &a[i]);
    sort(a, a + n);
    for (int i = 0; i <= x; i++)
      dp[i] = false;
    dp[0] = true;
    for (int i = 0; i < n; i++) {
      for (int j = a[i]; j <= x; j++) {
        dp[j] |= dp[j - a[i]];
      }
    }
    for (int i = x; i >= 0; i--) {
      if (dp[i] && prime[i]) {
        printf(i ? "%d\n" : "NA\n", i);
        break;
      }
    }
  }
  return 0;
}
accuracy: 1
time_ms: 290
memory_kb: 4924
final_rank: 10

code_snippet: #include <algorithm>
#include <cstdio>
#include <cstring>

using namespace std;

const int MAX_N = 30;
const int MAX_X = 1e6;

int n, x, a[MAX_N];
bool dp[MAX_X + 1], prime[MAX_X + 1];

int main()
{
    prime[0] = true, prime[2] = true;
    for (int i = 3; i <= MAX_X; i += 2)
        prime[i] = true;
    for (int i = 3; i <= 1000; i += 2)
    {
        if (!prime[i])
            continue;
        for (int j = i; i * j <= MAX_X; j += 2)
            prime[i * j] = false;
    }

    while (scanf("%d %d", &n, &x), n)
    {
        for (int i = 0; i < n; i++)
            scanf("%d", &a[i]);
        sort(a, a + n);
        memset(dp, false, sizeof(dp));
        dp[0] = true;
        for (int i = 0; i < n; i++)
        {
            for (int j = a[i]; j <= x; j++)
                dp[j] |= dp[j - a[i]];
        }
        for (int i = x; i >= 0; i--)
        {
            if (dp[i] && prime[i])
            {
                printf(i ? "%d\n" : "NA\n", i);
                break;
            }
        }
    }
    return 0;
}
accuracy: 1
time_ms: 270
memory_kb: 4904
final_rank: 3

code_snippet: #include <algorithm>
#include <cstdio>
#include <cstring>
using namespace std;
const int MAXN = 30;
const int MAXX = 1000000;
int n, x, a[MAXN];
bool dp[MAXX + 1], prime[MAXX + 1];
int main() {
  memset(prime, true, sizeof(prime));
  prime[0] = false, prime[1] = false;
  for (int i = 2; i * i <= MAXX; ++i) {
    if (prime[i]) {
      for (int j = i * i; j <= MAXX; j += i)
        prime[j] = false;
    }
  }
  while (scanf("%d%d", &n, &x), n) {
    for (int i = 0; i < n; ++i) scanf("%d", &a[i]);
    sort(a, a + n);
    memset(dp, false, sizeof(dp));
    dp[0] = true;
    for (int i = 0; i < n; ++i) {
      for (int j = a[i]; j <= x; ++j) {
        dp[j] |= dp[j - a[i]];
      }
    }
    for (int i = x; i >= 0; --i) {
      if (dp[i] && prime[i]) {
        printf("%d\n", i);
        goto end;
      }
    }
    puts("NA");
    end:;
  }
  return 0;
}
accuracy: 1
time_ms: 270
memory_kb: 4664
final_rank: 2