用Python进行客户端服务器编程? [英] Client Server programming in python?

查看:475
本文介绍了用Python进行客户端服务器编程?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

这里是python中多服务器和客户端的源代码.

Here is source code for multithreaed server and client in python.

在代码中,客户端和服务器在作业完成后关闭连接. 我想保持连接状态,并通过相同的连接发送更多数据,以避免每次关闭和打开套接字的开销.

In the code client and server closes connection after the job is finished. I want to keep the connections alive and send more data over the same connections to avoid overhead of closing and opening sockets every time.

以下代码来自: http://www.devshed.com/c/a/Python/Basic-Threading-in-Python/1/

import pickle
import socket
import threading

# We'll pickle a list of numbers:
someList = [ 1, 2, 7, 9, 0 ]
pickledList = pickle.dumps ( someList )

# Our thread class:
class ClientThread ( threading.Thread ):

   # Override Thread's __init__ method to accept the parameters needed:
   def __init__ ( self, channel, details ):

      self.channel = channel
      self.details = details
      threading.Thread.__init__ ( self )

   def run ( self ):

      print 'Received connection:', self.details [ 0 ]
      self.channel.send ( pickledList )
      for x in xrange ( 10 ):
         print self.channel.recv ( 1024 )
      self.channel.close()
      print 'Closed connection:', self.details [ 0 ]

# Set up the server:
server = socket.socket ( socket.AF_INET, socket.SOCK_STREAM )
server.bind ( ( '', 2727 ) )
server.listen ( 5 )

# Have the server serve "forever":
while True:
   channel, details = server.accept()
   ClientThread ( channel, details ).start()


import pickle
import socket
import threading

# Here's our thread:
class ConnectionThread ( threading.Thread ):

   def run ( self ):

      # Connect to the server:
      client = socket.socket ( socket.AF_INET, socket.SOCK_STREAM )
      client.connect ( ( 'localhost', 2727 ) )

      # Retrieve and unpickle the list object:
      print pickle.loads ( client.recv ( 1024 ) )

      # Send some messages:
      for x in xrange ( 10 ):
         client.send ( 'Hey. ' + str ( x ) + '\n' )

      # Close the connection
      client.close()

# Let's spawn a few threads:
for x in xrange ( 5 ):
   ConnectionThread().start()

推荐答案

为每个连接生成新线程是确实很糟糕的设计选择. 如果您受到很多联系的打击会怎样?

Spawning a new thread for every connection is a really bad design choice. What happens if you get hit by a lot of connections?

实际上,使用线程等待网络IO是不值得的.您的程序变得非常复杂,您绝对不会获得任何好处,因为在线程中等待网络不会使您等待更快.在这种情况下,您只会因使用线程而失败.

In fact, using threads to wait for network IO is not worth it. Your program gets really complex and you get absolutely no benefit since waiting for network in threads won't make you wait faster. You only lose by using threads in this case.

以下文字来自python文档:

The following text is from python documentation:

只有两种方法可以 单个处理器上的程序可以做到更多" 一次只能做一件事." 多线程编程是 最简单,最受欢迎的方法 它,但是还有另一个 不同的技术,可以让您 具有几乎所有的优点 多线程,实际上没有 使用多个线程.是真的 仅在您的程序为 很大程度上受I/O约束.如果您的程序是 处理器绑定,然后抢先 预定线程可能是什么 您真正需要的.网络服务器是 但是,很少受处理器的约束.

There are only two ways to have a program on a single processor do "more than one thing at a time." Multi-threaded programming is the simplest and most popular way to do it, but there is another very different technique, that lets you have nearly all the advantages of multi-threading, without actually using multiple threads. It’s really only practical if your program is largely I/O bound. If your program is processor bound, then pre-emptive scheduled threads are probably what you really need. Network servers are rarely processor bound, however.

如果是处理器绑定的服务器机箱.您总是可以留下另一个进程/线程来做处理器部分.继续:

And if it is a processor bound server case. you could always leave another process/thread to do the processor part. Continuing:

如果您的操作系统支持 在其I/O库中选择系统调用 (几乎所有的操作都可以),那么您可以使用 玩弄多种沟通 立刻建立频道;做其他工作 当您的I/O发生在 背景."虽然这个策略 看起来很奇怪和复杂, 特别是在一开始 更容易理解和控制的方式 而不是多线程编程.

If your operating system supports the select system call in its I/O library (and nearly all do), then you can use it to juggle multiple communication channels at once; doing other work while your I/O is taking place in the "background." Although this strategy can seem strange and complex, especially at first, it is in many ways easier to understand and control than multi-threaded programming.

因此,不要使用线程,而要使用非阻塞输入/输出:将套接字收集在列表中,并使用带有

So instead of using threads, use non-blocking input/output: collect the sockets in a list and use an event loop with select.select to know which socket has data to read. Do that in a single thread.

您可以选择像 twisted 这样的python异步网络框架来为您执行此操作.这将为您省去很多麻烦. Twisted的代码已经改进了很多年,涵盖了一些您将需要花费一些时间来掌握的极端情况.

You could choose a python asynchronous networking framework like twisted to do that for you. That will save you a lot of headaches. Twisted's code has been improved for years, and covers some corner cases you'll take time to master.

编辑:任何现有的异步IO库(例如Twisted)都是python代码.您可以自己编写它,但是已经为您编写了.我不明白为什么您不使用这些库之一,而是编写自己的最糟糕的代码,因为您是初学者.难以置信的IO很难做到.

EDIT: Any existing async IO libraries (like Twisted) are python code. You could have written it yourself, but it has already been written for you. I don't see why you wouldn't use one of those libraries and write your own worst code instead, since you are a beginner. Networing IO is hard to get right.

这篇关于用Python进行客户端服务器编程?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