当前位置: 首页 > news >正文

AT_abc403_f [ABC403F] Shortest One Formula

AT_abc403_f [ABC403F] Shortest One Formula

洛谷题目传送门

atcoder题目传送门

题目描述

给定一个正整数 NNN

请找出由字符 1+*() 组成的数学表达式中,满足以下所有条件的最短表达式 SSS

  1. SSS 符合以下 BNF 语法 中 <expr> 符号的定义
  2. SSS 表示的数学表达式计算结果等于 NNN

BNF 语法定义如下:

<expr>   ::= <term> | <expr> "+" <term>
<term>   ::= <factor> | <term> "*" <factor>
<factor> ::= <number> | "(" <expr> ")"
<number> ::= "1" | "1" <number> 

符合 <expr> 定义的表达式示例:

  • 1111+111:表示 1111+1111111+1111111+111
  • (1+1)*(1+1):表示 (1+1)×(1+1)(1+1)\times (1+1)(1+1)×(1+1)
  • (11+(1+1)*(1+1))+1:表示 (11+(1+1)×(1+1))+1(11+(1+1)\times (1+1))+1(11+(1+1)×(1+1))+1

不符合 <expr> 定义的表达式示例:

  • (1+1)(1+1)
  • 1+2
  • 1-1
  • 1/1
  • )1(
  • 1++1
  • +1
  • (+1)
  • 1*+1

输入格式

输入通过标准输入给出,格式如下:

NNN

输出格式

输出满足条件的最短表达式。

输入输出样例 #1

输入 #1

9

输出 #1

(1+1+1)*(1+1+1)

输入输出样例 #2

输入 #2

11

输出 #2

11

输入输出样例 #3

输入 #3

403

输出 #3

1+(1+1+1)*(1+11+11+111)

说明/提示

约束条件

  • 1≤N≤20001 \leq N \leq 20001N2000
  • 输入均为整数

样例解释 #1

值为 999 的表达式可能有多种形式,例如:

  • (1+1+1)*(1+1+1)
  • 1+1+1+1+1+1+1+1+1
  • (1+1)*(1+1)*(1+1)+1

其中 (1+1+1)*(1+1+1) 是最短的表达式。

思路详解

题目分析

根据题意,所谓的符合 <expr> 定义的表达式的式子其实有如下性质:

  1. 数字部分只由1组成。
  2. 运算只有+*()

由于他要求结果为NNN的最短表达式,我们可以先考虑求出最短表达式的长度。在这里我们可以考虑dpdpdp。可以考虑如下的dpdpdp

dpdpdp思路1

  1. dpdpdp定义:设fif_{i}fi为表达式的结果为iii的最短表达式长度,但是只靠这一个我们就可以更新吗?看似没有问题,不过我们发现在进行乘法运算时会有问题,此时fif_{i}fi可能会是形如A+BA+BA+B的形式,此时不能进行乘法。那我们考虑再定义gig_{i}gi为表达式结果为iii,且可以进行乘法转移(形如A∗BA*BAB(A)(A)(A))的最短字符串长度。
  2. 状态转移:显然1,11,111,11111,11,111,11111,11,111,1111这4个数字可以直接判断。首先考虑加法,加法只能是fif_{i}fi转移,所以可得fi=min(fj+fi−j+1)f_{i}=min(f_{j}+f_{i-j}+1)fi=min(fj+fij+1)。此时我们可以在fif_{i}fi外套一个括号,所以得gi=fi+2g_{i}=f_{i}+2gi=fi+2。再考虑乘法,乘法gi,fig_{i},f_{i}gi,fi都可以转移,所以得fi=gi=min(gi/j+gj+1)f_{i}=g_{i}=min(g_{i/j}+g_{j}+1)fi=gi=min(gi/j+gj+1)
  3. 答案:最短字符串长度显然为fNf_{N}fN

求解字符串

思考我们如何求解字符串,既然我们都使用dpdpdp了,那我们可以在dpdpdp过程中记录一下fif_{i}figig_{i}gi由何转移而来。

dpdpdp思路2

  1. dpdpdp定义:定义prefipref_{i}prefipregipreg_{i}pregi分别表示fif_{i}figig_{i}gi从何转移而来。
  2. 状态转移:若数字为1,11,111,11111,11,111,11111,11,111,1111,则prefi=pregi=0pref_{i}=preg_{i}=0prefi=pregi=0。在加法转移中,prefi=jpref_{i}=jprefi=j,表示他由j+(i−j)j+(i-j)j+(ij)转移。套括号时,记录pregi=ipreg_{i}=ipregi=i,表示他是由fif_{i}fi套括号形成的。在乘法中,记录pregi=j,prefi=−jpreg_{i}=j,pref_{i}=-jpregi=j,prefi=j表示他们是由j+(i/j)j+(i/j)j+(i/j)转移得到。
  3. 答案:最后递归输出即可

code

#include<bits/stdc++.h>
using namespace std;
const int N=3e3+5;
int n;
int f[N],g[N];
int pref[N],preg[N];
void find(int i,int k){//递归求出答案,k==0代表为f,否则为gif(k==0){if(pref[i]==0){cout<<i;}//直接输出,i=1,11,111,1111else if(pref[i]>0){find(pref[i],0);cout<<'+';find(i-pref[i],0);}//pref[i]>0表示为加法运算else {find(-pref[i],1);cout<<'*';find(i/(-pref[i]),1);}//否则为乘法运算,记得要变为g}else{if(preg[i]==0){cout<<i;}//直接输出else if(preg[i]==i){cout<<'(';find(i,0);cout<<')';}//套括号输出felse {find(preg[i],1);cout<<'*';find(i/(preg[i]),1);}//乘法运算,注意还是g}
}
int main(){cin>>n;memset(f,0x3f,sizeof(f));memset(g,0x3f,sizeof(g));for(int i=1;i<=n;i++){if(i==1){f[i]=g[i]=1;pref[i]=preg[i]=0;}else if(i==11){f[i]=g[i]=2;pref[i]=preg[i]=0;}else if(i==111){f[i]=g[i]=3;pref[i]=preg[i]=0;}else if(i==1111){f[i]=g[i]=4;pref[i]=preg[i]=0;}else{for(int j=1;j<i;j++)if(f[j]+f[i-j]+1<f[i])f[i]=f[j]+f[i-j]+1,pref[i]=j;//加法g[i]=f[i]+2;preg[i]=i;//f外套括号for(int j=2;j<i;j++)if(i%j==0&&g[i/j]+g[j]+1<g[i])g[i]=g[i/j]+g[j]+1,preg[i]=j;//乘法if(g[i]<f[i])f[i]=g[i],pref[i]=-preg[i];//f也可能为乘法}}find(n,0);return 0;
}
http://www.dtcms.com/a/352658.html

相关文章:

  • 【44页PPT】极简架构MES系统解决方案介绍(附下载方式)
  • 【Python】雷达簇类ply点云仿真生成,以及聚类算法的簇类目标检测
  • flutter专栏--dart基础知识
  • WebGIS开发智慧校园(6)JavaScript
  • 破解VMware迁移难题的技术
  • SSH密钥登录全流程详解
  • LeetCode-221. 最大正方形
  • 多模块 Starter 最佳实践(强烈推荐!!!)
  • Quarkus OIDC 安全链路时序图
  • git换行行为差异简述;.editorconfig换行行为简述
  • 打工人日报#20250826
  • 【PS实战】制作hello标志设计:从选区到色彩填充的流程(大学作业)
  • springboot启动的时候,只打印logo,不打印其他的任何日志的原因
  • 【ElasticSearch】数据同步
  • 人形机器人的“奥运会“:宇树科技领跑,动捕技术成训练关键
  • git submodule的基本使用
  • 数据与端点安全 (Protect data and apps)
  • 利用 Python 爬虫按关键字搜索 1688 商品详情 API 返回值说明(代码示例)实战指南
  • 从零开始配置前端环境及必要软件安装
  • 技术总结:AArch64架构下Jenkins Agent(RPM容器编译节点)掉线问题分析与排查
  • 基于用户行为分析的精确营销系统
  • 【java并发编程】--cas和synchronized
  • openEuler Embedded 的 Yocto入门 : 2. 构建一个Hello,world!
  • PWM控制实现呼吸灯
  • 基于CentOS7:Linux服务器的初始化流程
  • 基于51单片机的指纹红外密码电子锁
  • 【Elasticsearch】k-NN 搜索深度解析:参数优化与分数过滤实践
  • Pascal使用TMediaPlayer播放MIDI文件时的错误
  • 红外遥控模块
  • 逻辑流图、作业图、执行图、物理图