题解 CF991F 【Concise and clear】

题解 - C F 991 F \mathrm{CF991F} CF991F

题目意思

题目传送门

S o l \mathrm{Sol} Sol

我的方法特别复杂,细节及其多,代码长达 320 320 320

我们考虑构造形式:

x = a + b × c d x=a+b\times c^d x=a+b×cd

x = c d + e f x=c^d+e^f x=cd+ef

x = c d × e f + a x=c^d\times e^f+a x=cd×ef+a

x = c d × b + a x=c^d\times b+a x=cd×b+a

对于第一种情况我们暴力枚举 c d c^d cd 可以轻松算出 a , b a,b a,b

对于 c d + e f c^d+e^f cd+ef 这样的情况,我们可以先把 f x f_{x} fx 表示 x x x b c b^c bc 类型表示出来的最短长度。然后枚举 c d c^d cd 同时可以记录 e f e^f ef 的长度到最后统计答案的时候还原幂次形式即可。幂乘幂同理可得。

对于第三和四的情况我们可以枚举加的数 a a a 再与上面同理的做法计算即可。

最后答案与本身长度去小即可。

const int mod=1e9+7;
const int mo=998244353;
const int N=5e5+5;

int n,ans,P,BA,CS,Mul;
map<int,int> f;

inline int ksm(int x,int y)
{
    
    
	int ans=1ll;
	while(y)
	{
    
    
		if(y&1ll) ans=ans*x;
		x=x*x;
		y>>=1ll;
	}
	return ans;
}

inline int calc(int x)
{
    
    
	if(!x) return 0;
	return (int)log10(x)+1;
}

