day09-网络编程入门

Day09 网络编程入门

  1. 内容回顾
    # 多继承 :一个类有多个父亲
    # 查找变量遵循mro算法
    # super :查找mro算法中的下一个类
    # 多态 : 在python中处处是多态
    # 封装 : 属性和方法的私有化 : 只能在类的内部调用
    # # 不能继承也不能在类的外部使用
    # # A.__私有变量
    # 静态方法\类方法\属性方法 *****
    # 类方法 classmethod *****
    # 默认接收cls参数,表示当前所在的类
    # 调用的时候 类名\对象名都可以调用
    # class Student:
    # course = [‘python’,‘linux’]
    # def init(self,name):
    # self.name = name
    # @classmethod
    # def show_courses(cls):
    # # 在这个方法中没有用到对象空间中存储的内容
    # print(‘可选择的课程有:’,cls.course)
    # Student.show_courses()
    # alex = Student(‘alex’)
    # alex.show_courses()

        # 静态方法  ****
    # class Student:
    #     course = ['python','linux']
    #     @staticmethod
    #     def quit():
    #         exit()
    # obj = Student()
    # Student.quit()
    # obj.quit()
        # 属性方法  ***
            # 圆形面积 周长 年龄
    # class House:
    #     def __init__(self,length,width):
    #         self.len = length
    #         self.wid = width
    #     @property
    #     def area(self):
    #         return self.wid *self.len
    #
    # house = House(10,10)
    # print(house.area)
    
    # 反射       *****
        # 通过字符串使用变量(包括 类 函数 方法 各种变量)
    # class Manager:
    #     pass
    # import sys
    # Man= getattr(sys.modules[__name__],'Manager')
    # print(Man is Manager)
    
    # def login():pass
    # def register():pass
    # import sys
    # func1= getattr(sys.modules[__name__],'login')
    # func2= getattr(sys.modules[__name__],'register')
    # print(func1,func2)
    
    # 模块的导入 *****
    # import 模块名    # 模块名以小写开头 符合变量的命名规范
    # 模块名.变量名
    
    # from 模块名 import 变量名,函数名
    # from 模块名 import 变量名 as 新名字,函数名
    # from 模块名 import *
    # 直接使用变量名就可以了
    
    # 包的导入
    # import 包.包.包.模块名 as 新名字
        # 新名字.变量名
    # from 包.包.包 import 模块名
        # 模块名.变量名
    
    # sys.path 模块导入是从path列表中找到路径,从路径下导入模块
        # 如果我们要导入的模块在path的路径下都没找到,那么就会报错
    
    # 开发规范   *****
        # 后来拆了文件
            # 重新写入一遍数据
            # 读数据
    # from 项目名称.core import student
    # stu = student.Student()
    
    # 日志模块   *****
    # logging模块
    # import logging
    # from logging import handlers
    # handlers.RotatingFileHandler
    # handlers.TimedRotatingFileHandler
    # sh = logging.StreamHandler()
    # fn = logging.FileHandler(filename='xxx.log',encoding='utf-8')
    # logging.basicConfig(
    #     format= '',
    #     datefmt= '',
    #     level=logging.INFO,
    #     handlers=[sh,fn]
    # )
    
  2. 今日内容
    # 网络编程
    # 网络通信
    # 内置模块
    # hashlib模块
    # 并发编程
    # 同时服务多个用户

  3. 网络编程
    # C/S架构的 :qq 微信 钉钉 ftp 网盘
    # c:client
    # s:server
    # B/S架构 :百度 豆瓣 知乎
    # 对于客户端的依赖性比较小
    # 只要有一个浏览器有网 就能使用了
    # b:browser
    # s:server
    # B/S架构和C/S架构 : B/S架构是特殊的C/S架构
    # C/S架构 : 安全性 历史数据的保存
    # B/S架构 : 轻量级
    # pc端趋势 : B/S统一了入口
    # 移动端 : 微信小程序\支付宝支付平台垄断

    # ipv4协议 0.0.0.0-255.255.255.255
    # 192.168.11.22
    # 172.16.00.00
    # 10.0.1.1
    
    # ip地址能够帮助我们找到网络上唯一一台机器
    # port能够帮助我们确认一台机器上的唯一一个服务
    
    # 127.0.0.1 特殊的ip地址 本地回环地址
        # 本机中排除网络因素 进行代码的功能性测试
    # socket 套接字
    
  4. socket初识
    server
    # server
    import socket

    sk = socket.socket(family=socket.AF_INET, type=socket.SOCK_STREAM)   # 买手机
    # family = socket.AF_INET 当前基于网络通信的
    # type = socket.SOCK_STREAM 默认是tcp协议
    sk.bind(('192.168.36.202',9000))    # 装上电话卡	# 类名+()实例化过程
    sk.listen()                     # 开机
    while True:
        conn,addr = sk.accept() # 等电话,等待客户端来链接我
            # conn 就是server和客户端建立起来的一个连接
        while  True:
            msg_send = input('>>>')
            conn.send(msg_send.encode('utf-8')) # 接了电话并说了一句hello
            if msg_send.upper() == 'Q': break
            msg = conn.recv(1024).decode('utf-8')
            if msg.upper() == 'Q': break
            print(msg)
        conn.close()         # 挂电话
        break
    sk.close()           # 关手机
    
    # 无论在server 还是 client 只要输入q 就两边断开连接 - 挂电话
    

    Client
    # client
    import socket

    sk = socket.socket()  # 买手机
    
    sk.connect(('192.168.36.202',9000))
    while True:
        msg = sk.recv(1024).decode('utf-8')        # 字节 阻塞直到有数据发送过来
        if msg.upper() == 'Q': break
        print(msg) # 字节转字符串 decode
        msg_send = input('>>>')    # input写入的是字符串
        sk.send(msg_send.encode('utf-8')) # 发送的是字节,字符串转字节 encode
        if msg_send.upper() == 'Q': break
    sk.close()
    
  5. 网络通信协议
    # 实时通信 :占用连接 TCP协议
    # 打电话
    # qq电话 视频 远程协助
    # 微信电话 微信视频
    # 视频的上传 下载
    # 延时消息 :不占连接 UDP协议
    # 短信 彩信
    # qq 消息
    # 微信信息

    # 实时通信的:
        # 网络要求高
        # 打电话的时候 占用连接
        # 必须要提前建立连接
            # 两个人必须同时在线
    
    # TCP 保证数据传递的可靠性 占用连接 效率低
        # 先建立连接 : 三次握手
        # 开始通信 : 发邮件\文件的上传下载\qq文件微信文件\远程连接
        # 断开连接 : 四次挥手
    # UDP 不占连接 不可靠性
        # 不需要建立连接
        # 直接互相传就可以了
    
  6. socket初识
    server
    import socket

    sk = socket.socket(type=socket.SOCK_DGRAM)
    sk.bind(('127.0.0.1',8001))
    while True:
        msg,addr = sk.recvfrom(1024)
        print(msg.decode('utf-8'))
        send_msg = input('>>>')
        sk.sendto(send_msg.encode('utf-8'),addr)
    sk.close()
    

    client
    import socket

    sk = socket.socket(type=socket.SOCK_DGRAM)
    while True:
        send_msg = input('>>>')
        sk.sendto(send_msg.encode('utf-8'),('127.0.0.1',8001))
        msg,addr = sk.recvfrom(1024)
        print(msg.decode('utf-8'))
    sk.close()
    
  7. 飞秋测试
    # 内网的通信工具
    # 发送消息
    # 共享文件
    # 客户端
    # import socket
    # sk = socket.socket(type=socket.SOCK_DGRAM)
    # for i in range(1,255):
    # try:
    # sk.sendto(b’1:111:eva:eva:32:wahaha’,(‘192.168.36.%s’%(i),2425))
    # except:
    # pass

  8. Socket tcp协议的问题
    # server
    import socket
    sk = socket.socket()
    # sk.bind((‘127.0.0.1’,0-65535))
    sk.bind((‘127.0.0.1’,9002))
    sk.listen()

    conn,addr = sk.accept()
    msg = b'helloal7864862391862963496'  # 26helloal7864862391862963496
    print(len(msg))  # 26
    conn.send('0026')
    conn.send(msg)
    conn.send(b'5')
    conn.send(b'world')
    conn.close()
    sk.close()
    
    # 数据一旦黏在一起就会产生数据错误
    # 怎么解决?
    
    # client
    import time
    import socket
    sk = socket.socket()
    
    
    
    sk.connect(('127.0.0.1',9002))
    for i in range(100000):i*2
    msg1 = sk.recv(4)  # 2
    print(msg1)
    num = int(msg1.decode('utf-8'))
    msg = sk.recv(num)
    print(msg)
    msg1 = sk.recv(1)
    num = int(msg1.decode('utf-8'))
    msg = sk.recv(num)
    print(msg)
    sk.close()
    
  9. 解决tcp协议粘包问题
    # server
    import socket
    import struct

    def my_send(conn,msg):
        msgb = msg.encode('utf-8')
        len_msg = len(msgb)
        pack_len = struct.pack('i', len_msg)
        conn.send(pack_len)
        conn.send(msgb)
    
    sk = socket.socket()
    # sk.bind(('127.0.0.1',0-65535))
    sk.bind(('127.0.0.1',9002))
    sk.listen()
    
    conn,addr = sk.accept()
    msg1 = '你好'
    msg2 = '吃了么'
    my_send(conn,msg1)
    my_send(conn,msg2)
    conn.close()
    sk.close()
    
    # 数据一旦黏在一起就会产生数据错误
    # 怎么解决?
    
    import time
    import socket
    import struct
    sk = socket.socket()
    
    def my_recv(sk):
        pack_len = sk.recv(4)
        len_msg = struct.unpack('i', pack_len)[0]
        msg = sk.recv(len_msg).decode('utf-8')
        return msg
    
    sk.connect(('127.0.0.1',9002))
    for i in range(100000):i*2
    msg = my_recv(sk)
    print(msg)
    msg = my_recv(sk)
    print(msg)
    sk.close()
    
  10. 文件传输的例子
    # server
    # 接收文件
    import json
    import socket
    sk = socket.socket()
    sk.bind((‘127.0.0.1’,9001))
    sk.listen()

    conn,addr = sk.accept()
    file_dic = conn.recv(1024).decode('utf-8')
    dic = json.loads(file_dic)
    
    with open(dic['filename'],mode='wb') as f:
        while dic['filesize']>0:
            file_content = conn.recv(1024)
            dic['filesize'] -= len(file_content)
            f.write(file_content)
    conn.close()
    sk.close()
    
    # client
    import os
    import json
    import socket
    
    sk = socket.socket()
    sk.connect(('127.0.0.1',9001))
    # 输入需要发送的文件,获取并发送文件大小
    file_path = r'D:\ev录屏保存的视频\20190719_150518.mp4'
    file_name = os.path.basename(file_path)
    file_size = os.path.getsize(file_path)
    dic = {'filename':file_name,'filesize':file_size}
    str_dic = json.dumps(dic)
    dic_b = str_dic.encode('utf-8')
    sk.send(dic_b)
    with open(file_path,mode = 'rb') as f:
        content = f.read()
        sk.send(content)
    sk.close()
    

    装饰器
    def classmethod(func):
    def inner(*args,**kwargs):
    func(‘类’)
    return inner

    def staticmethod(func):
        def inner(*args,**kwargs):
            func()
        return inner
    
    @staticmethod
    def wahaha():
        print('in 娃哈哈')
    
    @classmethod
    def qqxing(cls):
        print('in qqxing',cls)
    
    wahaha()
    qqxing()
    
    
    import sys
    def processBar(num, total):
        rate = num / total
        rate_num = int(rate * 100)
        if rate_num == 100:
            r = '\r%s>%d%%\n' % ('=' * rate_num, rate_num,)
        else:
            r = '\r%s>%d%%' % ('=' * rate_num, rate_num,)
        sys.stdout.write(r)
        sys.stdout.flush
    
    processBar(100246000,112132327)
    

    思考题
    # 文件
    # 通过网络发送给你
    # 1.小文件?
    # 2.大文件?
    # 3.视频/图片怎么做?

  11. hashlib模块
    import hashlib
    # 密码不能明文存储
    # 获取到整个用户登录信息文件了所有的密码都泄露了
    # md5 = hashlib.md5(‘只有我知道,别人不知道的秘密的字符串%s’%‘alex’.encode(‘utf-8’))
    # md5.update(b’123456’)
    # ret = md5.hexdigest()
    # print(ret)

    # e10adc3949ba59abbe56e057f20f883e     32位
    # '123456'这个字符串通过md5这个算法加密之后的结果
    
    # afdc71bd7bc87c2c0205421d9e2b5359
    # ('123456'这个字符串通过md5这个算法+特有的字符串)加密之后的结果
    
    
    # md5 = hashlib.sha1()
    # md5.update(b'123456')
    # ret = md5.hexdigest()
    # print(ret)
    # 7c4a8d09ca3762af61e59520943dc26494f8941b  40位
    # '123456'这个字符串通过sha1这个算法加密之后的结果
    
    
    # 对比两个文件是否一致
    # import hashlib
    # md5 = hashlib.md5()
    # md5.update('你好你好你好再见'.encode('utf-8'))
    # ret = md5.hexdigest()
    # print(ret)
    
    # 7c5368a646b1d58cecf51dc99a8ec53c
    # 7c5368a646b1d58cecf51dc99a8ec53c
    # import hashlib
    # md5 = hashlib.md5()
    # md5.update('你好你好'.encode('utf-8'))
    # md5.update('你'.encode('utf-8'))
    # md5.update('好'.encode('utf-8'))
    # md5.update('再见'.encode('utf-8'))
    # ret = md5.hexdigest()
    # print(ret)
    
    import hashlib
    def get_md5(file):
        md5 = hashlib.md5()
        with open(file,'rb') as f:
            content = f.read()
            md5.update(content)
        ret = md5.hexdigest()
        return ret
    ret = get_md5(r'F:\python自动化27期\day9\5.网络通信协议.py') == get_md5(r'F:\python自动化27期\day9\5.网络通信协议2.py')
    print(ret)
    # b2ee53ee6c0ba5ba3af512d588901570
    # 2e60d69c94d355b82990abc408dc3f39
    
  12. socketserver模块
    # 并发
    import socketserver

    class Myserver(socketserver.BaseRequestHandler):
        def handle(self):
            conn = self.request
            while True:
                conn.send(b'hello')
    server = socketserver.ThreadingTCPServer(('127.0.0.1',9001),Myserver)
    server.serve_forever()
    
  13. client
    import socket
    sk = socket.socket()
    sk.connect((‘127.0.0.1’,9001))
    while True:
    ret = sk.recv(1024)
    print(ret)
    sk.close()
    作业:https://www.cnblogs.com/Eva-J/articles/7642557.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值