E012: Implicit Class Primary Constructor Arity

This error is emitted when an implicit class has more than one non-implicit parameter in its primary constructor. Implicit classes must accept exactly one primary constructor parameter. This restriction exists because implicit classes are designed for implicit conversions, which convert a single value of one type to another type.

While it's possible to create an implicit class with more than one non-implicit argument, such classes aren't used during implicit lookup.


Example

object Implicits:
  implicit class Wrapper(a: Int, b: String):
    def combined: String = s"$a-$b"

Error

-- [E012] Syntax Error: example.scala:2:17 -------------------------------------
2 |  implicit class Wrapper(a: Int, b: String):
  |  ^
  |  Implicit classes must accept exactly one primary constructor parameter
  |
3 |    def combined: String = s"$a-$b"
  |-----------------------------------------------------------------------------
  | Explanation (enabled by `-explain`)
  |- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  | Implicit classes may only take one non-implicit argument in their constructor. For example:
  |
  |  implicit class RichDate(date: java.util.Date)
  |
  | While it’s possible to create an implicit class with more than one non-implicit argument,
  | such classes aren’t used during implicit lookup.
   -----------------------------------------------------------------------------

Solution

// Use exactly one parameter
object Implicits:
  implicit class RichInt(val value: Int):
    def doubled: Int = value * 2

import Implicits.*
val result = 42.doubled
// Additional parameters can be implicit
object Implicits:
  implicit class Formatter(val value: Int)(using format: String = "%d"):
    def formatted: String = format.format(value)

import Implicits.*
val result = 42.formatted
// In Scala 3, prefer extension methods
extension (value: Int)
  def doubled: Int = value * 2

val result = 42.doubled