CSDN首页 空间 新闻 论坛 Blog 下载 读书 网摘 搜索 .NET Java 视频 接项目 求职 在线学习 买书 程序员 通知
不看会后悔的Windows XP之经验谈 简单快捷DIY实用家庭影院
CSDN社区
搜索 收藏 打印 关闭
CSDN社区 >  C/C++ >  C语言

求教PI小数点后8000位的程序!

楼主sxbobo2002(五月雪)2002-04-05 13:34:51 在 C/C++ / C语言 提问

PI=3.1415926.........  
  哪位能给出源程序,最好是c写的或者告诉我算法!  
  在此谢过。 问题点数:50、回复次数:18Top

1 楼PRCLionel(lionel)回复于 2002-04-05 21:33:40 得分 15

//   This   is   the   beginning   of   part   1  
   
  /*这里有个程序你可以试试,原来有点问题,我修改了一下,在Microsoft  
  **Virual   C++   6.0下编译通过,由于程序过长,我将它分成几个部分  
  **     Program   to   compute   PI,   by   Jason   Chen,   May   1999  
  **                                   checked   by   PRCLionel,April   2002  
  **     Compiled   &   Linked   by   Microsoft   Virual   C++   6.0  
  **  
  **     Open   VC++   IDE,   new   a   win32   console   application   project,  
  **     add   this   file   to   the   project   and   build   it.  
  **  
  */  
  #include   <stdlib.h>  
  #include   <stdio.h>  
  #include   <string.h>  
  #include   <malloc.h>  
  #include   <math.h>  
  #include   <time.h>  
  #include   <conio.h>  
  #include   <io.h>  
   
  int           *arctg5,   *arctg239,   *tmp;  
  int           DecLen,   BinLen;  
  int           x,   n,   sign,   NonZeroPtr;  
  int           Step;  
  char         fn_status[]       =   "~pi_sts.___";  
  char         fn_arctg5[]       =   "~atg5.___";  
  char         fn_arctg239[]   =   "~atg239.___";  
  char         fn_tmp[]             =   "~tmp.___";  
  time_t     TotalTime,   time1,   time2;  
   
   
   
  void   __cdecl   FirstDiv(int   *arctg_array)  
  {  
          __asm   {  
                  mov   esi,   arctg_array  
                  mov   dword   ptr   [esi],   1  
                  xor   edx,   edx  
                  mov   ebx,   x  
                  mov   ecx,   BinLen  
  fd1:         mov   eax,   [esi]  
                  div   ebx  
                  mov   [esi],   eax  
                  add   esi,   4  
                  loop   fd1  
                  mov   esi,   arctg_array  
                  mov   edi,   tmp  
                  mov   ecx,   BinLen  
                  pushf  
                  cld  
                  rep   movsd  
                  popf  
          }  
  }  
   
   
   
  void   __cdecl   arctgx(int   *arctg_array)  
  {  
          int                   NonZeroBytePtr;  
          int                   key;  
          FILE                 *fp;  
          for   (;NonZeroPtr<BinLen;)   {  
                  NonZeroBytePtr   =   NonZeroPtr   *   4;  
                  if   (_kbhit())   {  
                          key=_getch();  
                          if   (key==0   ||   key==0xe0)   _getch();  
                          if   (key=='p')   {  
                                  printf("Swap   data   to   disk   ...\n");  
                                  if   (x==25)  
                                          Step   =   1;  
                                  else  
                                          Step   =   2;  
                                  time(&time2);  
                                  TotalTime   +=   time2   -   time1;  
                                  if   ((fp=fopen(fn_status,"wt"))==NULL)   {  
                                          printf("Create   file   %s   error!!\n",   fn_status);  
                                          exit(0);  
                                  }  
                                  fprintf(fp,   "%d   %d   %d   %d   %d   %d   %d\n",  
                                          Step,   DecLen,   BinLen,   n,   sign,   NonZeroPtr,   TotalTime);  
                                  fclose(fp);  
                                  if   ((fp=fopen(fn_arctg5,"wb"))==NULL)   {  
                                          printf("Create   file   %s   error!!\n",   fn_arctg5);  
                                          exit(0);  
                                  }  
                                  if   (fwrite(arctg5,   4,   BinLen,   fp)   !=   (unsigned)BinLen)   {  
                                          printf("Write   file   %s   error!!\n",   fn_arctg5);  
                                          exit(0);  
                                  }  
                                  fclose(fp);  
                                  if   ((fp=fopen(fn_arctg239,"wb"))==NULL)   {  
                                          printf("Create   file   %s   error!!\n",   fn_arctg239);  
                                          exit(0);  
                                  }  
                                  if   (fwrite(arctg239,   4,   BinLen,   fp)   !=   (unsigned)BinLen)   {  
                                          printf("Write   file   %s   error!!\n",   fn_arctg239);  
                                          exit(0);  
                                  }  
                                  fclose(fp);  
                                  if   ((fp=fopen(fn_tmp,"wb"))==NULL)   {  
                                          printf("Create   file   %s   error!!\n",   fn_tmp);  
                                          exit(0);  
                                  }  
                                  if   (fwrite(tmp,   4,   BinLen,   fp)   !=   (unsigned)BinLen)   {  
                                          printf("Write   file   %s   error!!\n",   fn_tmp);  
                                          exit(0);  
                                  }  
                                  fclose(fp);  
                                  printf("Exit.\n");  
                                  exit(0);  
                          }  
                  }  
                  __asm   {  
                          mov   esi,   tmp  
                          add   esi,   NonZeroBytePtr  
                          xor   edx,   edx  
                          mov   ebx,   x  
                          mov   ecx,   BinLen  
                          sub   ecx,   NonZeroPtr  
  arctg1:           mov   eax,   [esi]  
                          div   ebx  
                          mov   [esi],   eax  
                          add   esi,   4  
                          loop   arctg1  
                          cmp   sign,   1  
                          jne   sub_  
                          mov   esi,   tmp  
                          add   esi,   NonZeroBytePtr  
                          mov   edi,   arctg_array  
                          add   edi,   NonZeroBytePtr  
                          xor   edx,   edx  
                          mov   ebx,   n  
                          mov   ecx,   BinLen  
                          sub   ecx,   NonZeroPtr  
  add_1:             mov   eax,   [esi]  
                          div   ebx  
                          add   [edi],   eax  
                          adc   dword   ptr   [edi-4],   0  
                          jnc   add_3  
                          push   edi  
                          sub   edi,   4  
  add_2:             sub   edi,   4  
                          add   dword   ptr   [edi],   1  
                          jc   add_2  
                          pop   edi  
  add_3:             add   esi,   4  
                          add   edi,   4  
                          loop   add_1  
                          jmp   adj_var  
  sub_:               mov   esi,   tmp  
                          add   esi,   NonZeroBytePtr  
                          mov   edi,   arctg_array  
                          add   edi,   NonZeroBytePtr  
                          xor   edx,   edx  
                          mov   ebx,   n  
                          mov   ecx,   BinLen  
                          sub   ecx,   NonZeroPtr  
  sub_1:             mov   eax,   [esi]  
                          div   ebx  
                          sub   [edi],   eax  
                          sbb   dword   ptr   [edi-4],   0  
                          jnc   sub_3  
                          push   edi  
                          sub   edi,   4  
  sub_2:             sub   edi,   4  
                          sub   dword   ptr   [edi],   1  
                          jc   sub_2  
                          pop   edi  
  sub_3:             add   esi,   4  
                          add   edi,   4  
                          loop   sub_1  
  adj_var:         add   n,   2  
                          neg   sign  
                          mov   esi,   tmp  
                          add   esi,   NonZeroBytePtr  
                          cmp   dword   ptr   [esi],   0  
                          jne   adj_var_ok  
                          inc   NonZeroPtr  
  adj_var_ok:  
                  }  
          }  
  }  
   
  /*   this   is   the   end   of   part   1   */Top

