Boost 无序地图漂亮打印机正在多次打印值以及不需要的值
Posted
技术标签:
【中文标题】Boost 无序地图漂亮打印机正在多次打印值以及不需要的值【英文标题】:Boost unordered map pretty printer is printing value multiple times along with unwanted values 【发布时间】:2014-03-20 14:10:34 【问题描述】:我正在尝试通过从此处向现有的 boost 漂亮打印机列表添加一个新打印机来为 boost::unordered_map 添加一个漂亮的打印机: https://sourceware.org/gdb/wiki/STLSupporthttps://github.com/ruediger/Boost-Pretty-Printer
但是,当我尝试打印我的地图时,会多次打印很多值和一些不需要的字符。我不确定应该对我现有的代码进行哪些修改以使其仅打印一次值,而没有任何不需要的字符。这是我在 myMap.cpp 中更新 myMap 的循环:
for (int i=0; i<=10; i++)
string s = to_string(i);
myMap[s] = i;
当我在 gdb 中将 myMap 打印为
(gdb)p myMap
我得到如下结果:
$1 = boost::unordered::detail = "1" = 1, "0" = 0, "2" = 2, "1" = 1, "0" = 0, "3" = 3,
"2" = 2, "1" = 1, "0" = 0, "4" = 4, "3" = 3, "2" = 2, "1" = 1, "0" = 0, "5" = 5, "4" = 4,
"3" = 3, "2" = 2, "1" = 1, "0" = 0, "6" = 6, "5" = 5, "4" = 4, "3" = 3, "2" = 2, "1" = 1,
"0" = 0, "7" = 7, "10" = 10, "6" = 6, "5" = 5, "4" = 4, "3" = 3, "2" = 2, "1" = 1,
"0" = 0, "8" = 8, "7" = 7, "10" = 10, "6" = 6, "5" = 5, "4" = 4, "3" = 3, "2" = 2,
"1" = 1, "0" = 0, "9" = 9, "8" = 8, "7" = 7, "10" = 10, "6" = 6, "5" = 5, "4" = 4,
"3" = 3, "2" = 2, "1" = 1, "0" = 0,
" \204`", '\000' <repeats 13 times>, "\321\n\002", '\000' <repeats 181 times>... = 0,
"9" = 9, "8" = 8, "7" = 7, "10" = 10, "6" = 6, "5" = 5, "4" = 4, "3" = 3, "2" = 2,
"1" = 1, "0" = 0
我的漂亮打印机的 python 代码如下所示:
@_register_printer
class BoostUnorderedMap:
"Pretty Printer for boost::unordered_map"
printer_name = 'boost::unordered_map'
version = '1.40'
type_name_re = '^boost::unordered::unordered_map<.*>$'
class _iterator:
def __init__(self,fields):
type_1 = fields.val.type.template_argument(0)
type_2 = fields.val.type.template_argument(1)
self.buckets = fields.val['table_']['buckets_']
self.bucket_count = fields.val['table_']['bucket_count_']
self.bucket_size = fields.val['table_']['size_']
self.current_bucket = 0
self.value = 0
self.iteration = 0
self.temp_node = 0
self.bucket_to_start = 0
pair = "std::pair<%s const, %s>" % (type_1, type_2)
self.pair_pointer = gdb.lookup_type(pair).pointer()
self.base_pointer = gdb.lookup_type("boost::unordered::detail::value_base< %s >" % pair).pointer()
self.node_pointer = gdb.lookup_type("boost::unordered::detail::ptr_node<std::pair<std::basic_string<char, std::char_traits<char>, std::allocator<char> > const, int> >").pointer()
self.node = self.buckets[self.current_bucket]['next_']
def __iter__(self):
return self
def next(self):
while not self.node:
self.current_bucket = self.current_bucket + 1
if self.current_bucket >= self.bucket_count:
raise StopIteration
self.node = self.buckets[self.current_bucket]['next_']
iterator = self.node.cast(self.node_pointer).cast(self.base_pointer).cast(self.pair_pointer).dereference()
self.node = self.node['next_']
return ('%s' % iterator['first'], iterator['second'])
def __init__(self, val):
self.val = val
def children(self):
return self._iterator(self)
def to_string(self):
return "boost::unordered::detail"
任何帮助将不胜感激。
【问题讨论】:
【参考方案1】:如果不了解有关 Boost 内部结构的更多信息,很难确切知道出了什么问题。如果是我,我可能会破解“下一个”方法来添加一些调试打印,看看出了什么问题。
无论如何,在您的 Python 代码中有一件事很突出。现在您正在返回这样的子元素:
return ('%s' % iterator['first'], iterator['second'])
但是,使用此 API 的常用方法是将地图的键和值作为单独的子项返回,然后使用 display_hint 方法返回“地图”。见
https://sourceware.org/gdb/onlinedocs/gdb/Pretty-Printing-API.html
您可以在下一个方法中使用“yield”轻松完成此操作。
【讨论】:
以上是关于Boost 无序地图漂亮打印机正在多次打印值以及不需要的值的主要内容,如果未能解决你的问题,请参考以下文章