各类算法笔试题汇总

1. 假设某卡牌类游戏里面,你搜集了 17 种卡牌,每种卡牌的攻击伤害率从小到大排列分别 为 1,4,9,… ,289,即 n 的平方(1<=n<=17,n 为正整数),并且每种卡牌的数量足够 多,现在请你计算出有多少种卡牌组合方式使得卡牌的总攻击率为 m(m<=500)比如 m=10, 那么有 4 种组合卡牌的方式,相同种卡牌可重复出现; 


【分析】 此类问题属于组合计数问题,在组合数学中,最经典的问题就是给定n个不同类型的砝码(单个类型的砝码数不固定),求当给定一个值时,求解能够完成称重的所有组合数。而此类问题一般可通过“生成函数(母函数)”的方法来解决。但这种方法再实际编程过程中,往往需要求解出一个通向式。故在此,我们将选取另一种方法来解决该问题。


首先,定义函数:   findNumber(E,n,energy)  , 其中 n = Math.sqrt(E) ; 该函数表示当总攻击率为E时,采用前n种卡牌进行组合,最终能达到目标的组合数。而对于上述问题,可以分解为两个子问题:①使用前n-1种选择组成E的组合数  ②至少使用第n种选择一次时组成m的组合数。 这样问题就变得迎刃而解了。采用递归的方式,将上述子问题相加即可得到最终的结果。


以下为该问题的JAVA代码:

import java.util.Scanner;
public class Main {

	public int  findNumber(int E, int n, int[] energy) {
		
		if(E == 0)
			return 1;
		if( E < 0 || n <= 0) 
			return 0;
		
		return findNumber(E, n-1, energy) + findNumber(E - energy[n], n, energy);
	}
	
	
	public static void main(String[] args) {
		
		int[] energy = new int[18];
		for(int i=0; i<energy.length; i++) {
			energy[i] = i*i; 
		}
		Scanner sc = new Scanner(System.in);
		int E = sc.nextInt();
		Main m = new Main();
		System.out.println(m.findNumber(E, (int)Math.sqrt(E), energy));
	}
}


2.题目要求:

输入: 第一行三个数n,m,k,分别表示n个数,取m个,且m个中的任意两个位置差要大于等于K,接下来一行,有n个整数,表示序列上的每个数。

输出: 最大和

 

数据范围:  n<=10000,  m<=100,m<=n


Sample Input

 4 2 2

 3 4 -5 1 

Sample Output

 5

  • 3
    点赞
  • 12
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值