当前位置: 首页 > news >正文

spark:RDD编程(Python版)

RDD运行原理

RDD设计背景

许多选代目前的MapReduce框架都是把中间结果写入到稳定存储 (比如磁盘)中带来了大量的数据复制、磁盘IO和序列化开销
RDD就是为了满足这种需求而出现的,它提供了一个抽象的数据架构,我们不必担心底层数据的分布式特性,只需将具体的应用逻辑表达为一系列转换处理,不同RDD之间的转换操作形成依赖关系,可以实现管道化,避免中间数据存储。

RDD概念

  1. 一个RDD就是一个分布式对象集合,本质上是一个只读的分区记录集合,每个RDD可分成多个分区,每个分区就是一个数据集片段,并且一个RDD的不同分区可以被保存到集群中不同的节点上,从而可以在集群中的不同节点上进行并行计算

  2. RDD提供了一种高度受限的共享内存模型,即RDD是只读的记录分区的集合,不能直接修改,只能基于稳定的物理存储中的数据集创建RDD,或者通过在其他RDD上执行确定的转换操作(如map、join和group by) 而创建得到新的RDD

  3. RDD提供了一组丰富的操作以支持常见的数据运算,分为“动作”(Action)和“转换” (Transformation)两种类型

  4. RDD提供的转换接口都非常简单,都是类似map、filter、groupBy、join等粗粒度的数据转换操作,而不是针对某个数据项的细粒度修改(不适合网页爬虫)

  5. 表面上RDD的功能很受限、不够强大,实际上RDD已经被实践证明可以高效地表达许多框架的编程模型(比如MapReduce、SQL、Pregel)

  6. Spark提供了RDD的API,程序员可以通过调用API实现对RDD的各种操作

rddtez

RDD运行过程

通过上述对RDD概念、依赖关系和Stage划分的介绍,结合之前介绍的Spark运行基本流程,再总结一下RDD在Spark架构中的运行过程:

(1)创建RDD对象;

(2)SparkContext负责计算RDD之间的依赖关系,构建DAG;

(3)DAGScheduler负责把DAG图分解成多个Stage,每个Stage中包含了多个Task,每个Task会被TaskScheduler分发给各个WorkerNode上的Executor去执行。

rddzxgc

RDD编程基础

1. RDD创建

  1. 从文件系统中加载数据创建RDD
>>> lines = sc.textFile("file:///opt/spark/mycode/rdd/word.txt")
>>> lines.foreach(print)
Hadoop is good
Spark is fast
Spark is better

t1

  1. 从分布式文件系统HDFS中加载数据
>>>lines = sc.textFile("hdfs://localhost:9000/user/hadoop/word.txt")
>>>lines = sc.textFile("/user/hadoop/word.txt")
>>>lines = sc.textFile("word.txt")

三条语句等价


  1. 通过并行集合(列表)创建RDD

可以调用SparkContext的parallelize方法,在Driver中一个已经存在的集合(列表)上创建。

>>>array = [1, 2, 3, 4, 5]
>>>rdd = sc.parallelize(array)
>>>rdd.foreach(print)
1
2
3
4
5

shuzusyt

2. RDD操作

1. 转换操作

对于RDD而言,每一次转换操作都会产生不同的RDD,供给下一个“转换”使用。

转换得到的RDD是惰性求值的,也就是说,整个转换过程只是记录了转换的轨迹,并不会发生真正的计算,只有遇到行动操作时,才会发生真正的计算,开始从血缘关系源头开始,进行物理的转换操作。

zhuanhuan

常用的RDD转换操作API:
caozuoAPI


· filter(func):筛选出满足函数func的元素,并返回一个新的数据集

>>>lines = sc.textFile("file:///opt/spark/mycode/rdd/word.txt")
>>>linesWithSpark = lines.filter(lambda line: "Spark" in line)
>>>linesWithSpark.foreach(print)
Spark is better
Spark is fast

caozuo1

· map(func):将每个元素传递到函数func中,并将结果返回为一个新的RDD

>>>data = [1, 2, 3, 4, 5]
>>>rdd1 = sc.parallelize(data)
>>>rdd2 = rdd1.map(lambda x:x+10)
>>>rdd2.foreach(print)
11
13
12
14
15

capzuo2

>>>lines = sc.textFile("file:///opt/spark/mycode/rdd/word.txt")
>>>words = lines.map(lambda line:line.split(" "))
>>>words.foreach(print)
['Hadoop', 'is', 'good']
['Spark', 'is', 'fast']
['Spark', 'is', 'better']

caozuo3

· flatMap(func)

>>>lines =sc.textFile("file:///opt/spark/mycode/rdd/word.txt")
>>>words = lines.flatMap(lambda line:line.split(" "))
>>>words.foreach(print)
Hadoop 
is 
good
Spark
is
fast
Spark
is
better

caozuo4

· groupByKey():应用于(K, V)键值对数据集时,返回一个新的(k, Iterable)形式的数据集

