Tính trị số của chuỗi Hexadecimal

Các mẹo vặt linh tinh khác, không thuộc nhóm nào
Đăng trả lời
Hình đại diện của thành viên
alexanderdna
Guru
Guru
Bài viết: 214
Ngày tham gia: Thứ 3 14/07/2009 11:13 am
Đến từ: Sài Gòn
Has thanked: 3 times
Been thanked: 15 times

Tính trị số của chuỗi Hexadecimal

Gửi bài by alexanderdna »

Thủ thuật: Tính trị số của chuỗi thập lục phân
Tác giả: alexanderdna
Mô tả: Từ một chuỗi lưu số hex ta tính ra trị số của nó
Chào mọi người! Hôm qua Alex đăng bài về mảng, thấy tuy dỡ mà được ủng hộ cũng khá, nên bữa nay làm gan đăng thêm một bài nữa.
Như ta đã biết, để cho hiện một số ở dạng thập lục phân (Hexadecimal), ta dùng hàm Hex hoặc Hex$. Hàm này nhận một trị số và trả về chuỗi hex tương ứng. Câu hỏi đặt ra là liệu có một hàm nào trong VB6 có công năng ngược lại không? Theo kiến thức eo hẹp của Alex thì không.
Dựa trên một ý tưởng về mã hóa Base64, Alex đã tìm ra một cách khá đơn giản như sau:

Mã: Chọn tất cả

Function Hex2Dec(ByVal strHex As String) As Integer    'Chuỗi các giá trị hợp lệ của hệ đếm thập lục phân    Const Base16 = "0123456789ABCDEF"    'Đổi về chữ in để phù hợp với chuỗi Base16    strHex = UCase(strHex)    Dim i As Integer, result As Integer, tmp As String    For i = 1 To Len(strHex)        tmp = Mid(strHex, i, 1)        'Trái tim của thuật toán là ở đây        result = result + (InStr(1, Base16, tmp) – 1) _            * (16 ^ (Len(strHex) – i))    Next    'Trả về kết quả    Hex2Dec = resultEnd Function
Sử dụng:

Mã: Chọn tất cả

Dim h As String, i As Integerh = "6F"i = Hex2Dec(h)
Lưu ý: chuỗi hex không được có ký hiệu "0x", "&H" hay bất cứ ký hiệu nào dùng để mô tả hệ đếm.

Phương pháp này không phải khó, Alex nghĩ chắc ai cũng biết thuật toán quy đổi hệ số. Ngày trước Alex dùng Select Case cho các chữ ABCDEF nên chương trình khá rối, nay chuyển sang chuỗi giá trị và InStr thì thấy mau lẹ hơn. Hàm này có thể mở rộng ra các hệ đếm khác, chỉ cần thay đổi chuỗi giá trị và đổi số 16 ở công thức result thành cơ số mới.
Hình đại diện của thành viên
truongphu
VIP
VIP
Bài viết: 4785
Ngày tham gia: Chủ nhật 04/11/2007 10:57 am
Đến từ: Cam Đức, Khánh hòa
Has thanked: 14 times
Been thanked: 530 times

Re: Tính trị số của chuỗi Hexadecimal

Gửi bài by truongphu »

alexanderdna đã viết:Từ một chuỗi lưu số hex ta tính ra trị số của nó
rất hoan nghênh alex. Dù sao dùng thêm dấu &H thì cũng tiện hơn

Mã: Chọn tất cả

MsgBox CLng(&H6F)
hoặc

Mã: Chọn tất cả

MsgBox CLng("&H" & "6F")
:D
o0o--truongphu--o0o

.........
Ghé thăm:
Chuyện Linh Tinh
Hình đại diện của thành viên
truongphu
VIP
VIP
Bài viết: 4785
Ngày tham gia: Chủ nhật 04/11/2007 10:57 am
Đến từ: Cam Đức, Khánh hòa
Has thanked: 14 times
Been thanked: 530 times

Re: Tính trị số của chuỗi Hexadecimal

Gửi bài by truongphu »

Dù sao tôi cũng phải góp với Alex một tay:

Mã: Chọn tất cả

Function Hex2Dec(ByVal strHex As String) As Long    Const Base16 = "0123456789ABCDEF"    Dim i As Byte, result As Long, tmp As String        For i = 1 To Len(strHex)            tmp = UCase(Mid(strHex, i, 1))            result = result + (InStr(1, Base16, tmp) - 1) * (16 ^ (Len(strHex) - i))        Next    Hex2Dec = resultEnd Function
1- Function Hex2Dec phải là As Long, As Interger thì dễ tràn bộ nhớ; tương tự result
2- Đưa hàm Ucase trước hàm Mid, gọn câu code
3- Cấu trúc code giữ nguyên, Code hay ở chổ dùng hàm InStr

Chúc mừng Alex
o0o--truongphu--o0o

.........
Ghé thăm:
Chuyện Linh Tinh
Hình đại diện của thành viên
truongphu
VIP
VIP
Bài viết: 4785
Ngày tham gia: Chủ nhật 04/11/2007 10:57 am
Đến từ: Cam Đức, Khánh hòa
Has thanked: 14 times
Been thanked: 530 times

Re: Tính trị số của chuỗi Hexadecimal

Gửi bài by truongphu »

Code trên còn có thể sửa thêm là:
Const Base16 = "123456789ABCDEF", bỏ số 0
do đó câu code sau sửa lại là:
result = result + (InStr(1, Base16, tmp)) * (16 ^ (Len(strHex) - i)), bỏ -1

