递归1——2021-02-27更

递归1

T1 圆环套圆环

题目:

一个有趣的圆环套圆环函数被定义如下:
G(n)=n-G(G(n-1)) (n是正整数)

G(0)=0

请你计算出圆环函数的值。

输入
一个非负整数n,n<=200。

输出
一个正整数,即G(n)。

输入样例
3

输出样例
2

思路:

这道题我一开始的想法很简单,就是直接递归题目中给的函数就行了,但是后来发现会TLE,但又想不通,然后我们班一个神犇跟我说要用记忆化搜索,但记忆化搜索又是神马东西呢,下一题再一块讲了。

代码:

#include<bits/stdc++.h>
using namespace std;
int n,m,h,s[210];
int g(int a)
{
    
    
	if(a==0)
		return 0;
	if(a==1)
		return 1;	
	if(s[a]!=0)
		return s[a];
	s[a]=a-g(g(a-1));	
	return s[a];	
}
int main()
{
    
    
	cin>>n;
	cout<<g(n);
	return 0;
} 

T2 桐桐的递归函数

题目:

桐桐经常找一些很有趣的数学书来阅读以增长自己的数学知识。一天,他偶然发现一个递归函数w(a,b,c)有以下性质:

   如果a≤0或b≤0或c≤0则返回1;
   如果a>20或b>20或c>20,则返回w(20,20,20);
   如果a<b并且b<c就返回w(a,b,c-1)+w(a,b-1,c-1)-w(a,b-1,c);
   其它别的情况就返回w(a-1,b,c)+w(a-1,b-1,c)+w(a-1,b,c-1)-w(a-1,b-1,c-1)。

请编程求出这个递归函数的值。

输入
会有若干行,并以-1,-1,-1结束。

保证输入的数在-9223372036854775808~9223372036854775807之间并且是整数(long long 能存)。

输出
若干行

格式:
w(a,_b,c)=_你的输出 (_代表空格)

输入样例
1 1 1
2 2 2
10 4 6
50 50 50
-1 7 18
-1 -1 -1

输出样例
w(1, 1, 1) = 2
w(2, 2, 2) = 4
w(10, 4, 6) = 523
w(50, 50, 50) = 1048576
w(-1, 7, 18) = 1

思路:

和T1思路类似,就是以题目给出的递归条件和方法进行递归,直到结束为止,但是如果直接递归,那么连样例都过不了。这时候就要用到记忆化搜索了。
记忆化搜索:用数组将曾经求过的数据存起来,下次如果再出现则直接调用,就不需要重复算了。

代码:

#include<bits/stdc++.h>
using namespace std;
typedef long long ULL; 
ULL s[30][30][30];

ULL dg(ULL a,ULL b,ULL c)
{
    
    
	if(a<=0||b<=0||c<=0)
		return 1;
	else if(a>20||b>20||c>20)
		return dg(20,20,20);
	if(s[a][b][c]!=0)
		return s[a][b][c];	
	else if(a<b&&b<c)
		s[a][b][c]=dg(a,b,c-1)+dg(a,b-1,c-1)-dg(a,b-1,c);
	else
		s[a][b][c]=dg(a-1,b,c)+dg(a-1,b-1,c)+dg(a-1,b,c-1)-dg(a-1,b-1,c-1);	
	return s[a][b][c];		
}
int main()
{
    
    
	ULL k1,k2,k3;
	while(1)
	{
    
    
		cin>>k1>>k2>>k3;
		if(k1==-1&&k2==-1&&k3==-1)
			break;
		cout<<"w("<<k1<<", "<<k2<<", "<<k3<<") = "<<dg(k1,k2,k3)<<endl;
	}
	return 0;
}

猜你喜欢

转载自blog.csdn.net/SSL_wyd/article/details/114168980