图书目录

目    录

第1章  Spark简介 1

1.1  Spark概念及其特点 1

1.2  Spark技术生态系统 2

1.3  Spark运行模式 4

1.4  Spark执行流程 8

1.5  Spark专有名词 9

1.6  本章小结 11

第2章  Spark集群环境部署 12

2.1  VM虚拟机安装 13

2.2  Ubuntu 22.04系统安装 19

2.3  Ubuntu 22.04网络配置 24

2.4  Ubuntu 22.04环境配置 28

2.5  ZooKeeper安装 33

2.6  Hadoop安装 35

2.6.1  下载并解压 35

2.6.2  配置系统环境变量 35

2.6.3  配置核心文件 36

2.6.4  分发Hadoop 40

2.6.5  启动和验证 40

2.7  Spark安装 47

2.7.1  下载和解压 47

2.7.2  配置系统环境变量 47

2.7.3  配置核心文件 47

2.7.4  分发Spark 48

2.7.5  Spark启动及UI界面查看 48

2.7.6  spark-shell启动验证 49

2.8  集群和代码下载 50

2.9  本章小结 52

第3章  Spark编程体验 54

3.1  Scala基础编程 54

3.1.1  基本语法 55

3.1.2  函数和方法 57

3.1.3  控制语句 59

3.1.4  函数式编程 62

3.1.5  类和对象 67

3.1.6  Scala异常处理 70

3.1.7  Trait(特征) 72

3.1.8  Scala文件I/O 73

3.1.9  Scala练习题 74

3.2  Spark创建项目 80

3.3  Spark程序编写与运行方法 90

3.4  本章小结 92

第4章  RDD深度解读 93

4.1  RDD的概念及特点 93

4.1.1  RDD的特点 94

4.1.2  RDD的算子分类 95

4.1.3  RDD创建方法 95

4.2  RDD的血缘和依赖 97

4.2.1  血缘与依赖的概念 98

4.2.2  Dependency依赖关系 98

4.3  RDD的Transformation算子 103

4.4  RDD的Action算子 122

4.5  RDD的特殊算子 129

4.5.1  cache和persist 129

4.5.2  checkpoint 131

4.6  RDD转换算子的惰性 133

4.6.1  Scala迭代器Iterator接口 133

4.6.2  Scala迭代器Lazy特性及原理 134

4.7  模拟Spark自定义RDD 135

4.8  Spark任务执行原理图解分析 138

4.8.1  WordCount程序元素分解 138

4.8.2  WordCount程序图解 139

4.8.3  Stage和Task的类型 142

4.9  案例:多种算子实现WordCount 143

4.9.1  map + reduceByKey 144

4.9.2  countByValue 145

4.9.3  aggregateByKey或foldByKey 146

4.9.4  groupByKey+map 147

4.9.5  Scala原生实现wordCount 148

4.9.6  combineByKey 149

4.10  本章小结 150

第5章  RDD的Shuffle详解 151

5.1  Shuffle的概念及历史 151

5.1.1  Shuffle的概念 151

5.1.2  Shuffle演进的历史 152

5.2  Shuffle的验证及复用性 153

5.2.1  案例:reduceByKey一定会Shuffle吗 153

5.2.2  案例:join操作一定会触发Shuffle吗 155

5.2.3  Shuffle数据的复用实验 156

5.3  HashShuffleManager 160

5.3.1  HashShuffleManager优化前 160

5.3.2  HashShuffleManager优化后 161

5.4  SortShuffleManager 162

5.4.1  普通运行机制 163

5.4.2  Bypass运行机制 164

5.5  本章小结 164

第6章  Spark共享变量 166

6.1  广播变量 166

6.1.1  广播变量的使用场景 166

6.1.2  广播变量的实现原理 168

6.1.3  案例:两个集合进行结合 168

6.2  累加器 170

6.2.1  累加器使用场景 170

6.2.2  累加器实现原理 171

6.2.3  案例:自定义累加器 173

6.2.4  案例:不使用累加器的方案 174

6.2.5  案例:使用累加器的方法 175

6.3  本章小结 176

第7章  Spark序列化和线程安全 177

7.1  Spark序列化 177

7.1.1  序列化问题的场景 177

7.1.2  数据Bean未实现序列化接口 178

7.1.3  函数闭包及其示例 179

7.2  Task线程安全 191

7.2.1  线程不安全及其解决方案 191

7.2.2  避免线程不安全的示例 192

7.3  本章小结 195

第8章  Spark内存管理机制 196

