sdut 2878 Circle 高斯消元

题意:

在一个0~n的环上每次可以向左走或向右走
求走到x的步数的期望
分析:
因为是环形的不好递推
考虑到 dp【i】=dp【(i+1)%n】/2+ dp【(i-1)%n】/2+1
可以转化为 dp【i】-dp【(i+1)%n】/2-dp【(i-1)%n】/2=1
所以可以列n个方程利用高斯消元来解貌似网上有别的做法表示看不懂orz
ACcode:
#include <cmath>  
#include <cstdio>  
#include <cstring>  
#include <algorithm>  
#include <iostream>  
#define maxn 1005  
using namespace std;  
double a[maxn][maxn],x[maxn];  
double Gauss(int n){  
    int row,col,max_r;  
    int equ=n,var=n;  
    for(row=0,col=0;row<equ&&col<var;row++,col++){  
        max_r=row;  
        for(int i=row+1;i<var;i++)  
            if(fabs(a[i][col])>fabs(a[max_r][col]))  
                max_r=i;  
        if(max_r!=row)  
            for(int j=row;j<n+1;j++)  
                swap(a[max_r][j],a[row][j]);  
        for(int i=row+1;i<var;i++)  
            if(fabs(a[i][col])>=1e-8){  
                double tmp=a[i][col]/a[row][col];  
                for(int j=col;j<n+1;j++)  
                    a[i][j]-=a[row][j]*tmp;  
            }  
    }  
    for(int i=equ-1;i>=0;i--){  
        double tmp=a[i][n];  
        for(int j=i+1;j<n;j++)  
            if(fabs(a[i][j])>1e-8)  
                tmp-=a[i][j]*x[j];  
        x[i]=tmp/a[i][i];  
    }  
    return x[0];  
}  
int main(){  
    int loop,my_x,n;  
    scanf("%d",&loop);  
    while(loop--){  
        scanf("%d%d",&n,&my_x);  
        memset(a,0,sizeof(a));  
        for(int i=0;i<n;++i)  
            if(i!=my_x){  
                a[i][i]=a[i][n]=1;  
                a[i][(i-1+n)%n]=a[i][(i+1)%n]=-0.5;  
            }  
        a[my_x][my_x]=1;a[my_x][n]=0;  
       printf("%.4lf\n",Gauss(n));  
    }  
    return 0;  
}


  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值