2. overview
- RDD의 기초
- RDD생성하기
- RDD의 연산
- 트랜스포메이션
- 액션
- 여유로운 수행 방식(Lazy evaluation)
- 스파크에 함수 전달하기
- 주로 쓰는 트랜스포메이션과 액션
- 가상 집합 연산
- 액션
- 영속화(캐싱)
3. RDD(Resilient Distributed DataSet)
분산되어 존재하는 데이터 요소들의 모임
- 새로운 RDD를 만들거나
- 존재하는 RDD를 변형하거나
- 결과 계산을위해 RDD에서 연산을 호출
스파크는 자동으로 RDD에 있는 데이터들을 클러스터에 분배, 수행하는 연산들을
병렬화
4. RDD 기초
- RDD는 분산되어 존재있는 변경 불가능한 객체 모음
- RDD는 사용자 정의 클래스를 포함해
파이썬, 자바, 스칼라의 어떤 타입의 객체든 가질 수 있다.
- 두 가지 타입의 연산을 지원
- 트랜스포메이션(transformation)
- 액션(action)
- 스파크는 RDD를 lazy evaluation으로 액션을 사용하는 시점에 처리
5. RDD 생성하기
두 가지 방법을 제공
- 외부 데이터를 로드
val lines = sc.textFile("README.md")
- 직접 만든 프로그램에서 데이터 집합을 병렬화
val lines2 = sc.parallelize(List("pandas", "i like pandas"))
6. RDD의 연산
두 가지 타입의 연산을 지원
- 트랜스포메이션(transformation)
- 새로운 RDD를 만들어내는 연산(ex. map(), filter())
- 액션(action)
- 프로그램에 결과를 돌려주거나 스토리지에 결과를 써 넣는 연산(ex. count(), first())
7. 트랜스포메이션
- 새로운 RDD를 만들어 돌려주는 연산
- 실제로 액션이 사용되는 시점에 계산됨
- RDD는 변경 불가능한 것
<console>:25: error: reassignment to val
- 트랜스포메이션 연산이 일어난 후, 새로운 RDD에 대한 레퍼런스를 리턴
- 가계도(lineage graph)
- 필요시 각 RDD를 재연산하거나 저장된 RDD를 유실될 경우 복구 하기 위함
8. 액션
- 프로그램에 최종 결과 값을 돌려주거나,
외부 저장소에 값을 기록하는 연산 작업
- 실제로 트랜스포메이션이 계산을 수행하도록 만든다.
- 새로운 액션을 호출할 때마다 전체 RDD가 처음부터 계산됨
9. 여유로운 수행 방식
- 스파크가 액션을 만나기 전까지 트렌스포메이션을 처리하지 않음
- 함수형 언어에서는 친숙한 방식
- RDD는 데이터를 가지고 있지 않다.
메타데이터에 명령어만 기록 후, 액션을 만날 때 실제로 수행
10. 스파크에 함수 전달하기
트랜스포메이션과 액션 일부는 함수를 전달해야하는 구조
word = rdd.filter(lambda s: “error” in s)
def containsError(s):
return “error” in s
word = rdd.filter(containsError)
11. 주로쓰는 트랜스포메이션
트랜스포메이션
- map()
- 함수를 받아 RDD의 각 데이터에 적용하고 결과를 돌려준다.
- filter()
- 함수를 받아 filter()함수를 통과한 데이터만 담아 결과를 돌려준다.
- flatMap()
12. 주로쓰는 트랜스포메이션
가상 집합 연산
- distinct()
- union()
- intersection()
- subtract()
- cartesian()
13. 주로쓰는 액션
- reduce()
- 두 개의 데이터를 합쳐 같은 타입 데이터 하나를 반환 하는 함수를 받는다.
val sum = rdd.reduce((x,y) => x+y)
- take()
- count()
- countByValue()
- collect()
- foreach()
14. RDD 타입 값 변환하기
- 몇몇의 함수들은 특정한 타입의 RDD에서만 사용가능
(mean(), variance(), key/value페어)
- 함수를 사용하기 전에 해당 타입이 지원하는지 여부 확인
15. 영속화(캐싱)
- RDD는 호출하는 액션들에 대한 모든 의존성을 재연산.
- 이를 방지하기 위해서 영속화(persist) 요청할 수 있다.
- LRU(Least Recently Used)를 사용해 관리.
import org.apache.spark.storage.StorageLevel
var result = input.map(x => x*x)
result.persist(StorageLevel.DISK_ONLY)
println(result.count())
println(result.collect().mkString(","))