2 楼PRCLionel(lionel)回复于 2002-04-05 21:34:44 得分 0

//   this   is   the   beginning   of   part   2    
   
  void   __cdecl   mul_array(int   *array,   int   multiplicator)  
  {  
          __asm   {  
                  mov   esi,   BinLen  
                  dec   esi  
                  shl   esi,   2  
                  add   esi,   array  
                  mov   ecx,   BinLen  
                  mov   ebx,   multiplicator  
                  xor   edi,   edi  
  mul1:       mov   eax,   [esi]  
                  mul   ebx  
                  add   eax,   edi  
                  adc   edx,   0  
                  mov   [esi],   eax  
                  mov   edi,   edx  
                  sub   esi,   4  
                  loop   mul1  
                  mov   [esi],   edx  
          }  
  }  
   
   
   
  void   __cdecl   sub2array(int   *array1,   int   *array2)  
  {  
          __asm   {  
                  mov   esi,   array1  
                  mov   edi,   array2  
                  mov   ecx,   BinLen  
                  dec   ecx  
  sub1:       mov   eax,   [edi+ecx*4]  
                  sbb   [esi+ecx*4],   eax  
                  loop   sub1  
          }  
  }  
   
   
   
  void   main(void)  
  {  
          struct   tm       *ts;  
          FILE                 *pi,   *fp;  
          int                   i,   tail,   p10tail;  
          printf("\nProgram   to   compute   PI,   by   Jason   Chen,   May   1999.\n");  
  printf("                               checked   by   PRCLionel,April   2002.\n");  
  printf("Compiled   &   Linked   by   Microsoft   Virual   C++   6.0\n");  
          printf("                 Dec   Length                               Time(h:m:s)\n");  
          printf("                         20000                                   00:00:07\n");  
          printf("                       100000                                   00:02:54\n");  
          printf("     (Running   on   PII-233,   128MB,   Win98   Dos   mode)\n");  
          if   ((fp=fopen(fn_status,"rt"))==NULL)   {  
                  printf("Decimal   length   =   ");  
                  scanf("%d",   &DecLen);  
                  if   (DecLen   <   100)   DecLen   =   100;  
                  BinLen   =   (int)(DecLen   /   log10(2)   /   32)   +   2;  
                  Step   =   0;  
                  TotalTime   =   0;  
          }  
          else   {  
                  printf("Reading   previous   data   ...\n");  
                  fscanf(fp,   "%d   %d   %d   %d   %d   %d   %d",  
                          &Step,   &DecLen,   &BinLen,   &n,   &sign,   &NonZeroPtr,   &TotalTime);  
                  fclose(fp);  
                  if   (Step*DecLen*BinLen*n*sign*NonZeroPtr*TotalTime   ==   0)   {  
                          printf("File   %s   error   !!\nExit!\n",   fn_status);  
                          exit(0);  
                  }  
          }  
  /*  
                a   bit   changed   by   PRCLionel   april   2002  
        -------------------------------------------------------  
  */  
          arctg5       =   (int*)calloc(BinLen,   4);  
          arctg239   =   (int*)calloc(BinLen,   4);  
          tmp             =   (int*)calloc(BinLen,   4);  
  /*   ------------------------------------------------------*/  
          if   (arctg5==NULL   ||   arctg239==NULL   ||   tmp==NULL)   {  
                  printf("Not   enough   memory   !!\n");  
                  exit(0);  
          }  
          if   (Step   ==   0)   {  
                  memset(arctg5,   0,   BinLen*4);  
                  memset(arctg239,   0,   BinLen*4);  
                  memset(tmp,   0,   BinLen*4);  
          }  
          else   {  
                  if   ((fp=fopen(fn_arctg5,"rb"))==NULL)   {  
                          printf("Open   file   %s   error!!\n",   fn_arctg5);  
                          exit(0);  
                  }  
                  if   (fread(arctg5,   4,   BinLen,   fp)   !=   (unsigned)BinLen)   {  
                          printf("File   %s   error!!\n",   fn_arctg5);  
                          exit(0);  
                  }  
                  fclose(fp);  
                  if   ((fp=fopen(fn_arctg239,"rb"))==NULL)   {  
                          printf("Open   file   %s   error!!\n",   fn_arctg239);  
                          exit(0);  
                  }  
                  if   (fread(arctg239,   4,   BinLen,   fp)   !=   (unsigned)BinLen)   {  
                          printf("File   %s   error!!\n",   fn_arctg239);  
                          exit(0);  
                  }  
                  fclose(fp);  
                  if   ((fp=fopen(fn_tmp,"rb"))==NULL)   {  
                          printf("Open   file   %s   error!!\n",   fn_tmp);  
                          exit(0);  
                  }  
                  if   (fread(tmp,   4,   BinLen,   fp)   !=   (unsigned)BinLen)   {  
                          printf("File   %s   error!!\n",   fn_tmp);  
                          exit(0);  
                  }  
                  fclose(fp);  
          }  
          printf("Working   ......\n");  
          printf("Press   'p'   to   pause   &   exit\n");  
          time(&time1);  
          if   (Step   ==   0)   {  
                  x   =   5;  
                  FirstDiv(arctg5);  
                  x   =   x   *   x;  
                  n   =   3;  
                  sign   =   -1;  
                  NonZeroPtr   =   1;  
                  arctgx(arctg5);  
          }  
          else   if   (Step   ==   1)   {  
                  x   =   5   *   5;  
                  arctgx(arctg5);  
          }  
          if   (Step   ==   0   ||   Step   ==   1)   {  
                  x   =   239;  
                  FirstDiv(arctg239);  
                  x   =   x   *   x;  
                  n   =   3;  
                  sign   =   -1;  
                  NonZeroPtr   =   1;  
                  arctgx(arctg239);  
          }  
          else   {  
                  x   =   239   *   239;  
                  arctgx(arctg239);  
          }  
          mul_array(arctg5,   16);  
          mul_array(arctg239,   4);  
          sub2array(arctg5,   arctg239);  
          if   ((pi=fopen("pi.txt","wt"))==NULL)   {  
                  printf("Create   file   pi.txt   error!!\n");  
                  exit(0);  
          }  
          printf("Writing   result   to   file:   pi.txt   ...\n");  
          fprintf(pi,   "%d",   arctg5[0]);  
          for   (i=1;   i<=DecLen/9;   i++)   {  
                  arctg5[0]   =   0;  
                  mul_array(arctg5,   1000000000);  
                  fprintf(pi,   "%09d",   arctg5[0]);  
          }  
          tail   =   DecLen   %   9;  
          p10tail   =   1;  
          for   (i=1;i<=tail;i++)   p10tail   *=   10;  
          arctg5[0]   =   0;  
          mul_array(arctg5,   p10tail);  
          fprintf(pi,   "%0*d",   tail,   arctg5[0]);  
          fclose(pi);  
          time(&time2);  
          TotalTime   +=   time2   -   time1;  
          printf("Done   !!\n");  
          ts   =   gmtime(&TotalTime);  
          ts->tm_mon   --;  
          ts->tm_mday   =   ts->tm_mday   -   1   +   ts->tm_mon   *   31;  
          printf("Time   :   ");  
          if   (ts->tm_mday   >   0)   printf("%d   Day(s)   ",   ts->tm_mday);  
          printf("%02d:%02d:%02d\n",   ts->tm_hour,   ts->tm_min,   ts->tm_sec);  
          if   (_unlink(fn_status)   ==   0)   {  
                  _unlink(fn_arctg5);  
                  _unlink(fn_arctg239);  
                  _unlink(fn_tmp);  
          }  
  }  
  //this   is   the   end   of   part   2  
  //this   is   the   end   of   fileTop

