欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

C++模擬2D牛頓力學效果的示例代碼

 更新時間:2023年06月04日 09:16:21   作者:[PE]經(jīng)典八炮  
這篇文章主要為大家詳細介紹了如何利用C++模擬2D牛頓力學效果,文中的示例代碼講解詳細,具有一定的學習價值,感興趣的小伙伴可以了解一下

簡介

如何用計算機來模擬真實世界呢?計算機最大的功能是計算,而物理學的種種公式就把現(xiàn)實世界中的物理規(guī)律以數(shù)學的語言描繪了出來,從而使我們可以通過計算大致模擬現(xiàn)實世界的物體運動。因此不難想到把物理學定律(這里用的是牛頓力學)用計算機語言描述出來,模擬現(xiàn)實世界。這個項目就用C++實現(xiàn)了此功能,為了方便,目前實現(xiàn)的是二維宇宙。

項目完成后,只要輸入各項參數(shù),我們就可以用它模擬現(xiàn)實中的運動了。下面是用該項目模擬某飛船圍繞某恒星運動的過程(注意,運動軌跡并不是預設的動畫,而是通過計算得出的)。

代碼

完整代碼如下:

namespace NewtonianPhysics
{
	using Scalar = long double;//標量
	const Scalar G = 6.67259e-11l;//萬有引力常數(shù)
	namespace _2D
	{
		class Vector//矢量
		{
		public:
			Scalar x;
			Scalar y;
			Vector() :x(0.l), y(0.l) {}
			Vector(Scalar inX, Scalar inY) :x(inX), y(inY) {}
			friend Vector operator+(const Vector& a, const Vector& b)
			{
				return Vector(a.x + b.x, a.y + b.y);
			}
			friend Vector operator-(const Vector& a, const Vector& b)
			{
				return Vector(a.x - b.x, a.y - b.y);
			}
			friend Vector operator*(const Vector& vec, Scalar n)
			{
				return Vector(vec.x * n, vec.y * n);
			}
			friend Vector operator*(Scalar n, const Vector& vec)
			{
				return Vector(vec.x * n, vec.y * n);
			}
			Vector& operator*=(Scalar n)
			{
				x *= n;
				y *= n;
				return *this;
			}
			Vector& operator+=(const Vector& right)
			{
				x += right.x;
				y += right.y;
				return *this;
			}
			Vector& operator-=(const Vector& right)
			{
				x -= right.x;
				y -= right.y;
				return *this;
			}
			Scalar LengthSq() const
			{
				return (x * x + y * y);
			}
			Scalar Length() const
			{
				return (std::sqrt(LengthSq()));
			}
			void Normalize()
			{
				float length = Length();
				x /= length;
				y /= length;
			}
			static Vector Normalize(const Vector& vec)
			{
				Vector temp = vec;
				temp.Normalize();
				return temp;
			}
		};
		class MassPoint
		{
		public:
			Scalar m;//質量/kg
			Vector location;//當前位置
			Vector v;//速度/(m/s)
			Vector f;//受到的合力/(N)
			MassPoint(Scalar mass, Vector _location = { 0,0 }, Vector velocity = { 0,0 })
				:m(mass), location(_location), v(velocity) {}
			void Update(Scalar deltaTime)
			{
				//由F=ma得出加速度并更新速度
				v += f * (1 / m) * deltaTime;
				//由速度得出位移并更新坐標
				location += v * deltaTime;
			}
		};
	}
}

標量和矢量

首先,我們定義了標量和矢量的類型。標量就是只有大小的量,如時間、質量等,而矢量是既有大小又有方向的量,如速度、加速度。標量用內置的long double類型即可。

矢量就是數(shù)學中的向量,在這里我們用Vector類來表示。根據(jù)數(shù)學定理,任何一個矢量都可以用平面直角坐標系中的一個坐標來表示。在Vector類里面,我們用兩個標量來表示橫坐標和縱坐標,并且定義了矢量的加法、減法、與實數(shù)的乘法。Length函數(shù)的作用是求矢量的長度,而LengthSq則是求矢量長度的平方。因為Length函數(shù)需要開方,速度比較慢,所以能用LengthSq就盡量用LengthSq。而Normalize函數(shù)的作用則是將矢量變成方向相同、長度為1的單位矢量。

增量時間

根據(jù)主流物理學理論,時間是連續(xù)的,然而,通過計算機模擬現(xiàn)實世界時,我們只能“一幀一幀”地計算。例如,如果我們每一幀代表0.1s,當前物體速度為10m/s,我們只能默認在這0.1s內物體的速度保持10m/s不變,盡管實際上速度可能變化了。這有點類似于微分,然而微分可以引入無窮小量,而計算機計算每一幀的時間不可能是無窮小,所以計算出來和實際結果一定有誤差。并且,每幀代表的時間越短,誤差越小。
在上面的例子中,0.1s就叫做增量時間(Δt)。

質點

牛頓力學的核心就是將物體抽象成質點(有質量無大小的點)進行研究。這里的MassPoint類就表示質點。在MassPoint類的成員變量中,m表示質量,v表示當前的速度,f表示受到的合力,location是當前的坐標。
Update函數(shù)根據(jù)物理定律對質點的狀態(tài)進行更新,它的參數(shù)就是增量時間。在這個函數(shù)中,我們先通過牛頓第二定律求出加速度,然后乘以增量時間得出速度,再乘以時間便得出了位移。

