题意:二维平面上右一点集\(S\),共\(n\)个元素,开始位于平面上任意点\(P\),\(P\)不一定属于\(S\),每次操作为选一条至少包含\(S\)中两个元素和当前位置\(P\)的直线,每条直线选取概率相同,同一直线上每个点\(Q \in S\) 选取概率相同,\(Q\)次询问 包含两个元素\(t,m\) 即点\(P\)到\(t\)共操作\(m\)次的最大概率

打了场\(CF\) 结果\(D\)题死活调不出来 只能一大早来补题了

可以想到记录\(f[i][j][k]\)表示从点\(i\)到点\(j\)走\(k\)步的概率 这个过程我们可以通过记录\(2^x\)的矩阵来存储

之后可以发现对于一个询问\(t,m\) 我们可以通过矩阵的转移得到走\(m-1\)步的答案 之所以不能直接走\(m\)步是因为第一步的点P不一定在\(S\)内 分析一下就可以发现 一条线\(l\)上的点的概率就\(\frac {\sum_{(i \in S)}probility[i]}{\sum_{(i \in S)}1}\) 对所有直线取个\(max\)就是答案了

复杂度 \(O((n + q) \cdot n^2 \cdot \log m)\)

#include<bits/stdc++.h>
using namespace std;
#define FO(x) {freopen(#x".in","r",stdin);freopen(#x".out","w",stdout);}
#define pa pair<int,int>
#define mod 1000000007
#define ll long long
#define mk make_pair
#define pb push_back
#define fi first
#define se second
#define cl(x) memset(x,0,sizeof x)
#ifdef Devil_Gary
#define bug(x) cout<<(#x)<<" "<<(x)<<endl
#define debug(...) fprintf(stderr, __VA_ARGS__)
#else
#define bug(x)
#define debug(...)
#endif
const int INF = 0x7fffffff;
const int N=2e2+5;
/*
char *TT,*mo,but[(1<<15)+2];
#define getchar() ((TT==mo&&(mo=(TT=but)+fread(but,1,1<<15,stdin),TT==mo))?-1:*TT++)//*/
inline int read(){
int x=0,rev=0,ch=getchar();
while(ch<'0'||ch>'9'){if(ch=='-')rev=1;ch=getchar();}
while(ch>='0'&&ch<='9'){x=(x<<1)+(x<<3)+ch-'0';ch=getchar();}
return rev?-x:x;
}
int n,flg,x[N],y[N];
double ans,pro[N],tmp[N];
vector<vector<int> > lines;
struct matrix{
double g[N][N];
matrix operator * (const matrix&a){
matrix c;cl(c.g);
for(int i=0;i<n;i++)
for(int j=0;j<n;j++)
for(int k=0;k<n;k++)
c.g[i][j]+=g[i][k]*a.g[k][j];
return c;
}
}f[15];
pa fix(pa a){
if(a.fi==0) return mk(0,1);
if(a.se==0) return mk(1,0);
int d=__gcd(a.fi,a.se);
a.fi/=d,a.se/=d;
if(a.fi<0) a.fi*=-1,a.se*=-1;
return a;
}
void add(int p){
map<pa ,vector<int>>cnt;
for(int i=0;i<n;i++) if(i!=p){
int dx=x[i]-x[p],dy=y[i]-y[p];
cnt[fix(mk(dx,dy))].pb(i);
}
int sz=cnt.size();
for(auto u:cnt){
u.se.pb(p),flg=1;
for(auto v:u.se){
f[0].g[p][v]+=1.0/u.se.size()/sz;
if(v<p) flg=0;
}
if(flg) lines.pb(u.se);
}
}
int main(){
#ifdef Devil_Gary
freopen("in.txt","r",stdin);
#endif
n=read();
for(int i=0;i<n;i++) x[i]=read(),y[i]=read();
for(int i=0;i<n;i++) add(i);
for(int i=1;i<=14;i++) f[i]=f[i-1]*f[i-1];
for(int Q=read();Q;Q--){
int t=read()-1,m=read()-1;
for(int i=0;i<n;i++) pro[i]=0;pro[t]=1.0;
for(int i=0;i<=14;i++){
if(m&(1<<i)){
for(int j=0;j<n;j++) tmp[j]=pro[j],pro[j]=0;
for(int j=0;j<n;j++) for(int k=0;k<n;k++){
pro[j]+=tmp[k]*f[i].g[j][k];
}
}
}
ans=0;
for(auto line:lines){
double temp=0;
for(auto u:line) temp+=pro[u];
ans=max(ans,temp/line.size());
}
printf("%.12lf\n",ans);
}
}

