转自:http://blog.csdn.net/chuanchuan608/article/details/17915959

目前正在学习python,使用的工具为python3.2.3。发现3x版本和2x版本有些差异,在套接字编程时,困扰了我很久,先将python核心编程书中的例子

代码如下:

服务器端:

    # Echo server program
from socket import *
from time import ctime HOST = '' # Symbolic name meaning all available interfaces
PORT = 50007 # Arbitrary non-privileged port
BUFSIZE = 1024
ADDR = (HOST, PORT) tcpSerSock = socket(AF_INET, SOCK_STREAM)
tcpSerSock.bind(ADDR)
tcpSerSock.listen(5) while True:
print('waiting for connection...')
tcpCliSock, addr = tcpSerSock.accept()
print('...connected from:', addr) while True:
data = tcpCliSock.recv(BUFSIZE)
if not data:
break
tcpCliSock.send(('[%s] %s' % (ctime(), data))) tcpCliSock.close()
tcpSerSock.close()

客户端

    # Echo client program
from socket import* HOST = '127.0.0.1'
PORT = 50007 # The same port as used by the server
BUFSIZE = 1024
ADDR = (HOST, PORT) tcpCliSock = socket(AF_INET, SOCK_STREAM)
tcpCliSock.connect(ADDR)
while True:
data = input('> ')
if not data:
break
tcpCliSock.send(data)
data = tcpCliSock.recv(BUFSIZE)
if not data:
break
print(data) tcpCliSock.close()

报错:

TypeError:'str' does not support the buffer interface

找问题找了好久,在StackOverflow上发现有人也出现同样的问题,并一个叫Scharron的人提出了解答:

In python 3, bytes strings and unicodestrings are now two different types. Since sockets are not aware of string encodings, they are using raw bytes strings, that have a slightly differentinterface from unicode strings.

So, now, whenever you have a unicode stringthat you need to use as a byte string, you need toencode() it. And whenyou have a byte string, you need to decode it to use it as a regular(python 2.x) string.

Unicode strings are quotes enclosedstrings. Bytes strings are b"" enclosed strings

When you use client_socket.send(data),replace it by client_socket.send(data.encode()). When you get datausing data = client_socket.recv(512), replace it by data =client_socket.recv(512).decode()

同时我看了一下python帮助文档:

Codec.encode(input[, errors])

Encodes the object input and returns atuple (output object, length consumed). Encoding converts a string object to abytes object using a particular character set encoding

Codec.decode(input[, errors])

Decodes the object input and returns atuple (output object, length consumed). Decoding converts a bytes objectencoded using a particular character set encoding to a string object.

input must be a bytes object or one whichprovides the read-only character buffer interface – for example, buffer objectsand memory mapped files.

套接字的成员函数send

socket.send(bytes[, flags]) 形参为字节类型

socket.recv(bufsize[, flags]) Receive datafrom the socket. The return value is abytes object representing the data received.

所以修正后代码如下:

服务器端:

   # Echo server program
from socket import *
from time import ctime HOST = '' # Symbolic name meaning all available interfaces
PORT = 50007 # Arbitrary non-privileged port
BUFSIZE = 1024
ADDR = (HOST, PORT) tcpSerSock = socket(AF_INET, SOCK_STREAM)
tcpSerSock.bind(ADDR)
tcpSerSock.listen(5) while True:
print('waiting for connection...')
tcpCliSock, addr = tcpSerSock.accept()
print('...connected from:', addr) while True:
data = tcpCliSock.recv(BUFSIZE).decode()
if not data:
break
tcpCliSock.send(('[%s] %s' % (ctime(), data)).encode()) tcpCliSock.close()
tcpSerSock.close()

客服端:

# Echo client program
from socket import* HOST = '127.0.0.1'
PORT = 50007 # The same port as used by the server
BUFSIZE = 1024
ADDR = (HOST, PORT) tcpCliSock = socket(AF_INET, SOCK_STREAM)
tcpCliSock.connect(ADDR)
while True:
data = input('> ')
if not data:
break
tcpCliSock.send(data.encode())
data = tcpCliSock.recv(BUFSIZE).decode()
if not data:
break
print(data) tcpCliSock.close()

运行结果: 达到预期

在使用这些函数时想当然去用,没有去查找帮助文档,没有弄清楚传参类型,可能是一个例题,没有注意这些,但是得吸取教训。

同样的在udp的情况下:修正过的

服务器端:

    from socket import *
from time import ctime HOST = '';
PORT = 21546
BUFSIZE = 1024
ADDR = (HOST, PORT) udpSerSock = socket(AF_INET, SOCK_DGRAM)
udpSerSock.bind(ADDR) while True:
print('waiting for message...')
data, addr = udpSerSock.recvfrom(BUFSIZE)
udpSerSock.sendto(('[%s] %s' %(ctime(), data.decode())).encode(), addr)
print('...received from and returned to:', addr) udpSerSock.close()

客户端:

    from socket import *  

    HOST = 'localhost'
PORT = 21567
BUFSIZE = 1024
ADDR = (HOST, PORT) while True:
tcpCliSock = socket(AF_INET, SOCK_STREAM)
tcpCliSock.connect(ADDR)
data = input('> ')
if not data:
break
tcpCliSock.send(('%s\r\n' % data).encode())
data = tcpCliSock.recv(BUFSIZE).decode()
if not data:
break
print(data.strip())
tcpCliSock.close()

使用socketserver模块:

服务器端:

    #TsTservss.py
