首页 > 系统相关 >(四)多进程的序列化

(四)多进程的序列化

时间:2023-04-12 18:56:12浏览次数:52  
标签:function cloudpickle 对象 进程 import 序列化 pickle

给出cloudpickle的GitHub地址:

https://github.com/cloudpipe/cloudpickle

 

 

 

 

 

=======================================================

 

 

 

单机的Python序列化模块有自带的pickle,但是在Python的分布式计算中进行序列化则是使用cloudpickle。之所以在分布式计算中Python的序列化使用cloudpickle模块的原因有:

1. cloudpickle是使用value序列化的方式,而pickle则是使用reference序列化的方式。因此在反序列化时pickle需要运行环境内存在序列化对象的定义,因为pickle进行序列化的只是对象(函数、类对象)的参数;而cloudpickle在序列化时会把对象的定义和参数值一并序列化,所以在分布式计算中传递cloudpickle序列化对象时接受方可以没有对象的定义(如果序列化的是类对象,那么接收方可以没有类的定义)。

例子:

复制代码
import pickle


class A():pass

a=A()

a_pick = pickle.dumps(a)
a_unpick = pickle.loads(a_pick)
print(a_unpick)


del A
b_unpick = pickle.loads(a_pick)
复制代码

 

 

 

复制代码
import cloudpickle as pickle


class A():pass

a=A()

a_pick = pickle.dumps(a)
a_unpick = pickle.loads(a_pick)
print(a_unpick)


del A
b_unpick = pickle.loads(a_pick)
复制代码

 

 

--------------------------------------------------------

 

复制代码
import cloudpickle, pickle


CONSTANT = 42
def my_function(data: int) -> int:
    return data + CONSTANT


pickled_function = cloudpickle.dumps(my_function)
pickled_function_2 = pickle.dumps(my_function)


CONSTANT = 0
depickled_function = cloudpickle.loads(pickled_function)
depickled_function_2 = pickle.loads(pickled_function_2)


print(depickled_function(43))
print(depickled_function_2(43))
复制代码

 

 

 

 

 

2. pickle模块不能序列化lambda函数,cloudpickle可以序列化lambda函数。

例子:

复制代码
import pickle
squared = lambda x: x ** 2
pickled_lambda = pickle.dumps(squared)

new_squared = pickle.loads(pickled_lambda)
new_squared(2)
复制代码

 

 

复制代码
import cloudpickle as pickle
squared = lambda x: x ** 2
pickled_lambda = pickle.dumps(squared)

new_squared = pickle.loads(pickled_lambda)
new_squared(2)
复制代码

 

 

 

 

===========================================

 

 

从上面的例子可以看出,cloudpickle更像是打包序列化,在序列化一个对象时会把该对象设计到的参数和定义也一并打包进行序列化。那么cloudpickle有没有打包不了的对象呢,这个确实还是有的,那就是序列化对象(函数、类对象)中如果包含有import语句的并不会把import语句中所涉及的对象进行一并打包。对于cloudpickle不能把序列化对象中包含的import引入的对象一并打包这个事情我个人的观点是其实现的难点在于import对象中会涉及大量的对象,这样进行一并打包要包含哪些对象难以确定、并且全部打包也是会造成序列化后对象字节码过长、序列化用时过长等问题。

例子:

模块: another_module.py

def g():
    print("hello world")
    return 100

 

 

 

模块 x.py:

复制代码
def f():
    from another_module import g
    return g()+1

import cloudpickle
fff=open("data", "wb")
fff.write(cloudpickle.dumps(f))
复制代码

 

 

 

运行 x.py,把序列化后字节数据存入data文件中:

 

 

----------------------------------

 

 

给出反序列化文件  y.py:

import cloudpickle
fff=open("abc", "rb")
f = cloudpickle.loads(fff.read())
f()

 

 

 

如果把序列化文件data和反序列化文件y.py放在另一个单独的文件夹中并运行y.py,结果如下:

 

 

可以看到,使用cloudpickle并没有把涉及到的import语句中引入的对象进行一并的打包序列化。

 

 

PS:    cloudpickle的底层实现依旧是调用pickle模块,可以说cloudpickle模块是对pickle模块的进一步包装,其实现的功能就是把pickle序列化中没有打包的对象以value的形式进行一并打包。

 

 

