• BZOJ 1415: [Noi2005]聪聪和可可


    题目链接:http://www.lydsy.com/JudgeOnline/problem.php?id=1415

    题意:

    有一个无向图,有N个景点1-N,有E条路。

    可可在景点M处,之后每个时间单位,可可会选择去相邻的景点中的一个或停留在原景点不动。去这些地方的概率是相等的。

    聪聪开始在景点C,聪聪会选择一个更靠近可可的景点,如果这样的景点有多个,则会选择一个标号最小的景点。

    如果走完第一步以后仍然没吃到可可,她还可以在本段时间内再向可可走近一步。

    在每个时间单位,聪聪先走,可可后走,若某时刻处于同一景点,则可可被吃到了。

    求平均情况下,聪聪几步可以吃掉可可。

    思路:

    预处理出P[i][j]表示聪聪在i点可可在j点,聪聪下一步要到达的点。

    dp[i][j]表示聪聪在i点可可在j点,聪聪抓住可可的平均步数。

    dp[0][0] = 0,如果P[P[i][j]][j] = j 或 P[i][j] = j,那么dp[i][j] = 1。

    除这两种情况,聪聪下一步的位置是P[P[i][j]][j],可可下一步是w[j][k]。概率为1/(j的度数+1)

    那么可以得到递推式dp[i][j]=(segma(dp[p[p[i][j]][j][w[j][k]])+dp[p[p[i][j]][j]][j])/(t[i]+1) + 1

     1 /*
     2  * Problem:
     3  * Created Time:  2015/12/9 15:55:15
     4  * File Name: test.cpp
     5  */
     6 //#include <bits/stdc++.h>
     7 #include <iostream>
     8 #include <cstring>
     9 #include <cstdio>
    10 #include <string>
    11 #include <queue>
    12 #include <vector>
    13 using namespace std;
    14 int N, E, C, M;
    15 #define maxn 1010
    16 vector <int> mp[maxn];
    17 int p[maxn][maxn];
    18 double dp[maxn][maxn];
    19 int dist[maxn];
    20 int t[maxn];
    21 int min(int a, int b)
    22 {
    23     return a<b?a:b;
    24 }
    25 void bfs(int s)
    26 {
    27     queue <int> q;
    28     q.push(s);
    29     int vis[maxn];
    30     memset(vis, 0, sizeof(vis));
    31     memset(dist, -1, sizeof(dist));
    32     dist[s] = 0;
    33     vis[s] = 1;    
    34     while(!q.empty())
    35     {
    36         int u = q.front(); q.pop();
    37         for(int i = 0; i < mp[u].size(); i++)
    38         {
    39             if(dist[mp[u][i]] == -1)
    40             {
    41                 dist[mp[u][i]] = dist[u]+1;
    42                 p[mp[u][i]][s] = u;
    43                 q.push(mp[u][i]);
    44             }
    45             else if(dist[mp[u][i]] == dist[u]+1) p[mp[u][i]][s] = min(p[mp[u][i]][s], u);
    46         }
    47     }
    48 }
    49 double dfs(int from, int to)
    50 {
    51     if(dp[from][to] != -1) return dp[from][to];
    52  
    53     if(from == to) return dp[from][to] = 0;
    54     if(p[from][to] == to || p[p[from][to]][to] == to) return dp[from][to] = 1.0;
    55  
    56     double sum = dfs(p[p[from][to]][to], to); //留在原地
    57     for(int i = 0; i < mp[to].size(); i++)
    58     {
    59         sum += dfs(p[p[from][to]][to], mp[to][i]);
    60     }
    61     sum /= (t[to]+1.0); sum += 1;
    62     return dp[from][to] = sum;
    63  
    64  
    65 }
    66 int main() 
    67 {
    68   //  freopen("in.txt", "r", stdin);
    69     while(~scanf("%d%d", &N, &E))
    70     {
    71         scanf("%d%d", &C, &M);
    72         for(int i = 1; i <= N; i++) mp[i].clear();
    73         memset(t, 0, sizeof(t));
    74         for(int i = 1; i <= E; i++)
    75         {
    76             int a, b;
    77             scanf("%d%d", &a, &b);
    78             t[a]++; t[b]++;
    79             mp[a].push_back(b);
    80             mp[b].push_back(a);  
    81         }
    82         memset(p, -1, sizeof(p));
    83         for(int i = 1; i <= N; i++) bfs(i);
    84         for(int i = 1; i <= N; i++)
    85         {
    86             for(int j = 1; j <= N; j++) dp[i][j] = -1;
    87         }
    88         double ans = dfs(C, M);
    89         printf("%.3lf
    ", ans);
    90           
    91     }
    92     return 0;
    93 }
  • 相关阅读:
    玩转xss
    Anonim小白成长计划
    mssql注入与绕过
    了解mssql数据库
    2020年度学习规划
    access 注入
    bypasswaf 之报错注入
    bypasswaf之盲注
    sql注入常用函数与bypasswaf
    一篇关于数据库的另类操作
  • 原文地址:https://www.cnblogs.com/titicia/p/5034102.html
Copyright © 2020-2023  润新知