3 楼NowCan(城市浪人)回复于 2002-04-07 13:48:04 得分 0

天,汇编的啊。Top

4 楼sxbobo2002(五月雪)回复于 2002-04-07 14:11:14 得分 0

呵呵~~汇编不会!  
  To:PRCLionel(Lionel)    
  谢谢你的程序!但你能否把程序的设计算法说一下,多谢!Top

5 楼sky_blue(蓝天2007)回复于 2002-04-07 14:15:17 得分 0

用级数可以实现的吧。Top

6 楼sxbobo2002(五月雪)回复于 2002-04-07 14:40:10 得分 0

级数?  
  pi/4=1-1/3+1/5-1/7....  
  是这个吗?  
  说详细一些,多谢!Top

7 楼mathe()回复于 2002-04-07 14:40:48 得分 0

上面的代码是使用:  
  Pi=16*arctgn(1/5)-4*arctgn(1/239)  
  然后对arctgn作泰勒展开。Top

8 楼PRCLionel(lionel)回复于 2002-04-08 15:52:27 得分 0

嘿嘿,已经有人回答了。Top

9 楼qsyang(二拳映月)回复于 2002-04-08 16:09:12 得分 10

同意mathe,那是著名的Machin公式。    
        你只要写个反正切的函数就行了。函数如下:  
  double   arctan(double   x)  
  {  
  int   I;  
  double   r,   e,   f,   sqr;  
  sqr=x*x;  
  r   =0;  
  e   =x;  
  I   =1;  
  while   ((double)(e/I)   >exp(-??))    
  //   ??:位数,不过你要8000位,还要加个移位器  
  {  
  f=e/I;  
  r=(I%4==1)?(r+f):(r-f);  
  e=e*sqr;  
  I+=2;  
  }  
  return   r;  
  }Top

