Problem 1
在小于10的自然数中,3或5的倍数有3、5、6和9,这些数之和是23。求小于1000的自然数中所有3或5的倍数之和。
分析:找出3的倍数之和和5的倍数之和再减去它们的最小公倍数之和即可
#include<bits/stdc++.h>
using namespace std;
int main() {
int sum3 = (3 + 999) * 333 / 2;
int sum5 = (5 + 995) * 199 / 2;
int sum15 = (15 + 990) * 66 / 2;
cout << (sum3 + sum5 - sum15) << "\n";
return 0;
}
Problem 2
斐波那契数列中的每一项都是前两项的和。由1和2开始生成的斐波那契数列的前10项为:
1,2,3,5,8,13,21,34,55,89,…
考虑该斐波那契数列中不超过四百万的项,求其中为偶数的项之和。
分析:考虑到只用求偶数我们直接暴力即可
#include<bits/stdc++.h>
using namespace std;
int main() {
int first = 1, second = 2;
int tmp = 0, ans = 2;
while (tmp < 4000000) {
tmp = first + second;
if (tmp % 2 == 0 && tmp < 4000000) {
ans += tmp;
}
first = second;
second = tmp;
}
cout << ans << "\n";
return 0;
}
Problem 3
13195的质因数包括5、7、13和29。600851475143的最大质因数是多少?
分析:sqrt(600851475143)不是很大,故可以直接暴力
#include<bits/stdc++.h>
using namespace std;
bool isprime(long long x) {
for (long long i = 2; i * i <= x; ++i) {
if (x % i == 0) {
return false;
}
}
return true;
}
int main() {
long long ans = 2;
for (long long i = 2; i * i <= 600851475143; ++i) {
if (600851475143 % i == 0 && isprime(i)) {
ans = max(ans, i);
}
}
cout << ans << "\n";
return 0;
}
Problem 4
回文数就是从前往后读和从后往前读都一样的数。由两个2位数相乘得到的最大的回文数是
9009 = 91 x 99求由两个3位数相乘得到的最大的回文数。
分析:字符串瞎搞都行
#include<bits/stdc++.h>
using namespace std;
int main() {
int ans = 0;
for (int i = 100; i <= 999; ++i) {
for (int j = 100; j <= 999; ++j) {
int x = i * j;
string s = to_string(x);
string hs = s;
reverse(hs.begin(), hs.end());
if (s == hs) {
ans = max(ans, x);
}
}
}
cout << ans << endl;
return 0;
}
Problem 5
2520是最小的能够被1到10整除的数。最小的能够被1到20整除的正数是多少?
分析:写一个计算lcm的函数,依次计算1到20的lcm即可
#include<bits/stdc++.h>
using namespace std;
long long lcm(long long a, long long b) {
long long big = max(a, b);
long long small = min(a, b);
long long Max = a * b;
for (long long i = big; i < Max; i += big) {
if (i % small == 0)
return i;
}
return Max;
}
int main() {
long long ans, a = 1, b = 2;
while (b != 20) {
ans = lcm(a, b);
a = ans;
b++;
}
cout << ans << endl;
return 0;
}
Problem 6
前十个自然数的平方的和是
12+22+…+102=385
前十个自然数的和的平方是
(1+2+…+10)2=552=3025
因此,前十个数的平方的和与和的平方之差是3025−385=2640。
求前一百个数的平方的和与和的平方之差。
分析:
用公式只有O(1)的复杂度
#include<bits/stdc++.h>
using namespace std;
int main() {
int n = 100;
cout << -((n * (n + 1) * (2 * n + 1) / 6) - (n * (n + 1) / 2) * (n * (n + 1) / 2)) << "\n";
return 0;
}
Problem 7
第10001个质数
前6个质数分别是2、3、5、7、11和13。
第10 001个质数是多少?
分析:线性筛玩一玩,反正数据量也不大~
#include<bits/stdc++.h>
using namespace std;
#define int long long
const int maxn = 2e6 + 10;
bool a[maxn];
int b[maxn];
signed main() {
memset(a, true, sizeof(a));
memset(b, 0, sizeof(b));
a[1] =false;
int n = 120000;
int k = 1;
for (int i = 2; i <= n; ++i) {
if (a[i]) b[k++] = i;
for (int j = 1; j <= k && i * b[j] <= n; ++j) {
a[i * b[j]] = false;
if (i % b[j] == 0) break;
}
}
/*for (int i = 9000; i <= 10000; ++i) {
cout << b[i] << " ";
}
cout << "\n";*/
cout << b[10001] << "\n";
return 0;
}
Problem 8
在如下的1000位数中,连续四个数字的最大乘积是 9×9×8×9=5832。
73167176531330624919225119674426574742355349194934 96983520312774506326239578318016984801869478851843 85861560789112949495459501737958331952853208805511 12540698747158523863050715693290963295227443043557 66896648950445244523161731856403098711121722383113 62229893423380308135336276614282806444486645238749 30358907296290491560440772390713810515859307960866 70172427121883998797908792274921901699720888093776 65727333001053367881220235421809751254540594752243 52584907711670556013604839586446706324415722155397 53697817977846174064955149290862569321978468622482 83972241375657056057490261407972968652414535100474 82166370484403199890008895243450658541227588666881 16427171479924442928230863465674813919123162824586 17866458359124566529476545682848912883142607690042 24219022671055626321111109370544217506941658960408 07198403850962455444362981230987879927244284909188 84580156166097919133875499200524063689912560717606 05886116467109405077541002256983155200055935729725 71636269561882670428252483600823257530420752963450
求这个1000位数中连续十三个数字的最大乘积。
分析:
数据量不大,暴力即可
#include<bits/stdc++.h>
using namespace std;
#define int long long
signed main() {
string s; cin >> s;
int ans = - 1;
for (int i = 0; i < s.size() - 12; ++i) {
int tmp = 1;
for (int j = i; j <= i + 12; ++j) {
tmp *= (int)(s[j] - '0');
}
ans = max(ans, tmp);
}
cout << ans << "\n";
return 0;
}
Problem 9
特殊毕达哥拉斯三元组
毕达哥拉斯三元组由三个自然数a<b<c组成,并满足
有且只有一个毕达哥拉斯三元组满足 a+b+c=1000。求这个三元组的乘积abc。
分析:
直接暴力,最多也才1e6
#include<bits/stdc++.h>
using namespace std;
#define int long long
signed main() {
int ans = 1;
for (int i = 1; i <= 1000; ++i) {
for (int j = 1; j <= 1000; ++j) {
int tmp = 1000 - i - j;
if (tmp * tmp == i * i + j * j) {
cout << i << " " << j << " " << tmp << "\n";
cout << i * j * tmp << "\n";
return 0;
}
}
}
return 0;
}
Problem 10
质数求和
所有小于10的质数的和是 2 + 3 + 5 + 7 = 17 。
求所有小于两百万的质数的和。
分析:
暴力即可
Code
#include<bits/stdc++.h>
using namespace std;
#define int long long
bool isprime(int n) {
for (int i = 2; i * i <= n; ++i) {
if (n % i == 0) return false;
}
return true;
}
signed main() {
int ans = 0;
for (int i = 2; i <= 2000000; ++i) {
if (isprime(i)) {
ans += i;
}
}
cout << ans << "\n";
return 0;
}