AIS数据分析详解
2010-08-10 14:01
441 查看
想必大家在刚接触AIS时,对AIS数据的解码感到困惑,其是采用6位ASCII压缩码传输的,所以对AIS数据的正确解析,就是完成任务的关键所在。通过最近的一个项目,了解了AIS数据的解码分析过程,现将其流程和相关代码列出,此参表可以参见快乐鹦鹉的AIS解码算法一文http://blog.csdn.net/happyparrot/archive/2007/04/26/1585185.aspx。
view plaincopy to clipboardprint?
Public Function fun_Decode(ByVal AISData As String) As String
On Error GoTo DoError
Dim strAisData As String ' 待解码的数据缓冲区
Dim i As Long
Dim strAisBin As String ' 存AIS数据转成二进制的
Dim strTemp As String
Dim strAisDec As String ' 存AIS数据转成十进制的
For i = 1 To Len(AISData)
strTemp = Mid(AISData, i, 1) ' 取ASCII
strAisDec = fun_Hex2Dec(AsciiToHex(strTemp)) ' AIS数据转成十进制的
If CInt(strAisDec) < 48 Or CInt(strAisDec) > 119 Or (CInt(strAisDec) > 87 And CInt(strAisDec) < 96) Then
Exit Function
Else
strAisDec = CStr(CInt(strAisDec) + 40)
If CInt(strAisDec) > 128 Then
strAisDec = CStr(CInt(strAisDec) + 32)
Else
strAisDec = CStr(CInt(strAisDec) + 40)
End If
strAisBin = fun_Hex2Bin(DecToHex(strAisDec)) ' AIS数据转成二进制的
'strAisBin = CDec(strAisDec)
fun_Decode = fun_Decode & (Right("000000" & strAisBin, 6)) ' 取AIS数据低六位
End If
Next i
Debug.Print fun_Decode
Debug.Print Len(fun_Decode)
Debug.Print BinToDec(strAisBin)
Exit Function
' --------------- 错误处理 部分, 注意: 前面正常代码必须有 结束语句 --------------------
DoError:
Call sub_DoErrors("Cls_AISDecode fun_Decode", Err.Description)
End Function
Public Function fun_Decode(ByVal AISData As String) As String
On Error GoTo DoError
Dim strAisData As String ' 待解码的数据缓冲区
Dim i As Long
Dim strAisBin As String ' 存AIS数据转成二进制的
Dim strTemp As String
Dim strAisDec As String ' 存AIS数据转成十进制的
For i = 1 To Len(AISData)
strTemp = Mid(AISData, i, 1) ' 取ASCII
strAisDec = fun_Hex2Dec(AsciiToHex(strTemp)) ' AIS数据转成十进制的
If CInt(strAisDec) < 48 Or CInt(strAisDec) > 119 Or (CInt(strAisDec) > 87 And CInt(strAisDec) < 96) Then
Exit Function
Else
strAisDec = CStr(CInt(strAisDec) + 40)
If CInt(strAisDec) > 128 Then
strAisDec = CStr(CInt(strAisDec) + 32)
Else
strAisDec = CStr(CInt(strAisDec) + 40)
End If
strAisBin = fun_Hex2Bin(DecToHex(strAisDec)) ' AIS数据转成二进制的
'strAisBin = CDec(strAisDec)
fun_Decode = fun_Decode & (Right("000000" & strAisBin, 6)) ' 取AIS数据低六位
End If
Next i
Debug.Print fun_Decode
Debug.Print Len(fun_Decode)
Debug.Print BinToDec(strAisBin)
Exit Function
' --------------- 错误处理 部分, 注意: 前面正常代码必须有 结束语句 --------------------
DoError:
Call sub_DoErrors("Cls_AISDecode fun_Decode", Err.Description)
End Function
结合自己在AIS项目中的理解,提出几点需要注意的方面:
1. AIS的数据校验采用的是异或校验,校验的数据时!和*之间的数据,比如原始数据位:!ABVDM,1,1,,B,169G?I0P007k`vT;BwhP7gv4@d0e,0*0A
则校验的数据应该是:ABVDM,1,1,,B,169G?I0P007k`vT;BwhP7gv4@d0e,0。下面列出异或算法的代码:
view plaincopy to clipboardprint?
Public Function ChkSumXOR(ByVal strMYGPS As String) As String
On Error GoTo DoError
Dim i As Integer ' 临时循环变量
Dim tmp As Variant ' 临时变量 保存每次读取的 字符内容
Dim Length As Integer ' 保存 需要计算校验码字符串的长度
Dim Result As Integer ' 保存 异或校验 计算的结果
strMYGPS = Trim(strMYGPS) ' 冗余设计, 前后不能有 空格 字符
Length = Len(strMYGPS) ' 计算 刷新字符串后的字符串长度
Result = 0
For i = 1 To Length
tmp = Mid(strMYGPS, i, 1)
tmp = Asc(tmp)
Result = Result Xor tmp
Next
ChkSumXOR = Hex(Result / 256) & Hex(Result Mod 256) ' Hex(Result) 为了使用者的方便 提供 2 位数字
ChkSumXOR = Mid(ChkSumXOR, 2, 2) '上述计算时 可能得到 3 位数据 显示后两位 (最高位此时为 0)
If Len(ChkSumXOR) = 1 Then ' 保证
ChkSumXOR = "0" & ChkSumXOR
End If
Exit Function
' --------------- 错误处理 部分, 注意: 前面正常代码必须有 结束语句 --------------------
DoError:
Call sub_DoErrors("mod_Public ChkSumXOR", Err.Description)
End Funct
Public Function ChkSumXOR(ByVal strMYGPS As String) As String
On Error GoTo DoError
Dim i As Integer ' 临时循环变量
Dim tmp As Variant ' 临时变量 保存每次读取的 字符内容
Dim Length As Integer ' 保存 需要计算校验码字符串的长度
Dim Result As Integer ' 保存 异或校验 计算的结果
strMYGPS = Trim(strMYGPS) ' 冗余设计, 前后不能有 空格 字符
Length = Len(strMYGPS) ' 计算 刷新字符串后的字符串长度
Result = 0
For i = 1 To Length
tmp = Mid(strMYGPS, i, 1)
tmp = Asc(tmp)
Result = Result Xor tmp
Next
ChkSumXOR = Hex(Result / 256) & Hex(Result Mod 256) ' Hex(Result) 为了使用者的方便 提供 2 位数字
ChkSumXOR = Mid(ChkSumXOR, 2, 2) '上述计算时 可能得到 3 位数据 显示后两位 (最高位此时为 0)
If Len(ChkSumXOR) = 1 Then ' 保证
ChkSumXOR = "0" & ChkSumXOR
End If
Exit Function
' --------------- 错误处理 部分, 注意: 前面正常代码必须有 结束语句 --------------------
DoError:
Call sub_DoErrors("mod_Public ChkSumXOR", Err.Description)
End Funct
2、关于AIS数据各个数据段的具体含义
!aaccc,x,y,z,u,c-c,v*hh <CR><LF>
aaccc为标识符,指明本条句子封装的背景信息;
x为传输该条消息所需的表达句数目(至多为9条);
y为本条句子在序列中的牌号;
z为同一序列的统一标识(0-9的循环);
u表示接收该条消息时对应的频道(A/B);
c-c为封装信息,需要映射6位ASCII码;
v表 示填充的字符,因为封装的字符需要是6的整数倍,若不满足,则需要填充0-5个字符;
hh表示的是检验和字段。
这里需要说明的是:关于填充字符,已经填充在封装信息,时期成为6的整数倍,在数据解码过程中无需在额外填充。
3、关于数据解析过程中,有些数据需要使用ASCII码,比如说船舶类型,这就涉及到将解码的二进制进行编码的问题,下面将实现程序列出:
+ expand sourceview plaincopy to clipboardprint?
·········10········20········30········40········50········60········70········80········90········100·······110·······120·······130·······140·······150
Public Function fun_Code(ByVal AISData As String) As String
On Error GoTo DoError
Dim strAisData As String ' 待解码的数据缓冲区
Dim i As Long
Dim strAisBin As String ' 存AIS数据 二进制
Dim strASCII As String
Dim strAisDec As String ' 存AIS数据转成十进制的
strAisData = AISData
For i = 1 To Len(strAisData) Step 6
strAisDec = BinToDec(Mid(strAisData, i, 6))
If CInt(strAisDec) >= 32 Then ' 在32以后 都是在六位的压缩码前加"00"
strAisBin = "00" & Mid(strAisData, i, 6)
ElseIf CInt(strAisDec) >= 0 And CInt(strAisDec) < 32 Then ' 0~31 都是在六位的压缩码前加"01"
strAisBin = "01" & Mid(strAisData, i, 6)
End If
strASCII = strASCII & Chr(CLng(BinToDec(strAisBin)))
Next i
fun_Code = strASCII
Exit Function
' --------------- 错误处理 部分, 注意: 前面正常代码必须有 结束语句 --------------------
DoError:
Call sub_DoErrors("Cls_AISDecode fun_Code", Err.Description)
End Function
Public Function fun_Code(ByVal AISData As String) As String
On Error GoTo DoError
Dim strAisData As String ' 待解码的数据缓冲区
Dim i As Long
Dim strAisBin As String ' 存AIS数据 二进制
Dim strASCII As String
Dim strAisDec As String ' 存AIS数据转成十进制的
strAisData = AISData
For i = 1 To Len(strAisData) Step 6
strAisDec = BinToDec(Mid(strAisData, i, 6))
If CInt(strAisDec) >= 32 Then ' 在32以后 都是在六位的压缩码前加"00"
strAisBin = "00" & Mid(strAisData, i, 6)
ElseIf CInt(strAisDec) >= 0 And CInt(strAisDec) < 32 Then ' 0~31 都是在六位的压缩码前加"01"
strAisBin = "01" & Mid(strAisData, i, 6)
End If
strASCII = strASCII & Chr(CLng(BinToDec(strAisBin)))
Next i
fun_Code = strASCII
Exit Function
' --------------- 错误处理 部分, 注意: 前面正常代码必须有 结束语句 --------------------
DoError:
Call sub_DoErrors("Cls_AISDecode fun_Code", Err.Description)
End Function
此算法对应的参表请查看 GB-T20068-2006船载自动识别系统(AIS)技术要求
本文来自CSDN博客,转载请标明出处:http://blog.csdn.net/lenyusun/archive/2010/03/19/5395978.aspx
view plaincopy to clipboardprint?
Public Function fun_Decode(ByVal AISData As String) As String
On Error GoTo DoError
Dim strAisData As String ' 待解码的数据缓冲区
Dim i As Long
Dim strAisBin As String ' 存AIS数据转成二进制的
Dim strTemp As String
Dim strAisDec As String ' 存AIS数据转成十进制的
For i = 1 To Len(AISData)
strTemp = Mid(AISData, i, 1) ' 取ASCII
strAisDec = fun_Hex2Dec(AsciiToHex(strTemp)) ' AIS数据转成十进制的
If CInt(strAisDec) < 48 Or CInt(strAisDec) > 119 Or (CInt(strAisDec) > 87 And CInt(strAisDec) < 96) Then
Exit Function
Else
strAisDec = CStr(CInt(strAisDec) + 40)
If CInt(strAisDec) > 128 Then
strAisDec = CStr(CInt(strAisDec) + 32)
Else
strAisDec = CStr(CInt(strAisDec) + 40)
End If
strAisBin = fun_Hex2Bin(DecToHex(strAisDec)) ' AIS数据转成二进制的
'strAisBin = CDec(strAisDec)
fun_Decode = fun_Decode & (Right("000000" & strAisBin, 6)) ' 取AIS数据低六位
End If
Next i
Debug.Print fun_Decode
Debug.Print Len(fun_Decode)
Debug.Print BinToDec(strAisBin)
Exit Function
' --------------- 错误处理 部分, 注意: 前面正常代码必须有 结束语句 --------------------
DoError:
Call sub_DoErrors("Cls_AISDecode fun_Decode", Err.Description)
End Function
Public Function fun_Decode(ByVal AISData As String) As String
On Error GoTo DoError
Dim strAisData As String ' 待解码的数据缓冲区
Dim i As Long
Dim strAisBin As String ' 存AIS数据转成二进制的
Dim strTemp As String
Dim strAisDec As String ' 存AIS数据转成十进制的
For i = 1 To Len(AISData)
strTemp = Mid(AISData, i, 1) ' 取ASCII
strAisDec = fun_Hex2Dec(AsciiToHex(strTemp)) ' AIS数据转成十进制的
If CInt(strAisDec) < 48 Or CInt(strAisDec) > 119 Or (CInt(strAisDec) > 87 And CInt(strAisDec) < 96) Then
Exit Function
Else
strAisDec = CStr(CInt(strAisDec) + 40)
If CInt(strAisDec) > 128 Then
strAisDec = CStr(CInt(strAisDec) + 32)
Else
strAisDec = CStr(CInt(strAisDec) + 40)
End If
strAisBin = fun_Hex2Bin(DecToHex(strAisDec)) ' AIS数据转成二进制的
'strAisBin = CDec(strAisDec)
fun_Decode = fun_Decode & (Right("000000" & strAisBin, 6)) ' 取AIS数据低六位
End If
Next i
Debug.Print fun_Decode
Debug.Print Len(fun_Decode)
Debug.Print BinToDec(strAisBin)
Exit Function
' --------------- 错误处理 部分, 注意: 前面正常代码必须有 结束语句 --------------------
DoError:
Call sub_DoErrors("Cls_AISDecode fun_Decode", Err.Description)
End Function
结合自己在AIS项目中的理解,提出几点需要注意的方面:
1. AIS的数据校验采用的是异或校验,校验的数据时!和*之间的数据,比如原始数据位:!ABVDM,1,1,,B,169G?I0P007k`vT;BwhP7gv4@d0e,0*0A
则校验的数据应该是:ABVDM,1,1,,B,169G?I0P007k`vT;BwhP7gv4@d0e,0。下面列出异或算法的代码:
view plaincopy to clipboardprint?
Public Function ChkSumXOR(ByVal strMYGPS As String) As String
On Error GoTo DoError
Dim i As Integer ' 临时循环变量
Dim tmp As Variant ' 临时变量 保存每次读取的 字符内容
Dim Length As Integer ' 保存 需要计算校验码字符串的长度
Dim Result As Integer ' 保存 异或校验 计算的结果
strMYGPS = Trim(strMYGPS) ' 冗余设计, 前后不能有 空格 字符
Length = Len(strMYGPS) ' 计算 刷新字符串后的字符串长度
Result = 0
For i = 1 To Length
tmp = Mid(strMYGPS, i, 1)
tmp = Asc(tmp)
Result = Result Xor tmp
Next
ChkSumXOR = Hex(Result / 256) & Hex(Result Mod 256) ' Hex(Result) 为了使用者的方便 提供 2 位数字
ChkSumXOR = Mid(ChkSumXOR, 2, 2) '上述计算时 可能得到 3 位数据 显示后两位 (最高位此时为 0)
If Len(ChkSumXOR) = 1 Then ' 保证
ChkSumXOR = "0" & ChkSumXOR
End If
Exit Function
' --------------- 错误处理 部分, 注意: 前面正常代码必须有 结束语句 --------------------
DoError:
Call sub_DoErrors("mod_Public ChkSumXOR", Err.Description)
End Funct
Public Function ChkSumXOR(ByVal strMYGPS As String) As String
On Error GoTo DoError
Dim i As Integer ' 临时循环变量
Dim tmp As Variant ' 临时变量 保存每次读取的 字符内容
Dim Length As Integer ' 保存 需要计算校验码字符串的长度
Dim Result As Integer ' 保存 异或校验 计算的结果
strMYGPS = Trim(strMYGPS) ' 冗余设计, 前后不能有 空格 字符
Length = Len(strMYGPS) ' 计算 刷新字符串后的字符串长度
Result = 0
For i = 1 To Length
tmp = Mid(strMYGPS, i, 1)
tmp = Asc(tmp)
Result = Result Xor tmp
Next
ChkSumXOR = Hex(Result / 256) & Hex(Result Mod 256) ' Hex(Result) 为了使用者的方便 提供 2 位数字
ChkSumXOR = Mid(ChkSumXOR, 2, 2) '上述计算时 可能得到 3 位数据 显示后两位 (最高位此时为 0)
If Len(ChkSumXOR) = 1 Then ' 保证
ChkSumXOR = "0" & ChkSumXOR
End If
Exit Function
' --------------- 错误处理 部分, 注意: 前面正常代码必须有 结束语句 --------------------
DoError:
Call sub_DoErrors("mod_Public ChkSumXOR", Err.Description)
End Funct
2、关于AIS数据各个数据段的具体含义
!aaccc,x,y,z,u,c-c,v*hh <CR><LF>
aaccc为标识符,指明本条句子封装的背景信息;
x为传输该条消息所需的表达句数目(至多为9条);
y为本条句子在序列中的牌号;
z为同一序列的统一标识(0-9的循环);
u表示接收该条消息时对应的频道(A/B);
c-c为封装信息,需要映射6位ASCII码;
v表 示填充的字符,因为封装的字符需要是6的整数倍,若不满足,则需要填充0-5个字符;
hh表示的是检验和字段。
这里需要说明的是:关于填充字符,已经填充在封装信息,时期成为6的整数倍,在数据解码过程中无需在额外填充。
3、关于数据解析过程中,有些数据需要使用ASCII码,比如说船舶类型,这就涉及到将解码的二进制进行编码的问题,下面将实现程序列出:
+ expand sourceview plaincopy to clipboardprint?
·········10········20········30········40········50········60········70········80········90········100·······110·······120·······130·······140·······150
Public Function fun_Code(ByVal AISData As String) As String
On Error GoTo DoError
Dim strAisData As String ' 待解码的数据缓冲区
Dim i As Long
Dim strAisBin As String ' 存AIS数据 二进制
Dim strASCII As String
Dim strAisDec As String ' 存AIS数据转成十进制的
strAisData = AISData
For i = 1 To Len(strAisData) Step 6
strAisDec = BinToDec(Mid(strAisData, i, 6))
If CInt(strAisDec) >= 32 Then ' 在32以后 都是在六位的压缩码前加"00"
strAisBin = "00" & Mid(strAisData, i, 6)
ElseIf CInt(strAisDec) >= 0 And CInt(strAisDec) < 32 Then ' 0~31 都是在六位的压缩码前加"01"
strAisBin = "01" & Mid(strAisData, i, 6)
End If
strASCII = strASCII & Chr(CLng(BinToDec(strAisBin)))
Next i
fun_Code = strASCII
Exit Function
' --------------- 错误处理 部分, 注意: 前面正常代码必须有 结束语句 --------------------
DoError:
Call sub_DoErrors("Cls_AISDecode fun_Code", Err.Description)
End Function
Public Function fun_Code(ByVal AISData As String) As String
On Error GoTo DoError
Dim strAisData As String ' 待解码的数据缓冲区
Dim i As Long
Dim strAisBin As String ' 存AIS数据 二进制
Dim strASCII As String
Dim strAisDec As String ' 存AIS数据转成十进制的
strAisData = AISData
For i = 1 To Len(strAisData) Step 6
strAisDec = BinToDec(Mid(strAisData, i, 6))
If CInt(strAisDec) >= 32 Then ' 在32以后 都是在六位的压缩码前加"00"
strAisBin = "00" & Mid(strAisData, i, 6)
ElseIf CInt(strAisDec) >= 0 And CInt(strAisDec) < 32 Then ' 0~31 都是在六位的压缩码前加"01"
strAisBin = "01" & Mid(strAisData, i, 6)
End If
strASCII = strASCII & Chr(CLng(BinToDec(strAisBin)))
Next i
fun_Code = strASCII
Exit Function
' --------------- 错误处理 部分, 注意: 前面正常代码必须有 结束语句 --------------------
DoError:
Call sub_DoErrors("Cls_AISDecode fun_Code", Err.Description)
End Function
此算法对应的参表请查看 GB-T20068-2006船载自动识别系统(AIS)技术要求
本文来自CSDN博客,转载请标明出处:http://blog.csdn.net/lenyusun/archive/2010/03/19/5395978.aspx
相关文章推荐
- AIS数据分析详解
- Excel2007中数据分析功能详解
- R数据分析——方法与案例详解(双色)
- 流媒体-FLV格式详解及数据分析
- asp.net中用VML动态的画出数据分析图表详解.
- 大数据入门第八天——MapReduce详解(三)MR的shuffer、combiner与Yarn集群分析
- 详解:大数据面临的安全问题及应对策略分析
- 游戏数据分析核心数据和算法公式详解
- asp.net中用VML动态的画出数据分析图表详解.
- javascript数据隐式转换详解与分析
- (转)JPEG图片数据结构分析- 附Png数据格式详解.doc
- PBOC/EMV-交易流程详解--POS与卡片的数据交互进行分析
- 【python数据挖掘课程】二十.KNN最近邻分类算法分析详解及平衡秤TXT数据集读取
- QPBOC交易流程详解--POS与卡片的数据交互进行分析
- Excel数据分析与业务建模_第三章_引用函数INDEX(语法详解及应用实例)
- 10.Spark Streaming源码分析:Receiver数据接收全过程详解
- QPBOC交易流程详解--POS与卡片的数据交互进行分析
- android中json数据分析及解析详解
- Titanic 多模型版 详解数据分析部分 机器学习初学者实战
- 网站分析数据的三种收集方式详解