>>>words = sc.parallelize([("Hadoop",1), ("is",1), ("good", 1), ("Spark",1),\
...("is",1), ("fast",1), ("Spark",1), ("is",1), ("better",1)])
>>>words1 = words.groupByKey()
>>>words1.foreach(print)
('Hadoop', <pyspark.resultiterable.Resultlterable object at 0x7fb210552c88>)
('better', <pyspark.resultiterable.Resultlterable object at 0x7fb210552e80>)
('fast', <pyspark.resultiterable.Resultlterable object at 0x7fb210552c88>)
('good', <pyspark.resultiterable.Resultlterable object at 0x7fb210552c88>)
('Spark', <pysparkresultiterable.Resultlterable object at 0x7fb210552f98>)
('is', <pyspark.resultiterable.Resultlterable object at 0x7fb210552e10>)

caozuo5

· reduceByKey(func) 应用于(K, V)键值对的数据集时,返回一个新的(K, V)形式的数据集,其中的每个值是将每个Key传递到函数func中进行聚合后得到的结果

>>>words = sc.parallelize([("Hadoop",1),("is",1),("good",1),("Spark",1),\
...("is",1),("fast",1),("Spark",1),("is",1),("better",1)])
>>>words1 = words.reduceByKey(lambda a,b:a+b)
>>>words1.foreach(print)
('good', 1)
('Hadoop', 1)
('better', 1)
('Spark', 2)
('fast', 1)
('is', 3)

caozo7

2. 行动操作

行动操作是真正触发计算的地方。Spark程序执行到行动操作时,才会执行真正的计算,从文件中加载数据,完成一次又-次转换操作,最终,完成行动操作得到结果。

常用的RDD行动操作API:
caozuo8

>>>rdd = sc.parallelize([1,2,3,4,5])
>>>rdd.count()
5
>>>rdd.first()
1
>>>rdd.take(3)
[1, 2, 3]
>>>rdd.reduce(lambda a,b:a+b)
15
>>>rdd.collect()
[1, 2, 3, 4, 5]
>>>rdd.foreach(lambda elem:print(elem))
1
2
3
4
5

3. 持久化

惰性机制:所谓的“惰性机制”是指,整个转换过程只是记录了转换的轨迹,并不会发生真正的计算,只有遇到行动操作时,才会触发“从头到尾”的真正的计算这里给出一段简单的语句来解释Spark的惰性机制

在Spark中,RDD采用惰性求值的机制,每次遇到行动操作,都会从头开始执行计算。每次调用行动操作,都会触发一次从头开始的计算。这对于迭代计算而言,代价是很大的,迭代计算经常需要多次重复使用同一组数据

下面就是多次计算同一个RDD的例子:

>>>list = ["Hadoop","Spark","Hive"]
>>>rdd = sc.parallelize(list)
>>>print(rdd.count())  //行动操作,触发一次真正从头到尾的计算
>>>print(','.join(rdd.collect()))  //行动操作,触发一次真正从头到尾的计算

可以通过持久化(缓存)机制避免这种重复计算的开销

可以使用persist0)方法对一个RDD标记为持久化

之所以说“标记为持久化”,是因为出现persist)语句的地方,并不会马上计算生成RDD并把它持久化,而是要等到遇到第一个行动操作触发真正计算以后,才会把计算结果进行持久化

持久化后的RDD将会被保留在计算节点的内存中被后面的行动操作重复使用

cjh

针对上面的实例,增加持久化语句以后的执行过程如下:

>>>list =["Hadoop", "Spark", "Hive"]
>>>rdd = sc.parallelize(list)
>>>rdd.cache()#会调用persist(MEMORY ONLY),但是,语句执行到这里并不会缓存rdd,因为这时rdd还没有被计算生成
>>>print(rdd.count()) #第一次行动操作,触发一次真正从头到尾的计算,这时上面的rdd.cache()才会被执行,把这个rdd放到缓存中
3
>>> print(','.join(rdd.collect()))#第二次行动操作,不需要触发从头到尾的计算,只需要重复使用上面缓存中的rdd
Hadoop,Spark,Hive

4. 分区

RDD是弹性分布式数据集,通常RDD很大,会被分成很多个分区,分别保存在不同的节点上


  1. 分区的作用

(1) 增加并行度

在这里插入图片描述


(2) 减少通讯开销

有两个表:
UserData (Userld,Userlnfo)
Events (UserlD,LinkInfo)
UserData 和 Events 表进行连接操作,获得(UserlD,Userlnfo,Linklnfo)

未分区时对UserData和Events两个表进行连接操作:
weifenqu

采用分区后对UserData和Events两个表进行连接操作:
在这里插入图片描述


  1. RDD分区原则

RDD分区的一个原则是使得分区的个数尽量等于集群中的CPU核心(core)数目

对于不同的Spark部署模式而言 (本地模式、Standalone模式、YARN模式、Mesos模式),都可以通过设置spark.default.parallelism这个参数的值,来配置默认的分区数目,一般而言:

(1)本地模式:默认为本地机器的CPU数目,若设置了local[N],则默认为N
(2)Apache Mesos:默认的分区数为8
(3)Standalone或YARN:在 “集群中所有CPU核心数目总和” 和 “2” 二者中取较大值作为默认值


  1. 设置分区的个数

(1) 创建RDD时手动指定分区个数

在调用textFile0和parallelize0方法的时候手动指定分区个数即可,语法格式如下:

