社区讨论
最后一个点WA了,没搞懂,求大佬帮忙
P1220关路灯参与者 3已保存回复 2
讨论操作
快速查看讨论及其快照的属性,并进行相关操作。
- 当前回复
- 2 条
- 当前快照
- 1 份
- 快照标识符
- @lo2us2bl
- 此快照首次捕获于
- 2023/10/23 20:07 2 年前
- 此快照最后确认于
- 2023/10/23 20:07 2 年前
dp顺序非常奇怪,写不明白,试着换广搜做了一下,神奇地只错了一个,但不明白后面怎么改了,求调
CPP#include<iostream>
#include<queue>
#include<cmath>
using namespace std;
queue<int> qx,qy;
int plc[55],val[55],dp[55][55];//dp[i][j]=a:关掉第[i,j]盏灯最少需要花费a元
bool zy[55][55];//老张关完[i,j]中的灯后站在左端点还是右端点,0左1右
int n,c,zc,idx,len,x,y;
bool check(int x,int y){//判断越界
if(x>0 && x<=c && y>=c && y<=n) return 1;
return 0;
}
int main(){
int i,j;
cin>>n>>c;
for(i=1;i<=n;i++){
cin>>plc[i]>>zc;
val[i]=val[i-1]+zc;//储存路径和
}
qx.push(c);//老张所在位置入队列
qy.push(c);
while(!qx.empty()){
len=qx.size();//储存当前长度,防止多算
for(i=0;i<len;i++){
x=qx.front();//顺序取数,进行递推
y=qy.front();
if(zy[x][y]==0) idx=x;//现在站在左边
else idx=y;//现在站在右边
if(check(x-1,y)==1){//向上搜索
zc=dp[x][y]+(val[n]-val[y]+val[x-1])*abs(plc[x-1]-plc[idx]);//关掉[x,y]上的路灯需要的最小花费加关掉了[x,y]上的路灯后移动花费乘距离
if(dp[x-1][y]==0){//未更新状态
dp[x-1][y]=zc;//更新
qx.push(x-1);//仅在第一次更新时加入队列,防止两个地方推到同一个地址时多加
qy.push(y);
}
else if(dp[x-1][y]>zc){//暂存的花费更小
dp[x-1][y]=zc;
zy[x-1][y]=0;//更新老张所处位置
}
}
if(check(x,y+1)==1){//向右搜索
zc=dp[x][y]+(val[n]-val[y]+val[x-1])*abs(plc[y+1]-plc[idx]);
if(dp[x][y+1]==0){
dp[x][y+1]=zc;
qx.push(x);
qy.push(y+1);
zy[x][y+1]=1;
}
else if(dp[x][y+1]>zc){
dp[x][y+1]=zc;
zy[x][y+1]=1;
}
}
qx.pop();//当前队首搜索完成,出队
qy.pop();
}
}
cout<<dp[1][n];//关掉第[1,n]盏灯需要的最小花费
return 0;
}
回复
共 2 条回复,欢迎继续交流。
正在加载回复...