2011-08-18 45 views
5

Tôi muốn chuyển đổi một int thành một mảng byte [4] bằng cách sử dụng BCD.Chuyển đổi một Int thành một mảng BCD

Int trong câu hỏi sẽ đến từ id thiết bị và cần thiết để nói chuyện với thiết bị qua cổng nối tiếp.

Có chức năng nào được thực hiện trước để thực hiện việc này hay bạn có thể cho tôi cách làm đơn giản này không?

dụ:

int id= 29068082 

sẽ ra:

byte[4]{0x82, 0x80, 0x06, 0x29}; 
+0

Tôi giả sử bạn có nghĩa là ', 0x29}'? –

+0

Tôi không biết bất kỳ hỗ trợ BCD nào trong lib, đặt cược tốt nhất của bạn là một chức năng tùy chỉnh sử dụng ToString làm trung gian. –

+0

Có, nó phải là 0x29 xin lỗi .. – Kingpin

Trả lời

7

Sử dụng phương pháp này.

public static byte[] ToBcd(int value){ 
     if(value<0 || value>99999999) 
      throw new ArgumentOutOfRangeException("value"); 
     byte[] ret=new byte[4]; 
     for(int i=0;i<4;i++){ 
      ret[i]=(byte)(value%10); 
      value/=10; 
      ret[i]|=(byte)((value%10)<<4); 
      value/=10; 
     } 
     return ret; 
    } 

Đây thực chất là cách hoạt động.

  • Nếu giá trị nhỏ hơn 0 hoặc lớn hơn 99999999, giá trị sẽ không vừa với bốn byte. Chính thức hơn, nếu giá trị nhỏ hơn 0 hoặc là 10^(n * 2) hoặc lớn hơn, trong đó n là số byte, giá trị sẽ không vừa với n byte.
  • Đối với mỗi byte:
    • Đặt byte đó thành phần còn lại của giá trị chia cho 10 thành byte. (Điều này sẽ đặt chữ số cuối cùng trong nibble [nửa byte] thấp của byte hiện tại thấp.)
    • Chia giá trị cho 10.
    • Thêm 16 lần phần còn lại của giá trị chia cho 10 byte. (. Điều này sẽ đặt các chữ số bây giờ cuối cùng trong nibble cao của byte hiện hành)
    • Chia giá trị bằng 10.

(Một tối ưu hóa là để thiết lập tất cả các byte 0 trước - được thực hiện ngầm bởi .NET khi nó phân bổ một mảng mới - và dừng lặp lại khi giá trị đạt đến 0. Việc tối ưu hóa sau này không được thực hiện trong đoạn mã trên, để đơn giản. phân chia/phần còn lại cho phép thu hồi thương và phần còn lại trong một bước phân chia, một tối ưu hóa thường không cần thiết.)

+0

hoạt động tuyệt vời :) – Kingpin

+0

Bạn có thể cho tôi biết điều gì đang xảy ra ở đây từng bước? Cảm ơn. – Anonymous

+0

@Anonymous: Tôi đã thêm giải thích. –

1

có thể là một chức năng phân tích cú pháp đơn giản có chứa vòng lặp này

i=0; 
while (id>0) 
{ 
    twodigits=id%100; //need 2 digits per byte 
    arr[i]=twodigits%10 + twodigits/10*16; //first digit on first 4 bits second digit shifted with 4 bits 
    id/=100; 

    i++; 
} 
1

Cùng phiên bản như Peter O. nhưng trong VB.NET

Public Shared Function ToBcd(ByVal pValue As Integer) As Byte() 
    If pValue < 0 OrElse pValue > 99999999 Then Throw New ArgumentOutOfRangeException("value") 

    Dim ret As Byte() = New Byte(3) {} 'All bytes are init with 0's 

    For i As Integer = 0 To 3 
     ret(i) = CByte(pValue Mod 10) 
     pValue = Math.Floor(pValue/10.0) 
     ret(i) = ret(i) Or CByte((pValue Mod 10) << 4) 
     pValue = Math.Floor(pValue/10.0) 
     If pValue = 0 Then Exit For 
    Next 

    Return ret 
End Function 

Bí quyết ở đây là phải nhận thức được rằng chỉ đơn giản là sử dụng pvalue/= 10 sẽ làm tròn giá trị vì vậy nếu ví dụ lập luận là "16", người đầu tiên một phần của byte sẽ đúng, nhưng kết quả của phép chia sẽ là 2 (khi 1,6 sẽ được làm tròn lên). Vì vậy tôi sử dụng phương pháp Math.Floor.

Các vấn đề liên quan