2014-05-19 2 views
6

클로저 범위를 벗어난 필드 나 메서드에 액세스 할 때 발생하는 일반적인 "작업이 직렬화되지 않음"문제를 이해합니다. 그것을 해결하기 위해클래스에서 중첩 된 메서드로 "작업이 직렬화되지 않음"을 피하십시오.

, 나는 보통 학급 전체 직렬화 할 필요가 피할 수 이러한 필드/방법의 로컬 복사본 정의 : 이제

class MyClass(val myField: Any) { 
    def run() = { 
    val f = sc.textFile("hdfs://xxx.xxx.xxx.xxx/file.csv") 

    val myField = this.myField 
    println(f.map(_ + myField).count) 
    } 
} 

를, 내가 실행 방법에 중첩 된 함수를 정의하면, 직렬화 할 수 없습니다 내가 mapFn 대신 데프의 발로 정의하면 심지어 낯선 사람, 그것은 작동 ... 범위에있을 것 "mapFn"를 생각하기 때문에

class MyClass() { 
    def run() = { 
    val f = sc.textFile("hdfs://xxx.xxx.xxx.xxx/file.csv") 

    def mapFn(line: String) = line.split(";") 

    val myField = this.myField 
    println(f.map(mapFn(_)).count) 

    } 
} 

내가 이해가 안 돼요 :

class MyClass() { 
    def run() = { 
    val f = sc.textFile("hdfs://xxx.xxx.xxx.xxx/file.csv") 

    val mapFn = (line: String) => line.split(";") 

    println(f.map(mapFn(_)).count)  
    } 
} 

스칼라가 중첩 함수를 나타내는 방식과 관련이 있습니까?

이 문제를 해결하기위한 권장 방법은 무엇입니까? 중첩 된 함수를 사용하지 않습니까?

+0

나는 이것도보고있다. 이 관찰을 공유해 주셔서 감사합니다. – MahdeTo

답변

1

첫 번째 경우에는 f.map(mapFN(_))f.map(new Function() { override def apply(...) = mapFN(...) })과 같고 두 번째 경우는 단지 f.map(mapFN)일까요? def으로 메소드를 선언 할 때, 그것은 익명의 클래스에서 아마도 암묵적인 $outer을 포함하는 메소드 일 뿐이다. 그러나 mapFunction이 필요하므로 컴파일러가이를 감쌀 필요가 있습니다. 래퍼에서 당신은 그 익명 클래스의 메소드를 참조하지만 인스턴스 자체는 참조하지 않습니다. val을 사용하는 경우 map에 전달하는 함수를 직접 참조 할 수 있습니다. 나는 이것에 대해 잘 모르겠다. 단지 큰 소리로 생각할 것이다 ...

관련 문제