-
Notifications
You must be signed in to change notification settings - Fork 29k
[SPARK-4397][Core] Reorganize 'implicit's to improve the API convenience #3262
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from 1 commit
1eda9e4
3ac4f07
9b73188
3bdcae2
185c12f
7266218
34641d4
52353de
2b5f5a4
9c27aff
fc30314
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
- Loading branch information
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -1427,46 +1427,56 @@ object SparkContext extends Logging { | |
|
|
||
| private[spark] val DRIVER_IDENTIFIER = "<driver>" | ||
|
|
||
| implicit object DoubleAccumulatorParam extends AccumulatorParam[Double] { | ||
| @deprecated("An API for backforward compatibility", "1.2.0") | ||
| object DoubleAccumulatorParam extends AccumulatorParam[Double] { | ||
| def addInPlace(t1: Double, t2: Double): Double = t1 + t2 | ||
| def zero(initialValue: Double) = 0.0 | ||
| } | ||
|
|
||
| implicit object IntAccumulatorParam extends AccumulatorParam[Int] { | ||
| @deprecated("An API for backforward compatibility", "1.2.0") | ||
| object IntAccumulatorParam extends AccumulatorParam[Int] { | ||
| def addInPlace(t1: Int, t2: Int): Int = t1 + t2 | ||
| def zero(initialValue: Int) = 0 | ||
| } | ||
|
|
||
| implicit object LongAccumulatorParam extends AccumulatorParam[Long] { | ||
| @deprecated("An API for backforward compatibility", "1.2.0") | ||
| object LongAccumulatorParam extends AccumulatorParam[Long] { | ||
| def addInPlace(t1: Long, t2: Long) = t1 + t2 | ||
| def zero(initialValue: Long) = 0L | ||
| } | ||
|
|
||
| implicit object FloatAccumulatorParam extends AccumulatorParam[Float] { | ||
| @deprecated("An API for backforward compatibility", "1.2.0") | ||
| object FloatAccumulatorParam extends AccumulatorParam[Float] { | ||
| def addInPlace(t1: Float, t2: Float) = t1 + t2 | ||
| def zero(initialValue: Float) = 0f | ||
| } | ||
|
|
||
| // TODO: Add AccumulatorParams for other types, e.g. lists and strings | ||
|
|
||
| implicit def rddToPairRDDFunctions[K, V](rdd: RDD[(K, V)]) | ||
| @deprecated("An API for backforward compatibility", "1.2.0") | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. update these accordingly too |
||
| def rddToPairRDDFunctions[K, V](rdd: RDD[(K, V)]) | ||
| (implicit kt: ClassTag[K], vt: ClassTag[V], ord: Ordering[K] = null) = { | ||
| new PairRDDFunctions(rdd) | ||
| } | ||
|
|
||
| implicit def rddToAsyncRDDActions[T: ClassTag](rdd: RDD[T]) = new AsyncRDDActions(rdd) | ||
| @deprecated("An API for backforward compatibility", "1.2.0") | ||
| def rddToAsyncRDDActions[T: ClassTag](rdd: RDD[T]) = new AsyncRDDActions(rdd) | ||
|
|
||
| implicit def rddToSequenceFileRDDFunctions[K <% Writable: ClassTag, V <% Writable: ClassTag]( | ||
| @deprecated("An API for backforward compatibility", "1.2.0") | ||
| def rddToSequenceFileRDDFunctions[K <% Writable: ClassTag, V <% Writable: ClassTag]( | ||
| rdd: RDD[(K, V)]) = | ||
| new SequenceFileRDDFunctions(rdd) | ||
|
|
||
| implicit def rddToOrderedRDDFunctions[K : Ordering : ClassTag, V: ClassTag]( | ||
| @deprecated("An API for backforward compatibility", "1.2.0") | ||
| def rddToOrderedRDDFunctions[K : Ordering : ClassTag, V: ClassTag]( | ||
| rdd: RDD[(K, V)]) = | ||
| new OrderedRDDFunctions[K, V, (K, V)](rdd) | ||
|
|
||
| implicit def doubleRDDToDoubleRDDFunctions(rdd: RDD[Double]) = new DoubleRDDFunctions(rdd) | ||
| @deprecated("An API for backforward compatibility", "1.2.0") | ||
| def doubleRDDToDoubleRDDFunctions(rdd: RDD[Double]) = new DoubleRDDFunctions(rdd) | ||
|
|
||
| implicit def numericRDDToDoubleRDDFunctions[T](rdd: RDD[T])(implicit num: Numeric[T]) = | ||
| @deprecated("An API for backforward compatibility", "1.2.0") | ||
| def numericRDDToDoubleRDDFunctions[T](rdd: RDD[T])(implicit num: Numeric[T]) = | ||
| new DoubleRDDFunctions(rdd.map(x => num.toDouble(x))) | ||
|
|
||
| // Implicit conversions to common Writable types, for saveAsSequenceFile | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -17,7 +17,34 @@ | |
|
|
||
| package org.apache.spark | ||
|
|
||
| import scala.language.implicitConversions | ||
| import scala.reflect.ClassTag | ||
|
|
||
| import org.apache.hadoop.io.Writable | ||
|
|
||
| /** | ||
| * Provides several RDD implementations. See [[org.apache.spark.rdd.RDD]]. | ||
| */ | ||
| package object rdd | ||
| package object rdd { | ||
|
|
||
| implicit def rddToPairRDDFunctions[K, V](rdd: RDD[(K, V)]) | ||
|
||
| (implicit kt: ClassTag[K], vt: ClassTag[V], ord: Ordering[K] = null) = { | ||
| new PairRDDFunctions(rdd) | ||
| } | ||
|
|
||
| implicit def rddToAsyncRDDActions[T: ClassTag](rdd: RDD[T]) = new AsyncRDDActions(rdd) | ||
|
|
||
| implicit def rddToSequenceFileRDDFunctions[K <% Writable: ClassTag, V <% Writable: ClassTag]( | ||
| rdd: RDD[(K, V)]) = | ||
| new SequenceFileRDDFunctions(rdd) | ||
|
|
||
| implicit def rddToOrderedRDDFunctions[K : Ordering : ClassTag, V: ClassTag]( | ||
| rdd: RDD[(K, V)]) = | ||
| new OrderedRDDFunctions[K, V, (K, V)](rdd) | ||
|
|
||
| implicit def doubleRDDToDoubleRDDFunctions(rdd: RDD[Double]) = new DoubleRDDFunctions(rdd) | ||
|
|
||
| implicit def numericRDDToDoubleRDDFunctions[T](rdd: RDD[T])(implicit num: Numeric[T]) = | ||
| new DoubleRDDFunctions(rdd.map(x => num.toDouble(x))) | ||
|
|
||
| } | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,73 @@ | ||
| package org.apache.spark | ||
|
|
||
| /** | ||
| * A test suite to make sure all `implicit` functions work correctly. | ||
| * Please don't `import org.apache.spark.SparkContext._` in this class. | ||
| * | ||
| * As `implicit` is a compiler feature, we don't need to run this class. | ||
| * What we need to do is making the compiler happy. | ||
| */ | ||
| class ImplicitSuite { | ||
|
|
||
|
|
||
| // We only want to test if `implict` works well with the compiler, so we don't need a real | ||
| // SparkContext. | ||
| def mockSparkContext[T]: org.apache.spark.SparkContext = null | ||
|
|
||
| // We only want to test if `implict` works well with the compiler, so we don't need a real RDD. | ||
| def mockRDD[T]: org.apache.spark.rdd.RDD[T] = null | ||
|
|
||
| def testRddToPairRDDFunctions(): Unit = { | ||
| val rdd: org.apache.spark.rdd.RDD[(Int, Int)] = mockRDD | ||
| rdd.groupByKey | ||
|
||
| } | ||
|
|
||
| def testRddToAsyncRDDActions(): Unit = { | ||
| val rdd: org.apache.spark.rdd.RDD[Int] = mockRDD | ||
| rdd.countAsync() | ||
| } | ||
|
|
||
| def testRddToSequenceFileRDDFunctions(): Unit = { | ||
| // TODO eliminating `import intToIntWritable` needs refactoring SequenceFileRDDFunctions. | ||
| // That will be a breaking change. | ||
| import org.apache.spark.SparkContext.intToIntWritable | ||
| val rdd: org.apache.spark.rdd.RDD[(Int, Int)] = mockRDD | ||
| rdd.saveAsSequenceFile("/a/test/path") | ||
| } | ||
|
|
||
| def testRddToOrderedRDDFunctions(): Unit = { | ||
| val rdd: org.apache.spark.rdd.RDD[(Int, Int)] = mockRDD | ||
| rdd.sortByKey() | ||
| } | ||
|
|
||
| def testDoubleRDDToDoubleRDDFunctions(): Unit = { | ||
| val rdd: org.apache.spark.rdd.RDD[Double] = mockRDD | ||
| rdd.stats() | ||
| } | ||
|
|
||
|
|
||
| def testNumericRDDToDoubleRDDFunctions(): Unit = { | ||
| val rdd: org.apache.spark.rdd.RDD[Int] = mockRDD | ||
| rdd.stats() | ||
| } | ||
|
|
||
| def testDoubleAccumulatorParam(): Unit = { | ||
| val sc = mockSparkContext | ||
| sc.accumulator(123.4) | ||
| } | ||
|
|
||
| def testIntAccumulatorParam(): Unit = { | ||
| val sc = mockSparkContext | ||
| sc.accumulator(123) | ||
| } | ||
|
|
||
| def testLongAccumulatorParam(): Unit = { | ||
| val sc = mockSparkContext | ||
| sc.accumulator(123L) | ||
| } | ||
|
|
||
| def testFloatAccumulatorParam(): Unit = { | ||
| val sc = mockSparkContext | ||
| sc.accumulator(123F) | ||
| } | ||
| } | ||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Does this provide binary compatibility for Spark programs compiled against earlier versions of Spark?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes. I mentioned it in the description of this PR.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do you mind updating the deprecation message to say
"Replaced by implicit objects in AccumulatorParam. This is kept here only for backward binary compatibility."
Do it for all the following.