使用 python socket 实现UDP/TCP网络通信_python3 实现udp协议通信 聊天室-程序员宅基地

技术标签: udp  python  网络  python 后端  工具  socket  理论知识  网络协议  

目录

目录

1.socket简介

2.创建socket

2.1创建UDPSocket

2.2创建TCPSocket

3.使用UDPSocket发送数据并接收

4.使用UDPSocket发送广播

5.UDPSocket聊天器 (多线程实现消息的收发功能)

6.使用TCPSocket建立客户端

7.使用TCPSocket建立服务端


1.socket简介

       socket(简称:套接字),是支持TCP和UDP(网络传输方式)网络通信的基本操作单元,可以看做是不同主机之间的进程进行双向通信的端点,简单的说就是通信的两方的一种约定,用套接字中的相关函数来完成通信过程。

        它能实现不同主机间的进程间通信,我们网络上各种各样的服务大多都是基于socket来完成通信的,例如浏览的网页、qq聊天、收发email等等。

2.创建socket

        socket起源于Unix,而Unix/Linux基本哲学之一就是“一切皆文件”,对于文件用打开、读写、关闭模式来操作。socket就是该模式的一个实现,socket即是一种特殊的文件,一些socket类就是对其进行的操作(读写IO、打开、关闭)

在Python中使用socket模块的socket类来完成:

import socket
socket.socket(AddressFamily, Type)

说明:

        1. 参数:AddressFamily(地址簇)

        socket.AF_INET IPv4          (默认)       

        socket.AF_INET6 IPv6

        socket.AF_UNIX                    只能够用于单一的Unix系统进程通信

        2.参数:Type(类型)

        socket.SOCK_STREAM        流式socket,for TCP(默认)

        socket.SOCK_DGRAM         数据报式socket,for UDP

2.1创建UDPSocket

import socket


# 使用IPv4 UDP方式来创建套接字
udp_socket = socket.socket(socket.AF_INET,socket.SOCK_DGRAM)  # 参数socket.AF_INET表示使用IPv4,参数socket.SOCK_DGRAM表示使用UDP

# 省略数据传递过程

# 关闭套接字
udp_socket.close()

2.2创建TCPSocket

import socket


# 使用IPv4 TCP方式来创建套接字
tcp_socket = socket.socket(socket.AF_INET,socket.SOCK_STREAM)  # 参数socket.AF_INET表示使用IPv4,参数socket.SOCK_STREAM表示使用TCP

# 省略数据传递过程

# 关闭套接字
tcp_socket.close()

3.使用UDPSocket发送数据并接收

核心方法:

        socket.sendto

sendto方法的参数:

        1.要发送的二进制数据        (使用.encode()方法可以将字符串转为二进制)

        2.接收者的ip地址和端口号  (元组类型:("127.0.0.1", 8080))

import socket


# 使用IPv4 UDP方式来创建套接字
udp_socket = socket.socket(socket.AF_INET,socket.SOCK_DGRAM)

#2.绑定一个本地信息
localaddr = ("192.168.68.196",8081)
udp_socket.bind(localaddr)

# 发送数据
udp_socket.sendto("hello".encode(),("192.168.68.196",8080))

# 关闭套接字
udp_socket.close()