====================================================

标签:function,cloudpickle,对象,进程,import,序列化,pickle
From: https://www.cnblogs.com/zhangxianrong/p/17310825.html

相关文章

  • (三)python多进程multiprocessing模块的变量传递问题:父进程中的numpy.array对象隐式序列
    参考:https://docs.python.org/zh-cn/3/library/multiprocessing.htmlcloudpickle——Python分布式序列化的专用模块python多进程multiprocessing模块的变量传递问题:父进程中的numpy.array对象隐式序列化到子进程后的inplace操作的问题-Death_Knight-博客园(cnblogs.com)......
  • ubusd守护进程
    核心部分是ubusd守护进程,它提供了其他守护进程将自己注册以及发送消息的接口。因为这个,接口通过使用Unixsocket来实现,并使用TLV(type-length-value)消息,ubus内部使用Blob_buf,Blob_attr等结构来表示。ubus有两种调用,一个是method调用,一个是notification,其中method包括等待函数返回......
  • 在C#中使用Attributes(特性)来控制枚举成员是否应该被序列化或映射
    如果标记了[NonSerialized]特性,会防止将该字段序列化。但是,该字段仍然可以用于foreach迭代,因为它仍然是枚举的有效成员。如果要防止特定枚举成员被foreach迭代,用[NonSerialized]特性是不起作用的。相反,可以创建一个自定义的Attribute继承自System.Attribute,并将其应用到需要隐藏的......
  • java怎么样判断一个进程是否已近结束
    以记事本程序为例Processp=Runtime.getRuntime().exec("notepad.exe");try{p.waitFor();//等待notepad.exe的结束}catch(InterruptedExceptionex){System.err.println("ERROR");System.exit(1);}//继续自己的程序参见http://zhidao.baidu.com/qu......
  • dll正由另一进程使用,因此该进程无法访问此文件
    打开Windows资源监视器:按下Win+R快捷键打开“运行”对话框,输入resmon命令并按下回车键。在资源监视器中,选择“CPU”选项卡,然后在“关联的句柄”列中查找GuiDB.dll文件。您应该能够找到锁定该文件的进程的名称和PID。然后右键关闭。......
  • java反序列化(三) JDBC反序列化
    JDBC反序列化前置知识JDBCJDBC(JavaDatabaseConnectivity)是Java提供对数据库进行连接、操作的标准API。Java自身并不会去实现对数据库的连接、查询、更新等操作而是通过抽象出数据库操作的API接口(JDBC),不同的数据库提供商必须实现JDBC定义的接口从而也就实现了对数据库的......
  • Linux操作系统进程的状态和转换(五态模型)
    1、进程的状态和装换1.1进程的三态模型按进程在执行过程中的不同情况至少要定义三种状态:运行(running)态:进程占有处理器正在运行的状态。进程已获得CPU,其程序正在执行。在单处理机系统中,只有一个进程处于执行状态;在多处理机系统中,则有多个进程处于执行状态。就绪(ready)态:进程具......
  • multiprocessing和tqdm配合使用(多进程下载文件进度条显示)
    代码importmultiprocessingasmpimportplatformfromtqdmimporttqdmimportwgetls=['url1','url2','url3']#这里填入实际要下载的urlpbar=tqdm(total=len(ls))pbar.set_description('Sleep')update=lambda*args:pbar.......
  • 多进程下载nadc上的数据
    importwgetfrombs4importBeautifulSoupasbsimportrequestsimportrandomimportrequestsfromtqdmimporttqdmfromconcurrent.futuresimportThreadPoolExecutor,Future,as_completed,waitfrommultiprocessingimportcpu_countheaders=[&#......
  • C#数据序列化研究:改进版KLV
    所谓KLV即Key-Length-Value,以【键-数据长度-数据】的形式将数据序列化成字节流,这是一种高性能和兼容性的数据序列化方案,,缺点就是用起来很麻烦,其出现的需求场景如下:1,硬件和云端的数据交互,最开始是以流的形式顺序写入数据,但是由于版本迭代,数据字段难免出现新增插入更新移除等现......