Skip to content

Commit

Permalink
Unchecked arithmetic (#452)
Browse files Browse the repository at this point in the history
* Unchecked arithmetic

* Fix line and column metadata

* Fetch metadata from various places as needed

* More

* Docstrings

* And the rest

* Pin coverage since coverage>=5.0 is not supported by coveralls.

TheKevJames/coveralls-python#203
  • Loading branch information
chrisrink10 committed Dec 15, 2019
1 parent f02c3db commit e596ef9
Show file tree
Hide file tree
Showing 2 changed files with 151 additions and 18 deletions.
165 changes: 149 additions & 16 deletions src/basilisp/core.lpy
Expand Up @@ -865,37 +865,41 @@
"Sum the arguments together. If no arguments given, returns 0."
([] 0)
([x] x)
([x & args]
(if (seq (rest args))
(recur (operator/add x (first args)) (rest args))
(operator/add x (first args)))))
([x y] (operator/add x y))
([x y & args]
(if (seq args)
(recur (operator/add x y) (first args) (rest args))
(operator/add x y))))

(defn -
"Subtract the arguments. If one argument given, returns the negation
of that argument."
([x] (operator/neg x))
([x & args]
(if (seq (rest args))
(recur (operator/sub x (first args)) (rest args))
(operator/sub x (first args)))))
([x y] (operator/sub x y))
([x y & args]
(if (seq args)
(recur (operator/sub x y) (first args) (rest args))
(operator/sub x y))))

(defn *
"Multiply the arguments. If no arguments given, returns 1."
([] 1)
([x] x)
([x & args]
(if (seq (rest args))
(recur (operator/mul x (first args)) (rest args))
(operator/mul x (first args)))))
([x y] (operator/mul x y))
([x y & args]
(if (seq args)
(recur (operator/mul x y) (first args) (rest args))
(operator/mul x y))))

(defn /
"Divide the arguments. If no arguments given, returns the inverse of
the argument."
([x] (basilisp.lang.runtime/divide 1 x))
([x & args]
(if (seq (rest args))
(recur (basilisp.lang.runtime/divide x (first args)) (rest args))
(basilisp.lang.runtime/divide x (first args)))))
([x y] (basilisp.lang.runtime/divide x y))
([x y & args]
(if (seq args)
(recur (basilisp.lang.runtime/divide x y) (first args) (rest args))
(basilisp.lang.runtime/divide x y))))

(defn mod
"Returns the modulo of num and div."
Expand Down Expand Up @@ -1325,6 +1329,135 @@
[x]
(python/int x))

;;;;;;;;;;;;;;;;;;;;;;;;;;
;; Unchecked Arithmetic ;;
;;;;;;;;;;;;;;;;;;;;;;;;;;

(defmacro ^:private defcopy
"Copy the Var `var` into a new Var as `name`.
Append the given docstring `doc` to the end of the new Var's `doc`."
([name var]
`(defcopy ~name nil ~var))
([name doc var]
(let [orig-var (basilisp.lang.runtime/resolve-var var *ns*)
orig-var-meta (meta orig-var)
var-doc (:doc orig-var-meta)
new-doc (if doc
(str var-doc "\n\n" doc)
var-doc)
vname (vary-meta name
assoc
:doc new-doc
:arglists (list 'quote (:arglists orig-var-meta)))]
`(def ~vname ~var))))

(defcopy unchecked-add
"Same as '+. Python integers are unlimited precision, so unchecked arithmetic
is only provided for compatibility with platforms without unlimited precision
integers."
+)
(defcopy unchecked-add-int
"Same as '+. Python integers are unlimited precision, so unchecked arithmetic
is only provided for compatibility with platforms without unlimited precision
integers."
+)
(defcopy unchecked-subtract
"Same as '-. Python integers are unlimited precision, so unchecked arithmetic
is only provided for compatibility with platforms without unlimited precision
integers."
-)
(defcopy unchecked-subtract-int
"Same as '-. Python integers are unlimited precision, so unchecked arithmetic
is only provided for compatibility with platforms without unlimited precision
integers."
-)
(defcopy unchecked-multiply
"Same as '*. Python integers are unlimited precision, so unchecked arithmetic
is only provided for compatibility with platforms without unlimited precision
integers."
*)
(defcopy unchecked-multiply-int
"Same as '*. Python integers are unlimited precision, so unchecked arithmetic
is only provided for compatibility with platforms without unlimited precision
integers."
*)
(defcopy unchecked-divide-int
"Same as '/. Python integers are unlimited precision, so unchecked arithmetic
is only provided for compatibility with platforms without unlimited precision
integers."
/)

(defcopy unchecked-inc
"Same as 'inc. Python integers are unlimited precision, so unchecked arithmetic
is only provided for compatibility with platforms without unlimited precision
integers."
inc)
(defcopy unchecked-inc-int
"Same as 'inc. Python integers are unlimited precision, so unchecked arithmetic
is only provided for compatibility with platforms without unlimited precision
integers."
inc)
(defcopy unchecked-dec
"Same as 'dec. Python integers are unlimited precision, so unchecked arithmetic
is only provided for compatibility with platforms without unlimited precision
integers."
dec)
(defcopy unchecked-dec-int
"Same as 'dec. Python integers are unlimited precision, so unchecked arithmetic
is only provided for compatibility with platforms without unlimited precision
integers."
dec)

(defn unchecked-negate
"Return the negation of x.
Same as (- x). Python integers are unlimited precision so unchecked arithmetic
is only provided for compatibility with platforms without unlimited precision
integers."
[x]
(- x))
(defcopy unchecked-negate-int unchecked-negate)

(defn unchecked-byte
"Coerce x to a byte. Value may be truncated or rounded."
[x]
(byte (mod x 256)))

(defn unchecked-char
"Coerce x to a char. Value may be truncated or rounded."
[x]
(cond
(instance? python/int x) (char (mod x sys/maxunicode))
:else (char x)))

(defcopy unchecked-double
"Same as 'double. Python integers are unlimited precision, so unchecked arithmetic
is only provided for compatibility with platforms without unlimited precision
integers."
double)
(defcopy unchecked-float
"Same as 'float. Python integers are unlimited precision, so unchecked arithmetic
is only provided for compatibility with platforms without unlimited precision
integers."
float)

(defcopy unchecked-int
"Same as 'int. Python integers are unlimited precision, so unchecked arithmetic
is only provided for compatibility with platforms without unlimited precision
integers."
int)
(defcopy unchecked-long
"Same as 'long. Python integers are unlimited precision, so unchecked arithmetic
is only provided for compatibility with platforms without unlimited precision
integers."
long)
(defcopy unchecked-short
"Same as 'short. Python integers are unlimited precision, so unchecked arithmetic
is only provided for compatibility with platforms without unlimited precision
integers."
short)

;;;;;;;;;;;;;;;;
;; Exceptions ;;
;;;;;;;;;;;;;;;;
Expand Down
4 changes: 2 additions & 2 deletions tox.ini
Expand Up @@ -6,7 +6,7 @@ parallel_show_output = {env:TOX_SHOW_OUTPUT:true}
setenv =
BASILISP_DO_NOT_CACHE_NAMESPACES = true
deps =
coverage
coverage==4.5.4
six==1.10.0
commands =
coverage run \
Expand All @@ -20,7 +20,7 @@ commands =
depends = py36, py37, py38
deps =
coveralls
coverage
coverage==4.5.4
six==1.10.0
passenv =
COVERALLS_REPO_TOKEN
Expand Down

0 comments on commit e596ef9

Please sign in to comment.