途灵编程•目标和•解题报告

目标和

题目描述

给你一个整数数组 a 和一个整数 t 。

向数组中的每个整数前添加 ‘+’ 或 ‘-’ ,然后串联起所有整数,可以构造一个 表达式 :

例如,a = {2, 1} ,可以在 2 之前添加 ‘+’ ,在 1 之前添加 ‘-’ ,然后串联起来得到表达式 “+2-1” 。

输出 通过上述方法构造的、运算结果等于 t 的不同 表达式 的数目。

输入格式
第一行,n

第二行,数组 a 的 n 个整数

第三行,t

输出格式
结果等于 t 的 表达式 数目

样例
输入样例:

5
1 1 1 1 1
3

输出样例:

5

样例解释: 一共有 5 种方法让最终目标和为 3 。

-1 + 1 + 1 + 1 + 1 = 3
+1 - 1 + 1 + 1 + 1 = 3
+1 + 1 - 1 + 1 + 1 = 3
+1 + 1 + 1 - 1 + 1 = 3
+1 + 1 + 1 + 1 - 1 = 3

数据范围与提示
1 <= n <= 20
0 <= a[i] <= 1000
0 <= a数组所有元素之和 <= 1000
-1000 <= t <= 1000

解题分析

这道题可理解为:枚举n个位置上运算符(+或-),可转换为枚举n个0或1(二进制数 00…00 ~ 11…11),即十进制整数0 ~ 2 n − 1 2^n-1 2n1

int main() {    
    int n;
    cin>>n;
    int a[20];
    for (int i = 0; i < n; i++) 
		cin>>a[i];
    int t;
    cin>>t;
    int s = 0;
    for (int i = 0; i < (1 << n); i++) {   // 整数i:0 ~ 2^n - 1。 (1 << n) 表示 2^n
        bitset<20> b(i);   // 将i转换为二进制数b:00...00 ~ 11...11
        int w = 0;
        for (int j = 0; j < n; j++) {
            if (b[j] == 0)   // 0表示-号
                w = w - a[j];
            else   // 1表示+号
                w = w + a[j];
        }
        if (w == t)
            s++;
    }
    cout << s;
    return 0;
}
  • 11
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
回溯法是一种解决问题的算法思想,它通常用于求解在一组可能的解中找到满足特定条件的解。回溯法的基本思想是在搜索过程中寻找问题的解,当发现当前的解不能满足要求时,回溯到上一步进行新的尝试。 回溯法的解题步骤如下: 1. 确定解空间:首先明确问题的解空间,即在哪些范围内搜索解。例如,在一个迷宫中搜索一条从起点到终点的路径,这里的解空间就是所有可能的路径。 2. 确定约束条件:对解的可行性进行限制,即确定问题的约束条件。例如,在迷宫问题中,路径必须是连续的、不能穿过障碍物等。 3. 确定搜索方式:根据问题的特点确定搜索方式。对于深度优先搜索,从起点开始向某个方向搜索,搜索到死路或找到终点时回溯到上一个节点继续搜索;对于广度优先搜索,从起点开始向周围扩展,记录所有可行解并逐层扩展。 4. 递归实现:通过递归实现回溯算法,根据搜索方式进行搜索,直到找到问题的解或者搜索完整个解空间。 5. 剪枝优化:在搜索过程中,可以通过剪枝操作来减少搜索的时间和空间复杂度,即对已经搜索的路径进行判断,如果不可能满足约束条件就不继续搜索。 6. 输出结果:当找到问题的解时,将其输出。 需要注意的是,回溯法的时间复杂度往往比较高,因此需要合理地进行剪枝和优化。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值