hcerim
hcerim

Reputation: 999

Override "operators" and println method in Scala

I need to create methods for basic operations for different types so the output of the expression: println(1 + 2*I + I*3 + 2) is 3+5i. I am new to Scala and here is what I have so far:

class IClass() {

  var value = 0
  def *(number: Int): String = {
    //value += number
    value + "i"
  }

}

object ComplexNumbers {

  var TotalValue: Int = 0
  var TotalString: String = ""
  // ...

  def Complex(num1: Int, num2: Int): String ={
    num1 + "+" + num2 + "i"
  }

  implicit class IntMultiply(private val a: Int) extends AnyVal {

    def + (b: String)= {
      if(b.contains("i")){
        TotalValue += a
        TotalString.concat(b)
      }
    }

    def * (b: IClass) = {
      //b.value += a
      a + "i"
    }
  }

  implicit class StringAdd(private val a: String) extends AnyVal {
    def + (b: String): String = {
      if(b.contains("i")){

      }
      a + "i"
    }
  }

  def main(args: Array[String]) {

    println(Complex(1,2)) // 1+2i

    val I = new IClass()
    println(1 + 2*I + I*3 + 2) // 3+5i

    // val c = (2+3*I + 1 + 4*I) * I
    // println(-c) // 7-3i
  }
}

I think I am going in a wrong direction with this because by implementing these operation methods on types I get an error in the println: Type Mismach because of the Any return type where I only update fields without returning anything. Any idea how to implement this?

Upvotes: 0

Views: 169

Answers (1)

Dima
Dima

Reputation: 40500

You should think of the complex numbers as a class with certain behaviors, and define it first, rather than focusing on the one concrete side effect you are after at the moment. It seems counter intuitive, but implementing a more abstract/general problem often makes the job easier than trying to narrow it down to just the task at hand.

case class ComplexInt(real: Int, im: Int) {
   def + (other: ComplexInt) = ComplexInt(real + other.real, im + other.im)
   def * (other: ComplexInt) = ComplexInt(
      real * other.real - im * other.im, 
      real * other.im + im * other.real
   )
   def unary_- = ComplexInt(-real, -im)
   def -(other: ComplexInt) = this + -other

   override def toString() = (if(real == 0 && im != 0) "" else real.toString) + (im match {
     case 0 => ""
     case 1 if real == 0 => "i"
     case 1 => " + i"
     case n if n < 0 || real == 0 => s"${n}i"
     case n => s"+${n}i"
   })
}

object ComplexInt {
   val I = ComplexInt(0, 1)
   implicit def fromInt(n: Int) = ComplexInt(n, 0)
}

Now, you just need to import ComplexInt.I, and then things like println(1 + 2*I + I*3 + 2) will print 3+5i etc.

You can even do (1 + 2*I)*(2 + 3*I) (evaluates to -4+7i).

Upvotes: 3

Related Questions