這樣,我們便實現(xiàn)了牛頓力學的基本功能。

實例

下面是簡介中飛船圍繞恒星運動的代碼示例(繪圖用了easyx):

using namespace NewtonianPhysics;
void Print(const _2D::MassPoint& p)
{
	setfillcolor(YELLOW);
	setlinecolor(RED);
	setlinestyle(PS_SOLID, 1);
	auto x = (p.location.x + 2e7) * 800 / 4e7, y = (2e7 - p.location.y) * 800 / 4e7;
	fillcircle(x, y, 5);
}
int main()
{
	initgraph(800, 800); 
	_2D::MassPoint a(5e30l, { 0,0 }), b(1e4, { 1e7,0 }, { 0,5e6 });
	while (1)
	{
		cleardevice();
		Print(a);
		Print(b);
		Sleep(100);
		//F=GMm/r2
		b.f = _2D::Vector::Normalize(a.location - b.location) * (G * a.m * b.m / (a.location - b.location).LengthSq());		a.Update(0.05);
		b.Update(0.1);
	}
	closegraph();
	return 0;
}

該代碼中,恒星的質量為5×1030kg,且位于(0,0)靜止不動;飛船的質量為1×104kg,初始位于(1×107,0),并且具有向上5×106m/s的初速度。通過萬有引力公式實時計算出恒星對飛船的引力,并調用Update函數(shù)進行更新。這樣便實現(xiàn)了模擬運動。當然,大家也可以調節(jié)這些數(shù)據(jù),或者加入更多的元素,實現(xiàn)更加復雜的運動過程(例如三體運動)。

到此這篇關于C++模擬2D牛頓力學效果的示例代碼的文章就介紹到這了,更多相關C++牛頓力學內容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關文章希望大家以后多多支持腳本之家!

相關文章

  • C++派生類與基類的轉換規(guī)則

    C++派生類與基類的轉換規(guī)則

    基類與派生類對象之間有賦值兼容關系,由于派生類中包含從基類繼承的成員,具體表現(xiàn)在以下幾個方面,需要的朋友可以參考下
    2012-11-11
  • C語言數(shù)據(jù)存儲歸類介紹

    C語言數(shù)據(jù)存儲歸類介紹

    使用編程語言進行編程時,需要用到各種變量來存儲各種信息。變量保留的是它所存儲的值的內存位置。這意味著,當您創(chuàng)建一個變量時,就會在內存中保留一些空間。您可能需要存儲各種數(shù)據(jù)類型的信息,操作系統(tǒng)會根據(jù)變量的數(shù)據(jù)類型,來分配內存和決定在保留內存中存儲什么
    2022-08-08
  • C語言數(shù)據(jù)結構之圖書借閱系統(tǒng)

    C語言數(shù)據(jù)結構之圖書借閱系統(tǒng)

    這篇文章主要為大家詳細介紹了C語言數(shù)據(jù)結構之圖書借閱系統(tǒng),文中示例代碼介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2022-03-03
  • OpenCV利用K-means實現(xiàn)根據(jù)顏色進行圖像分割

    OpenCV利用K-means實現(xiàn)根據(jù)顏色進行圖像分割

    K-means是一種經(jīng)典的無監(jiān)督聚類算法---不需要人工干預。本文將通過K-means算法實現(xiàn)根據(jù)顏色進行圖像分割的效果,感興趣的小伙伴可以嘗試一下
    2022-10-10
  • C++容器適配與棧的實現(xiàn)及dequeque和優(yōu)先級詳解

    C++容器適配與棧的實現(xiàn)及dequeque和優(yōu)先級詳解

    這篇文章主要介紹了C++容器適配與棧的實現(xiàn)及dequeque和優(yōu)先級,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習吧
    2022-10-10
  • c語言clock函數(shù)使用示例

    c語言clock函數(shù)使用示例

    這篇文章主要介紹了c語言clock函數(shù)使用示例,需要的朋友可以參考下
    2014-04-04
  • c++11?實現(xiàn)枚舉值到枚舉名的轉換問題

    c++11?實現(xiàn)枚舉值到枚舉名的轉換問題

    這篇文章主要介紹了c++11?實現(xiàn)枚舉值到枚舉名的轉換,本文給大家介紹的非常詳細,對大家的學習或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2022-03-03
  • C/C++位操作實例總結

    C/C++位操作實例總結

    這篇文章主要介紹了C/C++位操作實例總結,是C/C++程序設計中很重要的概念,需要的朋友可以參考下
    2014-08-08
  • 使用ShellClass獲取文件屬性詳細信息的實現(xiàn)方法

    使用ShellClass獲取文件屬性詳細信息的實現(xiàn)方法

    本篇文章是對ShellClass獲取文件屬性詳細信息的實現(xiàn)方法進行了詳細的分析介紹,需要的朋友參考下
    2013-05-05
  • C語言中static和auto用法詳解

    C語言中static和auto用法詳解

    大家好,本篇文章主要講的是C語言中static和auto用法詳解,感興趣的同學趕快來看一看吧,對你有幫助的話記得收藏一下
    2022-01-01

最新評論