【问题标题】:python `with .. as ..` statement and multiple return valuespython `with .. as ..` 语句和多个返回值
【发布时间】:2014-10-11 09:32:41
【问题描述】:

我正在尝试使用 python with-statement(又名上下文管理器)来确保由server_socket.accept() 创建的 TCP 连接套接字始终关闭。然而,显而易见的形式不起作用,因为accept() 返回多个值。

有没有办法为具有多个返回值的函数使用 with 语句?

下面是一个最小的示例,我想使用注释代码之类的代码来替换 try/finally 块。

#!/usr/bin/env python3

import socket
from socket import socket as Socket

with Socket(socket.AF_INET, socket.SOCK_STREAM) as server_socket:

        server_socket.bind(('', 8011))
        server_socket.listen(1)
        print("server ready")

        while True:

            # with server_socket.accept() as (connection_socket, _):
            #     request = connection_socket.recv(1024).decode('ascii')
            #     reply = request.upper()
            #     connection_socket.send(reply.encode('ascii'))

            try:
                connection_socket, _ = server_socket.accept()
                request = connection_socket.recv(1024).decode('ascii')
                reply = request.upper()
                connection_socket.send(reply.encode('ascii'))

            finally:
                connection_socket.close()

使用带注释的with语句时的错误信息是:

Traceback (most recent call last):
  File "./test.py", line 26, in <module>
    with server_socket.accept() as (connection_socket, _):
AttributeError: __exit__

这可能是因为元组没有with 所需的__exit__ 属性。

【问题讨论】:

    标签: python sockets with-statement contextmanager


    【解决方案1】:

    socket.socket 的返回值有一个实现__exit____enter__ 的内置上下文管理器。 accept 返回的元组没有,但您可以从元组中拆分出客户端套接字和地址,并在客户端套接字上单独使用 with

    import socket
    
    with socket.socket() as s:
        s.bind(('',8000))
        s.listen(1)
        c,a = s.accept(s)
        with c:
            while True:
                data = c.recv(1024)
                if not data: break
                c.sendall(data)
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2015-09-11
      • 1970-01-01
      • 1970-01-01
      • 2011-02-13
      • 1970-01-01
      • 2012-04-02
      • 1970-01-01
      相关资源
      最近更新 更多