10 楼Viper()回复于 2002-04-08 16:49:54 得分 0

kao,关注一下。Top

11 楼mengxihe(濛溪河)回复于 2002-04-10 12:45:35 得分 0

好像有个经典的算法就几行呀,怎么你们的程序那么长?  
   
  Top

12 楼microblue()回复于 2002-04-10 13:26:09 得分 0

目前   pi   值已计算到小数点后   206,158,430,000   位。  
  即便是是在   PC   机上也计算到     12,884,901,372   位。  
  具体情况请访问以下网站:  
  http://www.jason314.com/  
  Top

13 楼steedhorse(晨星)回复于 2002-04-10 14:39:32 得分 0

收藏。Top

14 楼Nizvoo()回复于 2002-04-10 15:06:08 得分 0

sfi   yn   .Top

15 楼microblue()回复于 2002-04-10 18:45:26 得分 15

以下是我写的一个计算   pi   值的程序,可以在   Unix   和   Windows   用编译和运行。  
  #include   <stdio.h>  
  #include   <stdlib.h>  
   
  main(int   argc,   char   *   argv[])  
  {  
      long   *   pi,   *   t,   m,   n,   r,   s;  
      int   t0[][3]   =   {48,   32,   20,   24,   8,   4},   k0[][3]   =   {1,   1,   0,   1,   1,   1};  
      int   n0[][3]   =   {18,   57,   239,   8,   57,   239},   d,   i,   j,   k,   p,   q;  
   
      d   =   (argc   >   1)   ?   (((i   =   atoi(argv[1]))   <   0)   ?   0   :   i)   :   1000;  
      q   =   (argc   >   2)   ?   1   :   0;  
      printf("%s\n\n",   "microblue   (R)   Pi   value   compute   Program     (C)   Tue   1999.11.30");  
      printf("pi=   %s%d   *   arctg(1/%d)   %s   %d   *   arctg(1/%d)   %s   %d   *   arctg(1/%d)   [%s]\n",  
          k0[q][0]   ?   ""   :   "-",   t0[q][0],   n0[q][0],   k0[q][1]   ?   "+"   :   "-",   t0[q][1],  
          n0[q][1],   k0[q][2]   ?   "+"   :   "-",   t0[q][2],   n0[q][2],   q   ?   "Stomer"   :   "Gauss");  
      if   ((t   =   (long   *)calloc((d   +=   5)   +   1,   sizeof(long)))   ==   NULL)   return   1;  
      if   ((pi   =   (long   *)calloc(d   +   1,   sizeof(long)))   ==   NULL)   return   2;  
      for   (i   =   d;   i   >=   0;   i--)   pi[i]   =   0;  
      for   (p   =   0;   p   <   3;   p++)   {  
          for   (k=k0[q][p],   n=n0[q][p],   t[i=j=d]=t0[q][p],   i--;   i   >=   0;   i--)   t[i]   =   0;  
          for   (r   =   0,   i   =   j;   i   >=   0;   i--)   {  
              r   =   (m   =   10   *   r   +   t[i])   %   n;  
              t[i]   =   m   /   n;  
              k   ?   (pi[i]   +=   t[i])   :   (pi[i]   -=   t[i]);  
          }  
          while   (j   >   0   &&   t[j]   ==   0)   j--;  
          for   (k   =   !k,   s   =   3,   n   *=   n;   j   >   0;   k   =   !k,   s   +=   2)   {  
              for   (r   =   0,   i   =   j;   i   >=   0;   i--)   {  
                  r   =   (m   =   10   *   r   +   t[i])   %   n;  
                  t[i]   =   m   /   n;  
              }  
              while   (j   >   0   &&   t[j]   ==   0)   j--;  
              for   (r   =   0,   i   =   j;   i   >=   0;   i--)   {  
                  r   =   (m   =   10   *   r   +   t[i])   %   s;  
                  m   /=   s;  
                  k   ?   (pi[i]   +=   m)   :   (pi[i]   -=   m);  
              }  
          }  
      }  
      for   (n   =   i   =   0;   i   <=   d;   pi[i++]   =   r)   {  
          n   =   (m   =   pi[i]   +   n)   /   10;  
          if   ((r   =   m   %   10)   <   0)   r   +=   10,   n--;  
      }  
      printf("pi=   %ld.",   pi[d]);  
      for   (i   =   d   -   1;   i   >=   5;   i--)  
          printf("%ld%s",   pi[i],   ((m   =   d   -   i   +   5)   %   65)   ?   ((m   %   5)   ?   ""   :   "   ")   :   "\n");  
      printf("%sDIGITS:   %d\n",   (m   %   65)   ?   "\n"   :   "",   d   -   5);  
      return   0;  
  }  
  Top

