zoukankan      html  css  js  c++  java
  • P3842 [TJOI2007]线段

    每行一个线段,必须要走完,显然可以发现从左往右走完或者从右往左走完是比较优的。从中间往下走浪费步数??(好像可以,但是我理解不来,也找不到有人这样写)
    那么是该从左往右还是从右往左呢。我们需要枚举了。这个状态又有最优子结构,这时候需要优雅的暴力--DP。

    (f[i][0])表示走完第i行的线段,并且在该线段左边时的最小步数
    (f[i][1])表示走完第i行的线段,并且在该线段右边时的最小步数

    (f[i][0/1])可以从(f[i-1][1/0])得出,分类讨论即可。
    关于为什么这样走最优,可以画图自己平移下

    
    #include<bits/stdc++.h>
    #define rep(i,j,k) for(register int i(j);i<=k;++i)
    #define drp(i,j,k) for(register int i(j);i>=k;--i)
    using namespace std;
    typedef long long lxl;
    template<typename T> 
    inline T  max(T &a, T &b) {
    	return a > b ? a : b;
    }
    template<typename T> 
    inline T  min(T &a, T &b) {
    	return a < b ? a : b;
    }
    
    inline char gt() {
    	static char buf[1 << 21], *p1 = buf, *p2 = buf;
    	return p1 == p2 && (p2 = (p1 = buf) + fread(buf, 1, 1 << 21, stdin), p1 == p2) ? EOF : *p1++;
    }
    template <typename T>
    inline void  read(T &x) {
    	register char ch = gt();
    	x = 0;
    	int w(0);
    	while(!(ch >= '0' && ch <= '9'))w |= ch == '-', ch = gt();
    	while(ch >= '0' && ch <= '9')x = x * 10 + (ch & 15), ch = gt();
    	w ? x = ~(x - 1) : x;
    }
    template <typename T>
    inline void out(T x) {
    	if(x < 0) x = -x, putchar('-');
    	char ch[20];
    	int num(0);
    	while(x || !num) ch[++num] = x % 10 + '0', x /= 10;
    	while(num) putchar(ch[num--]);
    	putchar('
    ');
    }
    const int N=2e4+79;
    int L[N],R[N]; 
    int f[N][2];
    int n;
    
    inline int dis(int a,int b){
    	return abs(a-b);
    }
    
    int main() {  
       read(n);
       rep(i,1,n) {
       	read(L[i]);read(R[i]);
       }
       memset(f,0x3f,sizeof f);
       f[1][1]=R[1]-1;
       f[0][1]=R[1]-1+(R[1]-L[1]);
       
       rep(i,2,n){
       	f[i][1]=min(f[i-1][1]+dis(R[i-1],L[i])+dis(L[i],R[i]),f[i-1][0]+dis(L[i-1],L[i])+dis(L[i],R[i]))+1;
       	f[i][0]=min(f[i-1][1]+dis(R[i-1],R[i])+dis(R[i],L[i]),f[i-1][0]+dis(L[i-1],R[i])+dis(L[i],R[i]))+1;
       }
       out(min(f[n][1]+dis(R[n],n),f[n][0]+dis(L[n],n)));
    	return 0;
    }
    
    

    当然这题也可以跑最短路。。网格图。要学会一题多解(强行增加时间复杂度,但是可以增强编程能力)
    增强建图能力(乱搞)
    去luogu看吧,懒得写了

    本文来自博客园,作者:{2519},转载请注明原文链接:https://www.cnblogs.com/QQ2519/p/15191564.html

  • 相关阅读:
    delphi 常用的将窗口置前的函数
    delphi中Message消息的使用方法
    批处理 删除文件
    CDR话单主要字段介绍
    集成学习算法总结----Boosting和Bagging
    Benchmark简介
    脚本中export不起作用的原因分析
    RAID详解[RAID0/RAID1/RAID10/RAID5]
    基于DPI(深度报文解析)的应用识别
    DPI (Deep Packet Inspection) 深度包检测技术
  • 原文地址:https://www.cnblogs.com/QQ2519/p/15191564.html
Copyright © 2011-2022 走看看