bzoj 1002 [FJOI2007]轮状病毒——打表找规律

题目:https://www.lydsy.com/JudgeOnline/problem.php?id=1002

看 Zinn 的博客:https://www.cnblogs.com/Zinn/p/9252831.html

时隔六个月,自己终于也 A 了这道题。

#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cmath>
#define db double
using namespace std;
const int N=105;
int n;db a[N][N];
db get()
{
  db ret=1;
  for(int i=1;i<=n;i++)
    {
      for(int j=i+1;j<=n;j++)
    if(fabs(a[j][i])>fabs(a[i][i]))
      {
        for(int t=i;t<=n;t++)swap(a[i][t],a[j][t]);
      }
      if(!a[i][i])return 0;
      for(int j=i+1;j<=n;j++)
    {
      db sl=a[j][i]/a[i][i];
      for(int t=i;t<=n;t++)a[j][t]-=sl*a[i][t];
    }
      ret*=a[i][i];
    }
  return ret;
}
int main()
{
  int lm;scanf("%d",&lm);
  for(n=3;n<=lm;n++)
    {
      for(int i=1;i<=n;i++)for(int j=1;j<=n;j++)a[i][j]=0;
      for(int i=1;i<=n;i++)
    {
      a[i][i]+=3;
      i==1?a[i][n]-=1:a[i][i-1]-=1;
      i==n?a[i][1]-=1:a[i][i+1]-=1;
      a[i][n+1]-=1;a[n+1][i]-=1;
    }
      a[n+1][n+1]+=n;
      printf("%.0f ",get());
    }
  puts("");
  return 0;
}

打表

精度误差真的很大。

#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const int N=105,base=1e8;
int n,a[N][N];
void mul(int *a,int *ret,int b)
{
  ret[0]=a[0];
  for(int i=1;i<=a[0];i++)
    ret[i]=a[i]*b;
  for(int i=1;i<=ret[0];i++)
    ret[i+1]+=ret[i]/base,ret[i]%=base;
  while(ret[ret[0]+1])ret[0]++,ret[ret[0]+1]+=ret[ret[0]]/base,ret[ret[0]]%=base;
}
void dec(int *a,int *b)
{
  for(int i=1;i<=a[0];i++)
    {
      a[i]-=b[i];
      if(a[i]<0)a[i]+=base,a[i+1]--;
    }
  while(a[0]&&!a[a[0]])a[0]--;
}
void add(int *a,int b)
{
  a[1]+=b;
  for(int i=1;i<=a[0]&&a[i]>=base;i++)
    a[i+1]++,a[i]-=base;
  if(a[a[0]+1])a[0]++;
}
void print(int *a)
{
  printf("%d",a[a[0]]);
  for(int i=a[0]-1;i;i--)printf("%08d",a[i]);puts("");
}
int main()
{
  scanf("%d",&n);
  if(n<=2){puts("1");return 0;}
  a[3][0]=1;a[3][1]=16;a[4][0]=1;a[4][1]=45;
  if(n<=4){printf("%d\n",a[n][1]);return 0;}
  for(int i=5;i<=n;i++)
    {
      mul(a[i-1],a[i],3);
      dec(a[i],a[i-2]);add(a[i],2);
    }
  print(a[n]);return 0;
}

原文地址:https://www.cnblogs.com/Narh/p/10206357.html

时间: 2024-11-03 13:06:25

bzoj 1002 [FJOI2007]轮状病毒——打表找规律的相关文章

bzoj 1002 [FJOI2007]轮状病毒 高精度&amp;&amp;找规律&amp;&amp;基尔霍夫矩阵

1002: [FJOI2007]轮状病毒 Time Limit: 1 Sec  Memory Limit: 162 MBSubmit: 2234  Solved: 1227[Submit][Status] Description 给定n(N<=100),编程计算有多少个不同的n轮状病毒. Input 第一行有1个正整数n. Output 将编程计算出的不同的n轮状病毒数输出 Sample Input 3 Sample Output 16 HINT Source 基尔霍夫矩阵总算编出来了,这道题考

[FJOI2007]轮状病毒 题解(dp(找规律)+高精度)

