結果

問題 No.425 ジャンケンの必勝法
ユーザー btkbtk
提出日時 2016-09-22 08:02:09
言語 C++14
(gcc 12.3.0 + boost 1.83.0)
結果
WA  
実行時間 -
コード長 2,838 bytes
コンパイル時間 2,076 ms
コンパイル使用メモリ 181,688 KB
実行使用メモリ 13,884 KB
最終ジャッジ日時 2024-04-28 18:25:29
合計ジャッジ時間 5,531 ms
ジャッジサーバーID
(参考情報)
judge4 / judge1
このコードへのチャレンジ
(要ログイン)

テストケース

テストケース表示
入力 結果 実行時間
実行使用メモリ
testcase_00 AC 2 ms
13,884 KB
testcase_01 WA -
testcase_02 AC 1 ms
6,944 KB
testcase_03 WA -
testcase_04 WA -
testcase_05 WA -
testcase_06 TLE -
testcase_07 -- -
testcase_08 -- -
testcase_09 -- -
testcase_10 -- -
testcase_11 -- -
testcase_12 -- -
testcase_13 -- -
testcase_14 -- -
testcase_15 -- -
testcase_16 -- -
testcase_17 -- -
testcase_18 -- -
testcase_19 -- -
testcase_20 -- -
testcase_21 -- -
testcase_22 -- -
権限があれば一括ダウンロードができます

ソースコード

diff #

#include<bits/stdc++.h>

using namespace std;

struct cww{
    cww(){
        ios::sync_with_stdio(false);cin.tie(0);
        cout<<fixed<<setprecision(20);
    }
}init;

typedef double D;
typedef vector<D> VD;
typedef vector<VD> VVD;

D vecmul(const VD a,const VD b){
    D res=0;
    int size=a.size();
    for(int i=0;i<size;i++)
        res+=a[i]*b[i];
    return res;
}
VD matmul(const VVD a,const VD b){
    int sz=a.size();
    VD res(sz,0.0);
    for(int i=0;i<sz;i++)
        for(int j=0;j<sz;j++)
            res[i]+=a[i][j]*b[j];
    return res;
}
VVD matmul(const VVD a,const VVD b){
    int sz=a.size();
    VVD res(sz,VD(sz,0.0));
    for(int i=0;i<sz;i++)
        for(int j=0;j<sz;j++)
            for(int k=0;k<sz;k++)
                res[i][j]+=a[i][k]*b[k][j];
    return res;
}
VD nxt(D p){
    D a=3/(1-p);
    D b=-a*(p/2);
    return {a,b,b-1};
}
VD prv(D p){
    D a=2/p;
    D b=-a*((1-p)/3);
    return {a,b,b-1};
}

const D eps=1e-9;
int main(){
    D p,q,a,b,c,d,s,p1,p0,ps,res;
    cin>>p>>q;
    //q==0だけ場合分け
    if(q==0){
        res=(p+2)/(4-p);
    }
    else{
        //p1=a*p0+bを求める
        {
            VD x={3,1,0};
            VD y={-1,0,1};
            D t=q;
            while(t<1){
                D nt=min(t+q,1.0);
                VVD mat={nxt(t),{1.0,0.0,0.0},{0.0,0.0,1.0}};
                x=matmul(mat,x);
                y=matmul(mat,y);
                t=nt;
            }
            a=x[0];b=y[0];
        }
        //p0=c*p1+dを求める
        {
            VD x={2,1,0};
            VD y={-1,0,1};
            D t=1-q;
            while(t>0){
                D nt=max(t-q,0.0);
                VVD mat={prv(t),{1.0,0.0,0.0},{0.0,0.0,1.0}};
                x=matmul(mat,x);
                y=matmul(mat,y);
                t=nt;
            }
            c=x[0];d=y[0];
        }
        //cout<<a<<" "<<b<<" "<<c<<" "<<d<<endl;
        //p0とp1がa,b,c,dから求まる
        p1=(a*d+b)/(1-a*c);
        p0=(c*p1+d);
        //cout<<"p0="<<p0<<endl;
    
        // cout<<"p1="<<p1<<endl;
        s=p;
        while(s-q>0)s-=q;
        {
            VVD m={{1.0,0.0,0.0},{0.0,1.0,0.0},{0.0,0.0,1.0}};
            D ss=s;
            while(ss<1){
                D nss=min(ss+q,1.0);
                m=matmul({nxt(ss),{1.0,0.0,0.0},{0.0,0.0,1.0}},m);
                ss=nss;
            }
            ps=(p1-m[0][1]*p0-m[0][2])/m[0][0];
        }
    
        //cout<<"ps="<<ps<<endl;
        {
            VVD m={{1.0,0.0,0.0},{0.0,1.0,0.0},{0.0,0.0,1.0}};
            D ss=s;
            while(ss<p){
                D nss=min(ss+q,1.0);
                m=matmul({nxt(ss),{1.0,0.0,0.0},{0.0,0.0,1.0}},m);
                ss=nss;
            }
            res=m[0][0]*ps+m[0][1]*p0+m[0][2];
        }
    }
    
    cout<<1.0/3+res/3.0<<endl;
    return 0;
}
0