Skip to content
Branch: master
Find file Copy path
Find file Copy path
Fetching contributors…
Cannot retrieve contributors at this time
189 lines (160 sloc) 5.22 KB
**** to become a clojure dialect: ****
ast doc:
parens: working, tested
nil: working, tested
integers: working, tested
reals: working, tested
bools: working, untested
strings: working, tested
simple: working, tested
qualified: working, tested
aliased: working, tested
maps: working, tested
vectors: working, tested
sets: working, tested
regexes: working, tested
simple: working, tested
qualified: working, tested
special forms
def: working, tested
if: working, tested
do: working, tested
let: working, tested
fn: working, tested
applications: working, tested
reader macros
anonymous shorthand fns:
manually specify whitespace
don't have grammar for bools and nil at all?
true, false, and nil can be defs
primitive types like Julia?
group all literals: nil bool keyword symbol string number map vector set seq char regex var
**** type features: ****
fully declarative
definition order doesn't matter
referencing undefined things doesn't fail until everything has been checked
this allows for cyclical dependencies
tracking function purity
all std lib fns are annotated as pure
all other fns are compositions of std lib fns
interop is impure
gradual static typing?
by default, only the essentials are type checked
the compiler will only raise a type error when it's certain something is wrong
type annotations can be added, which are used at compile-time
functions are generic by default
all std lib fns have type annotations
all other fns are compositions of std lib fns
interop requires annotations (or is type-unsafe?)
compile-time evaluation of literals and pure fns
any literals composed entirely of pure fns are evaluated at compile-time
any operations done to those literals are propagated at compile-time
zero-allocation containers
any compile-time literal at code gen will use this container
(conj [1 2] 3) results in a code gen static-vector [1 2 3]
static-string, static-vector, static-map, static-set
polymorphism comes from function specialization
functions can be specified with partial or fully specialized types
functions from any namespace can be specialized from any other
syntax for type specifiers
how will specialization work?
can one specialize across namespaces?
(deftype real (U integer float))
(deftype coord (vector real real))
(deftype none)
(deftype some [t] (keys ::value t))
(deftype optional [t] (U (some t) none))
(type find (-> real (vector real) (optional real)))
(type a real)
(type inc (-> real real))
(type + (-> real real real))
(type identity (all [t] (-> t t)))
(type count (all [t] (-> (collection t) integer)))
function specialization
(type print (-> any none))
(defn print [a]
(extend print
(-> string none)
(extend print
(all [t] (-> (collection t) none))
**** what's needed to make idiolisp usable: ****
website style
similar to
also emacs site
treat / in any identifier as namespacing
allow cyclical dependencies!
require everything be in a namespace; only prelude exists in global ns
basic stdlib (two layers: core and aux) -- core can run in kernel
arithmetic, logic, bit ops
basic IO
persistent immutable data structures
higher-order functions
generics are the big issue
use macros entirely? functions, structs, enums, macros, all generic
yes, absolutely
put instantiations in secret namespace
have the function macro handle generics and check for current instantiations
once implemented, remove normal functions entirely
everything is generic by default and type specification is optional
syntax/eval constructs for returning
use core.logic
first use it for overload resolution
integrate with function calls; require explicit types
ensure returns work
add type deduction
compile-time type for string literals
"foo" => static-string : (3)
allows for easier string usage without dynamic allocations, a la string_view
all functions are generic by default
type specifiers are optional and not preferred
specified with :: to disambiguate from generics
return types need to be specified; ∀ will remain the most common
functions may return multiple types; compiler should automatically use sum
type-safe heterogenous maps
conjoining may return a different type
generic type has possible key->value types, using sum where needed
requires matching all possible variants; maybe too cumbersome
map<string, int> conj string:float yields map<string, sum<int, float>>
map<string, int> conj foo:bar yields map<string, int, foo, bar>
specialize /std/destroy
requires generics? just overloading?
more tests!
** everything else: **
figure out logo
online repl sandbox
irc bot for #idiolisp
You can’t perform that action at this time.