python多线程实现kmeans,python多线程实现多任务 附demo

使用线程完成多任务需要导入threading包:import threading

1.线程类Thread参数说明:

Thread([group [, target [, name [, args [, kwargs]]]]])

group: 线程组,目前只能使用None

target: 执行的目标任务名

args: 以元组的方式给执行任务传参

kwargs: 以字典方式给执行任务传参

name: 线程名,一般不用设置

2.启动线程

启动线程使用start()方法, sub_thread.start()

3.线程注意点:

线程的执行顺序是无序的

主线程默认会等待所有的子线程结束后才结束

可以设置守护线程,当主线程结束时,子线程立即结束

4.设置守护主线程

# 设置成为守护主线程,主线程退出后子线程直接销毁不再执行子线程的代码

sub_thread = threading.Thread(target=run, daemon=True)

# 守护主线程方式二

# sub_thread.setDaemon(True)

5.获取当前程序的活动线程列表

thread_list = threading.enumerate()

print(thread_list)

6.自定义线程

import threading

import time

class MyThread(threading.Thread):

def __init__(self,count1, count2):

# 重写父类__init__方法

# 自定义线程类需要继承父类的构造方法

super().__init__()

self.count1 = count1

self.count2 = count2

# 定义成静态方法

@staticmethod

def task1(count):

print("task1",threading.current_thread())

for i in range(count):

print("任务1执行")

time.sleep(0.2)

@staticmethod

def task2(count):

print("task2",threading.current_thread())

for i in range(count):

print("任务2执行")

time.sleep(0.2)

# task1与task2属于同一个线程,顺序执行

def run(self):

self.task1(self.count1)

self.task2(self.count2)

if __name__ == '__main__':

# 创建自定义线程对象,自定义线程指定执行任务统一在run方法里完成,不需要target指定

# my_thread = MyThread()

# my_thread.run()

my_thread = MyThread(5, 5)

print(MyThread.daemon)

# my_thread.setDaemon(True)

my_thread.start()

7.解决多线程共享全局变量的问题

1.使用线程等待,join()方法

import threading

import time

# 全局变量 g_list

g_list = list()

def add_data():

for i in range(10):

g_list.append(i)

print("add", i)

time.sleep(0.2)

print("add_data:", g_list)

def read_data():

print("read_data",g_list)

if __name__ == '__main__':

add_data_thread = threading.Thread(target=add_data)

read_data_thread = threading.Thread(target=read_data)

add_data_thread.start()

# 主线程等待写入线程执行完成以后代码继续往下运行

add_data_thread.join()

read_data_thread.start()

2.互斥锁

import threading

g_num = 0

# 创建锁对象

lock = threading.Lock()

def task1():

# 取到锁 可以执行

lock.acquire()

# g_num为不可变数据 需要声明全局变量数据

global g_num

for i in range(1000000):

g_num += 1

print("task1",g_num)

lock.release()

def task2():

lock.acquire()

global g_num

for i in range(1000000):

g_num += 1

print("task2:",g_num)

lock.release()

if __name__ == '__main__':

first_sub_thread = threading.Thread(target=task1)

second_sub_thread = threading.Thread(target=task2)

first_sub_thread.start()

second_sub_thread.start()

demo1 多任务版 udp聊天器1.0

接受数据会阻塞整个线程 所以创建接收数据的子线程

import socket

import threading

# 显示功能菜单

def show_menu():

# 显示程序的功能菜单

print("-----------udp聊天器1.0------------")

print("0. 退出")

print("1. 发送数据")

print("---------------------------------------")

# 发送数据

def send_msg(current_udp_socket):

# 接收用户输入的数据

send_content = input("请输入您要发送的内容:")

# 对数据进行编码

send_data = send_content.encode("gbk")

# 发送数据

current_udp_socket.sendto(send_data, ("192.134.131.104", 8080))

# 接收数据

def recv_msg(current_udp_socket):

while True:

# 接收数据, 代码执行到recvfrom 会阻塞,直到收到对方的数据以后代码再继续往下执行

recv_data, ip_port = current_udp_socket.recvfrom(1024)

# 对二进制数据进行解码

recv_content = recv_data.decode("gbk")

print("接收到的数据为:", recv_content, ip_port)

if __name__ == '__main__':

# 创建udp的套接字

udp_socket = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)

# 给程序设置端口号

udp_socket.bind(("", 8989))

# 接受数据会阻塞整个线程 所以创建接收数据的子线程

recv_thread = threading.Thread(target=recv_msg, args=(udp_socket,))

# 设置守护主线程

# recv_thread.setDaemon(True)

# 启动子线程,执行对应的任务

recv_thread.start()

while True:

show_menu()

# 接收用户输入的功能选项

menu_option = input("请输入功能选项:")

if menu_option == "1":

# 发送数据

send_msg(udp_socket)

elif menu_option == "0":

break

# 关闭套接字

udp_socket.close()

demo2 多任务版 tcp服务端

当客户端和服务端建立连接成功以后,需要创建一个子线程,不同子线程负责接收不同客户端的消息

import socket

import threading

# 处理客户端的请求操作

def handle_client_request(service_client_socket, ip_port):