signed main()
{
    
    
	io.read(n);
	ans=calc(n);
	int S=sqrt(n);
	For(i,2,S) For(j,2,50)
	{
    
    
		int x=ksm(i,j);
		if(x>n) break;
		if(!f[x]) f[x]=calc(i)+calc(j)+1;
		else f[x]=min(f[x],calc(i)+calc(j)+1);
	}
	int base=2;
	int AA=0,BB=0,CC=0,Else=0,fll=0,FF=0;
	
	For(del,0,10)
	{
    
    
		int goal=n-del;
		base=2;
		for (;;)
		{
    
    
			if(base*base>goal) break;
			For(i,2,50)
			{
    
    
				int x=ksm(base,i);
				if(x>goal) break;
				int step=f[goal-x];
				if(!step&&x!=goal) continue;
				if(x==goal) 
				{
    
    
					int AD=calc(del)+(del>0);
					if(calc(base)+calc(i)+1+AD<ans) ans=AD+calc(base)+calc(i)+1,AA=base,BB=i,FF=del,CC=0;
				}
				else 
				{
    
    
					int AD=calc(del)+(del>0);
					if(calc(base)+calc(i)+2+step+AD<ans) ans=AD+calc(base)+calc(i)+2+step,AA=base,BB=i,CC=goal-x,Else=step,FF=del;
				}
			}
			base++;
		}
	}
	int Ans1=ans;
	int AAA=0,BBB=0,CCC=0,EElse=0,FFF=0;
	
	For(del,0,10)
	{
    
    
		int goal=n-del;
		base=2;
		for (;;)
		{
    
    
			if(base*base>goal) break;
			For(i,1,50)
			{
    
    
				int x=ksm(base,i);
				if(x>goal) break;
				if(goal%x) continue;
				int step=f[goal/x];
				if(!step&&x!=goal) continue;
				if(x==goal) 
				{
    
    
					int AD=calc(del)+(del>0);
					if(calc(base)+calc(i)+1+AD<ans) ans=AD+calc(base)+calc(i)+1,AAA=base,BBB=i,FFF=del,CCC=0;
				}
				else 
				{
    
    
					int AD=calc(del)+(del>0);
					if(calc(base)+calc(i)+2+step+AD<ans) ans=AD+calc(base)+calc(i)+2+step,AAA=base,BBB=i,CCC=goal/x,EElse=step,FFF=del;
				}
			}
			base++;
		}
	}
	
	int Ans2=ans;
	
	P=n;
	base=2;
	for (;;)
	{
    
    
		if(base*base>n) break;
		For(i,1,50)
		{
    
    
			int x=ksm(base,i);
			if(x>n) break;
			int rem=n/x;
			int A=calc(rem);
			if(rem==1) A=0;
			int B=calc(n-rem*x);
			if(f[n-rem*x]) B=min(B,f[n-rem*x]);
			int C=calc(i);
			int D=calc(base);
			if(n-rem*x) B++;
			if(i>1) C++;
			if(A>1) A++;
			if(A+B+C+D<ans) 
			{
    
    
				ans=A+B+C+D;
				P=n-rem*x;
				BA=base;
				CS=i;
				Mul=rem;
			}
		}
		base++;
	}
	
	if(ans==Ans2&&AAA&&BBB)
	{
    
    
		printf("%lld^%lld",AAA,BBB);
		int FFA=0,FFB=0;
		if(FFF)
		{
    
    
			int len=calc(FFF);
			if(f[FFF]<len)
			{
    
    
				For(i,2,S) For(j,2,50)
				{
    
    
					int x=ksm(i,j);
					if(x>FFF) break;
					if(x==FFF) 
					{
    
    
						if(calc(i)+calc(j)+1==f[FFF]) FFA=i,FFB=j;
					}
					if(FFA&&FFB) break;
				}
			}
		}
		if(CCC)
		{
    
    
			putchar('*');
			int DD=0,EE=0;
			For(i,2,S) For(j,2,50)
			{
    
    
				int x=ksm(i,j);
				if(x>n) break;
				if(x==CCC) 
				{
    
    
					if(calc(i)+calc(j)+1==EElse) DD=i,EE=j;
				}
				if(DD&&EE) break;
			}
			printf("%lld^%lld",DD,EE);
			if(FFF) 
			{
    
    
				putchar('+');
				if(FFA) printf("%lld^%lld",FFA,FFB);
				else printf("%lld",FFF);
			}
		}
		else if(FFF) 
		{
    
    
			putchar('+');
			if(FFA) printf("%lld^%lld",FFA,FFB);
			else printf("%lld",FFF);
		}
		return 0;
	}
	
	if(ans==Ans1&&AA&&BB)
	{
    
    
		printf("%lld^%lld",AA,BB);
		int FFA=0,FFB=0;
		if(FF)
		{
    
    
			int len=calc(FF);
			if(f[FF]<len)
			{
    
    
				For(i,2,S) For(j,2,50)
				{
    
    
					int x=ksm(i,j);
					if(x>FF) break;
					if(x==FF) 
					{
    
    
						if(calc(i)+calc(j)+1==f[FF]) FFA=i,FFB=j;
					}
					if(FFA&&FFB) break;
				}
			}
		}
		if(CC) 
		{
    
    
			putchar('+');
			int DD=0,EE=0;
			For(i,2,S) For(j,2,50)
			{
    
    
				int x=ksm(i,j);
				if(x>n) break;
				if(x==CC) 
				{
    
    
					if(calc(i)+calc(j)+1==Else) DD=i,EE=j;
				}
				if(DD&&EE) break;
			}
			printf("%lld^%lld",DD,EE);
			if(FF) 
			{
    
    
				putchar('+');
				if(FFA) printf("%lld^%lld",FFA,FFB);
				else printf("%lld",FF);
			}
		}
		else if(FF) 
		{
    
    
			putchar('+');
			if(FFA) printf("%lld^%lld",FFA,FFB);
			else printf("%lld",FF);
		}
		return 0;
	}
	if(P) 
	{
    
    
		int FFA=0,FFB=0;
		int len=calc(P);
		if(f[P]<len)
		{
    
    
			For(i,2,S) For(j,2,50)
			{
    
    
				int x=ksm(i,j);
				if(x>P) break;
				if(x==P) 
				{
    
    
					if(calc(i)+calc(j)+1==f[P]) FFA=i,FFB=j;
				}
				if(FFA&&FFB) break;
			}
		}
		if(FFA) printf("%lld^%lld",FFA,FFB);
		else printf("%lld",P);
	}
	if(BA) 
	{
    
    
		if(P) printf("+%lld^%lld",BA,CS);
		else printf("%lld^%lld",BA,CS);
	}
	if(Mul>1) printf("*%lld",Mul);
	return 0;
}

猜你喜欢

转载自blog.csdn.net/wangyiyang2/article/details/108980096