首页 > 其他分享 >洛谷P1880 [NOI1995] 石子合并 题解

洛谷P1880 [NOI1995] 石子合并 题解

时间:2024-12-01 14:03:36浏览次数:12  
标签:洛谷 dpmi int 题解 310 len 枚举 NOI1995 dp

此题解以纪念我终于差不多大概搞懂区间dp了(插个存档点,到时候忘了再回来看看)。

P1880 [NOI1995] 石子合并 题解

在做这道题之前,可以看看 P1775 石子合并(弱化版)(一道题解帮你搞定两道题,多划算)。

P1775 石子合并(弱化版)

形式化的题面

一堆石头摆在你面前,让你把他们扔到一起,每次扔都要花你这两堆石头的重量的力气,让你找出最省力的方法。

思路

使用区间dp

我们先手算一遍样例(如图)

接下来我们就要将他换成一个流程,再编写成代码。

再看图,是不是我们就可以想到,枚举所有合并的区间。

  1. 第一层循环从2到 n n n 枚举区间的长度 l e n len len。
  2. 第二层循环去枚举这个区间的左端点 i i i ,那么这个区间的右端点就是显而易见的 i + l e n i+len i+len 。
  3. 再枚举 l e n len len 长的区间枚举每个分割可能的位置 k k k ,使得 d p [ i ] [ j ] = d p [ i ] [ k ] + d p [ k + 1 ] [ j ] dp[i][j] = dp[i ][ k] + dp[k + 1][j] dp[i][j]=dp[i][k]+dp[k+1][j] ;所以我们的 k k k 从 i i i 开始枚举,到 j j j 结束 ( i < = k < j ) ( i <= k < j ) (i<=k<j)
  4. 最后注意一下循环的范围就好了
  5. 对于代价(体力),我们可以根据前缀和进行记录,在代码中,我用 s [ i ] s[i] s[i] 记录,那么区间 [ i ] [ j ] [i][j] [i][j] 的代价就是 s [ j ] − s [ i − 1 ] s[j]-s[i-1] s[j]−s[i−1]
根据上述思路写的代码
#include<bits/stdc++.h>
using namespace std;
int dp[310][310],s[310]={0},n,a[310];
int main()
{
	std::ios::sync_with_stdio(false);
    cin>>n;
    memset(dp,0x3f,sizeof(dp));
    for(int i=1;i<=n;i++)
    {
    	cin>>a[i];
    	s[i]=s[i-1]+a[i];//前缀和 
    	dp[i][i]=0;
	}
	for(int i=2;i<=n;i++)//模拟区间 
	{
		for(int j=0;j<=n-i+1;j++) 
		{
			int l=j+i-1;
			for(int k=j;k<l;k++)
			{
				dp[j][l]=min(dp[j][l],dp[j][k]+dp[k+1][l]+s[l]-s[j-1]);
			}
		}
	}
	cout<<dp[1][n];
    return 0;
}

P1880 [NOI1995] 石子合并

再看一下这道题,我们只需再加一个max就好了。

请注意,这道题有环,那我们该怎么处理呢?

  • 可以通过复制一遍这个数组,环转链就行了,在这道题中,
    4 9 5 4就可以处理为4 9 5 4 4 9 5 4就行了
代码
#include<bits/stdc++.h>
using namespace std;
int dpma[310][310]={0},dpmi[310][310]={0},s[310]={0},n,a[310],ma=0,mi=0x3f3f3f;
int main()
{
	ios::sync_with_stdio(false);
    cin>>n;
    for(int i=1;i<=n;i++)
    {
    	cin>>a[i];
    	a[i+n]=a[i];
    	s[i]=s[i-1]+a[i];
	}
	for(int i=n+1;i<=2*n;i++)//环状处理 
	{
		s[i]=a[i]+s[i-1];//前缀和 
	}
	for(int len=1;len<n;len++)//区间[i,j]的长度 
	{
		for(int i=1;i<=2*n-len;i++)//枚举左端点 
		{
			int j=i+len;//右端点显而易见 
			dpmi[i][j]=0x3f3f3f;//在枚举min的时候,我们要将这个mi放大,毕竟自然数中,没有比0小的数了。 
			for(int k=i;k<j;k++)
			{
				dpmi[i][j]=min(dpmi[i][j],dpmi[i][k]+dpmi[k+1][j]+s[j]-s[i-1]);
				dpma[i][j]=max(dpma[i][j],dpma[i][k]+dpma[k+1][j]+s[j]-s[i-1]); 
				//cout<<"mi:"<<dpmi[i][j]<<" ma:"<<dpma[i][j]<<endl; 
			}
		}
	}
	for(int i=1;i<=n;i++)
	{
		//我们要得到的是整个链的结果,所以当i为起点,那么len=n,结尾就是i+n-1 
		ma=max(ma,dpma[i][i+n-1]);//整个链 
		mi=min(mi,dpmi[i][i+n-1]);
	}
	cout<<mi<<endl<<ma;
    return 0;
}

