如何从此数据类型中提取十六进制值? - Python cantools
How to extract the hex value from this data type? - Python cantools
我正在使用 Python cantools
库从 CAN dbc 文件中提取消息,返回的数据类型如下所示:
message('Message_10', 0x146, False, 8, None),
我需要提取第二个值,0x146
并且消息名称的长度可能会发生变化,因此标准字符串切片无法始终如一地工作。
我的第一个想法是将 message('Message_10', 0x146, False, 8, None),
转换为字符串,然后删除所有不以 0x
开头的内容,但我怀疑有更好的方法。
这样做的目的是从 DBC 文件中提取所有 CAN ID,并创建一个字典,每个罐 ID 号作为键。然后监控 CAN 总线并使用与 CAN 总线上每个 CAN ID 关联的数据有效负载更新目录中的每个值。
这是我的代码片段,我最初尝试只提取消息名称,这很有效,但我需要消息 ID,0x146
,作为我字典中的键来与我看起来的进行比较正在上车
有人知道如何完成这个吗?
import cantools
db = cantools.database.load_file('C:\Users\Tim\Desktop\dbc_file.dbc')
def can_table(db):
messages = []
#pprint.pprint(db.messages)
for msg in range(0, len(db.messages)):
x = str(db.messages[msg])
x = x[7:] # Remove "message"
x = x.replace('(', '').replace(')', '').replace('\'', '')
x = x.split(', ') # Split into list
messages.append(x[0]) # First element is list is the message name
message_table = {}
# Populate values as None in dictionary
for i in messages:
message_table[i]=None
#pprint.pprint(message_table)
return message_table
调用 str()
后 x
的示例:
"message('Message_3', 0x143, False, 8, None)"
"message('Message_2', 0x142, False, 8, None)"
"message('Message', 0x141, False, 8, None)"
"message('Message_with_long_name', 0x201, False, 8, 'comment that explains what this message does')"
dir(db.messages[1])
的结果:
['__class__', '__delattr__', '__dict__', '__dir__', '__doc__', '__eq__', '__format__', '__ge__', '__getattribute__', '__gt__', '__hash__', '__init__', '__init_subclass__', '__le__', '__lt__', '__module__', '__ne__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__subclasshook__', '__weakref__', '_bus_name', '_check_mux', '_check_signal', '_check_signal_lengths', '_check_signal_tree', '_check_signals', '_check_signals_ranges_scaling', '_codecs', '_comment', '_create_codec', '_create_signal_tree', '_cycle_time', '_dbc', '_decode', '_encode', '_frame_id', '_get_mux_number', '_is_extended_frame', '_length', '_name', '_protocol', '_send_type', '_senders', '_signal_groups', '_signal_tree', '_signals', '_strict', 'bus_name', 'comment', 'cycle_time', 'dbc', 'decode', 'encode', 'frame_id', 'get_signal_by_name', 'is_extended_frame', 'is_multiplexed', 'layout_string', 'length', 'name', 'protocol', 'refresh', 'send_type', 'senders', 'signal_choices_string', 'signal_groups', 'signal_tree', 'signal_tree_string', 'signals']
第二个值为frame_id。就做 msg.frame_id
。不要将其转换为字符串。
for msg in db.messages:
print(msg.frame_id)
从 cantools 代码中,您可以看到使用 __repr__
方法将消息转换为字符串。
def __repr__(self):
return "message('{}', 0x{:x}, {}, {}, {})".format(
self._name,
self._frame_id,
self._is_extended_frame,
self._length,
"'" + self._comment + "'" if self._comment is not None else None)
我正在使用 Python cantools
库从 CAN dbc 文件中提取消息,返回的数据类型如下所示:
message('Message_10', 0x146, False, 8, None),
我需要提取第二个值,0x146
并且消息名称的长度可能会发生变化,因此标准字符串切片无法始终如一地工作。
我的第一个想法是将 message('Message_10', 0x146, False, 8, None),
转换为字符串,然后删除所有不以 0x
开头的内容,但我怀疑有更好的方法。
这样做的目的是从 DBC 文件中提取所有 CAN ID,并创建一个字典,每个罐 ID 号作为键。然后监控 CAN 总线并使用与 CAN 总线上每个 CAN ID 关联的数据有效负载更新目录中的每个值。
这是我的代码片段,我最初尝试只提取消息名称,这很有效,但我需要消息 ID,0x146
,作为我字典中的键来与我看起来的进行比较正在上车
有人知道如何完成这个吗?
import cantools
db = cantools.database.load_file('C:\Users\Tim\Desktop\dbc_file.dbc')
def can_table(db):
messages = []
#pprint.pprint(db.messages)
for msg in range(0, len(db.messages)):
x = str(db.messages[msg])
x = x[7:] # Remove "message"
x = x.replace('(', '').replace(')', '').replace('\'', '')
x = x.split(', ') # Split into list
messages.append(x[0]) # First element is list is the message name
message_table = {}
# Populate values as None in dictionary
for i in messages:
message_table[i]=None
#pprint.pprint(message_table)
return message_table
调用 str()
后 x
的示例:
"message('Message_3', 0x143, False, 8, None)"
"message('Message_2', 0x142, False, 8, None)"
"message('Message', 0x141, False, 8, None)"
"message('Message_with_long_name', 0x201, False, 8, 'comment that explains what this message does')"
dir(db.messages[1])
的结果:
['__class__', '__delattr__', '__dict__', '__dir__', '__doc__', '__eq__', '__format__', '__ge__', '__getattribute__', '__gt__', '__hash__', '__init__', '__init_subclass__', '__le__', '__lt__', '__module__', '__ne__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__subclasshook__', '__weakref__', '_bus_name', '_check_mux', '_check_signal', '_check_signal_lengths', '_check_signal_tree', '_check_signals', '_check_signals_ranges_scaling', '_codecs', '_comment', '_create_codec', '_create_signal_tree', '_cycle_time', '_dbc', '_decode', '_encode', '_frame_id', '_get_mux_number', '_is_extended_frame', '_length', '_name', '_protocol', '_send_type', '_senders', '_signal_groups', '_signal_tree', '_signals', '_strict', 'bus_name', 'comment', 'cycle_time', 'dbc', 'decode', 'encode', 'frame_id', 'get_signal_by_name', 'is_extended_frame', 'is_multiplexed', 'layout_string', 'length', 'name', 'protocol', 'refresh', 'send_type', 'senders', 'signal_choices_string', 'signal_groups', 'signal_tree', 'signal_tree_string', 'signals']
第二个值为frame_id。就做 msg.frame_id
。不要将其转换为字符串。
for msg in db.messages:
print(msg.frame_id)
从 cantools 代码中,您可以看到使用 __repr__
方法将消息转换为字符串。
def __repr__(self):
return "message('{}', 0x{:x}, {}, {}, {})".format(
self._name,
self._frame_id,
self._is_extended_frame,
self._length,
"'" + self._comment + "'" if self._comment is not None else None)