近似与精确——《狂人C》习题解答15(第三章习题5)
題目:從前有一個農夫,死后留下15頭牛,他在遺書中寫到:"妻子:分給全部牛的半數再加半頭;長子:分給剩下的牛的半數再加半頭;次子:分給剩下的牛的半數再加半頭;長女:分給最后剩下的。"編程求長女得到了幾頭牛。
??? 這是一個簡單的小學算術問題:
??? 15頭牛的一半是7又1/2 ,再加半頭得8,這是妻子所得。剩下7頭
??? 7頭牛的一半是3又1/2 ,再加半頭得4,這是長子所得。剩下3頭
??? 3頭牛的一半是1又1/2 ,再加半頭得2,這是次子所得。剩下1頭
??? 因而長女所得為1頭。
??? 但是如果寫出如下的代碼,則最多只能得60分。
#include <stdio.h> #include <stdlib.h>#define ZONGSHU 15. //總數:留下15頭牛 #define FENPEI_BL .5 //分配比例: 半數 #define EWAI_TJ .5 //額外添加:半頭 int main( void ) {double qizi , zhangzi , cizi , zhangnv ; //妻子、長子、次子、長女所得 double shengyu = ZONGSHU ; //剩余的數量 qizi = shengyu * FENPEI_BL + EWAI_TJ ; //妻子所得shengyu -= qizi ; //剩余的數量zhangzi = shengyu * FENPEI_BL + EWAI_TJ ; //長子所得shengyu -= zhangzi ; //剩余的數量cizi = shengyu * FENPEI_BL + EWAI_TJ ; //次子所得shengyu -= cizi ; //剩余的數量zhangnv = shengyu ; //長女:分給最后剩下的printf("長女得到了%f頭牛\n" , zhangnv ) ;system("PAUSE"); return 0;}輸出:長女得到了1.000000頭牛
??? 因為,第一,這個結果僅僅表示長女得到的牛數約等于1頭;第二,代碼并沒有真正實現前面的算術運算過程。譬如
??? qizi =? shengyu * FENPEI_BL +? EWAI_TJ ;
??? 所表示的含義僅僅是一些近似的值的一個近似運算,而非前面算術運算過程中的精確運算。因為就其本質和普遍情形來講,實浮點類型的數據只是對實數的一個近似表示,這注定實浮點類型的運算也只是一種近似運算。只不過在本題目中,近似的精度很高,計算結果恰好和精確的結果一致而已。如果把程序視為對筆算過程的精確模擬的話,顯然前面一段代碼并不符合要求。
??? 在計算機中,只有整數類型是對整數集合子集的近似表示。所以如果希望準確地模擬筆算過程就只能用整數類型。然而筆算過程涉及到了分數。在數學中,分數也是一種精確表示,然而在C語言中卻并沒有與之對應的“分數類型”。
??? 沒有相應的數據類型怎么辦?答案很簡單:沒有這種類型就創造這種數據類型。為創造性提供了廣闊的發揮空間是C語言的特點和魅力,也恰恰是編程的樂趣之一。
??? 由于分數是由分子、分母兩個部分組成,而分子、分母都是整數,因而可以用兩個整數類型的數據來表示分數。對于這樣的數據,C語言并沒有提供直接的運算,這種“分數”的運算需要自己用C語言所提供的運算模擬。
??? 例如,若計算a/b+c/d,則無法通過一次“+”運算完成,只能分兩次計算出和的分子“b*c+d*c”及和的分母“a*c”。
??? 按照這種辦法得到的代碼是
輸出:長女得到了1又0/16384頭牛
??? 這是一個精確的結果。
??? 【注:學習了控制語句和函數理論之后,后一個代碼可以進一步改進。】
?
轉載于:https://www.cnblogs.com/KBTiller/archive/2011/09/24/2189685.html
總結
以上是生活随笔為你收集整理的近似与精确——《狂人C》习题解答15(第三章习题5)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Chrome开发者工具和Firebug的
- 下一篇: hdu_1233(最小生成树)