网教30. 过桥

来源:互联网 发布:戴斯蒙德.道斯 知乎 编辑:程序博客网 时间:2024/04/30 19:55

题目描述:

小a有x只羊和y只狼,现在,他需要通过一座桥。由于桥面很窄,桥每次只允许通过小a和n只动物。小a很爱动物,所以他每次通过桥时都必须有一只动物陪着他,否则他会很寂寞。并且不论是在墙上或者是在桥的两头,一旦羊的数量少于狼的数量,狼就会开始吃羊。为了不让羊被吃掉,又要让所有动物和小a自己都通过桥,小a至少要过桥多少次?

输入:

多组数据,每一组数据包含三个整数x, y, n (0≤ x, y,n ≤ 200)。

输出:

对于每组数据,如果能顺利顺利过桥并且不损失一头羊,则输出需要的最少过桥次数。否则,输出-1。

 测试输入关于“测试输入”的帮助期待的输出关于“期待的输出”的帮助时间限制关于“时间限制”的帮助内存限制关于“内存限制”的帮助额外进程关于“{$a} 个额外进程”的帮助测试用例 1以文本方式显示
  1. 2↵
  2. 3 3 2↵
  3. 33 33 3↵
以文本方式显示
  1. 11↵
  2. -1↵
1秒64M0题解:
(据说这又是一个数论题)
按照以往(暂时已知)的套路,数论题总是可以变成BFS,所以我就用BFS试了试……
开两个结构数组,分别存在河的一边和另一边时候的羊数、狼数、走的次数。然后一个vis[200][200][2]三维分别存羊数、狼数、河的哪边。每次操作的时候是最少带一只动物,最多带n只,在河的两边和桥上都不能出现狼数>羊数的情况。对于符合题意的情况,就加入队列,并标记vis。一直BFS搜索,只到所有的动物都到了对岸,或者front<rear,结束,输出结果。
思路不难,一点一点写就能写出来。代码量(至少是我的代码量)较大,所以写着需要细心。细节的地方容易出千奇百怪的错,所以还是要注意细节。
AC代码:
#include<stdio.h>  #include<string.h>  struct node  {      int x, y, index;  }a[400005], b[400005];  int vis[205][205][2];  int x, y, n;    int bfs()  {      int front = 0, rear = 1;      a[front].x = x;      a[front].y = y;      a[front].index = 0;      b[front].x = 0;      b[front].y = 0;      b[front].index = 0;      vis[x][y][0] = 1;      vis[0][0][1] = 1;      int k = 0, flag = 0;      while (front < rear)      {          if (b[front].x == x&&b[front].y == y)          {              flag = 1;              return b[front].index;          }          if (a[front].index % 2 == 0)              k = 0;          else              k = 1;          if (k == 0)          {              for (int i = 0; i <= n; i++)              for (int j = 0; j <= n - i; j++)//i:带上几只羊,j:带上几只狼              {                  if (i + j == 0 || (i != 0 && i < j))                      continue;                  int x1 = a[front].x - i;                  int x2 = b[front].x + i;                  int y1 = a[front].y - j;                  int y2 = b[front].y + j;                  if (x1 > x || x2 > x || y1 > y || y2 > y || x1 < 0 || y1 < 0)                      continue;                  if (vis[x1][y1][0] == 0 && (x1 >= y1 || x1 == 0) && (x2 >= y2 || x2 == 0))                  {                      vis[x1][y1][0] = 1;                      a[rear].x = x1;                      a[rear].y = y1;                      a[rear].index = a[front].index + 1;                      b[rear].x = x2;                      b[rear].y = y2;                      b[rear].index = b[front].index + 1;                      rear++;                  }              }          }          else          {              for (int i = 0; i <= n; i++)              for (int j = 0; j <= n - i; j++)              {                  if (i + j == 0 || (i != 0 && i < j))                      continue;                  int x1 = a[front].x + i;                  int x2 = b[front].x - i;                  int y1 = a[front].y + j;                  int y2 = b[front].y - j;                  if (x1 > x || x2 > x || y1 > y || y2 > y || x2 < 0 || y2 < 0)                      continue;                  if (vis[x2][y2][1] == 0 && (x1 >= y1 || x1 == 0) && (x2 >= y2 || x2 == 0))                  {                      vis[x2][y2][1] = 1;                      a[rear].x = x1;                      a[rear].y = y1;                      a[rear].index = a[front].index + 1;                      b[rear].x = x2;                      b[rear].y = y2;                      b[rear].index = b[front].index + 1;                      rear++;                  }              }          }          front++;      }      return -1;  }  int main()  {      int t;      scanf("%d", &t);      while (t--)      {          memset(vis, 0, sizeof(vis));            scanf("%d%d%d", &x, &y, &n);          if (x < y || n < 1)              printf("-1\n");          else          {              int ans = bfs();              printf("%d\n",ans);          }      }      return 0;  }  


0 0
原创粉丝点击