[usaco gold 2016.1]无线电通信

题目描述

农夫约翰和奶牛贝西要去寻找丢失的奶牛,为了彼此能联系对方,他们带着无线电通讯设备。不幸的是电池快没有电了。所以它们要尽量节省电能。农夫从位置(fx,fy)出发,一共走N步,贝西从位置(bx,by)出发,一共走M步。农夫的路线是由一个长度为N的字符串限制,字符串只出现’N’或’E’或’S’或’W’中,表示东南西北四个方向。农夫每一单位时间可以选择不动,或者按照限制走出一步。奶牛贝西也是如此。但他们必须走完这个字符串。无线电设备每一单位时间消耗的电量等于他们的距离的平方。请问,他们走到终点,最少消耗多少电量?


输入
第一行两个整数n,m(1<=n,m<=1000),第二行为fx,fy表示农夫的起始位置,第三行为bx,by,表示贝西的起始位置。
接下来有两个字符串,第一个字符串表示农夫的路线,第二个字符串表示贝西的路线。

他们的坐标总是在(0<=x,y<=1000)。北是y的正方向,东为x的正方向。


输出
输出一个整数,表示最少消耗的电量。
样例输入
2 7
3 0
5 0
NN

NWWWWWN


样例输出

28


题解:
dp[i][j]: Farmer John走第i步,奶牛贝茜走到第j步时,最少消耗的电量
dp[i][j]=min( dp[i-1][j-1], dp[i][j-1], dp[i-1][j] )+cost( i, j )

把每一步的坐标都预处理出来,算cost的时候方便一些


#include<iostream> 
#include<cstring> 
#include<cstdio> 
#include<cstdlib> 
#include<cmath> 
#include<algorithm> 
using namespace std; 
const int INF=0x7f7f7f7f; 
const int N=1010; 
struct node{ int x, y; }f[N], b[N]; 
int n, m, dp[N][N]; 
char way[N]; 
  
int Cost( node a, node b ) {  
    return (a.x-b.x)*(a.x-b.x)+(a.y-b.y)*(a.y-b.y);  
} 
  
int main() { 
    scanf( "%d%d", &n, &m ); 
    scanf( "%d%d", &f[0].x, &f[0].y ); 
    scanf( "%d%d", &b[0].x, &b[0].y ); 
    scanf( "%s", way+1 ); 
    for( int i=1; i<=n; i++ ) { 
        if( way[i]=='E' ) f[i].x=f[i-1].x+1, f[i].y=f[i-1].y; 
        else if( way[i]=='S' ) f[i].x=f[i-1].x, f[i].y=f[i-1].y-1; 
        else if( way[i]=='W' ) f[i].x=f[i-1].x-1, f[i].y=f[i-1].y; 
        else if( way[i]=='N' ) f[i].x=f[i-1].x, f[i].y=f[i-1].y+1; 
    } 
    scanf( "%s", way+1 ); 
    for( int i=1; i<=m; i++ ) { 
        if( way[i]=='E' ) b[i].x=b[i-1].x+1, b[i].y=b[i-1].y; 
        else if( way[i]=='S' ) b[i].x=b[i-1].x, b[i].y=b[i-1].y-1; 
        else if( way[i]=='W' ) b[i].x=b[i-1].x-1, b[i].y=b[i-1].y; 
        else if( way[i]=='N' ) b[i].x=b[i-1].x, b[i].y=b[i-1].y+1; 
    } 
      
    memset( dp, 0x7f, sizeof dp ); dp[0][0]=0; 
      
    for( int i=0; i<=n; i++ ) 
        for( int j=0; j<=m; j++ ) { 
            int w=INF; 
            if( i ) w=min( w, dp[i-1][j] ); 
            if( j ) w=min( w, dp[i][j-1] ); 
            if( i && j ) w=min( w, dp[i-1][j-1] ); 
            dp[i][j]=min( dp[i][j], w+Cost( f[i], b[j] ) ); 
        } 
      
    printf( "%d\n", dp[n][m] ); 
    return 0; 
} 


  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值