[FJOI2007]轮状病毒 题解(dp(找规律)+高精度) 标签:题解 阅读体验:https://zybuluo.com/Junlier/note/1335733 没什么好说的,直接把规律找出来,有两种规律(据说还有多种dp),再套个高精度 \(First\) \(f[1]=1,f[2]=5,f[i]=3×f[i-1]-f[i-2]+2\) 就直接写个高精+低精和高精×低精和高精-高精就行了 \(Second\) \(f[1]=1,f[2]=3,f[i]=f[i-1]+f[i-2]\) \(i

BZOJ 1002 [FJOI2007]轮状病毒

1002: [FJOI2007]轮状病毒 Description 轮状病毒有很多变种,所有轮状病毒的变种都是从一个轮状基产生的.一个N轮状基由圆环上N个不同的基原子和圆心处一个核原子构成的,2个原子之间的边表示这2个原子之间的信息通道.如下图所示 N轮状病毒的产生规律是在一个N轮状基中删去若干条边,使得各原子之间有唯一的信息通道,例如共有16个不同的3轮状病毒,如下图所示 现给定n(N<=100),编程计算有多少个不同的n轮状病毒 Input 第一行有1个正整数n Output 计算出的不同的n

BZOJ 1002 FJOI2007 轮状病毒 递推+高精度

题目大意:轮状病毒基定义如图.求有多少n轮状病毒 这个递推实在是不会--所以我选择了打表找规律 首先执行下面程序 #include<cstdio> #include<cstring> #include<iostream> #include<algorithm> #define M 110 using namespace std; struct abcd{ int to,next; bool ban; }table[M<<2]; int head[

BZOJ 1002: [FJOI2007]轮状病毒 递推/基尔霍夫矩阵树定理

f[n]=3*f[n-1]-f[n-2]+2 1002: [FJOI2007]轮状病毒 Time Limit: 1 Sec  Memory Limit: 162 MB Submit: 2959  Solved: 1644 [Submit][Status][Discuss] Description 给定n(N<=100),编程计算有多少个不同的n轮状病毒. Input 第一行有1个正整数n. Output 将编程计算出的不同的n轮状病毒数输出 Sample Input 3 Sample Outpu

1002. [FJOI2007]轮状病毒【找规律+递推】

Description 轮状病毒有很多变种,所有轮状病毒的变种都是从一个轮状基产生的.一个N轮状基由圆环上N个不同的基原子 和圆心处一个核原子构成的,2个原子之间的边表示这2个原子之间的信息通道.如下图所示 N轮状病毒的产生规律是在一个N轮状基中删去若干条边,使得各原子之间有唯一的信息通道,例如共有16个不 同的3轮状病毒,如下图所示 现给定n(N<=100),编程计算有多少个不同的n轮状病毒 Input 第一行有1个正整数n Output 计算出的不同的n轮状病毒数输出 Sample Inpu

1002: [FJOI2007]轮状病毒

1002: [FJOI2007]轮状病毒 Time Limit: 1 Sec  Memory Limit: 162 MBSubmit: 2609  Solved: 1450[Submit][Status] Description 给定n(N<=100),编程计算有多少个不同的n轮状病毒. Input 第一行有1个正整数n. Output 将编程计算出的不同的n轮状病毒数输出 Sample Input 3 Sample Output 16 HINT Source 题解:这道题可以采用“打表—找规律

【递推】【高精度】【FJOI 2007】【bzoj 1002】轮状病毒

1002: [FJOI2007]轮状病毒 Time Limit: 1 Sec Memory Limit: 162 MB Submit: 3238 Solved: 1797 Description 给定n(N<=100),编程计算有多少个不同的n轮状病毒. Input 第一行有1个正整数n. Output 将编程计算出的不同的n轮状病毒数输出 Sample Input 3 Sample Output 16 题解: 递推. 打表可以找规律得,f[i]=3*f[i-1]-f[i-2]+2,但是需要高精

hdu 2147 kiki&#39;s game(DP(SG)打表找规律)

题意: n*m的棋盘,一枚硬币右上角,每人每次可将硬币移向三个方向之一(一格单位):左边,下边,左下边. 无法移动硬币的人负. 给出n和m,问,先手胜还是后手胜. 数据范围: n, m (0<n,m<=2000) 思路: dp[i][j]=0,说明从(i,j)这个点到时左下角先手败.dp[i][j]=1则先手胜. 然后记忆搜.但是记忆搜会超时. 搜完把整张表打出来,发现规律了,,,,然后,,,代码剩几行了. 代码: ///打表观察 /* int f[2005][2005]; int go(in