sc.textFile(path,partitionNum)

>>>list =[1,2,3,4,5]
>>>rdd =sc.parallelize(list,2)  #设置两个分区 

(2) 使用reparititon方法重新设置分区个数

通过转换操作得到新 RDD 时,直接调用 repartition 方法即可。例如:

>>>data = sc.parallelize([1,2,3,4,5], 2)
>>>len(data.glom().collect()) #显示data这个RDD的分区数量
2
>>>data.glom().collect()      #显示分区为2的情况
[[1, 2], [3, 4, 5]]
>>>rdd = data.repartition(1)  #对data这个RDD进行重新分区
>>>len(rdd.glom().collect())  #显示rdd这个RDD的分区数量
1
>>>rdd.glom().collect()
[[1, 2, 3, 4, 5]]             #显示分区为1的情况

  1. 自定义分区方法

Spark提供了自带的HashPartitioner(哈希分区)与RangePartitioner(区域分区),能够满足大多数应用场景的需求。与此同时,Spark也支持自定义分区方式,即通过提供一个自定义的分区函数来控制RDD的分区方式,从而利用领域知识进一步减少通信开销

>>>data = sc.parallelize(range(10), 5)
>>>data.glom().collect()
>>>[[0, 1], [2, 3], [4, 5], [6, 7], [8, 9]]>>>rdd = data.map(lambda x:(x,1)).partitionBy(10,lambda x:0).map(lambda x:x[0])
>>>rdd.glom().collect()   # 分到第一区
[[0, 1, 2, 3, 4, 5, 6, 7, 8, 9], [], [], [], [], [], [], [], [], []]>>>rdd = data.map(lambda x:(x,1)).partitionBy(10,lambda x:2).map(lambda x:x[0])
>>>rdd.glom().collect()   # 分到第三区
[[], [], [0, 1, 2, 3, 4, 5, 6, 7, 8, 9], [], [], [], [], [], [], []]>>>rdd = data.map(lambda x:(x,1)).partitionBy(10,lambda x:x).map(lambda x:x[0])
>>>rdd.glom().collect()   # 分到各自的key区
>>>[[0], [1], [2], [3], [4], [5], [6], [7], [8], [9]]>>>rdd = data.map(lambda x:(x,1)).partitionBy(10,lambda x:(x+1)%10).map(lambda x:x[0])
>>>rdd.glom().collect()   # 分到各自的(key+1)区(环式,舍去%效果一样)
>>>[[9], [0], [1], [2], [3], [4], [5], [6], [7], [8]]

3. 键值对RDD

1. 键值对RDD的创建

(1)第一种创建方式:从文件中加载
可以采用多种方式创建RDD,其中一种主要方式是使用 map() 函数来实现

>>>lines = sc.textFile("file:///opt/spark/mycode/pairrdd/word.txt")
>>>pairRDD = lines.flatMap(lambda line:line.split(" ")).map(lambda word:(word, 1))
>>>pairRDD.foreach(print)
('I', 1)
('love', 1)
('Hadoop', 1)

(2) 第二种创建方式:通过并行集合(列表)创建RDD

>>>list =["Hadoop", "Spark", "Hive", "Spark"]
>>>rdd = sc.parallelize(list)
>>>pairRDD =rdd.map(lambda word:(word,1))
>>>pairRDD.foreach(print)
('Hadoop', 1)
('Spark', 1)
('Hive', 1)
('Spark', 1)

2. 常用的键值对RDD转换操作
  1. reduceByKey(func)
  2. groupByKey()
  3. keys
  4. values
  5. sortByKey()
  6. mapValues(func)
  7. join
  8. combineByKey

· reduceByKey(func):使用func函数合并具有相同键的值

>>>pairRDD = sc.parallelize([("Hadoop",1),("Spark",1),("Hive",1),("Spark",1)])
>>>pairRDD.reduceByKey(lambda a,b:a+b).foreach(print)
('Spark', 2)
('Hive', 1)
('Hadoop', 1)

· groupByKey():对具有相同键的值进行分组

比如,对四个键值对(“spark”,1)、(“spark”,2)、(“hadoop”,3)和(“hadoop”,5)采用groupByKey()后得到的结果是: (“spark”,(1,2)) 和 (“hadoop”,(3,5))

>>>list =[("spark",1),("spark",2),("hadoop",3),("hadoop",5)]
>>>pairRDD = sc.parallelize(list)
>>>pairRDD.groupByKey()
PythonRDD[251] at RDD at PythonRDD.scala:53
>>>pairRDD.groupByKey().foreach(print)
('hadoop', <pyspark.resultiterable.Resultlterable object at0x7f2c1093ecf8>)
('spark',<pyspark.resultiterable.Resultlterable object at 0x7f2c1093ecf8>)

reduceByKey(func) 和 groupByKey

reduceByKey 用于对每个 key 对应的多个 value 进行 merge 操作,最重要的是它能够在本地先进行merge操作,并且merge操作可以通过函数自定义

groupByKey 也是对每个 key 进行操作,但只生成一个 sequencegroupByKey 本身不能自定义函数,需要先用groupByKey生成 RDD,然后才能对此 RDD 通过map进行自定义函数操作

