Trang 1 trên tổng số 2 12 Cuối cùngCuối cùng
Từ 1 tới 10 trên tổng số 13 kết quả

Đề tài: Kết quả quái lạ!

  1. #1
    Ngày gia nhập
    01 2008
    Bài viết
    8

    Question Kết quả quái lạ!

    Code:
    #include <iostream>
    #include <math.h>
    using namespace std;
    
    long double giaithua(int n)
    {
    	long double giai = n;
    	if(n == 1)
    		return 1;
    	else
    		giai *= giaithua(n-1);
    	return giai;
    }
    
    int main()
    {
    	long double x = giaithua(70);
    	cout << fixed << x << endl;
    	double y = pow(10, 25);
    	cout << endl << fixed << y;
    }
    Theo mình được biết thì kiểu double có giá trị trong khoảng 2.2E(-308) -> 1.8E(+308). Vậy thì kết quả vẫn có thể hiện hết đuợc.
    Nhưng kết quả mình nhận được là.
    Code:
    11978571669969891793327339282102242518556004970550477140128689166983962506507238
    776367392931467755520.000000
    
    10000000000000000905969664.000000
    Nhờ ai biết chỉ giùm.

    À còn thêm cái này nữa, các bạn có để ý thấy cái #include <math.h> không, không hiểu sao mà #include <cmath> không đuợc.
    Đã được chỉnh sửa lần cuối bởi ubuntu : 29-01-2008 lúc 10:07 PM.

  2. #2
    Ngày gia nhập
    12 2007
    Bài viết
    224

    Mình nghĩ đúng là kiểu double có miền giá trị trong khoảng -1.7E+308 -> 1.7E+308 thật đấy nhưng nó là kiểu số dấu phẩy độngđộ chính xác kép ( chính xác đến 15 số ) . Tức là miền giá trị của nó đã bao hàm cả những con số lẻ rồi . Nếu nói rằng giá trị lớn nhất của nó có thể đạt được là 1.7E+308 là ko đúng . Mong các bạn chỉnh sửa thêm .

  3. #3
    Ngày gia nhập
    01 2008
    Bài viết
    8

    Độ chính xác kép ở đây là về phần lẻ mà, nó chính xác đến 19 số lẻ. Còn phần nguyên thì có liên quan gì đâu, phần nguyên thì chỉ thể hiện ở miền giá trị thôi chứ nhỉ.

  4. #4
    Ngày gia nhập
    12 2007
    Bài viết
    224

    Em cũng ko rõ . Em chỉ suy như sau . Kiểu double dùng 8 byte = 64 bit để chứa giá trị . Như vậy max của nó có thể đạt được là (2^64)-1 = ( 1.84467440737096E+19 ) -1 . Nói như vậy em nghĩ ko đúng vì những ô bit của nó phải chứa thêm phần thập phân nữa . Nếu dùng 64 ô bit chỉ để chứa phần nguyện thì phần thập phân bỏ vào đâu ?

  5. #5
    Ngày gia nhập
    11 2007
    Bài viết
    0

    Kiểu lưu của em sieuphuong nói là kiểu lưu của số nguyên thôi, số thực có cách lưu khác, trong đó:
    - 1bit lưu dấu
    - 8bit lưu số mũ ( = exp )
    - các bit còn lại lưu phần thập phân
    Giá trị thực sự của số là (s × 2^e × m) với
    - s là dấu (+1/-1)
    - e = exp − 127
    - m = 1.xxxx trong đó xxxx là phần được lưu trong các bit cuối đó
    Cơ bản là vậy, còn chi tiết thì dài dòng lắm, chịu khó đọc tiếng Anh tí nhé: http://en.wikipedia.org/wiki/IEEE_fl...point_standard

    Về câu hỏi ở trên, kết quả cho ra là tương đối chính xác đấy chứ, chỉ để ý là phần các chữ số cuối thì sai, đó là do hiện tượng sai số ở cách lưu trữ số thực trên máy tính, đọc link ở trên thì sẽ hiểu rõ hơn

  6. #6
    Ngày gia nhập
    01 2008
    Bài viết
    8

    Mặc định Kết quả quái lạ!

    Vậy khi mình muốn nó hiện đúng tất cả thì làm như thế nào????

  7. #7
    Ngày gia nhập
    01 2008
    Nơi ở
    Rất nhiều sóng gió
    Bài viết
    360

    Độ dài kiểu tùy theo bạn cần tính bao nhiêu chữ số. 1 bit tương đương với khoảng 0.301 chữ số. Vậy 32 bit tương đương với khoảng 9.6 chữ số. 64 bit ~ 19.2 chữ số. Cần tính với các số 10 000 chữ số thì bạn phải dùng một kiểu có ít nhất 33 220 bit.

  8. #8
    Ngày gia nhập
    01 2008
    Bài viết
    8

    Vậy có nghĩa là C++ không thể tính được con số này sao?
    Nhưng theo mình test thử thì mình nghĩ là không phải vậy.
    Khi để pow(10, 308) nó vẫn có thể hiện đuợc giá trị, tuy không phải giá trị mình mong muốn.
    Đến khi pow(10, 309) nó hiện INF.
    Code:
    100000000000000001097906362944045541740492309677311846336810682903157585404911491537163328978494688899061249669721172515611590283743140088328307009198146046031271664502933027185697489699588559043338384466165001178426897626212945177628091195786707458122783970171784415105291802893207873272974885715430223118336.000000
    À còn thêm điều lạ nữa là kiểu long double là 12bytes.
    Nhưng sao trong lúc tính kiểu này thì thấy nó không khác double. Nghĩa là đến pow(10, 309) vẫn là INF
    Đã được chỉnh sửa lần cuối bởi ubuntu : 31-01-2008 lúc 08:54 AM.

  9. #9
    Ngày gia nhập
    12 2007
    Bài viết
    224

    long double là 12bytes.
    long double chỉ có 10 byte thôi .

  10. #10
    Ngày gia nhập
    01 2008
    Nơi ở
    Rất nhiều sóng gió
    Bài viết
    360

    Kiểu double chỉ có độ chính xác khoảng 15 chữ số. Bạn biểu diễn pow(10, 308) vẫn được hay bất cứ số thực nào không quá 1.7E+308 cũng được cả, nhưng chỉ có 15 chữ số đầu tiên là đảm bảo đúng (tức chữ số có nghĩa) mà thôi.

Các đề tài tương tự

  1. Trả lời: 0
    Bài viết cuối: 22-06-2012, 08:57 PM
  2. Trả lời: 0
    Bài viết cuối: 22-06-2012, 08:50 PM
  3. Trả lời: 0
    Bài viết cuối: 22-06-2012, 07:52 PM
  4. Trả lời: 0
    Bài viết cuối: 22-06-2012, 07:50 PM
  5. Trả lời: 0
    Bài viết cuối: 22-06-2012, 07:49 PM

Quyền hạn của bạn

  • Bạn không thể gửi đề tài mới
  • Bạn không thể gửi bài trả lời
  • Bạn không thể gửi các đính kèm
  • Bạn không thể chỉnh sửa bài viết của bạn