接收数据(两种方式):

        方式一:通过网络调试助手接收(下载地址:NetAssist.exe下载

对于接收到的中文是乱码的问题:

        可能是由于encode()方法默认使用UTF-8的编码方式

.encode()

 将其改为gb2312编码方式:

.encode("gb2312")

如下图标注部分为修改编码方式前后的对比: 

        方式二:通过python代码制作一个接收端

import socket

def main():
    #1.创建套接字
    udp_socket = socket.socket(socket.AF_INET,socket.SOCK_DGRAM)

    #2.绑定一个本地信息
    localaddr = ("192.168.68.196",8080)
    udp_socket.bind(localaddr)

    #3.接收数据
    while True:
        recv_data = udp_socket.recvfrom(1024) #1024表示每次接收1024字节
        recv_msg = recv_data[0] #存储接收到的数据
        send_addr = recv_data[1]#存储发送方的地址信息

    #4.打印接收到的数据
    # print(recv_data)
        print("%s:%s" % (str(send_addr),recv_msg.decode("gb2312")) )

    #5.关闭套接字
    udp_socket.close()

if __name__ == "__main__":
    main()

4.使用UDPSocket发送广播

        广播地址(Broadcast Address)是专门用于同时向网络中所有工作站进行发送的一个地址。在使用TCP/IP 协议的网络中,主机标识段host ID 为全1 的IP 地址为广播地址,广播的分组传送给host ID段所涉及的所有计算机。例如,对于10.1.1.0 (255.0.0.0 )网段,其广播地址为10.255.255.255 (255 即为二进制的11111111 ),当发出一个目的地址为10.255.255.255 的分组(封包)时,它将被分发给该网段上的所有计算机。

import socket


# 使用IPv4 UDP方式来创建套接字
udp_socket = socket.socket(socket.AF_INET,socket.SOCK_DGRAM)

#2.绑定一个本地信息
localaddr = ("192.168.68.196",8081)
udp_socket.bind(localaddr)

# 设置允许发送广播
udp_socket.setsockopt(socket.SOL_SOCKET, socket.SO_BROADCAST, True)

# 发送信息
udp_socket.sendto("大家好,我宣布个事儿".encode("gb2312"), ("255.255.255.255", 8080))

# 关闭套接字
udp_socket.close()

运行结果:(此时处于同一网段,端口为8080的客户端应该都能接收到广播信息)

5.UDPSocket聊天器 (多线程实现消息的收发功能)

实现效果:

python UDPSocket聊天器 (多线程实现消息的收发功能)

代码:

import socket
from threading import Thread,Lock

def send_msg(udp_socket):
    """发送信息的函数"""
    while True:
        input_msg = input("请输入聊天内容:\n")  # 用户输入一些信息
        udp_socket.sendto(input_msg.encode("gb2312"), ("192.168.68.196", 8081))

def recv_msg(udp_socket):
    """接收信息的函数"""
    while True:
        recv_data, tuple_ip_port = udp_socket.recvfrom(1024)
        recv_text = recv_data.decode("gb2312")
        print("接受到[%s]的信息:%s" % (str(tuple_ip_port), recv_text))

def main():
    # 创建套接字
    udp_socket = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)

    # 绑定端口
    udp_socket.bind(("", 8080))

    # 接收信息
    t1 = Thread(target=recv_msg, args=(udp_socket,))
    t1.start()

    # 发送信息
    t2 = Thread(target=send_msg, args=(udp_socket,))
    t2.start()

    # # 关闭套接字
    # udp_socket.close()

if __name__ == '__main__':
    main()

6.使用TCPSocket建立客户端

import socket

# 创建套接字
tcp_client_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)

# 建立连接
tcp_client_socket.connect(("192.168.68.196", 8081))

# 发送数据
tcp_client_socket.send("你好".encode("gb2312"))

# 接收数据
recv_data = tcp_client_socket.recv(1024).decode("gb2312")
print(recv_data)

# 关闭套接字
tcp_client_socket.close()

7.使用TCPSocket建立服务端

        ·能够实现一个客户端发来的多条信息

        ·能够接收多个客户端连接

import socket
from threading import Thread


def new_client_connect(new_client_socket, client_ip_port):
    while True:
        # 收发数据
        recv_data = new_client_socket.recv(1024)
        if len(recv_data) != 0:
            recv_text = recv_data.decode("gb2312")
            print("接收到[%s]的信息:%s" % (str(client_ip_port), recv_text))
        else:
            print("客户端断开连接")
            break

        # # 关闭连接
        # new_client_socket.close()  # 表示断开与当前的客户端的通信

def main():
    # 创建套接字
    tcp_server_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)

    # 绑定端口和ip
    tcp_server_socket.bind(("", 8081))

    # 设置套接字为被动监听模式,不能主动发送数据,128为允许接收的最大连接数
    tcp_server_socket.listen(128)

    while True:
        # 接收客户端连接
        new_client_socket, client_ip_port = tcp_server_socket.accept()

        t1 = Thread(target=new_client_connect, args=(new_client_socket, client_ip_port))
        t1.start()

        # tcp_server_socket.close()  # 表示不再接受新客户端的连接,已经连接的可以继续服务

if __name__ == '__main__':
    main()

 效果:

python TCPSocket服务器 (多线程实现消息的接收功能)

版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://blog.csdn.net/ChaoChao66666/article/details/126674607

智能推荐

bootstrap图片轮播-程序员宅基地

文章浏览阅读117次。<!DOCTYPE html><html><head> <title>Bootstrap 实例 - 简单的轮播(Carousel)插件</title> <link href="http://libs.baidu.com/bootstrap/3.0.3/css/bootstrap.min.css"..._bootstrap图片轮播将文字放在图片外面

html选择器_html中同级选择器能否继承-程序员宅基地

文章浏览阅读2.8k次,点赞6次,收藏12次。CSS的作用: 就是用来改变文本的样式CSS三大特性 继承性:给父类元素设置一些属性以后,子类也可以使用,叫继承性 如果对父类标签设置样式以后,如果子类标签没有单独设置样式默认继承父类的样式 注意: 1、并不是所有的都可以继承,只有以color font- text line开头的才可以继承 2、继承不仅仅是直接子代可以继承,后代同样可以继承 3、超链接..._html中同级选择器能否继承

NumPy 高维数组降维方法详细分析_用ndarray函数进行降维-程序员宅基地

