Kiểu dữ liệu thích hợp để giữ giá trị phần trăm?


Câu trả lời:


132

Giả sử có hai chữ số thập phân trên tỷ lệ phần trăm của bạn, loại dữ liệu bạn sử dụng phụ thuộc vào cách bạn định lưu trữ tỷ lệ phần trăm của mình. Nếu bạn định lưu trữ phần tương đương của chúng (ví dụ: 100,00% được lưu trữ dưới dạng 1,0000), tôi sẽ lưu trữ dữ liệu trong một decimal(5,4)kiểu dữ liệu với một CHECKràng buộc đảm bảo rằng các giá trị không bao giờ vượt quá 1,0000 (giả sử đó là giới hạn) và không bao giờ xuống dưới 0 (giả sử đó là sàn nhà). Nếu bạn định lưu trữ mệnh giá của chúng (ví dụ: 100,00% được lưu trữ dưới dạng 100,00), thì bạn nên sử dụng decimal(5,2)với một CHECKràng buộc thích hợp . Kết hợp với một tên cột tốt, nó làm cho các nhà phát triển khác hiểu rõ dữ liệu là gì và cách dữ liệu được lưu trữ trong cột.


12
Nó không phải là decimal(5,2)nơi 2 biểu thị số chữ số sau dấu phân cách thập phân?
Boris Callens

2
@BorisCallens - Không thể tin được là tôi đã bỏ lỡ điều đó suốt những năm qua. Vâng, đó là một lỗi đánh máy. decimal(5,2)là những gì nên được nắm bắt với một ràng buộc kiểm tra.
Thomas

4
Tôi cho rằng điều này ban đầu đã có decimal(5,4)và đã được thay đổi thành decimal(5,2)sau nhận xét trên ... Tôi nghĩ decimal(5,4)sẽ là định nghĩa tốt hơn - tức là bạn muốn lưu trữ 0 đến 1 với 2 chữ số thập phân, không phải 0 đến 100. Lý do là tỷ lệ phần trăm nằm ngoài 100; vì vậy 100% là 100/100 là 1. Làm theo cách này có ý nghĩa hơn đối với hầu hết các trường hợp (ví dụ: 100% * 100% = 100%không phải 10000%; 1 * 1 = 1).
JohnLBevan

4
@JohnLBevan - Nó phụ thuộc vào cách chúng được lưu trữ. Nếu các giá trị sẽ được lưu trữ dưới dạng hiển thị (ví dụ 100.00) thì bạn cần decimal(5,2). Nếu các giá trị sẽ được lưu trữ dưới dạng phân số (ví dụ 1.0000), thì bạn cần decimal(5,4). Sẽ cập nhật bài viết.
Thomas

Bất cứ ai có thể giải thích tại sao bạn cần 4 chữ số thập phân? Bạn không thể sử dụng 2? Như .91 === 91% hoặc 1.00 === 100%. Tôi đang thực hiện điều này ngay bây giờ và đang tự hỏi mức tăng với 4 vị trí. Một cái gì đó giống như số thập phân Pct (10, 2) KIỂM TRA (Pct> =. 01 VÀ Pct <= 1). Cảm ơn trước.
MH

31
  • Giữ như một decimal.
  • Thêm các ràng buộc kiểm tra nếu bạn muốn giới hạn phạm vi (ví dụ: từ 0 đến 100%; trong một số trường hợp có thể có lý do hợp lệ để vượt quá 100% hoặc thậm chí có khả năng trở thành phủ định).
  • Coi giá trị 1 là 100%, 0,5 là 50%, v.v. Điều này sẽ cho phép mọi phép toán hoạt động như mong đợi (tức là trái ngược với việc sử dụng giá trị 100 là 100%).
  • Sửa đổi độ chính xác và tỷ lệ theo yêu cầu (đây là hai giá trị trong dấu ngoặc columnName decimal(precision, scale). Độ chính xác cho biết tổng số chữ số có thể được giữ trong số, tỷ lệ cho biết có bao nhiêu chữ số đó sau chữ số thập phân, decimal(3,2)một số có thể được biểu diễn như #.##; decimal(5,3)sẽ là ##.###.
  • decimalnumericvề cơ bản là cùng một thứ. Tuy nhiên, decimalnó tuân thủ ANSI, vì vậy hãy luôn sử dụng nó trừ khi có quy định khác (ví dụ: theo tiêu chuẩn mã hóa của công ty bạn).

Các tình huống mẫu

  • Đối với trường hợp của bạn (0,00% đến 100,00%) mà bạn muốn decimal(5,4).
  • Đối với trường hợp phổ biến nhất (0% đến 100%) mà bạn muốn decimal(3,2).
  • Trong cả hai điều trên, các ràng buộc kiểm tra sẽ giống nhau

Thí dụ:

if object_id('Demo') is null
create table Demo
    (
        Id bigint not null identity(1,1) constraint pk_Demo primary key
        , Name nvarchar(256) not null constraint uk_Demo unique 
        , SomePercentValue decimal(3,2) constraint chk_Demo_SomePercentValue check (SomePercentValue between 0 and 1)
        , SomePrecisionPercentValue decimal(5,2) constraint chk_Demo_SomePrecisionPercentValue check (SomePrecisionPercentValue between 0 and 1)
    )

Đọc thêm:


4

Tôi đồng ý với Thomas và ít nhất tôi sẽ chọn giải pháp DECIMAL (5,4) cho các ứng dụng WPF.

Hãy xem Chuỗi định dạng số MSDN để biết lý do tại sao: http://msdn.microsoft.com/en-us/library/dwhawy9k#PFormatString

Định dạng phần trăm ("P") nhân một số với 100 và chuyển đổi nó thành một chuỗi biểu thị phần trăm.

Sau đó, bạn sẽ có thể sử dụng điều này trong mã XAML của mình:

DataFormatString="{}{0:P}"

2

Nếu 2 chữ số thập phân là mức độ chính xác của bạn, thì "smallint" sẽ xử lý điều này trong khoảng trống nhỏ nhất (2 byte). Bạn lưu trữ phần trăm nhân với 100.

CHỈNH SỬA: Loại thập phân có lẽ phù hợp hơn. Sau đó, bạn không cần phải mở rộng quy mô theo cách thủ công. Nó mất 5 byte cho mỗi giá trị.


Microsoft đã phá vỡ rất nhiều liên kết của nó .....
pcnate

0

Sử dụng số (n, n) trong đó n có đủ độ phân giải để làm tròn thành 1,00. Ví dụ:

declare @discount numeric(9,9)
    , @quantity int
select @discount = 0.999999999
    , @quantity = 10000

select convert(money, @discount * @quantity)

3
Câu hỏi này có một câu trả lời được chấp nhận được đánh giá khá cao từ hơn ba năm trước. Nếu bạn đang tìm kiếm câu hỏi cũ để trả lời, xin vui lòng tham khảo tại đây: stackoverflow.com/unanswered
valverij
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.