📜  新冠病毒 | TCS Codevita 2020

📅  最后修改于: 2021-10-25 05:07:34             🧑  作者: Mango

问题描述:

一个城市被表示为一个二维矩形矩阵。给定矩阵的外墙表示城市的边界。市民分散在城市的不同地点。它们要么用{a, c} 表示。冠状病毒已经感染了这座城市。

冠状病毒从坐标(0, 0)进入城市并沿对角线路径传播,直到遇到人类。如果它遇到一个被指定为的人,它的轨迹会逆时针(从右到左)旋转90 度。类似地,如果它遇到一个被指定为c 的人,它的轨迹会顺时针(从左到右)旋转90 度。感染人后,病毒继续沿其对角线移动。

在它的穿越过程中如果它第一次到达城市边界,它会旋转90度重新进入城市。然而,如果它第二次击中任何边界,病毒就会被摧毁。

你必须计算病毒的轨迹,打印可以找到受感染公民的城市地图,最后报告安全和受感染公民的数量。

输入:

一个9 行20 列的输入矩阵,由字符“ *”“a”“c”“.”组成。在哪里

  • “*”表示城市边界上的元素
  • “a”表示遇到病毒轨迹改变90度(逆时针方向)的公民
  • “c”表示遇到病毒轨迹改变90度(顺时针方向)的公民
  • “。” (点)表示城市内的空位

输出:

随机数的行,每行表示病毒轨迹的坐标。

从下一行开始,一个9 行20 列的输出矩阵由字符“ *”“a”“c”“.”组成。“-”在哪里

  • “*”表示城市边界上的元素
  • “a”表示遇到病毒轨迹改变90度(逆时针方向)的公民
  • “c”表示遇到病毒轨迹改变90度(顺时针方向)的公民
  • “。” (点)表示城市内的空位
  • “-”表示受感染公民所在的位置

接下来的两行打印了城市中安全和受感染公民的数量。

约束:

  • 0 <= x <= 20
  • 0 <= y <= 8
  • 病毒打不到三个角 (20, 8) (20, 0) (0, 8)

例子:

方法:解决这个问题的思路是先将输入所表示的图求反,根据给定的条件遍历图。请按照以下步骤解决问题:

  • 首先,将输入数组反转为反转数组。所以最后一行变成第一行,倒数第二行变成第二行,依此类推。这样做是为了在具有正xy的二维坐标系中查看图形。
  • 遍历图形并在名为bound的变量中跟踪病毒到达边界的次数并运行 while 循环,直到该变量的值小于或等于1
  • 初始化一个变量direct ,将运动方向保持为:
    • 如果 direct 为 1,则方向为东北。
    • 如果 direct 为 2,则方向为西北。
    • 如果 direct 为 3,则方向为东南。
    • 如果 direct 为 4,则方向为西南。
  • 病毒将有 4 个运动方向。病毒将从顶点(0, 0)开始,运动方向为1 (向东北方向移动)。当遇到墙壁时,变量的方向会发生变化。
  • 此外,当遇到‘a’时,将direct的值更改为产生的逆时针方向,当遇到‘c’时,将direct的值更改为从当前方向顺时针旋转90 度
  • 对于‘.’ (点)字符,保持当前位置变量递增或递减1以在直接变量的描述方向上对角移动。

下面是上述方法的实现:

C++
// C++ program for the above approach
  
#include 
using namespace std;
#define row 9
#define col 20
  