16 楼microblue()回复于 2002-04-10 19:05:06 得分 5

据   http://www.jason314.com   网站,目前PC机上流行的最快的圆周率计算程序是PiFast(该程序可能从   http://numbers.computation.free.fr/Constants/PiProgram/download.html   下载)。它除了计算圆周率,还可以计算e和sqrt(2)。PiFast可以利用磁盘缓存,突破物理内存的限制进行超高精度的计算,最高计算位数可达240亿位,并提供基于Fabrice   Bellard公式的验算功能。  
  PC机上的最高计算记录    
  最高记录   12,884,901,372位    
  时间   2000年10月10日    
  记录创造者   Shigeru   Kondo    
  所用程序   PiFast   ver3.3    
  机器配置   Pentium   III   1G,   1792M   RAM,WindowsNT4.0,40GBx2   (IDE,FastTrak66)    
  计算时间   1,884,375秒   (21.8天)    
  验算时间   29小时    
   
  而我使用   PiFast   version   4.1,   计算   100,000,000   位   pi   值,所用时间为     3820.52   seconds   (~   1.06   hours)。机器配置:   Pentium   4   1.6G,   256M   RAM,   WindowsXP,   40GB(IDE)。  
  不知那位高手有   PiFast   的源程序?  
  Top

17 楼PRCLionel(lionel)回复于 2002-04-12 18:56:42 得分 5

