【问题标题】:Python/Tornado Class wrapper caching issuePython/Tornado 类包装器缓存问题
【发布时间】:2015-10-03 03:59:11
【问题描述】:

我正在围绕 Python 的数组数据结构实现一个包装器。我在我的应用程序中这样做是出于实际原因,但这个示例代码只是为了重现问题而提供的。通过 Tornado 抽象,每个请求的数组似乎都没有被“清除”。

如果我不使用我的数组抽象,就没有问题。这让我相信 CPython 实现中的某个地方存在错误。

from tornado import websocket, web, ioloop
import json

class Array():
    _data = []
    def push(self, value):
        self._data.append(value)

    def json(self):
        return json.dumps(self._data)


class ClientHandler(web.RequestHandler):
    def prepare(self):
        self.set_header("content-type", "application/json")

    def get(self):
        array = Array()

        for i in range(0, 6):
            array.push({'id': i})

        self.write(array.json())
        self.finish()

app = web.Application([
    (r'/client', ClientHandler),
], debug=True)

if __name__ == '__main__':
    kwargs = {"address": "127.0.0.1"}
    app.listen(port=8888, **kwargs)
    ioloop.IOLoop.instance().start()

启动python进程后刷新页面后得到的输出依次如下:

序列 1

[{"id": 0}, {"id": 1}, {"id": 2}, {"id": 3}, {"id": 4}, {"id": 5}, {"id": 6}]

序列 2

[{"id": 0}, {"id": 1}, {"id": 2}, {"id": 3}, {"id": 4}, {"id": 5}, {"id": 6}, {"id": 0}, {"id": 1}, {"id": 2}, {"id": 3}, {"id": 4}, {"id": 5}, {"id": 6}]

序列 3

[{"id": 0}, {"id": 1}, {"id": 2}, {"id": 3}, {"id": 4}, {"id": 5}, {"id": 6}, {"id": 0}, {"id": 1}, {"id": 2}, {"id": 3}, {"id": 4}, {"id": 5}, {"id": 6}, {"id": 0}, {"id": 1}, {"id": 2}, {"id": 3}, {"id": 4}, {"id": 5}, {"id": 6}]

这个响应不是预期的输出。预期输出的 JSON 输出数组的长度应为 6。如果我不包装 Python 的数据结构,则不会发生此问题。

为什么会这样?我是一个新的狂热的 Python 用户,但如果它甚至不能处理简单的抽象,这种类型的事情会阻止我使用该语言。

额外

要运行这个:

  • pip install tornado 安装 Tornado 包,
  • 将我提供的代码保存在一个名为app.py的文件中
  • 执行python app.py
  • 在您的浏览器中打开 Web 应用程序以获取 http://127.0.0.1/client

【问题讨论】:

    标签: python arrays tornado python-internals


    【解决方案1】:

    问题是因为Array._data 实际上是Array 的静态成员,这意味着它的值在Array 的所有实例中都是相同的。

    class Array():
        _data = []
        def push(self, value):
            self._data.append(value)
    
        def json(self):
            return json.dumps(self._data)
    

    要解决问题,请将_data 设为实例成员。

    class Array():
        def __init__(self):
            self._data = []
    
        def push(self, value):
            self._data.append(value)
    
        def json(self):
            return json.dumps(self._data)
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2015-09-11
      • 2015-07-29
      • 1970-01-01
      • 1970-01-01
      • 2016-10-19
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多