// Funtion to print trajectory of the virus
// and safe and infected citizens
void coronaVirus(char arr[row][col])
{
  
    // To store Inverted Array
    char inverted[9][20];
  
    // Temporary array to store
    // original array
    char temp[9][20];
  
    // To store number of infected citizens
    int count = 0;
  
    // To store total number of citizens ('a', 'c')
    int total = 0;
  
    // To invert the array
    for (int i = 0; i <= 8; i++) {
        for (int j = 0; j < 20; j++) {
  
            // Invert the array row wise
            inverted[i][j] = arr[8 - i][j];
        }
    }
  
    // Count the number of citiens
    for (int i = 0; i <= 8; i++) {
        for (int j = 0; j < 20; j++) {
  
            // Count total number of citizens.
            if (inverted[i][j] == 'a'
                || inverted[i][j] == 'c') {
                total++;
            }
  
            // Copy inverted array in temp
            temp[i][j] = inverted[i][j];
        }
    }
  
    // To store number of times,
    // virus encountered a boundary
    int bound = 0;
  
    // Variable for row-wise traversal
    int i = 1;
  
    // Variable for column-wise traversal
    int j = 1;
  
    // Variable to store direction
    int direct = 1;
  
    // The virus starts from (0, 0) always
    cout << "0 0" << endl;
  
    // To break infinite looping
    int flag = 0;
  
    // Finding trajectory and safe
    // and infected citizens
    while (bound <= 1 && flag < 1000) {
        flag++;
        cout << i << " " << j << endl;
  
        // Virus has striked the boundary twice.
        // Therefore, end loop
        if (inverted[j][i] == '*' && bound == 1) {
            break;
        }
  
        // Virus striked the corners, end loop
        if (inverted[j][i] == '*') {
            if (i == 0 && j == 8 || i == 20 && j == 8
                || i == 20 && j == 0) {
                break;
            }
        }
  
        // First time for the virus
        // to hit the boundary
        if (inverted[j][i] == '*' && bound == 0) {
  
            // Increment bound variable
            bound++;
  
            // Srikes the left wall
            if (i == 0 && j != 8 && j != 0) {
  
                // Turns 90 degree clockwise
                if (direct == 2) {
                    direct = 1;
                    i++;
                    j++;
                }
  
                // Else turns 90 degree anticlockwise
                else if (direct == 4) {
                    direct = 3;
                    j--;
                    i++;
                }
            }
  
            // Strikes the right wall
            else if (i == 20 && j != 0 && j != 8) {
  
                // Turns 90 degree anticlockwise
                if (direct == 1) {
                    direct = 2;
                    i--;
                    j++;
                }
  
                // Else turns 90 degree clockwise
                else if (direct == 3) {
                    direct = 4;
                    i--;
                    j--;
                }
            }
  
            // Strikes the upper wall
            else if (j == 8 && i != 0 && i != 20) {
  
                // Turns 90 degree anticlockwise
                if (direct == 2) {
                    direct = 4;
                    i--;
                    j--;
                }
                // Else turns 90 degree clockwise
                else if (direct == 1) {
                    direct = 3;
                    j--;
                    i++;
                }
            }
  
            // Strikes the lower wall
            else if (j == 0 && i != 0 && i != 20) {
  
                // Turns 90 degree clockwise
                if (direct == 4) {
                    direct = 2;
                    i--;
                    j++;
                }
  
                // Else turns 90 degree anticlockwise
                else if (direct == 3) {
                    direct = 1;
                    i++;
                    j++;
                }
            }
            continue;
        }
  
        // Make 'c' visited by replacing it by'-'
        if (inverted[j][i] == 'c') {
            temp[j][i] = '-';
  
            // Turns all directions 90
            // degree clockwise
            if (direct == 1) {
                direct = 3;
                j--;
                i++;
            }
            else if (direct == 2) {
                direct = 1;
                i++;
                j++;
            }
            else if (direct == 3) {
                direct = 4;
                i--;
                j--;
            }
            else if (direct == 4) {
                direct = 2;
                i--;
                j++;
            }
  
            // Increment count of infected citizens
            count++;
            continue;
        }
  
        // Make 'a' visited by replacing it by'-'
        if (inverted[j][i] == 'a') {
            temp[j][i] = '-';
  
            // Turns all directions by 90 degree
            // anticlockwise
            if (direct == 1) {
                direct = 2;
                i--;
                j++;
            }
            else if (direct == 2) {
                direct = 4;
                i--;
                j--;
            }
            else if (direct == 3) {
                direct = 1;
                i++;
                j++;
            }
            else if (direct == 4) {
                direct = 3;
                j--;
                i++;
            }
  
            // Increment count of
            // infected citizens
            count++;
            continue;
        }
  
        // Increment the counter diagonally
        // in the given direction.
        if (inverted[j][i] == '.') {
            if (direct == 1) {
                i++;
                j++;
            }
            else if (direct == 2) {
                i--;
                j++;
            }
            else if (direct == 3) {
                j--;
                i++;
            }
            else if (direct == 4) {
                i--;
                j--;
            }
            continue;
        }
    }
  
    // Print the mirror of the array
    // i.e. last row must be printed first.
    for (int i = 0; i <= 8; i++) {
        for (int j = 0; j < 20; j++) {
            cout << temp[8 - i][j];
        }
        cout << endl;
    }
  
    // Print safe and infected citizens
    cout << "safe=" << (total - count) << endl;
    cout << "infected=" << (count) << endl;
}
  
// Driver Code
int main()
{
  
    // Given 2D array
    char arr[row][col]
        = { { '*', '*', '*', '*', '*', '*', '*',
              '*', '*', '*', '*', '*', '*', '*',
              '*', '*', '*', '*', '*', '*' },
            { '*', '.', '.', '.', '.', '.', '.',
              '.', '.', '.', '.', '.', '.', '.',
              '.', '.', '.', '.', '.', '*' },
            { '*', '.', '.', 'c', '.', '.', '.',
              '.', '.', '.', '.', '.', '.', '.',
              '.', '.', '.', '.', '.', '*' },
            { '*', '.', '.', '.', '.', 'c', '.',
              '.', '.', '.', '.', '.', '.', '.',
              '.', '.', '.', '.', '.', '*' },
            { '*', '.', '.', '.', '.', '.', '.',
              '.', '.', '.', 'a', '.', '.', '.',
              '.', '.', '.', '.', '.', '*' },
            { '*', '.', '.', '.', '.', '.', '.',
              '.', '.', '.', '.', '.', '.', '.',
              '.', '.', '.', '.', '.', '*' },
            { '*', '.', '.', '.', '.', '.', '.',
              '.', 'a', '.', '.', '.', '.', '.',
              '.', 'c', '.', '.', '.', '*' },
            { '*', '.', '.', '.', '.', '.', '.',
              '.', '.', '.', '.', '.', '.', '.',
              '.', '.', '.', '.', '.', '*' },
            { '*', '*', '*', '*', '*', '*', '*',
              '*', '*', '*', '*', '*', '*', '*',
              '*', '*', '*', '*', '*', '*' } };
  
    // Function Call
    coronaVirus(arr);
    return 0;
}


输出:
0 0
1 1
2 2
3 3
4 4
5 5
6 4
7 3
8 2
9 3
10 4
9 5
8 6
7 7
6 8
5 7
4 6
3 5
2 4
1 3
0 2
********************
*..................*
*..c...............*
*....-.............*
*.........-........*
*..................*
*.......-......c...*
*..................*
********************
safe=2
infected=3

时间复杂度: O(R*C) 其中 R 是行数,C 是列数
辅助空间: O(R*C)

如果您希望与专家一起参加现场课程,请参阅DSA 现场工作专业课程学生竞争性编程现场课程