Buffon投针实验报告
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
Buffon投针实验
一、实验目的:
在计算机上用试验方法求圆周率的近似值。
二、实验原理:
假设平面上有无数条距离为1的等距平行线,现向该平面随机投掷长度为L(L≤1)的针,则针与平行线相交的概率 P=。
设针的中心M与最近一条平行线的距离为x,则x~U(0,1);
针与平行线的夹角为(不管相交与否),则~U(0,)
如图:
()在矩阵上均匀分布,且针与平行线相交的充要条件为
x≤=;P=P{ x=}。
记录≤成立的次数,记为
由-大数定理:≈,则=2。
在计算机上产生
则=~U(0,),i=1,2,…,n;
再产生,则
, i=1,2,…,n
三、实验方法及代码:
在计算机上进行模拟实验,求出的实验值。
给定L,在计算机上利用MFC独立随机产生x和,然后判断≤是否成立.
代码如下:
#include "stdafx.h"
#include "buffon.h"
#include "ChildView.h"
#include "ChoiceDlg.h"
#include <ctime>
#include <cmath>
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
// CChildView
CChildView::CChildView()
{
Trynum=1000;
}
CChildView::~CChildView()
{
}
BEGIN_MESSAGE_MAP(CChildView,CWnd )
//{{AFX_MSG_MAP(CChildView)
ON_WM_PAINT()
ON_COMMAND(ID_TOOL_NUM, OnToolNum)
ON_COMMAND(ID_TOOL_RETRY, OnToolRetry)
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
// CChildView message handlers
BOOL CChildView::PreCreateWindow(CREATESTRUCT& cs)
{
if (!CWnd::PreCreateWindow(cs))
return FALSE;
cs.dwExStyle |= WS_EX_CLIENTEDGE;
cs.style &= ~WS_BORDER;
cs.lpszClass = AfxRegisterWndClass(CS_HREDRAW|CS_VREDRAW|CS_DBLCLKS,
::LoadCursor(NULL, IDC_ARROW), HBRUSH(COLOR_WINDOW+1), NULL);
return TRUE;
}
void CChildView::OnPaint()
{
CPaintDC dc(this),*pDC;
pDC=&dc;
CFont font, *pOldFont;
font.CreatePointFont(200,"宋体");
pOldFont=pDC->SelectObject(&font);
pDC->SetTextColor(RGB(255,0,0));
pDC->TextOut(100,5,"蒲丰投针试验");
pDC->SelectObject(pOldFont);
CPen myPen1,myPen2, *pOldPen1,*pOldPen2;
CRect rect1(30,30,920,620);
pDC->Rectangle(rect1);
myPen1.CreatePen(PS_SOLID, 1, RGB(0,0,255));
pOldPen1=pDC->SelectObject(&myPen1);
for(int i=100;i<600;i+=50)
{
pDC->MoveTo(50,i);
pDC->LineTo(900, i);
}
pDC->SelectObject(pOldPen1);
myPen2.CreatePen(PS_SOLID, 1, RGB(0,255,0));
pOldPen2=pDC->SelectObject(&myPen2);
srand(time(0));
int a,b,q,a1,b1,su,flag;
np=0;
for(int j=0;j<Trynum;j++)
{
a=rand()%850+50;
b=rand()%450+100;
q=rand()%180;
a1=25*cos(q);
b1=25*sin(q);
su=pow(-1,rand()%2);
pDC->MoveTo((a-su*a1),(b-su*b1));
pDC->LineTo((a+su*a1),(b+su*b1));
if( (b%50) >= 25 )
flag =50-b%50;
else
flag = b%50;
if( 25*sin(q) >= flag )
np++;
}
pDC->SelectObject(pOldPen2);
CString str;
int c=Trynum/(np*1.0);
int d=(int)((Trynum/(np*1.0)*100000))%100000;
str.Format("投针次数:%d;\n相交次数:%d;\nπ的估算值:%d.%d",Trynum,np,c,d);
MessageBox(str,"实验数据信息");
}
void CChildView::OnToolNum()
{
CChoiceDlg mydlg;
if(mydlg.DoModal()==IDOK){
this->Trynum = mydlg.m_Trynum ;
this->RedrawWindow();
}
}
void CChildView::OnToolRetry()
{
// TODO: Add your command handler code here
this->RedrawWindow();
}
四、实验数据处理与分析:
根据实验数据,得到近似值为3.2313,可得相对误差为δ=(3.2313-π)/π≈0.02856;
运行截图:
五、实验小结:
本次实验,通过MFC进行模拟投针,模拟效果较好,随着投针次数模拟的增多,实验结果逼近于π的真实值,但是实验程序有待优化,在较多投针次数的模拟中,实验程序运行速度较慢,可以改进相关算法来做适当调节。
而且,由于MFC缺乏更加逼真的动态演示功能,不能很好的生动模拟投针实验的全过程,所以可以尝试在以后的实验中尝试加入Flash或者视频等来弥补这一不足。