title: Generic Custom Operator Functions: A Curious Case of a Bad * Instruction
body: <p>I run into this problem, while playing with generics and custom operators in Swift. In the code snippet below, I am introducing two new prefix operators, ∑ and ∏ and then implement their prefix functions as vector sum and product respectively. In order not to have to implement these and similar functions for all the integer and floating point types separately, I defined two protocols instead: Summable (that requires + implementation) and Multiplicable (that requires * implementation). Also, I implemented the two functions for SequenceType arguments which works, for example, with Array and Rage types. Finally, you can see from the println calls at the end of the snippet that this all works quite nicely, except for ∏(1...100). Here the program crashes with EXC_BAD_INSTRUCTION and not much else to go on. Note that ∑(1...100) works, even though it is implemented in the same way. In fact, if I change the initial value in the line <code>return reduce(s, 1, {$0 * $1})</code> to 0 than the program completes without error, albeit with wrong outputs from calls to ∏.</p>
  
  <p>So, it all boils down to using 0 or 1 as an initial value!? When the code in the offending line is unpacked over several lines, it becomes clear that the crash occurs at <code>$0 * $1</code>. Note also that instead of the closures <code>{$0 * $1}</code> and <code>{$0 + $1}</code> I should be able to pass + and * operator functions directly. Alas, this offends the compiler: "Partial application of generic method is not allowed".</p>
  
  <p>Any ideas? How could swapping 1 (or any non zero Int) for 0 cause a crash? And why does this only happen with ranges for multiplication, while ranges for addition with either 0 or 1 initial values works fine?</p>
  
  <pre><code>prefix operator ∑ {}
  prefix operator ∏ {}
  
  protocol Summable { func +(lhs: Self, rhs: Self) -&gt; Self }
  protocol Multiplicable { func *(lhs: Self, rhs: Self) -&gt; Self }
  
  extension Int: Summable, Multiplicable {}
  extension Double: Summable, Multiplicable {}
  
  prefix func ∑&lt;T, S: SequenceType where T == S.Generator.Element, 
      T: protocol&lt;IntegerLiteralConvertible, Summable&gt;&gt;(var s: S) -&gt; T {
      return reduce(s, 0, {$0 + $1})
  }
  
  prefix func ∏&lt;T, S: SequenceType where T == S.Generator.Element, 
      T: protocol&lt;IntegerLiteralConvertible, Multiplicable&gt;&gt;(var s: S) -&gt; T {
      return reduce(s, 1, {$0 * $1})
  }
  
  let ints = [1, 2, 3, 4]
  let doubles: [Double] = [1, 2, 3, 4]
  
  println("∑ints = \( ∑ints )") // --&gt; ∑ints = 10
  println("∑doubles = \( ∑doubles )") // --&gt; ∑doubles = 10.0
  println("∑(1...100) = \( ∑(1...100) )") // --&gt; ∑(1...100) = 5050
  
  println("∏ints = \( ∏ints )") // --&gt; ∏ints = 24
  println("∏doubles = \( ∏doubles )") // --&gt; ∏doubles = 24.0
  println("∏(1...100) = \( ∏(1...100) )") // --&gt; CRASH: EXC_BAD_INSTRUCTION
  </code></pre>
  
  <p>EDIT:
  While rather embarrassing for me, the error I am making in this code makes for a cute test of your programming eye. See if you can figure it out before reading Martin's answer below. You'll feel good about yourself when you do. (I however, might need to look for another career.)</p>