>>>words =["one","two","two","three","three","three"]
>>>wordPairsRDD = sc.parallelize(words).map(lambda word:(word,1))
>>>wordCountsWithReduce = wordPairsRDD.reduceByKey(lambda a,b:a+b)
>>>wordCountsWithReduce.foreach(print)
('one', 1)
('two', 2)
('three', 3)
>>>wordCountsWithGroup = wordPairsRDD.groupByKey().map(lambda t:(t[0],sum(t[1])))
>>>wordCountsWithGroup.foreach(print)
('two', 2)
('three', 3)
('one', 1)

上面得到的 wordCountsWithReducewordCountsWithGroup 是完全一样的,但是,它们的内部运算过程是不同的


· keys:把Pair RDD中 key 返回形成一个新的RDD

>>>list = [("Hadoop",1),("Spark",1),("Hive",1),("Spark",1)]
>>>pairRDD = sc.parallelize(list)
>>>pairRDD.keys().foreach(print)
Hadoop
Spark
Hive
Spark

· valuse:把Pair RDD中 value 返回形成一个新的RDD

>>>list = [("Hadoop",1),("Spark",1),("Hive",1),("Spark",1)]
>>>pairRDD = sc.parallelize(list)
>>>pairRDD.valuse().foreach(print)
1
1
1
1

· sortByKey():返回一个根据键排序的RDD

>>>list = [("Hadoop",1),("Spark",1),("Hive",1),("Spark",1)]
>>>pairRDD = sc.parallelize(list)
>>>pairRDD.foreach(print)
('Hadoop', 1)
('Spark', 1)
('Hive', 1)
('Spark', 1)
>>>pairRDD.sortByKey().foreach(print)
('Hadoop', 1)
('Hive', 1)
('Spark', 1)
('Spark', 1)

sortByKey() 和 sortBy(func)

使用sortByKey():

>>>d1 = sc.parallelize([("c",8),("b",25),("c",17),("a",42),\
...("b",4),("d",9),("e",17),("c",2),("f",29),("g",21),("b",9)])
>>>d1.reduceByKey(lambda a,b:a+b).sortByKey(False).collect()
[('g', 21), ('f', 29), ('e', 17), ('d', 9), ('c', 27), ('b', 38), ('a', 42)]

使用sortBy(func):

>>>d1 = sc.parallelize([("c",8),("b",25),("c",17),("a",42),\
...("b",4),("d",9),("e",17),("c",2),("f",29),("g",21),("b",9)])
>>>d1.reduceByKey(lambda a,b:a+b).sortBy(lambda x:x,False).collect()
[('g', 21), ('f', 29), ('e', 17), ('d', 9), ('c', 27), ('b', 38), ('a', 42)]
>>>d1.reduceByKey(lambda a,b:a+b).sortBy(lambda x:x[0],False).collect()
[('g', 21), ('f', 29), ('e', 17), ('d', 9), ('c', 27), ('b', 38), ('a', 42)]
>>>d1.reduceByKey(lambda a,b:a+b).sortBy(lambda x:x[1],False).collect()
[('a', 42), ('b', 38), ('f', 29), ('c', 27), ('g', 21), ('e', 17), ('d', 9)]

· mapValues(func):对键值对RDD中的每个value都应用一个函数,但是,key不会发生变化

>>>list =[("Hadoop",1),("Spark",1),("Hive",1),("Spark",1)]
>>>pairRDD = sc.parallelize(list)
>>>pairRDD1 = pairRDD.mapValues(lambda x:x+1)
>>>pairRDD1.foreach(print)
('Hadoop', 2)
('Spark', 2)
('Hive', 2)
('Spark', 2)

mapValues(func) 和 map(func)

使用mapValues(func):

>>>rdd = sc.parallelize([("spark",2),("hadoop",6),("hadoop",4),("spark",6)])
>>>rdd.mapValues(lambda x:(x,1)).\
...reduceByKey(lambda x,y:(x[0]+y[0],x[1]+y[1])).\
...mapValues(lambda x:x[0]/x[1]).collect()
[('hadoop', 5.0), ('spark', 4.0)]

使用map(func):

>>>rdd = sc.parallelize([("spark",2),("hadoop",6),("hadoop",4),("spark",6)])
>>>rdd.map(lambda x:(x[0], (x[1],1))).\
...reduceByKey(lambda x,y:(x[0]+y[0],x[1]+y[1])).\
...map(lambda x:(x[0], (x[1][0]/x[1][1]))).collect()
[('hadoop', 5.0), ('spark', 4.0)]

· join:join就表示内连接。对于内连接,对于给定的两个输入数据集(K,V1)和(K,V2),只有在两个数据集中都存在的key才会被输出,最终得到一个(K,(V1,V2))类型的数据集。

>>>pairRDD1=sc.parallelize([("spark",1),("spark",2),("hadoop",3),("hadoop",5)])
>>>pairRDD2 =sc.parallelize([("spark","fast")])
>>>pairRDD3 = pairRDD1.join(pairRDD2)
>>>pairRDD3.foreach(print)
('spark', (1, 'fast'))
('spark', (2, 'fast'))

相关文章:

spark:RDD编程(Python版)