8.1  内存管理概述 196

8.2  堆内内存和堆外内存的区别 197

8.3  堆内内存 198

8.4  堆外内存 201

8.5  本章小结 204

第9章  Spark SQL简介 205

9.1  Spark SQL的定义和特性 205

9.2  Spark SQL编程抽象 206

9.3  Spark SQL快速体验 207

9.3.1  程序使用示例 208

9.3.2  命令行使用示例 209

9.3.3  新的编程入口SparkSession 211

9.4  本章小结 212

第10章  Spark SQL抽象编程详解 213

10.1  DataFrame创建 213

10.1.1  使用RDD创建DataFrame 214

10.1.2  从结构化文件创建DataFrame 220

10.1.3  外部存储服务创建DataFrame 224

10.2  DataFrame运算 230

10.2.1  SQL风格操作 230

10.2.2  DSL风格API(TableApi)语法 230

10.3  DataFrame输出 236

10.3.1  输出控制台 236

10.3.2  输出文件 236

10.3.3  输出到RDBMS 237

10.3.4  输出到Hive 237

10.3.5  DataFrame输出时的分区操作 238

10.4  RDD代码和SQL代码混合编程 240

10.4.1  Dataset和DataFrame的区别及取数 241

10.4.2  由RDD创建DataFrame 246

10.4.3  由RDD创建Dataset 256

10.5  RDD、Dataset与DataFrame的互相转换 261

10.6  本章小结 262

第11章  Spark SQL自定义函数 263

11.1  用户自定义函数UDF 263

11.1.1  UDF函数的概念及其特点 263

11.1.2  UDF案例1:字符串处理 264

11.1.3  UDF案例2:GEOHASH算法 265

11.1.4  UDF案例3:余弦相似度算法 269

11.1.5  UDF注意事项 271

11.2  用户自定义聚合函数UDAF 272

11.2.1  UDAF的编程模板 272

11.2.2  UDAF原理讲解 273

11.2.3  弱类型用户自定义聚合函数 274

11.2.4  强类型用户自定义聚合函数 276

11.2.5  UDAF注意事项 279

11.3  本章小结 279

第12章  Spark SQL源码解读 280

12.1  Spark SQL的执行过程 280

12.2  元数据管理器SessionCatalog 281

12.3  SQL解析成逻辑执行计划 281

12.4  Analyzer绑定逻辑计划 284

12.5  Optimizer优化逻辑计划 286

12.5.1  谓词下推 290

12.5.2  列裁剪 290

12.5.3  常量替换 291

12.5.4  常量累加 292

12.6  使用SparkPlanner生成物理计划 293

12.7  从物理执行计划获取inputRdd执行 296

12.8  本章小结 296

第13章  Spark性能调优 297

13.1  Spark常规性能调优 297

13.1.1  常规性能调优一:最优资源配置 297

13.1.2  常规性能调优二:RDD优化 298

13.1.3  常规性能调优三:并行度调节 299

13.1.4  常规性能调优四:广播大变量 299

13.1.5  常规性能调优五:Kryo序列化 300

13.1.6  常规性能调优六:调节本地化等待时长 300

13.1.7  常规性能调优七:ShuGle调优 301

13.1.8  常规性能调优八:JVM调优 302

13.2  Spark开发原则优化 304

13.2.1  开发原则一:避免创建重复的RDD 304

13.2.2  开发原则二:避免创建重复的DataFrame 305

13.2.3  开发原则三:尽可能复用同一个RDD 305

13.2.4  开发原则四:避免重复性的SQL查询,对DataFrame复用 306

13.2.5  开发原则五:注意数据类型的使用 307

13.2.6  开发原则六:写出高质量的SQL 308

13.3  Spark调优方法 310

13.3.1  优化数据结构 310

13.3.2  使用缓存(Cache) 310

13.3.3  对配置属性进行调优 312

13.3.4  合理使用广播 314

13.3.5  尽量避免使用Shuffle算子 315

13.3.6  使用map-side预聚合的Shuffle操作 316

13.3.7  使用高性能算子 317

13.3.8  尽量在一次调用中处理一个分区的数据 318

13.3.9  对数据进行序列化 318

13.4  Spark数据倾斜调优 319

13.4.1  调整分区数目 319

13.4.2  去除多余的数据 320

13.4.3  使用广播将Reduce Join转换为Map Join 320

13.4.4  将key进行拆分,大数据转换为小数据 321

13.4.5  数据倾斜定位和解决 322

13.5  本章小结 327

第14章  Spark实战案例 328