To:   sxbobo2002   (五月雪)    
  明白了么?  
  去  
  http://www.jason314.com/  
  好好看看吧。Top

18 楼willa(chocolate boy)回复于 2002-04-12 20:05:43 得分 0

关注Top

相关问题

  • 怎么样算PI到小数点后指定位?
  • 保留小数点三位
  • ◆◆◆◆简单小程序,如何让Edit2->Text显示保留到小数点后一位数,程序应怎样该?◆◆◆◆
  • 请教一个程序:求133/355的结果中的小数点后的第30位数字为多少?谢了!
  • 不编小程序,怎样把一个数的小数点2位以后去掉?
  • 小数点进位的问题
  • 取小数点后3位数,并且…
  • 小数点后多少位的问题?
  • 小数点后保留2位
  • 显示小数点位数的问题

关键词

  • c++
  • 算法
  • arctg
  • pi
  • pifast
  • 计算
  • 程序
  • arctgn
  • fn
  • ts

得分解答快速导航

  • 帖主:sxbobo2002
  • PRCLionel
  • qsyang
  • microblue
  • microblue
  • PRCLionel

相关链接

  • C/C++ Blog
  • C/C++类图书
  • C/C++类源码下载

广告也精彩

反馈

请通过下述方式给我们反馈
反馈
提问
网站简介|广告服务|VIP资费标准|银行汇款帐号|网站地图|帮助|联系方式|诚聘英才|English|问题报告
北京创新乐知广告有限公司 版权所有, 京 ICP 证 070598 号
世纪乐知(北京)网络技术有限公司 提供技术支持
Copyright © 2000-2008, CSDN.NET, All Rights Reserved
GongshangLogo