RDD运行原理 RDD设计背景 许多选代目前的MapReduce框架都是把中间结果写入到稳定存储 (比如磁盘)中带来了大量的数据复制、磁盘IO和序列化开销 RDD就是为了满足这种需求而出现的&#xff0c;它提供了一个抽象的数据架构&#xff0c;我们不必担心底层数据的分布式特性&#xf…...

中国元宇宙论坛暨常孝元宇宙发布会即将在京举行

中国元宇宙论坛暨常孝元宇宙发布会将于2024年1月9日在北京科技会堂盛大开启。本次论坛汇聚业内顶尖专家、学者和企业代表,共同探讨中国元宇宙、常孝元宇宙《神由都城》的未来发展、技术创新和应用场景。此次发布会将颠覆我们对数字世界的认知,带来前所未有的体验。 《神由都城》…...

华为认证 | 云计算方向HCIE有效期多久?实验报名费多少?

云计算技术已经成为了企业和个人发展的重要网络技术支撑。 而在这个领域中&#xff0c;华为HCIE云计算证书也成为了越来越多人追求的敲门砖。 然而&#xff0c;很多人对于这个证书的有效期以及实验报名费并不清楚。 下面将为你详细解答这些问题。 01 云计算方向HCIE有效期多…...

动物分类识别教程+分类释义+界面展示

1.项目简介 动物分类教程分类释义界面展示 动物分类是生物学中的一个基础知识&#xff0c;它是对动物进行分类、命名和描述的科学方法。本教程将向您介绍动物分类的基本原则和方法&#xff0c;并提供一些常见的动物分类释义。 动物分类的基本原则 动物分类根据动物的形态、…...

【Java动态代理如何实现】

✅Java动态代理如何实现 ✅JDK动态代理和Cglib动态代理的区别 ✅拓展知识仓✅静态代理和动态代理的区别✅动态代理的用途✅Spring AOP的实现方式&#x1f4d1;JDK 动态代理的代码段&#x1f4d1;Cglib动态代理的代码块 ✅注意事项&#xff1a; 在Java中&#xff0c;实现动态代理…...

数据库(部分函数)

函数&#xff1a; 单行函数&#xff1a;会对查询中的每一数据进行处理 字符函数 length&#xff08;列名&#xff09; select name&#xff0c; 日期函数&#xff1a; now() 年月日时分秒 curdate() 年月日 curtime()时分秒 …...

基于Vite+Vue3 给项目引入Axios

基于ViteVue3 给项目引入Axios,方便与后端进行通信。 系列文章指路&#x1f449; 系列文章-基于Vue3创建前端项目并引入、配置常用的库和工具类 文章目录 安装依赖新建src/config/config.js 用于存放常用配置进行简单封装解决跨域问题调用尝试 安装依赖 npm install axios …...

为什么查企业的时候有的公司没有显示注册资金?

我们在查询企业信息时&#xff0c;有时候会遇到某一家企业没有注册资金的情况&#xff0c;但是该企业又不是已经注销的。出现这种情况是什么原因呢&#xff1f; 1.该公司是一家分公司&#xff0c;分公司没有独立法人资格&#xff0c;因此没有注册资金。 2.有些情况下&#xf…...

DataProcess-VOC数据图像和标签一起进行Resize

VOC数据图像和标签一起进行Resize 参加检测比赛的时候&#xff0c;很多时候工业原始数据尺度都比较大&#xff0c;如果对数据不提前进行处理&#xff0c;会导致数据在加载进内存时花费大量的时间&#xff0c;所以在执行训练程序之前需要将图像提前进行预处理。对于目标检测的数…...

MultiValueMap

MultiValueMap是Spring框架中提供的一个接口&#xff0c;它继承了Map接口&#xff0c;用于存储键值对&#xff0c;但与普通的Map不同的是&#xff0c;MultiValueMap中一个键可以对应多个值&#xff0c;因此它也可以被称为“多值Map”。 MultiValueMap的使用场景一般是在需要存…...

山西电力市场日前价格预测【2023-12-25】

日前价格预测 预测说明&#xff1a; 如上图所示&#xff0c;预测明日&#xff08;2023-12-25&#xff09;山西电力市场全天平均日前电价为469.89元/MWh。其中&#xff0c;最高日前电价为1048.40元/MWh&#xff0c;预计出现在08:30。最低日前电价为252.77元/MWh&#xff0c;预计…...

【华为OD机试真题2023CD卷 JAVAJS】5G网络建设

华为OD2023(C&D卷)机试题库全覆盖,刷题指南点这里 5G网络建设 时间限制:4s 空间限制:256MB 限定语言:不限 题目描述: 现需要在某城市进行5G网络建设,已经选取N个地点设置5G基站,编号固定为1到N,接下来需要各个基站之间使用光纤进行连接以确保基站能互联互通,不同…...

OSI 七层参考模型及TCP/IP 四层模型

OSI 七层参考模型 七层模型&#xff0c;亦称 OSI &#xff08; Open System Interconnection &#xff09;参考模型&#xff0c;即开放式系统互联。参考模型是国际标准化组织&#xff08;ISO &#xff09;制定的一个用于计算机或通信系统间互联的标准体系&#xff0c;一般称为…...

