《數學建模》筆記(一)—— 第一章對變化進行建模
個人簡介
初學數學建模,準備精讀機械工業出版社,Frank R.Giordano 等人著,姜啓源、葉其孝 等譯的《數學建模》,並創作博客,來將自己的學習心得、學習過程與大家共享。
我之前搞過ACM,對C語言和一些算法、數據結構瞭解較深,用python搞過一些小項目,比較熟悉裏面的包,如:Matplotlib、NumPy、Tensorflow等等,但是對Matlab瞭解甚少,之前用過與之相似的Octave做過一些NN的小程序,除此之外全無瞭解。
0 、預備知識
首先介紹什麼是數學模型,數學模型是對現實世界的理想化,但永遠都不是精確的表示,每個模型都有自己的侷限性,但是好的模型能夠提供有價值的結果和結論。
比例性
多數模型簡化了現實的情況,模型只能近似第表示實際的行爲,一種非常強有力的簡化關係就是比例性,兩個變量y和x是(互成)比例的,如果一個變量總是另一個變量的常數倍,也就是說:如果存在某個非零常數k,使得:
那麼我們說y與x是(互成)比例的,我們記作:
對變化進行建模
對變化進行建模,非常有用的一個公式就是:
通過移項,我們很自然的可以得到另一個公式:
我們有可能會面臨兩種情況:
- 變化的行爲是在離散的時間段上發生的,一個非常經典的例子就是每月還貸款 ,爲了解決這種問題,我們可以使用接下來將要介紹的差分方程。
- 行爲在時間上是連續發生的,那麼我們構建模型就需要使用後面纔會講的微分方程。
1、 用差分方程對變化進行建模
首先,我們來了解,什麼是差分:
1.1 對於一個數列 A = {a0,a1,a2,…} 它的一階差分是:
1.2 經典問題
考慮一開始價值爲1000美金的儲蓄存單在月利率爲1%的條件下的累計價值,下面的數列表示該儲存單逐月的價值:
我們對這個數列求差分,可以得到它的差分數列爲:
我們可以很輕易的知道:
有根據我們之前給出的式子:
我們就得到了一個從當前項,轉移到下一項的轉移方程(我個人喜歡這麼叫),最終我們得到了一個這樣的動力系統模型:
然後我們把代碼一寫,就可以把它變化的過程表示的清楚明瞭。我使用的是python,python在繪圖方面的表現明顯強於matlab,從另外一個角度來說,我用python用得順手(逃)。
import matplotlib.pyplot as plt
A=[1000];#list A , A[0] is 1000$
for i in range(100):# Calculat A[1],A[2],...,A[100]
A.append(A[i]+A[i]*0.01);
plt.plot(range(101),A);#X is 0 --> 100 , Y is A[0] --> A[100]
plt.title(u"Bank deposits as a function of year", fontproperties='font')
plt.xlabel(u"year", fontproperties='font')
plt.ylabel(u"deposit", fontproperties='font')
plt.show();# Show the picture
我們可以得到以下關係
通過觀察,我們知道,這個存款的上漲速度是不斷地變快的,但是有生之年,還是漲不了多少。
那麼,上面給出的方程:
我們可以把它拆分成無數個代數方程,我們把它稱爲一個動力系統,我們可以看出,如果我們一致這個系統中的某一項,我們之恩那個緊接着算出來它的下一項,而不能直接算出特定項的值,所以我們需要進行迭代100次才能算出a100的值。
如果我們每個月都要從賬戶中取走50塊錢的話,我們就可以得到新的轉移方程:
我們稍微改一下自己的程序,就可以得到新的變化曲線,如下:
這時,經過我們的思考——不對啊!錢怎麼能是負的呢!我們需要更改一下範圍,再更改範圍後,我們得到了新的圖片:
這樣就非常完美了,我們可以看出,23年後錢會被花光,準確的說是第23年取錢時,賬戶中不足50元。
一個序列就是定義域爲全體非負整數集合上的一個函數,其值域爲實數的一個子集,一個動力系統就是序列各項之間的一種關係,數值解就是滿足該動力系統的一張數值表。
2、用差分法方程近似描述變化
上一個例子中,我們每個月的利息以及從銀行中取走的錢都是固定的,我們的模型準確無比,完全貼合現實,但是現實是殘酷的,我們的模型往往不能準確的描述客觀世界,所以,我們需要畫出現實世界的變化,觀察模式,然後用數學術語來近似描述變化。
離散變化與連續變化
很明顯,在上一小節中,我們的存款每年只會發生一次變化,所以我們說,它的變化是在離散的時間區間上發生的。而正如我們所說,現實很殘酷,很多的變化是連續地發生的,比如下面這個例子。
例1 酵母培養物的增長
下面表格中的數據是從測量酵母培養物增長的實驗收集來的,圖形顯示可以假設種羣量的變化和當前種羣量的大小成比例。即:pn = pn+1 - pn = k*p,其中pn表示n小時後種羣生物量的多少,而k是一個正常數,k的值依賴於時間測量。
以小時計的時間_n | 觀察到的酵母生物量_ pn | 生物量的變化_pn+1 - p n |
---|---|---|
0 | 9.6 | 8.7 |
1 | 18.3 | 10.7 |
2 | 29.0 | 18.2 |
3 | 47.2 | 23.9 |
4 | 71.1 | 48.0 |
5 | 119.1 | 55.5 |
6 | 174.6 | 82.7 |
7 | 257.3 | NULL |
我們先把圖畫出來,以方便觀察(我們以n爲X軸,pn爲Y軸,進行繪圖)
據書中所說,這個k我們的取值大約是在0.5左右,那麼我們可以給出一個假設的比例模型:
我們得到了相鄰兩項之間的關係:
但顯然,這是不合理的。
模型存在的問題
- 食物、空間等資源只能支持某個最大限度的種羣量而不能支持無限量的增長,當接近這個最大限度時,增長速度變慢。
例二 進一步討論酵母培養物的增長
我們得到了一張新的表格:
以小時計的時間_n | 觀察到的酵母生物量_ pn | 生物量的變化_pn+1 - p n |
---|---|---|
0 | 9.6 | 8.7 |
1 | 18.3 | 10.7 |
2 | 29.0 | 18.2 |
3 | 47.2 | 23.9 |
4 | 71.1 | 48.0 |
5 | 119.1 | 55.5 |
6 | 174.6 | 82.7 |
7 | 257.3 | 93.4 |
8 | 350.7 | 90.3 |
9 | 441.0 | 72.3 |
10 | 513.3 | 46.4 |
11 | 559.7 | 35.1 |
12 | 594.8 | 34.6 |
13 | 629.4 | 11.4 |
14 | 640.8 | 10.3 |
15 | 651.1 | 4.8 |
16 | 655.9 | 3.7 |
17 | 659.6 | 2.2 |
18 | 661.8 | NULL |
我們還是和剛纔一樣,把圖給他畫出來:
我們可以看到,隨着時間的增多,微生物的增長趨勢逐漸放緩,而且根據圖形,我們可以估計出,我們的容納量是在665左右[因爲超過665後,增速很快的降低了](這可能是因爲,在達到容納量後培養基所提供的營養物質、以及培養皿所提供的空間,都不適宜該微生物的生存了),在知道樣本容納量後我們可以使用這樣的模型:
其中Capacity代表容納量,在這個模型中,有:
這樣構建出的模型,隨着pn的增長,變化逐漸減小
我們可以畫出一個(665 - pn)*pn與之間的關係圖:
觀察到這裏,我女朋友找我視頻了,我視頻完再慢慢寫嘿嘿嘿。
好了,視頻完了,開始繼續寫。
我們可以近似地求出,斜率k與等於 0.00082,所以我們可以給出模型:
通過移項,我們可以得到:
該方程是二次的,這種動力系統是非線性的,而且一般不能球的解析解,也就是講,一般不能求得用n來表示的解析解,只能迭代的進行求解,下面我們根據我們的模型來進行預測:
假設我們已知p0 = 9.6 那麼我們可以進行預測:
如圖中所示,紅色的點代表實際情況中的點,而黑色的代表我們預測的值,我們可以看出,雖然中間一段沒對上,但是我們的模型已經將它變化的趨勢表現得淋漓盡致了。
小結
書上除了這兩個例題之外還給出了三個其他例題,在此就不多枚舉了。總體來說,當我們發現我們解決的問題的曲線大致是一個S型曲線的時候,就可以使用這種模型進行解決。而且除了這種非線性的,我們也可以構建一個像是 這樣的模型.一切根據實際情況而判斷.
3、動力系統的解法
猜測法(抄書)
猜測法是強有力的數學方法,先假設動力系統的解的形式,然後再去判斷假設是否合理,這種方法要基於探索和觀察並據此摸清解的模式,下面我們從一個例子開始。
再論儲蓄存單
我們在第一節中講過儲蓄存單的問題,在初始時我們有1000美元,每年有1%的利息,如果既不存款也不付款,那麼我們會有如下的動力系統:
很顯然,這個數列是無限增長的,而且我們可以說,這個數列的第k項
,emmm,所以我們就可以說,這個動力系統的解爲:
總體的講,猜測法可以分爲以下幾個步驟:
- 觀察模式
- 猜測動力系統解的形式(個人認爲這個是最重要的)
- 用代入法來測試該猜測(我們上面沒有寫這個部分)
- 接受或拒絕該猜測取決於再代入和代數運算後結構是否滿足該動力系統,爲了接受該猜測,帶入的結果必須是恆等式
模型一:線性動力系統
這個線性動力系統就像是我們上面說的這個例子中的一樣,總體有:
這個非常簡單,我們就不多講述。
模型一再討論:的長期行爲
在這裏我們對r進行分類討論,根據他們的不同圖像,來討論動力系統的長期行爲。
- 的情況:
- 時的取值無界,很簡單,不談了
- 時的取值逐漸趨向於0,也很簡單
- 時的取值不變,更簡單
- 當時,我們假定,可以畫出這樣的圖像:
- 爲了實現這個功能,我們可以用python寫一個簡單的迭代就可以了:
import matplotlib.pyplot as plt
X=[0];
Y=[100];
for i in range (50):
X.append(i+1);
Y.append(Y[i]*(-1.1));
plt.plot(X,Y);
plt.show();
動力系統,r,b爲常數
定義 當時,如果對所有的有,則將數a成爲動力系統的平衡點或不動點,即是該動力系統的常數解
求平衡點並對其進行分類
我們已知動力系統滿足下式:
又因爲該動力系統是平衡的,所以有:
所以我們可以知道:
通過簡單的運算,可以得到:
所以說,爲該系統的平衡點
而對於某個(依賴初始條件的)常數c,動力系統的解爲:
非線性方程組
回想一下我們之前寫過的一個式子:
我們經過一系列的代數運算後可以把它化簡爲一個這樣的式子:
在這個動力系統中,r非常小的變化會引起解行爲發生巨大的變化,像是時,我們編寫程序:
import matplotlib.plot as plt
X=[0];
Y=[0.1];
for i in range(100):
Y.append(3.75*(1-Y[i])*Y[i]);
X.append(i+1);
plt.scatter(X,Y);
plt.show();
會發現,現在的系統發生了巨大的變化,我們上圖中所展示出的行爲稱爲混沌行文,混沌系統展示了他們對系統的常數參數的敏感性,給定的混沌系統對初始條件可以十分敏感。
4、差分方程組
在本節中,我們研究差分方程組,對於所選擇的起始值,建立數值解以求當差該系統的長期行爲。在第三節中我們知道,平衡點是一種取值,一旦到達了平衡點,系統就不會再有變化了。本節中,我們要求出平衡點,然後對平衡點附近的起始值進行探究,如果從靠近一個平衡點的起始值開始,我們想知道該系統是否:
- 仍然靠近該平衡點
- 趨近該平衡點
- 不再靠近該平衡點
再平衡點附近會發生什麼將提供有關該動力系統長期行爲的洞察,該動力系統展示週期行爲麼?有震盪行爲麼?由數值解描述的長期行爲對初始條件、所研究的行爲的建模中用到的比例常數的微小變化敏感麼?
例1 汽車租賃公司
一家汽車租賃公司在奧蘭多和坦帕都有分公司,這家公司是專門爲滿足在這兩個城市開展旅遊活動的旅行社的需要而開設的,因此,遊客可以在一個城市租車而在另一個城市還車,遊客可能在兩個城市都有旅行計劃。該公司想確定對這種方便的接換車方式的收費應該爲多少。因爲汽車可以在兩個城市歸還,每個城市就要有足夠的車輛以滿足用車需要,如果置放的車輛不夠了,那麼要從奧蘭多運送多少車輛到坦帕運送多少車輛到奧蘭多呢?對這些問題的回答將有助於該公司計算出它的期望成本。
歷史數據揭示:約有60%在奧蘭多出租的車輛還到了奧蘭多,另外40%的車輛還到了坦帕。在坦帕分公司出租的車中,有70%仍舊還到了坦帕,另外30%的車輛還到了奧蘭多。
動力系統模型 我們來研究該系統的一個模型,令n表示營業天數,有定義:
因此歷史記錄顯示該系統應該是
平衡點 該系統的平衡點就是是系統不再發生變化的O_n和T_n的值。如果它們存在的話,分別稱爲平衡點O和T,同時有 和,帶入我們的模型,我們可以得到以下的方程:
我們解這個方程組可以得到,,如果該公司有7000輛車,而且開始時在奧蘭多有3000輛車而在坦帕有4000輛車,那麼我們的模型預測:
因此如果該系統在處開始,將保持不變
接下來我們探究如果從不同於平衡點的值開始會怎麼樣,我們對以下四個初始條件來迭代該系統:
序號 | 奧蘭多 | 坦帕 |
---|---|---|
1 | 7000 | 0 |
2 | 5000 | 2000 |
3 | 2000 | 5000 |
4 | 0 | 7000 |
接下來我們編程,將圖像畫出
以下四張圖片對應序號從1到4的情況:
對初始條件的敏感性以及長期行爲 四種情況中的每一種情況在第一週內都是和平衡點很接近的,甚至在其中一個城市沒有車的情況下也是如此,結果暗示平衡點是穩定的而且對起始值不敏感的。