从ROSbag中提取数据

时间:2017-06-07 14:26:43

标签: python linux io ros

我对python很陌生,只需要能够从一个rosbag中提取原始数据消息,这样我就可以用算法操作它来查找LiDAR数据中的模式。

我在github上发现了一个脚本从rosbag中提取数据但是得到了这个错误(在Ubuntu 16.04中从终端运行):

adam@manatee:~/workspace/TORC/LiDAR$ python ExtractDataROSbag.py 2017-02-27-09-35-59_0.bag
[OK] Found bag: 2017-02-27-09-35-59_0.bag
Traceback (most recent call last):
  File "ExtractDataROSbag.py", line 130, in <module>
    run()
  File "ExtractDataROSbag.py", line 40, in run
    bag = rosbag.Bag(inputFileName)
  File "/opt/ros/kinetic/lib/python2.7/dist-packages/rosbag/bag.py", line 173, in __init__
    self._open(f, mode, allow_unindexed)
  File "/opt/ros/kinetic/lib/python2.7/dist-packages/rosbag/bag.py", line 1096, in _open
    if   mode == 'r': self._open_read(f, allow_unindexed)
  File "/opt/ros/kinetic/lib/python2.7/dist-packages/rosbag/bag.py", line 1118, in _open_read
    self._file     = open(f, 'rb')
IOError: [Errno 2] No such file or directory: '2017-02-27-09-35-59_0.bag'

它似乎遍历代码的开头并识别包文件,打印&#34; Found Bag&#34;甚至在此之后设置变量,但随后错误开始。

我正在运行的脚本的完整代码如下:

#!/usr/bin/python

# Copyright 2010 Ankur Sinha
# Author: Ankur Sinha
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program.  If not, see <http://www.gnu.org/licenses/>.
#
# File : extractRawInfo.py
#

import rosbag
import sys
import os
import pickle

# Global variable for input file name

def run():
    """
    Main run method. Calls other helper methods to get work done
    """

    if len(sys.argv) != 2:
        sys.stderr.write('[ERROR] This script only takes input bag file as argument.n')
    else:
        inputFileName = sys.argv[1]
        print "[OK] Found bag: %s" % inputFileName

        bag = rosbag.Bag(inputFileName)
        topicList = readBagTopicList(bag)

        while True:
            if len(topicList) == 0:
                print "No topics in list. Exiting"
                break
            selection  = menu(topicList)

            if selection == -92:
                print "[OK] Printing them all"
                for topic in topicList:
                    extract_data(bag, topic, inputFileName)
                break
            elif selection == -45:
                break
            else:
                topic = topicList[selection]
                extract_data(bag, topic, inputFileName)
                topicList.remove(topicList[selection])

        bag.close()

def extract_data (bag, topic, inputFileName):
    """
    Spew messages to a file

    args:
        topic -> topic to extract and print to txt file
    """

    outputFileName = os.path.splitext(os.path.split(inputFileName)[1])[0] + topic.replace("/","-") + ".txt"
    print "[OK] Printing %s" % topic
    print "[OK] Output file will be called %s." % outputFileName

    outputFh = open(outputFileName, "w")

    for topic, msg, t in bag.read_messages(topics=topic):
        pickle.dump(msg,outputFh)

    outputFh.close()
    print "[OK] DONE"

def menu (topicList):
    """
    Print the user menu and take input

    args:
        topicList: tuple containing list of topics

    returns:
        selection: user selection as integer
    """

    i = 0
    for topic in topicList:
        print '[{0}] {1}'.format(i, topic)
        i = i+1
    if len(topicList) > 1:
        print '[{0}] Extract all'.format(len(topicList))
        print '[{0}] Exit'.format(len(topicList) + 1)
    else:
        print '[{0}] Exit'.format(len(topicList))

    while True:
        print 'Enter a topic number to extract raw data from:'
        selection = raw_input('>>>')
        if int(selection) == len(topicList):
            return -92 # print all
        elif int(selection) == (len(topicList) +1):
            return -45 # exit
        elif (int(selection) < len(topicList)) and (int(selection) >= 0):
            return int(selection)
        else:
            print "[ERROR] Invalid input"

def readBagTopicList(bag):
    """
    Read and save the initial topic list from bag
    """
    print "[OK] Reading topics in this bag. Can take a while.."
    topicList = []
    for topic, msg, t in bag.read_messages():
        if topicList.count(topic) == 0:
            topicList.append (topic)

    print '{0} topics found:'.format(len(topicList))
    return topicList

if __name__ == "__main__":
    run()

1 个答案:

答案 0 :(得分:0)

  1. 确保指定的文件确实存在。将文件名复制出错误消息并让系统找到它。不要重新输入名称,因为如果您第一次引入错误,则可以再次执行此操作。

  2. 如果文件确实存在,请尝试在命令行上提供.bag文件的完整路径。