【数据结构实验】NOJ002 实验1.2 高精度计算PI值

1. 题目

在这里插入图片描述

2. 分析

在这里插入图片描述
在这里插入图片描述

3. 代码

加了一些看起来冗杂的注释。。。(没错就是为了交报告

#include <iostream>
#include <malloc.h>

using namespace std;

typedef struct node{
	int data;
	struct node *pre;
	struct node *next;
}Node;
 
void createList(Node *head){	// 创建一个双向链表 
	head->next = head;
	head->pre = head;
	Node *p, *q;
	p = head;
	// 直接预设1000位,题意所需位数n在1000以内 
	for(int i=0; i<1000; i++){
		q = (Node*) malloc(sizeof(Node));
		q->data = 0;
		q->pre = p;
		p->next = q;
		q->next = head;
		head->pre = q;
		p = p->next;
	} 
}

void cal(Node *headnum, Node *headsum){

	headnum->next->data = 3;    //由于取的是PI/6,计算结果为1/2,则6/2=3
	headsum->next->data = 3; 
	int a=0, b=0;	// a存当前项的计算值,b存进位或余数 
	// 方法是计算出2000项的加和的值,之后按照题目所需的n值进行取相应位数
	for(int i=1; i<=2000; i++){  // 对每一项(即每一个i值所对应的项)进行计算
		Node *p, *q;
		//先计算大数乘法,从低位即链表尾部开始计算
		p = headnum->pre;	 
		while(p != headnum){
			a = p->data * (2*i-1) * (2*i-1) + b;	// 存放当前位计算后的值,之后根据当前位的计算值计算进位b和p->data 
			p->data = a % 10;	// 进位的部分,留在当前位上 
			b = a/10;	// 进位的部分,存在b里面,之后在进位时参与计算(计算a) 
			p = p->pre;	// 指针前移一位 
		}
		b = 0;
		//再计算大数除法,从高位开始计算 
		p = headnum->next;	
		while(p != headnum){
			a = p->data + b*10;	//除法借位b需要乘以10,加上当前p->data,成为当前需要计算的值 
			p->data = a/((2*i+1)*(2*i)*4);	// 对于除法,商可以直接留在当前位上
			b = a % ((2*i+1)*(2*i)*4);      // 对于除法,余数需要在下一位进行借位,即成为b
			p = p->next;    //指针后移一位
		}
		b = 0;
        //最后将每一项加入sum中,由于是由于是大数和大数的加法,从低位开始加起
		p = headnum->pre;   // p指向每一项的值(此时该项已经在之前计算出来了)
		q = headsum->pre;   // q指向之前已经计算好的sum值,准备与新计算出来的项num相加
		while(p != headnum){
			a = p->data + q->data + b;   //存放当前位加上进位的值
			q->data = a%10;              //非进位部分,留在当前位上
			b = a/10;                    //进位部分,存在b中
			p = p->pre;                  //指针前移一位
            q = q->pre;                  //指针前移一位
        }
	}
}

int main(int argc, char** argv) {
	int n; 
	cin >> n;
	Node *headnum, *headsum;    // 两个链表,分别存放 当前计算的项num 和 加和sum
	headnum = (Node*)  malloc(sizeof(Node));
	headsum = (Node*)  malloc(sizeof(Node));
	createList(headnum);
	createList(headsum);
	cal(headnum, headsum);
	cout << "3.";
	Node *p = headsum->next->next;
	for(int i=0; i<n; i++){
		cout << p->data;
		p = p->next;
	}
	return 0;
}
  • 0
    点赞
  • 15
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值