本质上,SparkContext对编程来说, 主要功能就是创建第一个RDD出来
RDD的创建主要有2种方式:
并行化创建是指将本地集合转向分布式RDD,这一步就是分布式的开端,本地转分布式
rdd = sparkcontext.parallelize(参数1, 参数2)
# 参数1:集合对象,例如list
# 参数2:分区数
示例如下:
# 导入Spark的相关包
from pyspark import SparkConf, SparkContext
if __name__ == '__main__':
# 0. 初始化执行环境 构建SparkContext对象
conf = SparkConf().setAppName("test").setMaster("local[*]")
sc = SparkContext(conf=conf)
# 演示通过并行化集合的方式去创建RDD, 本地集合 -> 分布式对象(RDD)
rdd = sc.parallelize([1, 2, 3, 4, 5, 6, 7, 8, 9])
# parallelize方法, 没有给定 分区数, 默认分区数是多少? 根据CPU核心来定
print("默认分区数: ", rdd.getNumPartitions())
rdd = sc.parallelize([1, 2, 3], 3)
print("分区数: ", rdd.getNumPartitions())
# collect方法, 是将RDD(分布式对象)中每个分区的数据, 都发送到Driver中, 形成一个Python List对象
# collect: 分布式 转 -> 本地集合
print("rdd的内容是: ", rdd.collect())
可以读取本地数据,也可以读取HDFS上的数据
rdd = sparkcontext.textFile(参数1, 参数2)
# 参数1:文件路径,支持本地文件,也支持HDFS路径
# 参数2:可选,表示最小分区数量,spark有自己的判断,在它允许的范围内,参数2有效果,超出spark的范围,参数2失效
示例如下:
from pyspark import SparkConf, SparkContext
if __name__ == '__main__':
# 构建SparkContext对象
conf = SparkConf().setAppName("test").setMaster("local[*]")
sc = SparkContext(conf=conf)
# 通过textFile API 读取数据
# 读取本地文件数据
file_rdd1 = sc.textFile("../data/input/words.txt")
print("默认读取分区数: ", file_rdd1.getNumPartitions())
print("file_rdd1 内容:", file_rdd1.collect())
# 加最小分区数参数的测试
file_rdd2 = sc.textFile("../data/input/words.txt", 3)
# 最小分区数是参考值, Spark有自己的判断, 你给的太大Spark不会理会
file_rdd3 = sc.textFile("../data/input/words.txt", 100)
print("file_rdd2 分区数:", file_rdd2.getNumPartitions())
print("file_rdd3 分区数:", file_rdd3.getNumPartitions())
# 读取HDFS文件数据测试
hdfs_rdd = sc.textFile("hdfs://node1:8020/input/words.txt")
print("hdfs_rdd 内容:", hdfs_rdd.collect())
在通过读取文件创建RDD中,可以使用wholeTextFile,适合读取一堆小文件
。此API偏向于少量分区读取数据,因为这个API表明了自己是小文件读取专用,那么文件的数据很小分区很多,导致shuffle的几率更高,所以要尽量少分区读取数据。
sparkcontext.wholeTextFiles(参数1, 参数2)
# 参数1,:文件路径,支持本地文件,也支持hdfs路径
# 参数2:可选,表示最小分区数据
注意:参数2 话语权不足,这个API分区数量最多也只能设置到文件数量大小
from pyspark import SparkConf, SparkContext
if __name__ == '__main__':
conf = SparkConf().setAppName("test").setMaster("local[*]")
sc = SparkContext(conf=conf)
# 读取小文件文件夹
rdd= sc.wholeTextFiles("../data/input/tiny_files")
print(rdd.map(lambda x:x[1]).collect())