14.1  Spark Core电影数据分析 328

14.1.1  表格及数据样例 329

14.1.2  连续登录超过3天的用户DSL风格 329

14.1.3  连续登录超过3天的用户SQL风格 330

14.1.4  电影统计DSL风格 332

14.1.5  电影统计SQL风格 333

14.1.6  电影统计运行结果 336

14.2  Spark Core日志数据分析 337

14.2.1  前期准备 338

14.2.2  统计PV和可视化 339

14.2.3  统计UV和可视化 342

14.2.4  统计TopN和可视化 346

14.3  Spark SQL电商数据分析 350

14.3.1  数据和表格说明 350

14.3.2  加载数据 351

14.3.3  计算每年的销售单数和销售总额 354

14.3.4  查询每年最大金额的订单及其金额 355

14.3.5  计算每年最畅销的货品 356

14.4  Spark SQL金融数据分析 358

14.4.1  数据准备 359

14.4.2  最大值和最小值 360

14.4.3  平均值 361

14.4.4  样本标准差和总体标准差 361

14.4.5  中位数 362

14.4.6  四分位数 364

14.5  本章小结 365

第15章  Spark面试题 366

15.1  Spark核心概念面试题 366

15.1.1  简述Spark是什么 366

15.1.2  简述Spark 3.0的特性 367

15.1.3  简述Spark生态系统有哪些组件 367

15.1.4  简述Spark的运行流程 368

15.1.5  简述Spark的主要功能与特性 368

15.1.6  简述Spark中RDD的Partitioner是如何决定的 369

15.1.7  简述SparkContext与SparkSession之间的区别是什么 369

15.1.8  简述Spark的几种运行模式 370

15.1.9  简述DAG为什么适合Spark 371

15.1.10  简述DAG如何划分Stage 371

15.2  Spark架构原理面试题 372

15.2.1  简述Spark SQL的执行原理 372

15.2.2  简述Spark SQL执行的流程 372

15.2.3  简述Spark相较于MapReduce的优势 373

15.2.4  简述RDD的宽依赖和窄依赖产生的原理 373

15.2.5  简述Stage的内部逻辑 374

15.2.6  简述为什么要根据宽依赖划分Stage 374

15.2.7  简述Spark on YARN运行过程 374

15.2.8  简述YARN Client与YARN Cluster的区别 375

15.2.9  简述Spark的YARN Cluster涉及的参数有哪些 376

15.2.10  简述Spark广播变量的实现和原理 376

15.3  Spark编程实践面试题 377

15.3.1  简述RDD是什么 377

15.3.2  简述对RDD机制的理解 377

15.3.3  简述RDD的宽依赖和窄依赖 378

15.3.4  简述RDD持久化原理是什么 378

15.3.5  简述RDD的容错机制 378

15.3.6  简述RDD的缓存级别 378

15.3.7  简述DAG中为什么要划分Stage 380

15.3.8  简述Spark SQL的数据倾斜解决方案 380

15.3.9  简述Spark SQL如何将数据写入Hive表 381

15.3.10  简述Spark SQL如何使用UDF 381

15.4  Spark性能调优面试题 382

15.4.1  简述Spark Checkpoint 382

15.4.2  简述Spark中Checkpoint和持久化机制的区别 383

15.4.3  简述Spark中的OOM问题 384

15.4.4  简述Spark程序执行时,如何修改默认Task执行个数 384

15.4.5  简述Spark Join操作的优化经验 385

15.4.6  简述Map Join的实现原理 386

15.4.7  简述Spark Shuffle在什么情况下会产生 387

15.4.8  简述Spark Shuffle会在哪些算子中出现 387

15.4.9  简述Spark中的Transform和Action 387

15.4.10  Spark的Job、Stage、Task如何划分 389

15.5  Spark实战应用面试题 389

15.5.1  简述Map和flatMap的区别 389

15.5.2  简述Map和mapPartition的区别 390

15.5.3  简述reduceByKey和groupByKey的区别 391

15.5.4  简述DataFrame的Cache和Persist的区别 391

15.5.5  简述reduceByKey和reduce的区别 392

15.5.6  简述Spark运行时并行度的设置 393

15.5.7  简述Spark解决了Hadoop的哪些问题 394

15.5.8  简述RDD、DataFrame、Dataset和DataStream的区别 395

15.5.9  简述Spark和MapReduce Shuffle的区别 395

15.5.10  简述RDD中reduceBykey与groupByKey哪个性能好 396

15.6  本章小结 396