文章浏览阅读1.2w次,点赞7次,收藏9次。numpy的flat、flatten、ravel、reshape四个函数都是对多维数组进行降维(降至一维)使用方法:import numpy as npa = np.arange(64).reshape([4,4,4])print(a)#对三维数组a进行降维打击b = a.reshape(-1)print('reshape方法:\n',b)c = []for x in a.flat: c.append(x)print('flat迭代器:\n',c)d = a.flatt_用ndarray函数进行降维

用g.raphael.js高速绘制饼图、柱状图、点状图、折线图(上)_raphael,化饼状图·-程序员宅基地

文章浏览阅读3.5k次。首先介绍一下什么是g.raphael。这个又要说到什么是raphael.js。raphael是一个javascript库,可以用来跨浏览器绘制各种图形,只要是你想得到的图形都可以用raphael绘制出来,而且raphael还可以实现各种常用和常见的动画效果,比如放大、移动、旋转等等。总之只要你想得到的效果,raphael基本上都可以实现。但是问题来了,挖掘机技术……啊呸,raphael本身绘制一些_raphael,化饼状图·

黑马程序员_Java学习日记23_高新技术2-程序员宅基地

文章浏览阅读849次。----------------------android培训、java培训、期待与您交流! ---------------------1.反射概述Class类代表Java类,它的各个实例对象又分别对应什么?a.对应各个类在内存中的字节码。b.一个类被类加载器加载到内存中,占用一片存储空间,这个空间里面的内容就是类的字节码,不同的类的字节码是不同的,所以他们在内存中的内容是

Springboot+rabbitmq的简单使用_rabbitmq 和springboot 实现简单功能-程序员宅基地

文章浏览阅读9.4k次,点赞7次,收藏23次。Springboot+rabbitmq的简单使用Rabbitmq是什么Rabbitmq的简单图解rabbitmq的使用过程Springboot集成Rabbitmq实现即时消息发送Rabbitmq是什么MQ全称为Message Queue, 消息队列(MQ)是一种应用程序对应用程序的通信方法。应用程序通过读写出入队列的消息(针对应用程序的数据)来通信,而无需专用连接来链接它们。RabbitMQ..._rabbitmq 和springboot 实现简单功能

随便推点

AppStorage 基础教程SwiftUI 2新属性-程序员宅基地

文章浏览阅读544次。AppStorage 基础教程SwiftUI2新属性AppStorage属性包装程序类型,通过UserDefaults实现数据持久化。定义@frozen @propertyWrapper struct AppStorage<Value>实战代码import SwiftUIstruct ContentView: View { @AppStorage("text") var text = "" var body: some View { VStack_appstorage

NoParameters接口的使用-程序员宅基地

文章浏览阅读1.1k次。今天从同事那里了解到一个接口 org.apache.struts2.interceptor.NoParameters,之前从来没用过,私下研究了一下觉得很有用,记下来留作以后参考: NoParameters.java,源码附上:[code="java"]package org.apache.struts2.interceptor;/** * This marker inter..._swagger noparameters

Android 多个应用之间声音竞争之Android 系统处理音频焦点(AudioFocus)_android 后台播放与其他应用播放器声音重叠-程序员宅基地

文章浏览阅读6.9k次。问题发现最近在项目中发现我们的自己的apk和第三方的媒体apk会出现串音问题。即两者之间的声音会重叠在一起。解决问题1. 使用多媒体按键去控制第三方应用的声音播放(无效果)通过触发媒体的按钮来操作播放器状态:KeyEvent.KEYCODE_MEDIA_PAUSE public static void sendMediaButton(Context context, in..._android 后台播放与其他应用播放器声音重叠

Linux提权方法总结-程序员宅基地

文章浏览阅读1.6k次,点赞6次,收藏6次。Linux提权方式总结_linux提权

基于javaweb+springboot的电商书城平台系统(java+springboot+mysql+spring+jsp)_基于springboot+jsp的涉外电子商务系统-程序员宅基地

文章浏览阅读232次。基于javaweb+springboot的电商书城平台系统(java+springboot+mysql+spring+jsp)JAVA springboot 电商书城平台系统(已调试) 主要实现了书城网站的浏览、加入购物车操作、订单操作、支付操作、分类查看、搜索、以及后台上传图书信息以及订单管理和一些基本操作功能主要技术:java springboot springbmvc shiro mybatis mysql jquery css js jsp bootstarp.js主要功能截图_基于springboot+jsp的涉外电子商务系统

java.net.URISyntaxException: Illegal character in scheme name at index 0: 10-程序员宅基地

文章浏览阅读8.7k次,点赞40次,收藏3次。今天用java调用一个http请求结果报java.net.URISyntaxException: Illegal character in scheme name at index 0: 10这个错误,首先百度,跳出一堆博客结果全是复制黏贴,第一页全是一个答案,都是什么有|等特殊字符,结果我的url里面根本没有这些特殊字符。大家写技术博客只会抄袭他人,复制过来真是可耻。下面是我自己的排查结果,..._java.net.urisyntaxexception: illegal character in scheme name at index 0: 10

推荐文章

热门文章

相关标签