2017-07-13 22 views
2
上のスイッチフィールド

I持って、データセット内の次のスキーマ -スパークのJavaエンコーダ - collectAsList

root 
|-- userId: string (nullable = true) 
|-- data: map (nullable = true) 
| |-- key: string 
| |-- value: struct (valueContainsNull = true) 
| | |-- startTime: long (nullable = true) 
| | |-- endTime: long (nullable = true) 
|-- offset: long (nullable = true) 

そして、私持っている以下のクラス(+セッターと私は簡単にするため省略ゲッター) -

public class MyClass { 

    private String userId; 

    private Map<String, MyDTO> data; 

    private Long offset; 
} 

public class MyDTO { 

    private long startTime; 
    private long endTime; 

} 

私は結果に以下の方法を収集 -

Encoder<MyClass> myClassEncoder = Encoders.bean(MyClass.class); 
    Dataset<MyClass> results = raw_df.as(myClassEncoder); 
    List<MyClass> lst = results.collectAsList(); 

私は私が望む結果を得るために、いくつかの計算を行うと、私はそれを収集する前に結果が正しい方法ですべてです。 これがための結果である -

results.select(results.col("data").getField("2017-07-01").getField("startTime")).show(false); 

出力 -

MyClass userData = results.collectAsList().get(0); MyDTO userDTO = userData.getData().get("2017-07-01"); System.out.println("userDTO startTime: " + userDTO.getStartTime()); System.out.println("userDTO endTime: " + userDTO.getEndTime()); 

- -

data startTime: 1498870800 
data endTime: 1498854000 

どれ

|data[2017-07-01].startTime|data[2017-07-01].endTime| 
+------------------------------------+--------------+ 
|1498854000    |1498870800    | 

これがためreusltsを収集した後の結果であります手掛かり?それは火花の問題ですか?どのように私はそれをバイパスできますか?

+0

私は同様の問題を抱えています。回避策または既知のバグ? –

+0

'spark'から 'java'に移動するときに問題が発生すると思います –

+0

df.toJSON()を見つけて、jacksonオブジェクトマッパーを使用して目的のクラスにキャストしています。 これは特にデータメンバーが異なるタイプの場合に重大な問題です。ここのバグを参照してください - https://issues.apache.org/jira/browse/SPARK-21402 –

答えて

1

このバグSPARK-21402を回避するために、列インデックスを持つセッターとゲッターを追加できます。

public static class MyDTO { 
    private long startTime; 
    private long endTime; 

    public long get1StartTime() { 
     return startTime; 
    } 

    public void set1StartTime(long startTime) { 
     this.startTime = startTime; 
    } 

    public long get2EndTime() { 
     return startTime; 
    } 

    public void set2EndTime(long endTime) { 
     this.endTime = endTime; 
    } 
} 
関連する問題