问题描述:给定一个自然数n,由n开始可以依次产生半数集set(n)中的数如下:
(1)set(n)中包含n;
(2)在n的左边加上一个自然数,但该自然数不能超过最近添加的数的一半;
(3)按此规则进行处理,直至不能添加自然数为止。
例如,set(6)={6,16,26,126,36,136}。
编程任务:对于给定的自然数n,编程计算半数集set(n)中元素的个数。
通过分析所描述问题的特点可知,半数集set(n)中元素个数的求解是个递归的过程。设set(n)中的元素个数为f(n),则显然有递归表达式:
f(n)=1+∑f(i),i=1,2……n/2
普通递归实现
/**
* 问题描述:给定一个自然数n,由n开始可以依次产生半数集set(n)中的数如下: (1)set(n)中包含n;
* (2)在n的左边加上一个自然数,但该自然数不能超过最近添加的数的一半; (3)按此规则进行处理,直至不能添加自然数为止。
* 例如,set(6)={6,16,26,126,36,136}。 编程任务:对于给定的自然数n,编程计算半数集set(n)中元素的个数。
* 注意:该半数集是多重集。
*
* @author tule
*
*/
public class Main {
public static void main(String[] args) {
Scanner cin =new Scanner(System.in);
System.out.println("输入所求半数集N:");
int n =cin.nextInt();
System.out.println(halfSet(n, n+""));
}
public static int halfSet(int n, String pre) {
int ans = 1;
System.out.println(pre);
if (n > 1)
for (int i = 1; i <= n / 2; i++)
ans += halfSet(i, i + pre);
return ans;
}
}
用数组存储已知的子结果的算法:不适合输出所有结果
public class Main {
private static int[] a;
public static void main(String[] args) {
Scanner cin =new Scanner(System.in);
System.out.println("输入所求半数集N:");
int n =cin.nextInt();
a= new int[n+1];
System.out.println(halfSet(n, n+""));
}
public static int halfSet(int n, String pre) {
int ans = 1;
// System.out.println(pre);
if(a[n]!=0)return a[n];
if (n > 1)
for (int i = 1; i <= n / 2; i++)
ans += halfSet(i, i + pre);
a[n] = ans;
return ans;
}
}