from socketserver import TCPServer as TCP, StreamRequestHandler as SRH
from time import ctime HOST = ''
PORT = 21567
ADDR = (HOST, PORT) class MyRequestHandler(SRH):
def handle(self):
print('...connected from:', self.client_address)
self.wfile.write(('[%s] %s' %(ctime(), self.rfile.readline().decode())).encode()) tcpServ = TCP(ADDR, MyRequestHandler)
print('waiting for connection...')
tcpServ.serve_forever()

客户端:

    from socket import *  

    HOST = 'localhost'
PORT = 21567
BUFSIZE = 1024
ADDR = (HOST, PORT) while True:
tcpCliSock = socket(AF_INET, SOCK_STREAM)
tcpCliSock.connect(ADDR)
data = input('> ')
if not data:
break
tcpCliSock.send(('%s\r\n' % data).encode())
data = tcpCliSock.recv(BUFSIZE).decode()
if not data:
break
print(data.strip())
tcpCliSock.close()

Python 3中套接字编程中遇到TypeError: 'str' does not support the buffer interface的解决办法的更多相关文章

  1. python3使用套接字遇到TypeError: 'str' does not support the buffer interface如何解决

    这是我查看的博客 http://blog.csdn.net/chuanchuan608/article/details/17915959 直接引用里面的关键语句: When you use clien ...

  2. python——TypeError: 'str' does not support the buffer interface

    import socket import sys port=51423 host="localhost" data=b"x"*10485760 #在字符串前加 ...

  3. python编写telnet登陆出现TypeError:'str' does not support the buffer interface

    python3支持byte类型,python2不支持.在python3中,telnet客户端向远程服务器发送的str要转化成byte,从服务器传过来的byte要转换成str,但是在python2不清楚 ...

  4. python3 TypeError: 'str' does not support the buffer interface in python

    http://stackoverflow.com/questions/38714936/typeerror-str-does-not-support-the-buffer-interface-in-p ...

  5. Linux 套接字编程中的 5 个隐患(转)

    本文转自IBM博文Linux 套接字编程中的 5 个隐患. “在异构环境中开发可靠的网络应用程序”. Socket API 是网络应用程序开发中实际应用的标准 API.尽管该 API 简单,但是开发新 ...

  6. (转载)Linux 套接字编程中的 5 个隐患

    在 4.2 BSD UNIX® 操作系统中首次引入,Sockets API 现在是任何操作系统的标准特性.事实上,很难找到一种不支持 Sockets API 的现代语言.该 API 相当简单,但新的开 ...

  7. Linux 套接字编程中的 5 个隐患

    http://www.ibm.com/developerworks/cn/linux/l-sockpit/ 在 4.2 BSD UNIX® 操作系统中首次引入,Sockets API 现在是任何操作系 ...

  8. Linux 套接字编程中要注意的细节

    隐患 1.忽略返回状态 第一个隐患很明显,但它是开发新手最容易犯的一个错误.如果您忽略函数的返回状态,当它们失败或部分成功的时候,您也许会迷失.反过来,这可能传播错误,使定位问题的源头变得困难. 捕获 ...

  9. python TCP socket套接字编程以及注意事项

    TCPServer.py #coding:utf-8 import socket #s 等待链接 #c 实时通讯 s = socket.socket(socket.AF_INET,socket.SOC ...

随机推荐

  1. Kerberos验证过程

    参考文献: How the Kerberos Version 5 Authentication Protocol Works: Logon and Authentication SQL Kerbero ...

  2. Btrace

    http://www.iteye.com/topic/1005918 背景 周五下班回家,在公司班车上觉得无聊,看了下btrace的源码(自己反编译). 一些关于btrace的基本内容,可以看下我早起 ...

  3. /dev/tty 与 /dev/pts

     打开3个bash会话窗口  [root@server1 fd]# cd /proc/7489/fd[root@server1 fd]# ll总用量 0lrwx------ 1 root root 6 ...

  4. PureMVC(JS版)源码解析(十一):Model类

          这篇博文讲PureMVC三个核心类——Model类.Model类的构造函数及工厂函数[即getInstance()方法]和View类.Controller类是一样的,这里就不重复讲解了,只 ...

  5. cookie 和 HttpSession

    保存会话数据的两种技术 Cookie Cookie 是客户端技术,程序把每个用户的数据以cookie的形式写给用户的浏览器.当用户使用浏览器再去访问服务器中的web资源时,就会带着各自的数据去.web ...

  6. 把QQ聊天记录插入数据库中

    最近在做毕设,其中一个环节是分析qq聊天记录,在分析之前需要先把qq聊天记录导出,然后存入数据库中,qq聊天记录导出后是文本文档,导出方式: 1.登录qq后,点击任意一个好友,查看与他的聊天记录,点击 ...

  7. 对于Maven管理的项目制定虚拟目录

    基于Maven管理的web项目结构: target目录是用来存放项目打包之后生成的文件的目录,此目录中的文件必须调用mvn clean package后才能生成, 如果把虚拟目录设置在此目录中,则每次 ...

  8. 设计模式之Facade模式

    Facade(外观)模式为子系统中的各类(或结构与方法)提供一个简明一致的界面,隐藏子系统的复杂性,使子系统更加容易使用.他是为子系统中的一组接口所提供的一个一致的界面. 在遇到以下情况使用Facad ...

  9. jquery中Live方法不可用,Jquery中Live方法失效

    jquery中Live方法不可用,Jquery中Live方法失效 >>>>>>>>>>>>>>>>> ...

  10. 还原或删除sql server 2008数据库时,经常烩出现: “因为数据库正在使用,所以无法获得对数据库的独占访问权”,终解决方案

    还原或删除sql server 2008数据库时,经常烩出现: “因为数据库正在使用,所以无法获得对数据库的独占访问权”,终解决方案如下 关键SQL语句: ALTER DATABASE [dateba ...