Codeforces 989E A Trance of Nightfall 矩阵快速幂+DP的更多相关文章

  1. Codeforces 576D Flights for Regular Customers 矩阵快速幂+DP

    题意: 给一个$n$点$m$边的连通图 每个边有一个权值$d$ 当且仅当当前走过的步数$\ge d$时 才可以走这条边 问从节点$1$到节点$n$的最短路 好神的一道题 直接写做法喽 首先我们对边按$ ...

  2. Codeforces Round #536 (Div. 2) F 矩阵快速幂 + bsgs(新坑) + exgcd(新坑) + 欧拉降幂

    https://codeforces.com/contest/1106/problem/F 题意 数列公式为\(f_i=(f^{b_1}_{i-1}*f^{b_2}_{i-2}*...*f^{b_k} ...

  3. codeforces 691E 矩阵快速幂+dp

    传送门:https://codeforces.com/contest/691/problem/E 题意:给定长度为n的序列,从序列中选择k个数(可以重复选择),使得得到的排列满足xi与xi+1异或的二 ...

  4. Codeforces 514E Darth Vader and Tree 矩阵快速幂

    Darth Vader and Tree 感觉是个很裸的矩阵快速幂, 搞个100 × 100 的矩阵, 直接转移就好啦. #include<bits/stdc++.h> #define L ...

  5. CodeForces 450B Jzzhu and Sequences(矩阵快速幂)题解

    思路: 之前那篇完全没想清楚,给删了,下午一上班突然想明白了. 讲一下这道题的大概思路,应该就明白矩阵快速幂是怎么回事了. 我们首先可以推导出 学过矩阵的都应该看得懂,我们把它简写成T*A(n-1)= ...

  6. codeforces 450B B. Jzzhu and Sequences(矩阵快速幂)

    题目链接: B. Jzzhu and Sequences time limit per test 1 second memory limit per test 256 megabytes input ...

  7. Product Oriented Recurrence(Codeforces Round #566 (Div. 2)E+矩阵快速幂+欧拉降幂)

    传送门 题目 \[ \begin{aligned} &f_n=c^{2*n-6}f_{n-1}f_{n-2}f_{n-3}&\\ \end{aligned} \] 思路 我们通过迭代发 ...

  8. Codeforces 954 dijsktra 离散化矩阵快速幂DP 前缀和二分check

    A B C D 给你一个联通图 给定S,T 要求你加一条边使得ST的最短距离不会减少 问你有多少种方法 因为N<=1000 所以N^2枚举边数 迪杰斯特拉两次 求出Sdis 和 Tdis 如果d ...

  9. P1357 花园 (矩阵快速幂+ DP)

    题意:一个只含字母C和P的环形串 求长度为n且每m个连续字符不含有超过k个C的方案数 m <= 5  n <= 1e15 题解:用一个m位二进制表示状态 转移很好想 但是这个题是用矩阵快速 ...

随机推荐

  1. Python单元测试unittest - 单元测试框架

    一.unittest简介 unitest单元测试框架最初是有JUnit的启发,它支持测试自动化,共享测试的设置和关闭代码,将测试聚合到集合中,以及测试与报告框架的独立性. 二.unittest相关概念 ...

  2. 转载:Java中的字符串常量池详细介绍

    引用自:http://blog.csdn.net/langhong8/article/details/50938041 这篇文章主要介绍了Java中的字符串常量池详细介绍,JVM为了减少字符串对象的重 ...

  3. UITableView滑动性能优化扩展

    一点UITableView滑动性能优化扩展 影响UITableView的滑动,有哪些因素呢?  关于这一点,人眼能识别的帧率是60左右,这也就是为什么,电脑屏幕的最佳帧率是60Hz.  屏幕一秒钟会刷 ...

  4. 并发之atomicInteger与CAS机制

    并发之atomic与CAS自旋锁 通过前几章的讲解我们知道i++这种类似操作是不安全的.针对这种情况,我们可能会想到利用synchronize关键字实现线程同步,保证++操作的原子性,的确这是一种有效 ...

  5. linux 搜索文件

    https://blog.csdn.net/json_ligege/article/details/72865645 1.find   find是最常见和最强大的查找命令,你可以用它找到任何你想找的文 ...

  6. poj1742 多维背包

    普通的多维背包做不了,需要优化一下 但是没有学优化..别的方法也是可以做的 省去一个 表示阶段的 i 维度,dp[j]表示面值为j的钱是否被凑出来了,used[j]表示第i种硬币在凑面值为j的时候被用 ...

  7. 【HTTP】 Fiddler简介

    1.为什么是Fiddler? 抓包工具有很多,小到最常用的web调试工具firebug,达到通用的强大的抓包工具wireshark.为什么使用fiddler?原因如下: a.Firebug虽然可以抓包 ...

  8. python 全栈开发,Day113(方法和函数的区别,yield,反射)

    一.方法和函数的区别 面向对象 初级 class StarkConfig(object): def __init__(self,model_class): self.model_class = mod ...

  9. [转] python安装numpy和pandas

    最近要对一系列数据做同比比较,需要用到numpy和pandas来计算,不过使用python安装numpy和pandas因为linux环境没有外网遇到了很多问题就记下来了.首要条件,python版本必须 ...

  10. c++ primer 笔记 (二)

    第二章笔记  (貌似记得有点多)   把负值赋给unsigned对象时完全合法的,其结果是该负数对该类型的取值个数求模后的值   -1     (对265求模)  255   float型只能保证6位 ...