62f1f40830
Add set of new core functions to the stdlib. Moved the auto-import code from compile_expression to HySymbol so that "even?' in this style expression will be found and imported. (list (filter even? [1 2 3 4 5])) The core functions are documented in 2 sections, one for basic functions like (even?..) and (nth ...) and one for all the sequence functions. Update: This removes all the caching decorators, misnamed as 'lazy-seq' from the core. All sequence methods now just use yield to return a generator, so they are Python-lazy Further refinements of core functions Cleaned up the docs to use 'iterator' instead of 'generator' Fixed drop to just return the iterator instead of an extra yield loop. But also added a test to catch dropping too many.
238 lines
6.9 KiB
Hy
238 lines
6.9 KiB
Hy
(import time)
|
|
|
|
;;;; some simple helpers
|
|
|
|
(defn assert-true [x]
|
|
(assert (= True x)))
|
|
|
|
(defn assert-false [x]
|
|
(assert (= False x)))
|
|
|
|
(defn assert-equal [x y]
|
|
(assert (= x y)))
|
|
|
|
(defn test-cycle []
|
|
"NATIVE: testing cycle"
|
|
(assert-equal (list (take 7 (cycle [1 2 3]))) [1 2 3 1 2 3 1])
|
|
(assert-equal (list (take 2 (cycle [1 2 3]))) [1 2]))
|
|
|
|
(defn test-dec []
|
|
"NATIVE: testing the dec function"
|
|
(assert-equal 0 (dec 1))
|
|
(assert-equal -1 (dec 0))
|
|
(assert-equal 0 (dec (dec 2))))
|
|
|
|
(defn test-distinct []
|
|
"NATIVE: testing the distinct function"
|
|
(setv res (list (distinct [ 1 2 3 4 3 5 2 ])))
|
|
(assert-equal res [1 2 3 4 5])
|
|
;; distinct of an empty list should be []
|
|
(setv res (list (distinct [])))
|
|
(assert-equal res [])
|
|
;; now with an iter
|
|
(setv test_iter (iter [1 2 3 4 3 5 2]))
|
|
(setv res (list (distinct test_iter)))
|
|
(assert-equal res [1 2 3 4 5]))
|
|
|
|
(defn test-drop []
|
|
"NATIVE: testing drop function"
|
|
(setv res (list (drop 2 [1 2 3 4 5])))
|
|
(assert-equal res [ 3 4 5])
|
|
(setv res (list (drop 3 (iter [1 2 3 4 5]))))
|
|
(assert-equal res [ 4 5])
|
|
(setv res (list (drop 0 [1 2 3 4 5])))
|
|
(assert-equal res [1 2 3 4 5])
|
|
(setv res (list (drop -1 [1 2 3 4 5])))
|
|
(assert-equal res [1 2 3 4 5])
|
|
(setv res (list (drop 6 (iter [1 2 3 4 5]))))
|
|
(assert-equal res [])
|
|
(setv res (list (take 5 (drop 2 (iterate inc 0)))))
|
|
(assert-equal res [2 3 4 5 6]))
|
|
|
|
(defn test-even []
|
|
"NATIVE: testing the even? function"
|
|
(assert-true (even? -2))
|
|
(assert-false (even? 1))
|
|
(assert-true (even? 0)))
|
|
|
|
(defn test-filter []
|
|
"NATIVE: testing the filter function"
|
|
(setv res (list (filter pos? [ 1 2 3 -4 5])))
|
|
(assert-equal res [ 1 2 3 5 ])
|
|
;; test with iter
|
|
(setv res (list (filter pos? (iter [ 1 2 3 -4 5 -6]))))
|
|
(assert-equal res [ 1 2 3 5])
|
|
(setv res (list (filter neg? [ -1 -4 5 3 4])))
|
|
(assert-false (= res [1 2])))
|
|
|
|
(defn test-inc []
|
|
"NATIVE: testing the inc function"
|
|
(assert-equal 3 (inc 2))
|
|
(assert-equal 0 (inc -1)))
|
|
|
|
(defn test-instance []
|
|
"NATIVE: testing instance? function"
|
|
(defclass Foo [object])
|
|
(defclass Foo2 [object])
|
|
(defclass Foo3 [Foo])
|
|
(setv foo (Foo))
|
|
(setv foo3 (Foo3))
|
|
(assert-true (instance? Foo foo))
|
|
(assert-false (instance? Foo2 foo))
|
|
(assert-true (instance? Foo foo3))
|
|
(assert-true (instance? float 1.0))
|
|
(assert-true (instance? int 3))
|
|
(assert-true (instance? str (str "hello"))))
|
|
|
|
(defn test-iterable []
|
|
"NATIVE: testing iterable? function"
|
|
;; should work for a string
|
|
(setv s (str "abcde"))
|
|
(assert-true (iterable? s))
|
|
;; should work for unicode
|
|
(setv u "hello")
|
|
(assert-true (iterable? u))
|
|
(assert-true (iterable? (iter u)))
|
|
;; should work for a list
|
|
(setv l [1 2 3 4])
|
|
(assert-true (iterable? l))
|
|
(assert-true (iterable? (iter l)))
|
|
;; should work for a dict
|
|
(setv d {:a 1 :b 2 :c 3})
|
|
(assert-true (iterable? d))
|
|
;; should work for a tuple?
|
|
(setv t (, 1 2 3 4))
|
|
(assert-true (iterable? t))
|
|
;; should work for a generator
|
|
(assert-true (iterable? (repeat 3)))
|
|
;; shouldn't work for an int
|
|
(assert-false (iterable? 5)))
|
|
|
|
(defn test-iterate []
|
|
"NATIVE: testing the iterate function"
|
|
(setv res (list (take 5 (iterate inc 5))))
|
|
(assert-equal res [5 6 7 8 9])
|
|
(setv res (list (take 3 (iterate (fn [x] (* x x)) 5))))
|
|
(assert-equal res [5 25 625])
|
|
(setv f (take 4 (iterate inc 5)))
|
|
(assert-equal (list f) [5 6 7 8]))
|
|
|
|
(defn test-iterator []
|
|
"NATIVE: testing iterator? function"
|
|
;; should not work for a list
|
|
(setv l [1 2 3 4])
|
|
(assert-false (iterator? l))
|
|
;; should work for an iter over a list
|
|
(setv i (iter [1 2 3 4]))
|
|
(assert-true (iterator? i))
|
|
;; should not work for a dict
|
|
(setv d {:a 1 :b 2 :c 3})
|
|
(assert-false (iterator? d))
|
|
;; should not work for a tuple?
|
|
(setv t (, 1 2 3 4))
|
|
(assert-false (iterator? t))
|
|
;; should work for a generator
|
|
(assert-true (iterator? (repeat 3)))
|
|
;; should not work for an int
|
|
(assert-false (iterator? 5)))
|
|
|
|
(defn test-neg []
|
|
"NATIVE: testing the neg? function"
|
|
(assert-true (neg? -2))
|
|
(assert-false (neg? 1))
|
|
(assert-false (neg? 0)))
|
|
|
|
(defn test-none []
|
|
"NATIVE: testing for `is None`"
|
|
(assert-true (none? None))
|
|
(setv f None)
|
|
(assert-true (none? f))
|
|
(assert-false (none? 0))
|
|
(assert-false (none? "")))
|
|
|
|
(defn test-nth []
|
|
"NATIVE: testing the nth function"
|
|
(assert-equal 2 (nth [1 2 4 7] 1))
|
|
(assert-equal 7 (nth [1 2 4 7] 3))
|
|
(assert-true (none? (nth [1 2 4 7] 5)))
|
|
(assert-true (none? (nth [1 2 4 7] -1)))
|
|
;; now for iterators
|
|
(assert-equal 2 (nth (iter [1 2 4 7]) 1))
|
|
(assert-equal 7 (nth (iter [1 2 4 7]) 3))
|
|
(assert-true (none? (nth (iter [1 2 4 7]) -1)))
|
|
(assert-equal 5 (nth (take 3 (drop 2 [1 2 3 4 5 6])) 2)))
|
|
|
|
(defn test-odd []
|
|
"NATIVE: testing the odd? function"
|
|
(assert-true (odd? -3))
|
|
(assert-true (odd? 1))
|
|
(assert-false (odd? 0)))
|
|
|
|
(defn test-pos []
|
|
"NATIVE: testing the pos? function"
|
|
(assert-true (pos? 2))
|
|
(assert-false (pos? -1))
|
|
(assert-false (pos? 0)))
|
|
|
|
(defn test-remove []
|
|
"NATIVE: testing the remove function"
|
|
(setv r (list (remove odd? [1 2 3 4 5 6 7])))
|
|
(assert-equal r [2 4 6])
|
|
(assert-equal (list (remove even? [1 2 3 4 5])) [1 3 5])
|
|
(assert-equal (list (remove neg? [1 2 3 4 5])) [1 2 3 4 5])
|
|
(assert-equal (list (remove pos? [1 2 3 4 5])) []))
|
|
|
|
(defn test-repeat []
|
|
"NATIVE: testing repeat"
|
|
(setv r (repeat 10))
|
|
(assert-equal (list (take 5 r)) [10 10 10 10 10])
|
|
(assert-equal (list (take 4 r)) [10 10 10 10])
|
|
(setv r (repeat 10 3))
|
|
(assert-equal (list r) [10 10 10]))
|
|
|
|
(defn test-repeatedly []
|
|
"NATIVE: testing repeatedly"
|
|
(setv r (repeatedly (fn [] (inc 4))))
|
|
(assert-equal (list (take 5 r)) [5 5 5 5 5])
|
|
(assert-equal (list (take 4 r)) [5 5 5 5])
|
|
(assert-equal (list (take 6 r)) [5 5 5 5 5 5]))
|
|
|
|
(defn test-take []
|
|
"NATIVE: testing the take function"
|
|
(setv res (list (take 3 [1 2 3 4 5])))
|
|
(assert-equal res [1 2 3])
|
|
(setv res (list (take 4 (repeat "s"))))
|
|
(assert-equal res ["s" "s" "s" "s"])
|
|
(setv res (list (take 0 (repeat "s"))))
|
|
(assert-equal res [])
|
|
(setv res (list (take -1 (repeat "s"))))
|
|
(assert-equal res []))
|
|
|
|
(defn test-take-nth []
|
|
"NATIVE: testing the take-nth function"
|
|
(setv res (list (take-nth 2 [1 2 3 4 5 6 7])))
|
|
(assert-equal res [1 3 5 7])
|
|
(setv res (list (take-nth 3 [1 2 3 4 5 6 7])))
|
|
(assert-equal res [1 4 7])
|
|
(setv res (list (take-nth 4 [1 2 3 4 5 6 7])))
|
|
(assert-equal res [1 5])
|
|
(setv res (list (take-nth 5 [1 2 3 4 5 6 7])))
|
|
(assert-equal res [1 6])
|
|
(setv res (list (take-nth 6 [1 2 3 4 5 6 7])))
|
|
(assert-equal res [1 7])
|
|
(setv res (list (take-nth 7 [1 2 3 4 5 6 7])))
|
|
(assert-equal res [1])
|
|
;; using 0 should raise ValueError
|
|
(let [[passed false]]
|
|
(try
|
|
(setv res (list (take-nth 0 [1 2 3 4 5 6 7])))
|
|
(catch [ValueError] (setv passed true)))
|
|
(assert passed)))
|
|
|
|
(defn test-take-while []
|
|
"NATIVE: testing the take-while function"
|
|
(setv res (list (take-while pos? [ 1 2 3 -4 5])))
|
|
(assert-equal res [ 1 2 3 ])
|
|
(setv res (list (take-while neg? [ -1 -4 5 3 4])))
|
|
(assert-false (= res [1 2])))
|