#include <algorithm> #include <cstdio> #include <functional> #include <vector> constexpr bool kEnableLogging = false; long long global_limit; // bucket1 contains primes between 2 and 11. bucket2 contains primes between 13 // and 97. constexpr int kBucket1Lower = 2; constexpr int kBucket1Upper = 11; constexpr int kBucket2Lower = 13; constexpr int kBucket2Upper = 97; std::vector<int> bucket1, bucket2; // Smooth numbers for primes from bucket1. std::vector<long long> extra_smooth; int number_bucket2_smooth; // Highest smooth number ever encountered. long long result; void Rec(const std::vector<int>& bucket, size_t index, long long result, const std::function<void(long long)>& callback) { if (index == bucket.size()) { callback(result); return; } while (true) { Rec(bucket, index + 1, result, callback); if (global_limit / result >= bucket[index]) { result *= bucket[index]; } else { break; } } } int main() { int num_primes; scanf("%d%lld", &num_primes, &global_limit); for (int i = 0; i < num_primes; ++i) { int p; scanf("%d", &p); if (p >= kBucket1Lower && p <= kBucket1Upper) { bucket1.push_back(p); } if (p >= kBucket2Lower && p <= kBucket2Upper) { bucket2.push_back(p); } } // Generate smooth numbers for bucket1. Guaranteed not to exceed ~300k. const auto bucket1_callback = [](long long smooth) { extra_smooth.push_back(smooth); }; Rec(bucket1, 0, 1, bucket1_callback); if (kEnableLogging) { printf("Found %d extra smooth numbers.\n", extra_smooth.size()); } std::sort(extra_smooth.begin(), extra_smooth.end()); const auto bucket2_callback = [](long long smooth) { ++number_bucket2_smooth; // It is guaranteed that extra_smooth() has at least one element (1). int l = 0, u = extra_smooth.size() - 1, r = -1; while (l <= u) { int m = (l + u) / 2; if (global_limit / smooth >= extra_smooth[m]) { result = std::max(result, extra_smooth[m] * smooth); l = m + 1; } else { u = m - 1; } } }; Rec(bucket2, 0, 1, bucket2_callback); if (kEnableLogging) { printf("Found %lld smooth from bucket2.\n", number_bucket2_smooth); } printf("%lld\n", result); return 0; }
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 | #include <algorithm> #include <cstdio> #include <functional> #include <vector> constexpr bool kEnableLogging = false; long long global_limit; // bucket1 contains primes between 2 and 11. bucket2 contains primes between 13 // and 97. constexpr int kBucket1Lower = 2; constexpr int kBucket1Upper = 11; constexpr int kBucket2Lower = 13; constexpr int kBucket2Upper = 97; std::vector<int> bucket1, bucket2; // Smooth numbers for primes from bucket1. std::vector<long long> extra_smooth; int number_bucket2_smooth; // Highest smooth number ever encountered. long long result; void Rec(const std::vector<int>& bucket, size_t index, long long result, const std::function<void(long long)>& callback) { if (index == bucket.size()) { callback(result); return; } while (true) { Rec(bucket, index + 1, result, callback); if (global_limit / result >= bucket[index]) { result *= bucket[index]; } else { break; } } } int main() { int num_primes; scanf("%d%lld", &num_primes, &global_limit); for (int i = 0; i < num_primes; ++i) { int p; scanf("%d", &p); if (p >= kBucket1Lower && p <= kBucket1Upper) { bucket1.push_back(p); } if (p >= kBucket2Lower && p <= kBucket2Upper) { bucket2.push_back(p); } } // Generate smooth numbers for bucket1. Guaranteed not to exceed ~300k. const auto bucket1_callback = [](long long smooth) { extra_smooth.push_back(smooth); }; Rec(bucket1, 0, 1, bucket1_callback); if (kEnableLogging) { printf("Found %d extra smooth numbers.\n", extra_smooth.size()); } std::sort(extra_smooth.begin(), extra_smooth.end()); const auto bucket2_callback = [](long long smooth) { ++number_bucket2_smooth; // It is guaranteed that extra_smooth() has at least one element (1). int l = 0, u = extra_smooth.size() - 1, r = -1; while (l <= u) { int m = (l + u) / 2; if (global_limit / smooth >= extra_smooth[m]) { result = std::max(result, extra_smooth[m] * smooth); l = m + 1; } else { u = m - 1; } } }; Rec(bucket2, 0, 1, bucket2_callback); if (kEnableLogging) { printf("Found %lld smooth from bucket2.\n", number_bucket2_smooth); } printf("%lld\n", result); return 0; } |