【面向对象】对比JavaScript、Go、Ada、Python、C++、Java、PHP的访问限制。

在不同编程语言中&#xff0c;控制成员&#xff08;变量、方法、类等&#xff09;可见性的机制不尽相同。以下是对比JavaScript、Go、Ada、Python、C、Java、PHP所使用的访问限制关键字和约定&#xff1a; 一、JavaScript ### JavaScript访问限制 早期的JavaScript并没有类似…...

力扣(leetcode)第26题删除有序数组中的重复项(Python)

26.删除有序数组的重复项 题目链接&#xff1a;26.删除有序数组的重复项 给你一个非严格递增排列 的数组 nums &#xff0c;请你 原地 删除重复出现的元素&#xff0c;使每个元素 只出现一次 &#xff0c;返回删除后数组的新长度。元素的 相对顺序 应该保持 一致 。然后返回 …...

【内存泄漏】内存泄漏及常见的内存泄漏检测工具介绍

内存泄漏介绍 什么是内存泄漏 内存泄漏是指程序分配了一块内存&#xff08;通常是动态分配的堆内存&#xff09;&#xff0c;但在不再需要这块内存的情况下未将其释放。内存泄漏会导致程序浪费系统内存资源&#xff0c;持续的内存泄漏还导致系统内存的逐渐耗尽&#xff0c;最…...

FPGA-ZYNQ-7000 SoC在嵌入式系统中的优势