标签:洛谷,dpmi,int,题解,310,len,枚举,NOI1995,dp
From: https://blog.csdn.net/yhlz64/article/details/144168817

相关文章

  • 20241201每日一题洛谷P1683
    普及-每日一题洛谷P1683题目描述不是任何人都可以进入桃花岛的,黄药师最讨厌像郭靖一样呆头呆脑的人。所以,他在桃花岛的唯一入口处修了一条小路,这条小路全部用正方形瓷砖铺设而成。有的瓷砖可以踩,我们认为是安全的,而有的瓷砖一踩上去就会有喷出要命的毒气,那你就死翘翘了,我们认为......
  • 洛谷 P1036 [NOIP2002 普及组] 选数 C语言
    题目:https://www.luogu.com.cn/problem/P1036题目描述已知 nn 个整数 x1,x2,⋯ ,xn,以及 1 个整数 k(k<n)。从 n 个整数中任选 k 个整数相加,可分别得到一系列的和。例如当 n=4,k=3,4 个整数分别为 3,7,12,19时,可得全部的组合与它们的和为:3+7+12=223+7+19=297+12......
  • 洛谷 奇怪的电梯
    1.题目描述呵呵,有一天我做了一个梦,梦见了一种很奇怪的电梯。大楼的每一层楼都可以停电梯,而且第i层楼(1≤i≤N)上有一个数字Ki​(0≤Ki​≤N)。电梯只有四个按钮:开,关,上,下。上下的层数等于当前楼层上的那个数字。当然,如果不能满足要求,相应的按钮就会失灵。例如:3,3,1,2,5代表了Ki......
  • 洛谷 P1605 迷宫 C语言 bfs
    题目:https://www.luogu.com.cn/problem/P1605题目描述给定一个 N×M方格的迷宫,迷宫里有 TT 处障碍,障碍处不可通过。在迷宫中移动有上下左右四种方式,每次只能移动一个方格。数据保证起点上没有障碍。给定起点坐标和终点坐标,每个方格最多经过一次,问有多少种从起点坐标到......
  • 【Q1~Q6题解】第七届传智杯全国IT技能大赛-程序设计赛道第一场院校赛(初赛)思路+解题代
    本文为作者的题解解析。Q1~Q6,思路仅供参考文章目录Q1:汤姆和杰瑞解题代码解题思路Q2:游游的重组偶数解题代码解题思路Q3:小红的四子棋解题代码解题思路Q4:小欧的平面连线解题代码解题思路Q5:小红的数组操作解题代码解题思路Q6:游......
  • C语言 神奇的幻方(洛谷 p2615 )幻方是一种很神奇的N*N矩阵
            题目:神奇的幻方(洛谷p2615)幻方是一种很神奇的N*N矩阵:它由数字1,2,3,…,N*N构成,且每行、每列及两条对角线上的数字之和都相等。当N为奇数时,可以通过以下方法构建一个幻方:首先将1写在第一行的中间;之后,按如下方式从小到大依次填写每个数k(k=2,3,…,N*N)若(k-1)在第一......
  • 【洛谷】P2089 烤鸡
    #include<iostream>usingnamespacestd;intmain(){ intn,a,b,c,d,e,f,g,h,i,j,num=0; cin>>n; for(a=1;a<=3;a++) { for(b=1;b<=3;b++) { for(c=1;c<=3;c++) { for(d=1;d<=3;d++) { for(e=1;e<=3;e++) { ......
  • 洛谷 P1680 奇怪的分组(组合数学)
    题目传送门https://www.luogu.com.cn/problem/P1680解题思路这是一道组合数学题。既然题目说了第  个组要大于  个人,那我们不妨先给每个组分  个人。但题目说了是大于  个人,我们只给每个组分了  个人,所以还得分几个人。那么问题就变成了:对于剩下的  个人,我们......
  • 国产化硬件系统上,部署视频监控平台系统软件出现的脚本问题解决
    目录一、问题描述二、解决方法        1、检查部署脚本权限        2、检查脚本中语法是否有问题        3、使用tee命令对文件进行修改        4、查看银河麒麟系统的安全设置        在国产系统银河麒麟硬件设备上部署视频......
  • P1135 奇怪的电梯 JAVA题解
    题目描述呵呵,有一天我做了一个梦,梦见了一种很奇怪的电梯。大楼的每一层楼都可以停电梯,而且第 ii 层楼(1≤i≤N1≤i≤N)上有一个数字 KiKi​(0≤Ki≤N0≤Ki​≤N)。电梯只有四个按钮:开,关,上,下。上下的层数等于当前楼层上的那个数字。当然,如果不能满足要求,相应的按钮就会失灵。例......