     # (2!1000)=499500 <=> 1
     # (998!1000)=499500 <=> 1
     #
-    #                       Sign bit        Expected
+    #                   Negative integer?   Expected
     #                      ⍺   ⍵  ⍵-⍺        Result
     #                     -----------      ----------
     # 3!5   <=> 10  #      0   0   0       (!⍵)÷(!⍺)×!⍵-⍺
     # 5!3   <=> 0   #      0   0   1       0
-    #               #      0   1   0       Domain Error
+    # see below     #      0   1   0       Domain Error
     # 3!¯5  <=> ¯35 #      0   1   1       (¯1*⍺)×⍺!⍺-⍵+1
     # ¯3!5  <=> 0   #      1   0   0       0
     #               #      1   0   1       Cannot arise
     # ¯5!¯3 <=> 6   #      1   1   0       (¯1*⍵-⍺)×(|⍵+1)!(|⍺+1)
     # ¯3!¯5 <=> 0   #      1   1   1       0
+    #
+    # 0.5!¯1 !!! DOMAIN ERROR
     dyad: Beta = real (n, k) ->
-      r =
-        if 0 <= n < k or k < 0 <= n or n < k < 0
-          0
-        else if n < 0 <= k
-          if not isInt k then throw DomainError()
-          Math.pow(-1, k) * Beta k - n - 1, k
-        else if k <= n < 0
-          if not isInt n - k then throw DomainError()
-          Math.pow(-1, n - k) * Beta Math.abs(k + 1), Math.abs(n + 1)
-        else
-          Math.exp lnΓ(n + 1) - lnΓ(k + 1) - lnΓ(n - k + 1)
+      r = switch 4*negInt(k) + 2*negInt(n) + negInt(n - k)
+        when 0b000 then Math.exp lnΓ(n + 1) - lnΓ(k + 1) - lnΓ(n - k + 1)
+        when 0b001 then 0
+        when 0b010 then throw DomainError()
+        when 0b011 then Math.pow(-1, k) * Beta k - n - 1, k
+        when 0b100 then 0
+        when 0b101 then ;
+        when 0b110 then Math.pow(-1, n - k) * Beta Math.abs(k + 1), Math.abs(n + 1)
+        when 0b111 then 0
       if isInt(n) and isInt(k) then Math.round r else r
+
+negInt = (x) -> isInt(x) and x < 0
+smallFactorials = do -> [x = 1].concat(for i in [1..25] then x *= i)

    # !¯1   !!! DOMAIN ERROR
    # !¯200 !!! DOMAIN ERROR
    monad: real (x) ->
      if isInt x, 0, 25
        r = 1; i = 2; (while i <= x then r *= i++); r
      else if x > 150
        1 / 0
      else if x < 0 and x is Math.floor x
        throw DomainError()
      else if x < -150
        0
      else
        Γ(x + 1)

    # Binomial (`!`)
    #

{pervasive, real, withIdentity} = require './vhelpers'
{isInt, prod} = require '../helpers'
{APLArray} = require '../array'
{DomainError} = require '../errors'
Γ = require 'gamma'
