Scala Implicits and Type Classes 2 — Questions and Answers
Question 1: What is the primary use of an implicit class in Scala 2?
- To create classes that are automatically instantiated at startup
- To add extension methods to an existing type (Correct answer)
- To define classes whose constructor arguments are implicit
- To create singleton companion objects automatically
Correct answer: To add extension methods to an existing type
An implicit class wraps an existing type so the compiler can automatically apply its methods when called on values of the wrapped type, effectively adding extension methods.
Question 2: In Scala 3, which keyword marks a parameter as one that should be filled by a `given` instance?
- implicit
- given
- using (Correct answer)
- infer
Correct answer: using
Scala 3 uses `using` in the parameter list to declare that an argument should be supplied by a `given` instance from the scope.
Question 3: Which syntax correctly defines a `Show[Int]` type class instance in Scala 2?
- implicit val intShow: Show[Int] = new Show[Int] { def show(n: Int): String = n.toString } (Correct answer)
- given intShow: Show[Int] = new Show[Int] { def show(n: Int): String = n.toString }
- type Show[Int] = new Show[Int] { def show(n: Int): String = n.toString }
- val implicit intShow: Show[Int] = new Show[Int] { def show(n: Int): String = n.toString }
Correct answer: implicit val intShow: Show[Int] = new Show[Int] { def show(n: Int): String = n.toString }
In Scala 2, type class instances are provided as `implicit val` (or `implicit object`) definitions that the compiler can inject automatically.
Question 4: What does the `@implicitNotFound` annotation do in Scala?
- Prevents any implicit from being resolved for the annotated type
- Provides a custom, user-friendly error message when an implicit for that type cannot be found (Correct answer)
- Marks a class as excluded from implicit search
- Disables implicit conversions for a specific type parameter
Correct answer: Provides a custom, user-friendly error message when an implicit for that type cannot be found
`@implicitNotFound("...")` placed on a type class trait lets library authors show a descriptive error message instead of the default compiler message when an instance is missing.
Question 5: In Scala 2, in what priority order does the compiler search for implicit values?
- Companion objects first, then local scope, then imports
- Local scope first, then imports, then companion objects of involved types (Correct answer)
- Imports first, then local scope, then companion objects
- Global scope only, regardless of local definitions
Correct answer: Local scope first, then imports, then companion objects of involved types
Scala 2 searches for implicits in local scope (highest priority), then imported scope, then the companion objects of the types involved (the 'implicit scope').
Question 6: What does the context bound syntax `def foo[T: Ordering](x: T, y: T)` mean in Scala?
- T must be a subtype of Ordering
- The method requires an implicit `Ordering[T]` parameter, supplied automatically by the compiler (Correct answer)
- T is bounded to only ordered primitive types
- The method returns an Ordering instance for T
Correct answer: The method requires an implicit `Ordering[T]` parameter, supplied automatically by the compiler
`[T: Ordering]` is syntactic sugar for `[T](implicit ev: Ordering[T])`, requiring an `Ordering` type class instance for `T` to be in scope.
Question 7: Which Scala feature allows you to retroactively add type class instances to types you don't own or control?
- Inheritance and subclassing
- Mixin composition with traits
- Implicit (or given) instances defined outside the type (Correct answer)
- Type aliases and newtypes
Correct answer: Implicit (or given) instances defined outside the type
Because implicit/given instances are resolved by the compiler from any in-scope location, you can define them for third-party types without modifying the original source — this is ad-hoc polymorphism.
What is the primary use of an implicit class in Scala 2?