# 循环接收客户端发送的数据

while True:

# 接收客户端发送的数据

recv_data = service_client_socket.recv(1024)

if recv_data:

print(recv_data.decode("gbk"), ip_port)

service_client_socket.send("ok,问题正在处理中...".encode("gbk"))

else:

print("客户端下线了:", ip_port)

break

# 终止和客户端进行通信

service_client_socket.close()

if __name__ == '__main__':

tcp_server_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)

tcp_server_socket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, True)

tcp_server_socket.bind(("", 9090))

tcp_server_socket.listen(128)

# 循环等待接收客户端的连接请求

while True:

# 等待接收客户端的连接请求

service_client_socket, ip_port = tcp_server_socket.accept()

print("客户端连接成功:", ip_port)

# 当客户端和服务端建立连接成功以后,需要创建一个子线程,不同子线程负责接收不同客户端的消息

sub_thread = threading.Thread(target=handle_client_request, args=(service_client_socket, ip_port))

# 设置守护主线程

sub_thread.setDaemon(True)

# 启动子线程

sub_thread.start()

# tcp服务端套接字可以不需要关闭,因为服务端程序需要一直运行

# tcp_server_socket.close()

demo3 多任务版 服务器端文件下载器(异步)

创建子线程,使用子线程处理对应客户端请求操作

import socket

import os

import time

import threading

# 处理客户端下载请求文件的操作

def handle_client_request(ip_port, service_client_socket):

# 代码执行到此,说明连接建立成功

print("客户端的ip地址和端口号:", ip_port)

# 接收客户端请求数据(其实就是客户端发送的文件名)

recv_data = service_client_socket.recv(1024)

# 对二进制数据进行解码

file_name = recv_data.decode("utf-8")

print(file_name)

# 判断指定文件或者文件夹是否存在

if os.path.exists(file_name):

# 根据客户端请求文件名打开指定文件,读取文件中的数据

# with open :

with open(file_name, "rb") as file: # file 表示打开的文件对象

while True:

# 读取文件数据

file_data = file.read(1024)

if file_data:

# 发送数据给客户端

service_client_socket.send(file_data)

# 提示: 发送数据设置延时,测试是否是同时下载文件

time.sleep(0.5)

else:

# 文件读取完成

break

else:

service_client_socket.send("客户端请求的文件不存在!".encode("utf-8"))

# 关闭和客户端通信的套接字

service_client_socket.close()

if __name__ == '__main__':

tcp_server_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)

# 提示: 默认是tcp断开连接,真正释放端口号需要等待1-2分钟

tcp_server_socket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, True)

tcp_server_socket.bind(("", 8989))

# 设置监听

tcp_server_socket.listen(128)

# 循环等待接收客户端的连接请求,可以服务于多个客户端,不同的客户端可以异步下载文件

while True:

# 等待接收客户端的连接请求

service_client_socket, ip_port = tcp_server_socket.accept()

# 创建子线程,使用子线程处理对应客户端请求操作

sub_thread = threading.Thread(target=handle_client_request, args=(ip_port, service_client_socket))

# 启动子线程执行对应的任务

sub_thread.start()

# 关闭服务端的套接字, 最后这个代码可以省略,因为服务端的程序需要一直运行,服务端的套接字不能关闭

# tcp_server_socket.close()

简单认为,哪种行为会在主线程中阻塞主线程的运行,就为哪种行为创建线程去执行该行为,这样不会阻塞主线程的进行。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
以下是一个简单的Python实现K-means聚类算法的示例代码: ```python import numpy as np import matplotlib.pyplot as plt # 初始化数据点 X = np.array([[1, 2], [1, 4], [1, 0], [4, 2], [4, 4], [4, 0]]) # 定义K-means算法 def kmeans(X, K): # 随机选择K个中心点 centers = X[np.random.choice(range(len(X)), K, replace=False)] while True: # 分配每个数据点到最近的中心点 labels = np.array([np.argmin(np.sqrt(np.sum((X - center)**2, axis=1))) for center in centers]) # 计算每个簇的平均值并更新中心点 new_centers = np.array([X[labels == i].mean(axis = 0) for i in range(K)]) # 如果中心点不再变化,则算法收敛 if np.all(centers == new_centers): break centers = new_centers return centers, labels # 调用K-means算法 centers, labels = kmeans(X, 2) # 绘制数据点和中心点 plt.scatter(X[:,0], X[:,1], c=labels) plt.scatter(centers[:,0], centers[:,1], marker='*', s=300, c='r') plt.show() ``` 在此示例中,我们首先初始化了一个包含六个数据点的数组X,然后定义了一个名为kmeans的函数,该函数接受X和K(簇的数量)作为参数。 在函数中,我们首先随机选择K个中心点,然后在while循环中执行以下操作: 1. 将每个数据点分配到最近的中心点(即,将每个数据点分配到最近的簇)。 2. 计算每个簇的平均值并更新中心点。 3. 如果中心点不再变化,则算法收敛并退出循环。 最后,我们调用kmeans函数并将其结果传递给scatter函数以绘制数据点和中心点。在此示例中,我们将数据点用不同颜色的圆圈表示,将中心点用红色星号表示。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值