为了账号安全,请及时绑定邮箱和手机立即绑定

使用 Python Api 在 C 中实现的二叉树将 PyObject 转换为字节

使用 Python Api 在 C 中实现的二叉树将 PyObject 转换为字节

慕神8447489 2023-03-16 11:26:22
我的 PyObject 在获取它的值时变成了一个 Bytes 对象所以最近,我正在用 C 做一个项目,我在其中实现了几种类型的树,以便能够在 python 中使用它们,因为 C btree 实现比 Python 快得多。(Ikr 有一些可用的库,但由于在锁定期间我有更多的空闲时间,我想,我可以做我自己的库。)一切正常,直到我想找到一个元素,并在同一行打印它的值。当我这样做时,我的Node对象变成了一个Bytes对象,没有任何进一步的赋值。更多信息操作系统:Ubuntu 16.04。Python 版本:Python 3.5.2GCC:5.4.0-6 Ubuntu蟒蛇代码:import mylibimport randommaxv = 10def addValues(tree, values):    for value in values:        tree.insert(value)def main():    my_list = [i for i in range(maxv)]    #random.shuffle(my_list)    tree    = mylib.BinaryTree('test')    addValues(tree, my_list)    print(tree.find(3).getValue())    print(tree.sort(False))    main()预期输出(如果主函数中最后一行之前的行是有效的print(tree.find(3))):3[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]我用上面的测试代码得到的输出:3Segmentation fault发生分段错误,因为包含值的节点在打印其值时3成为Bytes对象。下面的代码将打印新的Node.import mylibimport randommaxv = 10def addValues(tree, values):    for value in values:        tree.insert(value)def main():    my_list = [i for i in range(maxv)]    #random.shuffle(my_list)    tree    = mylib.BinaryTree('test')    addValues(tree, my_list)    print(tree.find(0).getValue()) #0 is going to be the root node's value, since random.shuffle is not happening.    print(tree.root)    print(tree.sort(False))    main()输出:0b'0'Segmentation fault我花了几天时间对此进行调试,而且由于我绝对不是 C 编程高手,(您将在下面看到),我找不到错误。我想继续,并实现更多功能,但我无法找到错误。我有可能错过了一些如此微不足道的事情,或者我不知道的事情。遗憾的是,我不是经验丰富的 C 程序员。:/我的模块包含更多代码,我不会发布这个问题不需要的代码。如果您认为应该多看一些以理解我的代码,请随时告诉我!我也希望我的代码可读性好!有人可以解释到底发生了什么吗?谢谢你!
查看完整描述

1 回答

?
临摹微笑

TA贡献1982条经验 获得超2个赞

正如评论中所讨论的那样,这是一个引用计数错误。AC API 函数必须返回 Python 所称的“新引用”。这意味着要么返回在函数内部有意创建的内容(例如 的结果PyList_New)以增加现有对象的引用计数。

具体来说BinaryTree_Find,您没有返回新的参考。因此,Python 最终会释放一个仍然构成 BinaryTree 一部分的对象。一旦发生这种情况,您可能会遇到各种奇怪且令人困惑的行为。我建议添加Py_INCREF(result).

为了帮助诊断此类问题,值得printf向对象构造函数和析构函数添加语句(作为临时调试措施),这样您就可以检查有关何时分配和释放它们的假设。


查看完整回答
反对 回复 2023-03-16
  • 1 回答
  • 0 关注
  • 83 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信