Mã: Chọn tất cả

Function Hex2Dec(ByVal strHex As String) As Long    Const Base16 = "123456789ABCDEF"    Dim i As Byte, result As Long, tmp As String        For i = 1 To Len(strHex)            tmp = UCase(Mid(strHex, i, 1))            result = result + (InStr(1, Base16, tmp)) * (16 ^ (Len(strHex) - i))        Next    Hex2Dec = resultEnd Function
OK?
o0o--truongphu--o0o

.........
Ghé thăm:
Chuyện Linh Tinh
Hình đại diện của thành viên
alexanderdna
Guru
Guru
Bài viết: 214
Ngày tham gia: Thứ 3 14/07/2009 11:13 am
Đến từ: Sài Gòn
Has thanked: 3 times
Been thanked: 15 times

Re: Tính trị số của chuỗi Hexadecimal

Gửi bài by alexanderdna »

Cám ơn bác truongphu, con lại có thêm một kinh nghiệm mới.
Và tất nhiên, hàm chuyển đổi trên tuy chẳng bằng CInt, CLng,... của VB nhưng nếu sửa lại để chuyển đổi hệ số khác (2, 8, 64 hoặc một hệ kỳ khôi nào đó mà người dùng tự nghĩ ra) thì hẳn là hữu dụng, phải không bác Phú?

Con xin góp thêm hàm chuyển từ hệ thập phân sang hệ khác (ví dụ: bát phân):

Mã: Chọn tất cả

Function ToOct(ByVal source As Long) As String    Const OctString = "01234567"    Dim result As String    Do While source <> 0        result = Mid(OctString, (source Mod 8) + 1, 1) & result        source = source \ 8    Loop    ToOct = resultEnd Function
Tất nhiên trên đây chỉ là ví dụ, vì thực tế VB có hàm Oct() xài rất tiện lợi, mà các hệ đếm khác có cơ số từ 10 trở xuống cũng không cần chuỗi giá trị chi cho mệt (xài thẳng phép mod luôn). Song từ đây có thể chuyển sang cơ số lớn hơn 10, ngay cả Base64 cũng không thành vấn đề.
luan_nguyen
Bài viết: 1
Ngày tham gia: Thứ 2 05/03/2012 2:48 pm

Re: Tính trị số của chuỗi Hexadecimal

Gửi bài by luan_nguyen »

xin hỏi bác trường phú vấn đề này: " con đang viết một phần mềm điều khiển nhỏ cài trên PC điều khiển các thiết bị không dây qua cổng COM nhưng trong VB.NET con chỉ thấy có truyền dạng chuỗi ko có truyền dạng số hex, mà những thiết bị không dây đó nhất định phải truyền nhận bằng số hex chẳng hạn: 8F 00 B3 00 EF EF 0F FF, không biết bác Phú đã gặp vấn đề này chưa?" xin bác chỉ giúp
Hình đại diện của thành viên
truongphu
VIP
VIP
Bài viết: 4785
Ngày tham gia: Chủ nhật 04/11/2007 10:57 am
Đến từ: Cam Đức, Khánh hòa
Has thanked: 14 times
Been thanked: 530 times

Re: Tính trị số của chuỗi Hexadecimal

Gửi bài by truongphu »

luan_nguyen đã viết:mà những thiết bị không dây đó nhất định phải truyền nhận bằng số hex chẳng hạn: 8F 00 B3 00 EF EF 0F FF
Chuôi Hex đấy là chuỗi byte
Với VB6, ta chuyển từ deci sang hex với hàm Hex

vd chuỗi cần xử lý là: luan_nguyen có 37 con gà nòi
qua Hex:
6C 75 61 6E 5F 6E 67 75 79 65 6E 20 63 F3 20 33 37 20 63 6F 6E 20 67 E0 20 6E F2 69

  1. Private Sub Form_Load()
  2. Dim Mang() As Byte
  3. Mang = "luan_nguyen có 37 con gà nòi"
  4.  
  5. Dim MM$
  6. For i = 0 To UBound(Mang)
  7.     If Mang(i) > 0 Then MM = MM & Hex(Mang(i)) & " "
  8. Next
  9. Text1 = MM
  10. End Sub
o0o--truongphu--o0o

.........
Ghé thăm:
Chuyện Linh Tinh
Hình đại diện của thành viên
dazzlingvit
Guru
Guru
Bài viết: 960
Ngày tham gia: Thứ 3 18/01/2011 10:21 am
Đến từ: Sinh ra từ hư vô, sống trong thế giới ảo...
Has thanked: 6 times
Been thanked: 112 times
Tiếp xúc:

Re: Tính trị số của chuỗi Hexadecimal

Gửi bài by dazzlingvit »

luan_nguyen đã viết:xin hỏi bác trường phú vấn đề này: " con đang viết một phần mềm điều khiển nhỏ cài trên PC điều khiển các thiết bị không dây qua cổng COM nhưng trong VB.NET con chỉ thấy có truyền dạng chuỗi ko có truyền dạng số hex, mà những thiết bị không dây đó nhất định phải truyền nhận bằng số hex chẳng hạn: 8F 00 B3 00 EF EF 0F FF, không biết bác Phú đã gặp vấn đề này chưa?" xin bác chỉ giúp
Mình nghĩ hex ở đây là cái bạn nhìn thấy thôi, còn thực chất truyền tuần tự nó truyền từng bit :)
Dazzling V.I.T
Hãy gọi tôi là vịt :)
Đăng trả lời

Quay về