我有一些代码,其中类的实例具有父< - >子引用,例如:
class Node(object):
def __init__(self):
self.parent = None
self.children = {}
def AddChild(self, name, child):
child.parent = self
self.children[name] = child
def Run():
root, c1, c2 = Node(), Node(), Node()
root.AddChild("first", c1)
root.AddChild("second", c2)
Run()
Run Code Online (Sandbox Code Playgroud)
我认为这会创建循环引用root,c1并且c2在Run()完成后不会被释放,对吗?那么,如何让它们被释放?我想我可以做点什么root.children.clear(),或者self.parent = None- 但如果我不知道该怎么做呢?
这是使用weakref模块的合适时间吗?什么,我究竟是什么弱反应?该parent属性?该children属性?整个对象?上述所有的?我看到有关WeakKeyDictionary和weakref.proxy的讨论,但我不清楚它们应该如何使用,如果有的话,在这种情况下.
这也是在python2.4上(无法升级).
更新:示例和摘要
weakref-ify的哪些对象取决于哪个对象可以在没有另一个对象的情况下生存,以及哪些对象相互依赖.生命时间最长的对象应包含较短寿命对象的弱化参数.同样,不应该将weakrefs设置为依赖项 - 如果它们是依赖项,依赖项可能会默默地消失,即使它仍然需要.
例如,如果你有一个树结构,root有子节点kids,但可以没有子root节点,那么该对象应该使用weakrefs kids.如果子对象依赖于父对象的存在,情况也是如此.下面,子对象需要父对象来计算其深度,因此强对齐parent.kids但是,属性的成员是可选的,因此使用weakrefs来阻止循环引用. …
今天早些时候,我需要一次迭代一个字符串2个字符来解析格式化的字符串"+c-R+D-E"(有一些额外的字母).
我最终得到了这个,但它看起来很难看.我最后评论它正在做什么,因为它感觉不明显.它几乎似乎是pythonic,但并不完全.
# Might not be exact, but you get the idea, use the step
# parameter of range() and slicing to grab 2 chars at a time
s = "+c-R+D-e"
for op, code in (s[i:i+2] for i in range(0, len(s), 2)):
print op, code
Run Code Online (Sandbox Code Playgroud)
有没有更好/更清洁的方法来做到这一点?
我的另一个类似的问题,但讨论偏离了我正在讨论的问题.
假设我有一个处理费用报告(ER)的系统.您可以创建和编辑它们,添加附件以及批准/拒绝它们.
费用报告可能如下所示:
GET /er/1
=>
{"title": "Trip to NY", "totalcost": "400 USD",
"comments": [
"john: Please add the total cost",
"mike: done, can you approve it now?"
],
"approvals": [
{"john": "Pending"}, {"finance-group": "Pending"}]
}
Run Code Online (Sandbox Code Playgroud)
看起来很好,对吗?这是费用报告文件的样子.
如果要更新它,可以执行以下操作:
POST /er/1
{"title": "Trip to NY 2010"}
Run Code Online (Sandbox Code Playgroud)
如果您要批准它,您可以这样做:
POST /er/1/approval
{"approved": true}
Run Code Online (Sandbox Code Playgroud)
但是,如果您想要更新报告并同时批准该怎么办?我们怎么做?如果你只想批准,那么做POST一些/er/1/approval有意义的事情.
我们可以在URL中放置一个标志POST /er/1?approve=1,并将数据更改作为正文发送,但该标志似乎不是RESTful.
我们也可以提交特殊领域,但这似乎也有点hacky.如果我们这样做,那么为什么不发送带有set_title或者属性的数据add_to_cost?
我们可以创建一个新的资源来进行更新和批准,但是(1)我想不出如何在没有动词的情况下命名它,以及(2)根据可以对哪些动作进行命名来定义资源似乎是不对的.它(如果我们添加更多动作会怎么样?)
我们可以有一个X-Approve:True | False标题,但标题似乎是错误的工具.如果不在浏览器中使用javascript,也很难获得设置的标题.
我们可以使用自定义媒体类型,application/approve+yes但这似乎并不比创建新资源更好.
我们可以创建一个临时的"批处理操作"URL /er/1/batch/A.然后,客户端发送多个请求,可能POST /er/1/batch/A …
在Python中,我知道__hash__给定对象的值返回应该与该对象的生命周期相同.但是,出于好奇,如果不是,会发生什么?这会造成什么样的破坏?
class BadIdea(object):
def __hash__(self):
return random.randint(0, 10000)
Run Code Online (Sandbox Code Playgroud)
我知道__contains__并且__getitem__会表现得很奇怪,因此,dicts和sets会表现得很奇怪.你也可能在dict/set中得到"孤立"值.
还有什么可能发生的?它可能会使解释器崩溃,还是破坏内部结构?
作为我的发布过程的一部分,我必须比较我的应用程序使用的一些JSON配置数据.作为第一次尝试,我只是漂亮地打印了JSON并对它们进行了差异化(使用kdiff3或者只是diff).
然而,随着数据的增长,kdiff3会混淆输出中的不同部分,使得添加看起来像巨型修改,奇数删除等.这使得很难弄清楚什么是不同的.我也尝试过其他差异工具(meld,kompare,diff,还有其他一些),但它们都有同样的问题.
尽管我付出了最大努力,但我似乎无法以diff工具可以理解的方式格式化JSON.
示例数据:
[
{
"name": "date",
"type": "date",
"nullable": true,
"state": "enabled"
},
{
"name": "owner",
"type": "string",
"nullable": false,
"state": "enabled",
}
...lots more...
]
Run Code Online (Sandbox Code Playgroud)
以上可能不会导致问题(当开始有数百行时会出现问题),但这就是所比较的要点.
这只是一个样本; 完整对象是4-5个属性,有些属性中有4-5个属性.属性名称非常统一,但它们的值非常不同.
通常,似乎所有的diff工具都会将结束"}"与关闭"}"的下一个对象混淆.我似乎无法打破这种习惯.
我尝试添加空格,更改缩进,并在各个对象之前和之后添加一些"BEGIN"和"END"字符串,但该工具仍然感到困惑.
我正在尝试使用asyncio并且必须将它与一些普通的多线程阻塞代码混合使用,因此我需要使用run_in_exector卸载执行.
该ASYNCIO文档警告说,"大部分功能"是不是线程安全的,这call_soon_threadsafe是唯一的线程功能.还有一些其他的,例如Future.add_done_callback,明确记录为线程安全的.然后它有一句话说"你可以使用run_in_executor在其他线程中运行回调",但是没有特别评论它的线程安全性.
run_in_executor不是doc'd是线程安全的,但是查看源代码,如果采用正确的代码路径,它看起来是线程安全的.
有谁知道它是否应该是线程安全的,但只是没有记录那样?
我已经戳了一下,但是当请求成功时我没有看到HTTP状态代码,但是在"不返回点"之后出现错误.
例如,假设你处理一个请求,它已经提交给了数据库,但是在返回结果时你运行了内存,或遇到了NPE,或者你有什么.这本来是一种200回应,但现在,在内部,你无法返回正确的,格式良好的反应.
202 Accepted 因为我们已经处理了请求,所以似乎不合适.
什么状态代码意味着"成功,但错误"?甚至还存在吗?
我知道sys.exc_info文档说在处理回溯对象时要小心,但我仍然不确定某些情况下的安全性或不安全性.此外,文档说"警告:不要这样做!",紧接着是"注意:实际上,它确定",这进一步让我感到困惑.
在任何情况下,文档和" 为什么需要在Python中显式删除sys.exc_info()回溯? "(Alex Martelli的回答),似乎暗示它唯一的局部变量引用分配给它们的追溯值,一个问题.
这给我留下了一些问题:
随意告诉我我的结论或假设在哪里是错误的,因为我已经多次因为我已经写了这个问题而将自己的信念和不相信我自己的陈述推理出来了:).
虽然我想要回答我的具体例子,但我也要求提供关于如何在更深奥的情况下安全地处理追溯的一般建议,知识或战争故事(例如,你必须运行循环并想要累积任何引发异常,你必须生成一个新线程,并且需要报告任何引发的异常,你必须创建闭包和回调,并且必须回复引发的异常等.
示例1:执行错误处理的内部函数
def DoWebRequest():
thread, error_queue = CreateThread(ErrorRaisingFunc)
thread.start()
thread.join()
if not error_queue.empty():
# Purposefully not calling error_queue.get() for illustrative purposes
print 'error!'
def CreateThread(func):
error_queue = Queue.Queue()
def Handled():
try:
func()
except Exception:
error_queue.put(sys.exc_info())
thread = threading.Thread(target=Handled)
return thread, error_queue
Run Code Online (Sandbox Code Playgroud)
Handled()闭包是否导致引发任何引发的异常error_queue并导致循环引用,因为error_queue还包含回溯?从error_queue(即调用.get())中移除回溯足以消除循环引用?
示例2:exc_info范围内的长生命对象,或返回exc_info
long_lived_cache = {}
def Alpha(key):
expensive_object = long_lived_cache.get(key)
if not expensive_object:
expensive_object = ComputeExpensiveObject()
long_lived_cache[key] = expensive_object …Run Code Online (Sandbox Code Playgroud) 我想在前面加上一个重要的通知,我不是一个C/C++程序员,并且很少知道库的链接如何在C中工作.
我们的代码使用libstdc ++.so.6(gcc 3.4,我认为).我们有第三方预编译(闭源)库使用libstdc ++.so.5(gcc 2.something或3.2,我认为).这是在Linux上.我们有第三方库的.a和.so版本.
是否可以使用第三方库构建我们的应用程序?怎么样?是否有可能在没有libstdc ++的情况下构建/运行我们的应用程序.so.5安装了我们的机器,怎么样?
如果我忘记了一些重要信息,请告诉我 - 我几乎不知道这些东西是什么.我意识到完全答案可能是不可能的; 我真的在寻找方向和指导.静态链接,动态,重建,预建某某,切换到版本x,或者符号链接quizdoodle等.
更新:
我们尝试使用dlopenwith RTLD_LOCAL将第三方库与我们应用程序的其余部分隔离开来.这似乎大部分都有效,但是,由于未知原因,我们留下了大量内存泄漏.我们怀疑,当我们调用时dlopen,第三方库会malloc从已经加载的.so.6中提取符号,并且事情变得混乱.
对于咯咯笑,我们尝试将第三方库放入LD_PRELOAD,然后运行我们的应用程序,内存泄漏似乎完全消失.
有没有人对Python Selector有任何意见或经验?它看起来很棒,但我对pypi的"Alpha"状态以及缺乏单元测试有点迟钝.
我最喜欢它的简单,自包含和纯WSGI.我发现的所有其他url路由器都假设我正在使用django,或者pylons,或者粘贴,或者引入许多其他依赖项,或者只是不要让我创建一个简单的url模式映射到wsgi应用程序.真的,我想做的就是:
mapper.add("/regex/{to}/{resource}", my_wsgi_app)
mapper.add("/another/.*", other_wsgi_app)
...etc...
Run Code Online (Sandbox Code Playgroud)
无论如何,有没有人以前使用它,或知道有哪些项目?