PTA | 素数分解 | C++

素数,又称质数,是指除 1 和其自身之外,没有其他约数的正整数。例如 2、3、5、13 都是素数,而 4、9、12、18 则不是。
虽然素数不能分解成除 1 和其自身之外整数的乘积,但却可以分解成更多素数的和。
你需要编程 求出一个正整数最多能分解成多少个互不相同的素数的和。
例如,21 = 2 + 19是21的合法分解方法。21 = 2 + 3 + 5 + 11则是分解为最多素数的方法。
再比如:128,最多可以分解为9个素数的和。

输入格式:

n (n≤200)。

输出格式:

n 最多能分解成多少个不同的素数的和。

数据范围

对于30%的数据,n≤50

对于100%的数据,n≤200

输入样例:

21

输出样例:

4

输入样例:

128

输出样例:

9

代码及注释 

#include<bits/stdc++.h>
using namespace std;
int result=0;
bool isprime(int x)
{
    for(int k=2; k<x; k++)
    {
    	if(x%k == 0)
        {
            return false;
        }
    }
    return true;
}
void compare(const vector<int>& combination) {
    // for (int num : combination) {
    //     cout << num << " ";
    // }
    // cout << endl;
    if(combination.size()>result)
    {
        result=combination.size();
    }
}
//递归函数,找到所有加法组合
void findCombination(int end, int start, vector<int>& combination) {
    if (end== 0) {//达到目标数,输出当前组合
        compare(combination);
        return;
    }
    for (int i = start; i <= end; i++) {
        if(isprime(i))
        {
            combination.push_back(i);//加入当前数到组合中
            findCombination(end- i, i+1, combination);//递归求和
            combination.pop_back();//回溯
        }
    }
}
//主函数,找到从1到target的所有加法组合
void findAllCombination(int end) {
    vector<int> combination;
    findCombination(end, 2, combination);
}
int main()
{
    int n;
    cin>>n;
    findAllCombination(n);
    cout<<result;
}

解析

这题跟素数没多大关系了,主要是用递归和循环找到一个数以内所有的加数的组合。加入素数判断即可。

举个例子,从1到10:

初始调用

  • findAllCombination(10) 调用 findCombination(10, 1, combination)

  • combination 初始为空 []

第一次递归调用

  1. findCombination(10, 1, combination):

    • 从 i = 1 开始循环,尝试将 1 加入组合。

    • combination = [1]

    • 递归调用 findCombination(9, 2, combination)

第二次递归调用

  1. findCombination(9, 2, combination):

    • 从 i = 2 开始循环,尝试将 2 加入组合。

    • combination = [1, 2]

    • 递归调用 findCombination(7, 3, combination)

第三次递归调用

  1. findCombination(7, 3, combination):

    • 从 i = 3 开始循环,尝试将 3 加入组合。

    • combination = [1, 2, 3]

    • 递归调用 findCombinations(4, 4, combination)

第四次递归调用

  1. findCombination(4, 4, combination):

    • 从 i = 4 开始循环,尝试将 4 加入组合。

    • combination = [1, 2, 3, 4]

    • 递归调用 findCombinations(0, 5, combination)

第五次递归调用(达到目标)

  1. findCombination(0, 5, combination):

    • 因为 target == 0,达成目标数,输出组合 [1, 2, 3, 4]

    • 返回到上一级调用。

回溯并继续寻找其他组合

  1. 回到 findCombination(4, 4, combination):

    • 回溯,将 4 从组合中移除,combination = [1, 2, 3]

    • i = 5,由于 5 > 4,因此直接结束循环,返回上一级。

  2. 回到 findCombination(7, 3, combination):

    • 回溯,将 3 从组合中移除,combination = [1, 2]

    • i = 4,尝试将 4 加入组合。

    • combination = [1, 2, 4]

    • 递归调用 findCombination(3, 5, combination)

  3. 继续递归下去,直到找到所有组合。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值