2022年 11月 9日

python核心编程答案(第十六章)

(一)网络提供的服务分两种: 面向连接的服务和无连接的服务. 

对于无连接的服务(邮寄), 发送信息的计算机把数据以一定的格式封装在帧中, 把目的地址和源地址加在信息头上, 然后把帧交给网络进行发送. 无连接服务是不可靠的. 

对于面向连接的服务(电话), 发送信息的源计算机必须首先与接收信息的目的计算机建立连接. 这种连接是通过三次握手(three hand shaking)的方式建立起来的. 一旦连接建立起来, 相互连接的计算机就可以进行数据交换. 与无连接服务不同, 面向连接的服务是以连接标识符来表示源地址和目的地址的. 面向连接的服务是可靠的, 当通信过程中出现问题时, 进行通信的计算机可以得到及时通知.
(二)
略
(三)
TCP
(四)
服务端
  1. __author__ = 'longlong'
  2. from socket import *
  3. from time import ctime
  4. HOST = raw_input('Please input your host:')   #注意主机名不能随便打,我小白。。。发现只有127.XX.XX.XX在本机可以正常使用
  5. PORT = int(raw_input('Please input your port:'))
  6. BUFSIZ = 1024
  7. ADDR = (HOST, PORT)
  8. tcpSerSork = socket(AF_INET, SOCK_STREAM)
  9. tcpSerSork.bind(ADDR)
  10. tcpSerSork.listen(5)
  11. while True:
  12. print ('wait for connection...')
  13. tcpCliSork, addr = tcpSerSork.accept()
  14. print ('... connected from:', addr)
  15. while True:
  16. data = tcpCliSork.recv(BUFSIZ)
  17. if not data:
  18. break
  19. tcpCliSork.send('[%s] %s' % (ctime(), data))
  20. tcpCliSork.close()
  21. tcpSerSork.close()

客户端

  1. __author__ = 'longlong'
  2. from socket import *
  3. HOST = raw_input('Please input your host:') #注意主机名不能随便打,我小白。。。发现只有127.XX.XX.XX在本机可以正常使用
  4. PORT = int(raw_input('Please input your port:'))
  5. ADDR = (HOST, PORT)
  6. BUFSIZE = 1024
  7. tcpCliSock = socket(AF_INET, SOCK_STREAM)
  8. tcpCliSock.connect(ADDR)
  9. while True:
  10. data = raw_input('>')
  11. if not data:
  12. break
  13. tcpCliSock.send(data)
  14. data = tcpCliSock.recv(BUFSIZE)
  15. if not data:
  16. break
  17. print data
  18. tcpCliSock.close()

(五)
服务端:

  1. __author__ = 'longlong'
  2. import socket
  3. HOST = ''
  4. PORT = 23456
  5. ADDR = (HOST, PORT)
  6. s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
  7. s.bind(ADDR)
  8. s.listen(1)
  9. conn, addr = s.accept()
  10. print 'connect by', addr
  11. while True:
  12. data = conn.recv(1024)
  13. print 'by:', data
  14. if not data:
  15. break
  16. conn.close()
  17. s.close()

客户端:
__author__ = 'longlong'
import socket
HOST = 'localhost'
PORT = 23456
ADDR = (HOST, PORT)
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect(ADDR)
while True:
    data = raw_input('Please input your data:')
    s.send(data)
    if not data:
        break
s.close()

进阶:
服务端:
__author__ = 'longlong'
import socket
import time
import os
HOST = ''
PORT = 23445
ADDR = (HOST, PORT)
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.bind(ADDR)
s.listen(1)
conn, addr = s.accept()
print 'connect by', addr
while True:
    data = conn.recv(1024)
    if data == 'data':
        conn.send(time.ctime(time.time()))
        continue
    if data == 'os':
        conn.send(os.name)
        continue
    if data == 'ls':
        path = os.curdir
        conn.send(' '.join(os.listdir(path)))
        continue
    print 'by:', data
    if not data:
        break