FPGA-ZYNQ-7000 SoC在嵌入式系统中的优势 本章节主要参考书籍《Xilinx Zynq-7000 嵌入式系统设计与实现 基于ARM Cortex-A9双核处理器和Vivado的设计方法 (何宾&#xff0c;张艳辉编著&#xff09;》 本章节主要讲述FPGA-ZYNQ-7000 SoC在嵌入式系统中的优势&#xff0c;学习笔…...

如何在Vue3中实现无缝热重载:提升你的开发效率

Vue3中的热重载&#xff08;Hot Module Replacement&#xff0c;简称HMR&#xff09;是一种开发时的功能&#xff0c;它允许开发者在不刷新整个页面的情况下&#xff0c;实时替换、添加或删除模块。这意味着当你对Vue组件进行修改并保存时&#xff0c;这些更改会立即反映在浏览…...

盒子 Box

UVa1587 思路&#xff1a; 1.输入每个面的长宽并将每个面较长的一边放在前面 2.判断是否存在三对面分别相等 3.判断是否存在三组四棱相等 #include <stdio.h> #include <stdlib.h> #define maxn 100int cmp(const void* e1, const void* e2) {return (int)(*(d…...

uni-app附件下载预览 并解决打开附件时黑屏

// 预览附件perviewFile(file) {console.log(点击附件, file)var strfile.previewUrlvar filTypestr.split(.)console.log(filType,filType)uni.downloadFile({url: success: function(res) {console.log(打开文档成功, res);if (res.statusCode 200) {uni.saveFile({tempFile…...

卸载了Visual Studio后,在vscode中执行npm i或npm i --force时报错,该怎么解决?

卸载了Visual Studio后&#xff0c;在vscode中执行npm i或npm i --force时报错,该怎么解决&#xff1f; 报错内容&#xff1a;原因解决办法 报错内容&#xff1a; npm ERR! code 1 npm ERR! path E:\VScode\codeDate\yugan\node_modules\node-sass npm ERR! command failed np…...

渗透测试 | 信息收集常用方法合集

目录 一、关于域名 1.子域名收集 a.搜索引擎查找 b.在线查询 c.工具 d.SSL/TLS证书查询 2.端口型站点收集 3.目录文件扫描 a.目录扫描工具 b.github搜索 c.google搜索 d.在线网站 e.文件接口工具 4.旁站和C段 a.旁站查询 b.C段查询 5.网站技术架构信息 a.基础…...

使用 ElementUI 组件构建无边框 Window 桌面应用(WinForm/WPF)

生活不可能像你想象得那么好,但也不会像你想象得那么糟。 我觉得人的脆弱和坚强都超乎自己的想象。 有时,我可能脆弱得一句话就泪流满面;有时,也发现自己咬着牙走了很长的路。 ——莫泊桑 《一生》 一、技术栈 Vite + Vue3 + TS + ElementUI(plus) + .NET Framework 4.7.2…...

JavaScript中数组的方法和函数作用域问题

1 -函数作用域问题-: 函数的外层作用域&#xff0c;在函数创建时就已确定&#xff0c;和函数的调用位置无关 var name 嘿嘿;// 函数的外层作用域&#xff0c;在函数创建时就已确定&#xff0c;和函数的调用位置无关// JS中的作用域被称为 词法作用域function fn() {console.…...

nodejs设置x-xss-protection解决xss问题

在Node.js中设置X-XSS-Protection可以通过使用helmet库来完成。 首先&#xff0c;确保已经安装了helmet库。如果没有安装&#xff0c;可以运行以下命令进行安装&#xff1a; npm install helmet --save 然后&#xff0c;在你的Node.js应用程序中引入并配置helmet库&#xff…...

C/C++不同整数类型的区别

在C/C中涉及的整数相关的类型大致有如下几种&#xff1a; char、unsigned charshort、unsigned shortint、unsigned intlong、unsigned longlong long、unsigned long longint8_t、uint8_tint32_t、uint32_tint64_t、uint64_tDWORDDWORD32、DWORD64size_t、ssize_tSIZE_T、SSI…...

如何理解JDK、JRE、JVM区别与联系

摘要&#xff1a;JDK是 Java 语言的软件开发工具包(SDK)。在JDK的安装目录下有一个jre目录&#xff0c;里面有两个文件夹bin和lib&#xff0c;在这里可以认为bin里的就是jvm&#xff0c;lib中则是jvm工作所需要的类库&#xff0c;而jvm和 lib合起来就称为jre。 一、JDK JDK(Ja…...

用友GRP-U8 SmartUpload01 文件上传漏洞

漏洞描述 用友GRP-U8行政事业内控管理软件是一款专门针对行政事业单位开发的内部控制管理系统&#xff0c;旨在提高内部控制的效率和准确性。该软件/u8qx/SmartUpload01.jsp接口存在文件上传漏洞&#xff0c;未经授权的攻击者可通过此漏洞上传恶意后门文件&#xff0c;从而获取…...

react 路由v6

这里是区别&#xff1a;V5 vs V6 这里是官网&#xff1a;可以查看更多高级属性 一、基本使用&#xff1a; 1、配置文件 src/routes/index import React from "react";const Home React.lazy(() > import("../Pages/Home")); const About React.laz…...

rpc【通义】rpc原理【gpt】

一 rpc RPC&#xff08;Remote Procedure Call&#xff0c;远程过程调用&#xff09;是一种编程技术&#xff0c;它允许在分布式系统中的一个程序像调用本地函数一样调用另一个程序&#xff08;位于不同的机器或进程中&#xff09;的函数或方法。RPC的主要目标是隐藏网络通信的…...

Leetcode 2973. Find Number of Coins to Place in Tree Nodes

Leetcode 2973. Find Number of Coins to Place in Tree Nodes 1. 解题思路2. 代码实现 题目链接&#xff1a;2973. Find Number of Coins to Place in Tree Nodes 1. 解题思路 这道题思路上其实挺简单的&#xff0c;就是一个遍历的思路&#xff0c;找到每一个点对应的子树当…...

如何调动销售人员使用CRM的积极性?

CRM系统在销售人员眼中是流程监管工具也是单调枯燥的操作空间&#xff0c;如何让销售爱上CRM系统&#xff1f;1.让CRM简化销售工作&#xff1b;2.智能提醒销售各项事务&#xff1b;3.让CRM界面更加丰富多彩&#xff0c;通过这些方法帮助销售经理轻松管理团队&#xff0c;销售对…...

数值分析期末复习

第一章 科学计算 误差 解题步骤 x : 真实值 x:真实值 x:真实值 x ∗ : 近似值 x^*:近似值 x∗:近似值 先求绝对误差 e ∗ e^* e∗: x − x ∗ x - x^* x−x∗ 绝对误差限是 ∣ x − x ∗ ∣ ≤ ε |x - x^{*}| \le \varepsilon ∣x−x∗∣≤ε 求相对误差限: ∣ x − x ∗…...

k8s的探针

一、探针原理 分布式系统和微服务体系结构的挑战之一是自动检测不正常的应用程序&#xff0c;并将请求&#xff08;request&#xff09;重新路由到其他可用系统&#xff0c;恢复损坏的组件。健康检查是应对该挑战的一种可靠方法。使用 Kubernetes&#xff0c;可以通过探针配置运…...

Python 爬虫之下载视频(五)

爬取第三方网站视频 文章目录 爬取第三方网站视频前言一、基本情况二、基本思路三、代码编写四、注意事项&#xff08;ffmpeg&#xff09;总结 前言 国内主流的视频平台有点难。。。就暂且记录一些三方视频平台的爬取吧。比如下面这个&#xff1a; 一、基本情况 这次爬取的方…...

Gradle下载地址

Gradle下载地址 Gradle是一个基于JVM的构建工具&#xff0c;是一款通用灵活的构建工具&#xff0c;Gradle也是第一个构建集成工具&#xff0c;与ant、maven、ivy有良好的相容相关性。支持maven&#xff0c; Ivy仓库&#xff0c;支持传递性依赖管理&#xff0c;而不需要远程仓库…...

顺序表的实现(头插、尾插、头删、尾删、查找、删除、插入)

目录 一. 数据结构相关概念​ 二、线性表 三、顺序表概念及结构 3.1顺序表一般可以分为&#xff1a; 3.2 接口实现&#xff1a; 四、基本操作实现 4.1顺序表初始化 4.2检查空间&#xff0c;如果满了&#xff0c;进行增容​编辑 4.3顺序表打印 4.4顺序表销毁 4.5顺…...

VMware虚拟机安装Ubuntu系统教程

所使用的文件如下&#xff1a; VMware Workstation 17 Pro ubuntu-22.04.3-desktop-amd64.iso 一、ubuntu 命名规则及各版本一览表 1.ubuntu 命名规则&#xff1a; 例如&#xff1a;ubuntu 16.04 LTS 是长期维护版本&#xff1b;ubuntu 17.04 是新特性版本 前两位数字为发…...

41 sysfs 文件系统

前言 在 linux 中常见的文件系统 有很多, 如下 基于磁盘的文件系统, ext2, ext3, ext4, xfs, btrfs, jfs, ntfs 内存文件系统, procfs, sysfs, tmpfs, squashfs, debugfs 闪存文件系统, ubifs, jffs2, yaffs 文件系统这一套体系在 linux 有一层 vfs 抽象, 用户程序不用…...

C++面试宝典第9题:找出第K大元素

题目 给定一个整数数组a,同时给定它的大小N和要找的K(1 <= K <= N),请根据快速排序的思路,找出数组中第K大的数(保证答案存在)。比如:数组a为[50, 23, 66, 18, 72],数组大小N为5,K为3,则第K大的数为50。 解析 这道题主要考察应聘者对于快速排序的理解,以及实…...

“马屁精”李白

“李白一斗诗百篇&#xff0c;长安市上酒家眠。天子呼来不上船&#xff0c;自称臣是酒中仙。”这是诗圣杜甫笔下的李白&#xff0c;也是我们脑海里坚信无二的李白。恃才傲物又狂放不羁的诗仙&#xff0c;怎么会低眉顺眼地去拍人马屁呢&#xff1f; 但我要说的是&#xff0c;人…...

python之glob的用法

目录 获取特定扩展名的所有文件 获取特定目录下的所有文件 递归获取所有文件 转义特殊字符 iglob glob 是 Python 中用于文件模式匹配的一个模块。它使用 Unix shell-style 的通配符来进行匹配&#xff0c;并返回所有匹配的文件路径列表。 下面是一些 glob 的基本用法&am…...

【adb】电脑通过ADB向手机传输文件

具体步骤如下&#xff1a; Step1 下载ADB工具 下载最新版本的 ADB工具 !!! 注意&#xff1a;一定要是最新版本的ADB&#xff0c;否则很可能导致无法识别到手机。 将下载的ADB解压以后的文件如下图所示&#xff1a; Step2 添加环境变量 将 ADB的路径 D:\platformtools &…...

npm的常用使用技巧

npm是一个强大的工具&#xff0c;可以帮助你管理Node.js项目中的依赖项。以下是一些有用的npm使用技巧&#xff1a; 使用npm install命令&#xff1a;这个命令可以安装项目的依赖项。如果你想安装一个特定的版本&#xff0c;你可以使用npm install <package><version…...

【网络奇遇记】揭秘计算机网络的性能指标:速率|带宽|吞吐量|时延

&#x1f308;个人主页&#xff1a;聆风吟 &#x1f525;系列专栏&#xff1a;网络奇遇记、数据结构 &#x1f516;少年有梦不应止于心动&#xff0c;更要付诸行动。 文章目录 &#x1f4cb;前言一. 速率1.1 数据量1.2 速率 二. 带宽三. 吞吐量四. 时延4.1 发送时延4.2 传播时延…...

ACM中算法时间约束

ACM中算法时间约束 一般ACM竞赛C/C的时间限制是一秒&#xff0c;因此可以根据题目数据来推断该题所使用的算法。 算法的时间复杂度在 1 0 7 10^7 107左右合适&#xff0c;最多不能超过 1 0 8 10^8 108&#xff0c; O ( n ) O(n) O(n)的极限就在 1 0 8 10^8 108左右。 问题规…...

C++11的列表初始化和右值引用

目录 前言 一、C11的简介 二、C11的小故事。 三、统一的列表初始化 1.列表初始化 2.initializer_list 四、右值引用 1.什么是左值 2.什么是右值 3.右值引用写法 4.右值的分类 5.右值引用的作用 6.STL容器中的右值引用 7.万能引用 总结 前言 C11相较于之C98&…...

千帆起航:探索百度智能云千帆AppBuilder在AI原生应用开发中的革新之路

千帆起航&#xff1a;探索百度千帆AppBuilder在AI原生应用开发中的革新之路 1.揭开帷幕&#xff0c;大模型第二次战役 自从 ChatGPT 横空出世后&#xff0c;一石激起千层浪&#xff0c;人工智能也正在从感知理解走向生成创造&#xff0c;这是一个关键里程碑。生成式大模型完成…...

RevIT™ AAV Enhancer, 提高AAV产量的又一利器!

腺相关病毒 (AAV) 是基因治疗中使用最广泛的传递机制。近年来&#xff0c;基于AAV病毒所开发的基因疗法的研发及临床试验注册数量也呈指数级增长。截止本文撰写之时&#xff0c;美国食品和药物管理局已批准五项AAV疗法&#xff0c;也是全球市场上最为昂贵的药物&#xff0c;其中…...

Kubectl 部署有状态应用(下)

接上文 《Kubectl 部署有状态应用&#xff08;上&#xff09;》创建完StatefulSet后&#xff0c;本文继续介绍StatefulSet 扩展、更新、删除等内容。 StatefulSet 中的 Pod 验证序数索引和稳定的网络身份 StatefulSet 中的 Pod 具有唯一的序数索引和稳定的网络身份。 查看 …...