Project Euler 11 ~ 15

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/jsszwc/article/details/87902865

Project Euler 11 Largest product in a grid

题目:

https://projecteuler.net/problem=11

题意:

在给定的20×20方阵中,四个在同一方向(从下至上、从上至下、从右至左、从左至右或者对角线)上相邻的数的乘积最大是多少?

思路:

检查从左到右、从上到下、主对角线、副对角线共四个方向上连续四个数的最大乘积

代码:

#include <bits/stdc++.h>

using namespace std;

const int N = 20 + 10;

int arr[N][N];

int toRight(int x, int y) {
    int val = 1;
    for(int i = 0; i < 4; i++) {
        val *= arr[x][y+i];
    }
    return val;
}

int toDown(int x, int y) {
    int val = 1;
    for(int i = 0; i < 4; i++) {
        val *= arr[x+i][y];
    }
    return val;
}

int toMainDiagonal(int x, int y) {
    int val = 1;
    for(int i = 0; i < 4; i++) {
        val *= arr[x+i][y+i];
    }
    return val;
}

int toParadiagonal(int x, int y) {
    int val = 1;
    for(int i = 0; i < 4; i++) {
        val *= arr[x+i][y-i];
    }
    return val;
}

int main() {
    int n = 20;
    //控制台读入方阵
    for(int i = 0; i < n; i++) {
        for(int j = 0; j < n; j++) {
            scanf("%d", &arr[i][j]);
        }
    }

    int ans = -1;
    for(int i = 0; i < n; i++) {
        for(int j = 0; j < n; j++) {
            if(j + 4 <= 20) {
                ans = max(ans, toRight(i, j));
            }
            if(i + 4 <= 20) {
                ans = max(ans, toDown(i, j));
            }
            if(i + 4 <= 20 && j + 4 <= 20) {
                ans = max(ans, toMainDiagonal(i, j));
            }
            if(i + 4 <= 20 && j - 4 >= -1) {
                ans = max(ans, toParadiagonal(i, j));
            }
        }
    }

    printf("%d\n", ans);

    return 0;
}

Project Euler 12 Highly divisible triangular number

题目:

https://projecteuler.net/problem=12

题意:

在这里插入图片描述

思路:

遍历三角形数,检查其约数是否符合要求,注意求约数个数时,复杂度是 O ( n ) O(\sqrt{n})

代码:

#include <bits/stdc++.h>

using namespace std;

bool check(int val) {
    int cnt = 0;
    for(int i = 2; i*i <= val; i++) {
        if(val % i == 0) {
            if(val/i == i) {
                cnt++;
            } else {
                cnt += 2;
            }
        }
    }
    return cnt > 500;
}

int main() {
    int val = 0;
    for(int i = 1; true; i++) {
        val += i;
        if(check(val)) {
            break;
        }
    }

    printf("%d\n", val);

    return 0;
}

Project Euler 13 Large sum

题目:

https://projecteuler.net/problem=13

题意:

计算出给定的一百个50位数的和的前十位数字。

思路:

大整数加法

代码:

#include <bits/stdc++.h>

using namespace std;

const int N = 100 + 10;

char str[N][N];

void add(char *s1, char *s2, char *s3) {
    int len1 = strlen(s1), len2 = strlen(s2);
    reverse(s1, s1 + len1);
    reverse(s2, s2 + len2);
    int carry = 0, len3 = 0;
    for(int i = 0; i < len1 || i < len2; i++) {
        carry += i < len1 ? s1[i]-'0' : 0;
        carry += i < len2 ? s2[i]-'0' : 0;
        s3[len3++] = char(carry%10 + '0');
        carry /= 10;
    }
    if(carry) {
        s3[len3++] = char(carry + '0');
    }
    s3[len3] = '\0';
    reverse(s1, s1 + len1);
    reverse(s2, s2 + len2);
    reverse(s3, s3 + len3);
}

int main() {
    int n = 100;
    for(int i = 0; i < n; i++) {
        scanf("%s", str[i]);
    }

    char ans[N] = {}, temp[N];
    for(int i = 0; i < n; i++) {
        add(str[i], ans, temp);
        strcpy(ans, temp);
    }

    for(int i = 0; i < 10; i++) {
        printf("%c", ans[i]);
    }

    return 0;
}

Project Euler 14 Longest Collatz sequence

题目:

https://projecteuler.net/problem=14

题意:

在这里插入图片描述

扫描二维码关注公众号,回复: 5307970 查看本文章

思路:

直接依次暴力求解每个数字的考拉兹序列项数是可以的,一个小优化就是在求的过程中,利用已知答案,减少计算量

代码:

#include <bits/stdc++.h>

using namespace std;

typedef long long LL;
const int N = 1000000 + 10;

int step[N];

int work(LL x) {
    int cnt = 1;
    while(x != 1) {
        if(x & 1) {
            x = 3 * x + 1;
        } else {
            x /= 2;
        }
        if(x < N && step[x] != -1) {
            cnt += step[x];
            break;
        }
        cnt++;
    }
    return cnt;
}

int main() {
    int n = 1000000;
    int num = -1, ans = -1;
    memset(step, -1, sizeof(step));
    for(int i = 1; i <= n; i++) {
        step[i] = work(i);
        if(step[i] > num) {
            num = step[i];
            ans = i;
        }
    }

    printf("%d\n", ans);

    return 0;
}

Project Euler 15 Lattice paths

题目:

https://projecteuler.net/problem=15

题意:

在这里插入图片描述

思路:

定义 d p [ i ] [ j ] dp[i][j] 为走到第i行第j列的点(这里是点),所有的不同路径数。因为要么从第 i 1 i-1 行第 j j 列走下来,要么从第 i i 行第j 1 -1 列走过来,那么有状态转移方程:
d p [ i ] [ j ] = d p [ i 1 ] [ j ] + d p [ i ] [ j 1 ] dp[i][j] = dp[i-1][j] + dp[i][j-1]

代码:

#include <bits/stdc++.h>

using namespace std;

typedef long long LL;
const int N = 20 + 10;

LL dp[N][N];

int main() {
    int n = 21;
    memset(dp, 0, sizeof(dp));
    for(int i = 1; i <= n; i++) {
        for(int j = 1; j <= n; j++) {
            if(i == 1 && j == 1) {
                dp[1][1] = 1;
            } else {
                dp[i][j] = dp[i][j-1] + dp[i-1][j];
            }
        }
    }

    printf("%lld\n", dp[n][n]);

    return 0;
}

猜你喜欢

转载自blog.csdn.net/jsszwc/article/details/87902865