• Codeforces Round #327 div2


    Problem_A(591A):

    题意:

      有一段长度为l的路,两个人分别在两个端点,1, l。 现在已知每个人的速度为p,q. 求第一个人(初始位置在1)在他们第二次相遇的时候的位置。

      当他们相遇的时候, 他们会掉头返回走, 走到端点再返回来。

    思路:

      首先可以确定的是, 这两个人每次相遇的地点都是一样的。

      然后, 设他们相遇时时间为t, 所以有:p * t + q * t = l

      即:t = l / (p + q)

      第一个人位置即为:t * p = l / (p + q) * p;

    代码:

      

     1 #include <cmath>
     2 #include <cstdio>
     3 #include <cstring>
     4 #include <cstdlib>
     5 #include <ctime>
     6 #include <set>
     7 #include <map>
     8 #include <list>
     9 #include <stack>
    10 #include <queue>
    11 #include <string>
    12 #include <vector>
    13 #include <fstream>
    14 #include <iterator>
    15 #include <iostream>
    16 #include <algorithm>
    17 using namespace std;
    18 #define LL long long
    19 #define INF 0x3f3f3f3f
    20 #define MOD 1000000007
    21 #define eps 1e-6
    22 #define MAXN 1000000
    23 #define MAXM 100
    24 #define dd {cout<<"debug"<<endl;}
    25 #define pa {system("pause");}
    26 #define p(x) {printf("%d
    ", x);}
    27 #define pd(x) {printf("%.7lf
    ", x);}
    28 #define k(x) {printf("Case %d: ", ++x);}
    29 #define s(x) {scanf("%d", &x);}
    30 #define sd(x) {scanf("%lf", &x);}
    31 #define mes(x, d) {memset(x, d, sizeof(x));}
    32 #define do(i, x) for(i = 0; i < x; i ++)
    33 #define dod(i, x, l) for(i = x; i >= l; i --)
    34 #define doe(i, x) for(i = 1; i <= x; i ++)
    35 int l, p, q;
    36 
    37 int main()
    38 {
    39     scanf("%d %d %d", &l, &p, &q);
    40     printf("%.4lf
    ", (double)(l * 1.0 / (p * 1.0 + q * 1.0)) * (p * 1.0));
    41     return 0;
    42 }
    View Code

    Problem_B(591B):

    题意:

      给一个长度为n的字符串, 然后进行m次操作。

      每次操作(ch_a, ch_b):将当前字符串中所有的字符ch_a替换成ch_b, 所有的ch_b替换成ch_a

      求操作完后的字符串。

    思路:

      乍一看是个模拟, 再一看数据量2* 10 ^5 有点大, 不能直接模拟。

      题目中有个条件:所有字母均为小写字母!!!

      小写字母只有26个, 每次对这26个字母进行操作即可。

      设 f[i] = j 为初始字母为i + 'a'的字符 当前变换成j + 'a' 字符

      每次找出值为ch_a, ch_b的字符, 然后对其进行赋值操作即可。

      这样一来就成了O(m * 26) 妥妥的1s

    代码:

      

     1 #include <cmath>
     2 #include <cstdio>
     3 #include <cstring>
     4 #include <cstdlib>
     5 #include <ctime>
     6 #include <set>
     7 #include <map>
     8 #include <list>
     9 #include <stack>
    10 #include <queue>
    11 #include <string>
    12 #include <vector>
    13 #include <fstream>
    14 #include <iterator>
    15 #include <iostream>
    16 #include <algorithm>
    17 using namespace std;
    18 #define LL long long
    19 #define INF 0x3f3f3f3f
    20 #define MOD 1000000007
    21 #define eps 1e-6
    22 #define MAXN 200010
    23 #define MAXM 30
    24 #define dd {cout<<"debug"<<endl;}
    25 #define pa {system("pause");}
    26 #define p(x) {printf("%d
    ", x);}
    27 #define pd(x) {printf("%.7lf
    ", x);}
    28 #define k(x) {printf("Case %d: ", ++x);}
    29 #define s(x) {scanf("%d", &x);}
    30 #define sd(x) {scanf("%lf", &x);}
    31 #define mes(x, d) {memset(x, d, sizeof(x));}
    32 #define do(i, x) for(i = 0; i < x; i ++)
    33 #define dod(i, x, l) for(i = x; i >= l; i --)
    34 #define doe(i, x) for(i = 1; i <= x; i ++)
    35 int n, m;
    36 int name[MAXN];
    37 int f[MAXM];
    38 char read_char()
    39 {
    40     char ch;
    41     while(ch = getchar())
    42     {
    43         if(ch >= 'a' && ch <= 'z') return ch;
    44     }
    45 }
    46 int find_char(int x)
    47 {
    48     for(int i = 0; i < MAXM; i ++)
    49         if(f[i] == x) return i;
    50     return -1;
    51 }
    52 
    53 int main()
    54 {
    55     scanf("%d %d", &n, &m);
    56     for(int i = 0; i < n; i ++)
    57         name[i] = (read_char() - 'a');
    58     for(int i = 0; i < MAXM; i ++)
    59         f[i] = i;
    60     char ch_a, ch_b;
    61     for(int i = 0;i < m; i ++)
    62     {
    63         ch_a = read_char();
    64         ch_b = read_char();
    65         int pos_a = find_char(ch_a - 'a');
    66         int pos_b = find_char(ch_b - 'a');
    67         f[pos_a] = ch_b - 'a';
    68         f[pos_b] = ch_a - 'a';
    69     }
    70     for(int i = 0; i < n; i ++)
    71         printf("%c", f[name[i]] + 'a');
    72     printf("
    ");
    73     return 0;
    74 }
    View Code

    Problem_C(590A):

    题意:

      给一个长度为n的数组a[], 它有如下变化:

        1:b[0] = a[0], b[n-1] = b[n - 1]

        2:b[i] = (a[i - 1] , a[i], a[i + 1])的中位数

      且a[i] = 0 || a[i] = 1

      求出最少多少次变化之后, 此数组不能再变化(即变化后和变化前一样)

    思路:

      有一个规律不难发现:如果有两个以上连续相同的数 如11, 00 那么这两个数在接下来的变化中会保持不变!!!

      很简单, 因为是中位数, 而且只有0 1 那么如果a[i]的左右两边有一个或以上相同的数 那么a[i]就不会变。

      然后再来看看那些不连续的数的规律:

           1 1 0 1 0 1 0 1 0 0

      这个数最后会变成 1 1 1 1 1 0 0 0 0 0! 对称了, 再来看一个

           0 0 1 0 1 0 1 0 0

      变化后:   0 0 0 0 0 0 0 0 0 全变成0 了! 再改变一下两端连续的那个值找找规律  就会发现

        如果不连续串的长度为奇数, 那么它的左右两端肯定是相等的, 那么它中间的这段不连续的串最后都会变成它。且次数为(len / 2 + len % 2)

        如果不连续串的长度为偶数, 那么它的左右两端肯定是不等的,最后中间这段不连续的串都会对半变化! 左边的与左端点相等, 右边的与右端点相等。次数为 len /2

    代码:

      

      1 #include <cmath>
      2 #include <cstdio>
      3 #include <cstring>
      4 #include <cstdlib>
      5 #include <ctime>
      6 #include <set>
      7 #include <map>
      8 #include <list>
      9 #include <stack>
     10 #include <queue>
     11 #include <string>
     12 #include <vector>
     13 #include <fstream>
     14 #include <iterator>
     15 #include <iostream>
     16 #include <algorithm>
     17 using namespace std;
     18 #define LL long long
     19 #define INF 0x3f3f3f3f
     20 #define MOD 1000000007
     21 #define eps 1e-6
     22 #define MAXN 1000000
     23 #define MAXM 100
     24 #define dd {cout<<"debug"<<endl;}
     25 #define pa {system("pause");}
     26 #define p(x) {printf("%d
    ", x);}
     27 #define pd(x) {printf("%.7lf
    ", x);}
     28 #define k(x) {printf("Case %d: ", ++x);}
     29 #define s(x) {scanf("%d", &x);}
     30 #define sd(x) {scanf("%lf", &x);}
     31 #define mes(x, d) {memset(x, d, sizeof(x));}
     32 #define do(i, x) for(i = 0; i < x; i ++)
     33 #define dod(i, x, l) for(i = x; i >= l; i --)
     34 #define doe(i, x) for(i = 1; i <= x; i ++)
     35 int n;
     36 int a[MAXN];
     37 void read()
     38 {
     39     for(int i = 0; i < n; i ++)
     40         scanf("%d", &a[i]);
     41 }
     42 
     43 void solve()
     44 {
     45     int cnt = 0;
     46     for(int i = 0; i < n;)
     47     {
     48         int j = i;
     49         while(j + 1 < n && a[j] != a[j + 1])
     50             j ++;
     51         j ++;
     52         cnt = max(cnt, (j - i - 2) / 2 + (j - i - 2) % 2);
     53         if((j - i) % 2 == 1)
     54         {
     55             for(int k = i + 1; k < j; k ++)
     56                 a[k] = a[i];
     57         }
     58         else 
     59         {
     60             for(int k = i + 1; k < (i + j) / 2; k ++)
     61                 a[k] = a[i];
     62             for(int k = (i + j) / 2; k < j; k ++)
     63                 a[k] = a[j - 1];
     64         }
     65         i = j;
     66     }
     67     printf("%d
    ", cnt);
     68     for(int i = 0; i < n - 1; i ++)
     69         printf("%d ", a[i]);
     70     printf("%d
    ", a[n - 1]);
     71 }
     72 int get_ans(int l, int r)
     73 {
     74     if(l == r) return 0;
     75     if(a[l] == a[r])
     76     {
     77         for(int i = l + 1; i < r; i ++)
     78             a[i] = a[l];
     79         return (r - l) / 2;
     80     } 
     81     else 
     82     {
     83         for(int i = l + 1; i < (l + r + 1) / 2; i ++)
     84             a[i] = a[l];
     85         for(int i = (l + r + 1) / 2; i < r; i ++)
     86             a[i] = a[r];
     87         return (r - l - 1) / 2;
     88     }
     89 }
     90 void solve_2()
     91 {
     92     int l = 0, ans = 0;
     93     for(int i = 0; i < n; i ++)
     94         if(i == n - 1 || a[i] == a[i + 1])
     95         {
     96             ans = max(ans, get_ans(l, i));
     97             l = i + 1;
     98         }
     99     printf("%d
    ", ans);
    100     for(int i = 0; i < n; i ++)
    101         printf(i == n - 1? "%d
    " : "%d ", a[i]);
    102 }
    103 
    104 int main()
    105 {
    106     scanf("%d", &n);
    107     read();
    108     // solve();
    109     solve_2();
    110     return 0;
    111 }
    View Code

    Problem_D(590B):

    题意:

      在一个二维坐标系上, 给两个点, 一个起点(x1, y1), 一个终点(x2, y2).

      一个时间t, 一个最大速度vmax

      然后给两个速度向量(vx, vy), (wx, wy).

      从起点飞到终点, 方向和速度可以在任何时刻随意变换, 速度不超过vmax即可。

      在前t秒, 会受到风的阻力(vx, vy). t秒风的速度变成(wx, wy)。 求到终点的最短时间。

    思路:

      首先, 不考虑方向和风的影响, 以最大速度前进, 那么ts内的移动的距离就是vmax * t。 如果再加上方向呢?

      是不是就成了一个圆:

        圆心 O = (x1, y1)

        半径 r = vmax * t

      再加上风的影响呢?

      是不就就是将这个圆整体位移(vx*t, vy*t) ?

      此时圆为:

        圆心 O = (x1 + vx * t, y1 + vy * t)

        半径 r = vmax * t

      如果此时, 终点在圆内, 是否代表在ts内可以到达?

      如果终点在圆外, 那么设时间为w, 此时这个圆:

        圆心O =  (x1 + vx * t + wx * (w - t), y1 + vy * t + wy * (w - t))

        半径r = vmax * w

      

      所以, 对时间进行二分, 找到最小的满足终点在圆内的时间即可。

    代码:

      

     1 #include <cmath>
     2 #include <cstdio>
     3 #include <cstring>
     4 #include <cstdlib>
     5 #include <ctime>
     6 #include <set>
     7 #include <map>
     8 #include <list>
     9 #include <stack>
    10 #include <queue>
    11 #include <string>
    12 #include <vector>
    13 #include <fstream>
    14 #include <iterator>
    15 #include <iostream>
    16 #include <algorithm>
    17 using namespace std;
    18 #define LL long long
    19 #define INF 0x3f3f3f3f
    20 #define MOD 1000000007
    21 #define eps 1e-6
    22 #define MAXN 1000000
    23 #define MAXM 100
    24 #define dd {cout<<"debug"<<endl;}
    25 #define pa {system("pause");}
    26 #define p(x) {printf("%d
    ", x);}
    27 #define pd(x) {printf("%.7lf
    ", x);}
    28 #define k(x) {printf("Case %d: ", ++x);}
    29 #define s(x) {scanf("%d", &x);}
    30 #define sd(x) {scanf("%lf", &x);}
    31 #define mes(x, d) {memset(x, d, sizeof(x));}
    32 #define do(i, x) for(i = 0; i < x; i ++)
    33 #define dod(i, x, l) for(i = x; i >= l; i --)
    34 #define doe(i, x) for(i = 1; i <= x; i ++)
    35 double x[2], y[2];
    36 double v, t;
    37 double vx, vy, wx, wy;
    38 double sqr(double x)
    39 {
    40     return x * x;
    41 }
    42 double dis(double x1, double y1, double x2, double y2)
    43 {
    44     return sqrt(sqr(x1 - x2) + sqr(y1 - y2));
    45 }
    46 bool is_ok(double tmp_t)
    47 {
    48     double tx, ty;
    49     if(tmp_t > t)
    50     {
    51         tx = x[0] + t * vx + wx * (tmp_t - t);
    52         ty = y[0] + t * vy + wy * (tmp_t - t);
    53     }
    54     else 
    55     {
    56         tx = x[0] + tmp_t * vx;
    57         ty = y[0] + tmp_t * vy;
    58     }
    59     double ans = dis(tx, ty, x[1], y[1]);
    60     if(ans < v * tmp_t) return true;
    61     return false;
    62 }
    63 
    64 int main()
    65 {
    66     scanf("%lf %lf %lf %lf", &x[0], &y[0], &x[1], &y[1]);
    67     scanf("%lf %lf", &v, &t);
    68     scanf("%lf %lf %lf %lf", &vx, &vy, &wx, &wy);
    69     double ans_l = 0, ans_r = 1e8, mid;
    70     while((ans_r - ans_l) >= eps)
    71     {
    72         mid = (ans_l + ans_r) / 2.0;
    73         if(is_ok(mid)) ans_r = mid;
    74         else ans_l = mid;
    75     }
    76     printf("%.7lf
    ", ans_l);
    77     return 0;
    78 }
    View Code

    Porblem_E(590C):

    题意:

      一个n * m的网格, #代表不能走, .代表沼泽,1 2 3 分别代表一类区域

      现在要将这三个区域连通, 你可以把沼泽变成路。 求变化最少的沼泽, 使得三个区域连通起来。

    思路:

      因为1,2,3 可以看成三个块, 也可以看成三类起点。

      将所有的1, 2, 3记录下来, 以此为起点, 搜索三次。

      然后枚举它们三个区域的交点, 算出到三个区域的长度(沼泽数量),取最小值即可。

    代码:

      

      1 #include <cmath>
      2 #include <cstdio>
      3 #include <cstring>
      4 #include <cstdlib>
      5 #include <ctime>
      6 #include <set>
      7 #include <map>
      8 #include <list>
      9 #include <stack>
     10 #include <queue>
     11 #include <string>
     12 #include <vector>
     13 #include <fstream>
     14 #include <iterator>
     15 #include <iostream>
     16 #include <algorithm>
     17 using namespace std;
     18 #define LL long long
     19 #define INF 1000100
     20 #define MOD 1000000007
     21 #define eps 1e-6
     22 #define MAXN 1010
     23 #define MAXM 3
     24 #define dd {cout<<"debug"<<endl;}
     25 #define pa {system("pause");}
     26 #define p(x) {printf("%d
    ", x);}
     27 #define pd(x) {printf("%.7lf
    ", x);}
     28 #define k(x) {printf("Case %d: ", ++x);}
     29 #define s(x) {scanf("%d", &x);}
     30 #define sd(x) {scanf("%lf", &x);}
     31 #define mes(x, d) {memset(x, d, sizeof(x));}
     32 #define do(i, x) for(i = 0; i < x; i ++)
     33 #define dod(i, x, l) for(i = x; i >= l; i --)
     34 #define doe(i, x) for(i = 1; i <= x; i ++)
     35 int n, m;
     36 int step[MAXM][MAXN][MAXN];
     37 int dir[4][2] = {{-1, 0}, {1, 0}, {0, -1}, {0, 1}};
     38 int grid[MAXN][MAXN];
     39 int read_ch()
     40 {
     41     char ch;
     42     while(ch = getchar())
     43     {
     44         if(ch >= '1' && ch <= '3') return (int)(ch - '1');
     45         if(ch == '.') return -1;
     46         if(ch == '#') return -2;
     47     }
     48 }
     49 bool check(int i, int j)
     50 {
     51     if(i < 0 || i >= n || j < 0 || j >= m || grid[i][j] == -2) return false;
     52     return true;
     53 }
     54 void bfs(int pos)
     55 {
     56     queue <int> Q;
     57     while(!Q.empty()) Q.pop();
     58     for(int i = 0; i < n; i ++)
     59         for(int j = 0; j < m; j ++)
     60             if(grid[i][j] == pos)
     61             {
     62                 Q.push(i);
     63                 Q.push(j);
     64                 step[pos][i][j] = 0;
     65             }
     66     while(!Q.empty())
     67     {
     68         int x = Q.front();
     69         Q.pop();
     70         int y = Q.front();
     71         Q.pop();
     72 
     73         for(int i = 0; i < 4; i ++)
     74         {
     75             int xx = x + dir[i][0];
     76             int yy = y + dir[i][1];
     77             if(!check(xx, yy)) continue;
     78             if(step[pos][xx][yy] > step[pos][x][y] + (grid[x][y] == -1))
     79             {
     80                 step[pos][xx][yy] = step[pos][x][y] + (grid[x][y] == -1);
     81                 Q.push(xx);
     82                 Q.push(yy);
     83             }
     84         }
     85     }
     86 }
     87 
     88 void show(int pos)
     89 {
     90     printf("%d
    ", pos);
     91     for(int i = 0; i < n; i ++, printf("
    "))
     92         for(int j = 0; j < m; j ++)
     93             printf("%d ", step[pos][i][j]);
     94     printf("
    ");
     95 }
     96 
     97 int main()
     98 {
     99     mes(grid, 0);
    100     for(int k = 0; k < MAXM; k ++)
    101         for(int i = 0; i < MAXN; i ++)
    102             for(int j = 0; j < MAXN; j ++)
    103                 step[k][i][j] = INF;
    104 
    105     scanf("%d %d", &n, &m);
    106     for(int i = 0; i < n; i ++)
    107         for(int j = 0; j < m; j ++)
    108             grid[i][j] = read_ch();
    109 
    110     for(int i = 0; i < MAXM; i ++)
    111         bfs(i);
    112 
    113     int ans = INF * 3;
    114     for(int i = 0; i < n; i ++)
    115         for(int j = 0; j < m; j ++)
    116             ans = min(ans, step[0][i][j] + step[1][i][j] + step[2][i][j] + (grid[i][j] == -1));
    117     if(ans >= INF) ans = -1;
    118     printf("%d
    ", ans);
    119     return 0;
    120 }
    View Code
  • 相关阅读:
    AccessTokenValidation3 源码分析 jwttoken验证流程图
    .net core dump分析
    9102年了,汇总下HttpClient问题,封印一个
    Asp.net 性能监控之压测接口“卡住” 分析
    IdentityServer4源码颁发token分析及性能优化
    博客园设置看板娘和看板猫
    C# winform websocket学习笔记(三)HTML客户端
    C# winform websocket学习笔记(三)winform客户端
    C# winform websocket学习笔记(二)winform服务端
    C# winform websocket学习笔记(一)准备
  • 原文地址:https://www.cnblogs.com/By-ruoyu/p/5526407.html
Copyright © 2020-2023  润新知