conn.close()
s.close()
客户端:
__author__ = 'longlong'
import socket
HOST = 'localhost'
PORT = 23445
ADDR = (HOST, PORT)
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect(ADDR)
while True:
    data = raw_input('Please input your data:')
    if not data:
        break
    s.send(data)
    data = s.recv(1024)
    print data
s.close()
(六)
>>> import socket
>>> socket.getservbyname('daytime', 'udp')
13
(七)
服务端:
__author__ = 'longlong'
import socket

HOST = raw_input('Please a host name:')
PORT = input('Please input a port:')

ADDR = (HOST, PORT)

s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.bind(ADDR)
s.listen(1)
print ('wait for a connect...')
conn, addr = s.accept()
print 'connect from', addr
try:
    while True:
        data = conn.recv(1024)
        print '<', data
        data = raw_input('>')
        conn.send(data)
        if not data:
            break
except:
    print 'welcome use me next!'
    conn.close()
    s.close()
客户端:
__author__ = 'longlong'
import socket
HOST = raw_input('Please input a host name:')
PORT = input('Please input a port:')
ADDR = (HOST, PORT)

s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect(ADDR)
try:
    while True:
        data = raw_input('>')
        if not data:
            break
        s.send(data)
        data = s.recv(1024)
        print '<', data
        if not data:
            break
except:
    print 'welcome use me next!'
    s.close()
(八)(九)(十)
全用多线程写,直接写最高级版本,
实现了各种连接各种聊天,暂时不能私聊。。。
只能群聊
客户端

  1. __author__ = 'longlong'
  2. import socket
  3. import threading
  4. outString = ''
  5. inString = ''
  6. HOST = raw_input('Please input your server\'s ip:')
  7. nick = raw_input('Please input your nick:')
  8. PORT = 9000
  9. ADDR = (HOST, PORT)
  10. s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
  11. s.connect(ADDR)
  12. s.send(nick)
  13. def dealOut(conn):
  14. global outString
  15. while True:
  16. outString = raw_input()
  17. outString = nick+':'+outString
  18. if not outString:
  19. return
  20. conn.send(outString)
  21. def dealIn(conn):
  22. global inString
  23. while True:
  24. inString = conn.recv(1024)
  25. if not inString:
  26. return
  27. if inString != outString:
  28. print inString
  29. threading.Thread(target=dealIn, args=(s, )).start()
  30. threading.Thread(target=dealOut, args=(s, )).start()

服务端:

  1. __author__ = 'longlong'
  2. import socket
  3. import sys
  4. import threading
  5. data = ''
  6. con = threading.Condition()
  7. HOST = raw_input('Please input your host name:')
  8. PORT = 9000
  9. ADDR = (HOST, PORT)
  10. s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
  11. s.bind(ADDR)
  12. s.listen(10)
  13. def clientThreadIn(conn, nick):
  14. global data
  15. while True:
  16. try:
  17. temp = conn.recv(1024)
  18. if temp == nick+':'+'exit':
  19. conn.close()
  20. NotifyAll(temp)
  21. except:
  22. NotifyAll(nick+' leave the room')
  23. s.close()
  24. break
  25. def NotifyAll(temp):
  26. global data
  27. if con.acquire():
  28. data = temp
  29. con.notifyAll()
  30. con.release()
  31. def clientThreadOut(conn, nick):
  32. global data
  33. while True:
  34. if con.acquire():
  35. con.wait()
  36. if data:
  37. try:
  38. conn.send(data)
  39. con.release()
  40. except:
  41. con.release()
  42. return
  43. while True:
  44. conn, addr = s.accept()
  45. nick = conn.recv(1024)
  46. print 'connent with', addr
  47. NotifyAll('welcome join us '+nick)
  48. conn.send(data)
  49. threading.Thread(target=clientThreadIn, args=(conn, nick)).start()
  50. threading.Thread(target=clientThreadOut, args=(conn, nick)).start()

(十一)
明天继续更新