It may be more helpful to have a general audience friendly section on built-ins somewhere in the documentation and to include information in docstrings for individual built-in functions.
On Sunday, December 27, 2015 at 4:25:26 PM UTC-5, Ismael Venegas Castelló wrote: > > I think this would be useful even if not exported so we can give better > error messages, ie: > > julia> @which 1 === 1 > ERROR: ArgumentError: argument is not a generic function > in methods at reflection.jl:140 > > Ok, so it's not a generic function, then what it is? > > julia> @which 1 === 1 > ERROR: ArgumentError: argument `is` is a builtin function not a generic > function > for a list of builtin functions use `builtins()` > in methods at reflection.jl:140 > > > ERROR: ArgumentError: argument `x` is an intrinsic function not a X > function > for a list of intrinsic functions use `intrinsics()` > in methods at reflection.jl:140 > > > Which I think it's better, IMHO, I had absolutely no idea `is` was an anon > func, nor that it was a builtin, and we don't list or explain the > difference in the manual, which pherhaps could be included also, even if > its in the dev docs. > > Is a builtin the same as an intrinsic? Why is `is` not a `BuiltinFunction` > or something like that? > > I think this could be used if we are going to change Function to an > abstract type, (I red this recently), then all the other function variants > could be subtypes of Function (IntrinsicFunction is alone in the Type tree). > > What I don't understand quite well is if ther is going to be an > `AnonymousFunction` type, I understand that this will be lowered to > gensymed generic functions, am I right? > > All in all I think that what we really need are more informative error > messages, the `info` function could be used a lot more IMHO for example, > and the functions I proposed could be used for this purpose, even if the > implementation changes, the point remains the same, more > introspection/reflexion and better info/war/error messages overall. > > > El domingo, 27 de diciembre de 2015, 15:08:40 (UTC-6), Stefan Karpinski > escribió: >> >> Perhaps, but all of this is going to change fairly soon. Why is this >> information useful? >> >> On Sun, Dec 27, 2015 at 4:03 PM, Ismael Venegas Castelló < >> [email protected]> wrote: >> >>> We could use something like this: >>> >>> julia> isbuiltin(x) = in(symbol(x), builtins()) >>> isbuiltin (generic function with 1 method) >>> >>> julia> isbuiltin(is) >>> true >>> >>> We could also change this functions documentation, something like this: >>> >>> help?> is >>> search: ind2sub ind2sub! @ip_str include_string @int128_str is isa issym >>> isqrt >>> >>> Builtin function: >>> >>> is(x, y) -> Bool >>> ===(x,y) -> Bool >>> ≡(x,y) -> Bool >>> >>> Determine whether x and y are identical, in the sense that no program >>> could >>> distinguish them. Compares mutable objects by address in memory, and >>> compares immutable objects (such as numbers) by contents at the bit >>> level. >>> This function is sometimes called egal. >>> >>> .. ===(x, y) >>> ≡(x,y) >>> >>> See the :func:`is` operator >>> >>> >>> >>> El domingo, 27 de diciembre de 2015, 14:59:31 (UTC-6), Ismael Venegas >>> Castelló escribió: >>>> >>>> So `is` is a builtin anonymous function? >>>> >>>> julia> Base.function_name(is) >>>> :anonymous >>>> >>>> Stefan perhaps we should add a builtins function to inference.jl? >>>> Indeed it's not obvious at all! >>>> >>>> julia> function builtins() >>>> nams = filter(s -> isdefined(Base, s), names(Base, true, >>>> true)) >>>> objs = map(s -> Base.(s), nams) >>>> funcs = filter(x -> isa(x, Function) && isa(x.env, Symbol), >>>> objs) >>>> sort!(map(symbol, unique(funcs))) >>>> end >>>> builtins (generic function with 1 method) >>>> >>>> julia> builtins() >>>> 24-element Array{Any,1}: >>>> :_apply >>>> :_expr >>>> :applicable >>>> :apply_type >>>> :arraylen >>>> :arrayref >>>> :arrayset >>>> :arraysize >>>> :fieldtype >>>> :getfield >>>> :invoke >>>> :is >>>> :isa >>>> :isdefined >>>> :issubtype >>>> :kwcall >>>> :method_exists >>>> :nfields >>>> :setfield! >>>> :svec >>>> :throw >>>> :tuple >>>> :typeassert >>>> :typeof >>>> >>>> julia> >>>> >>>> >>>> >>>> El domingo, 27 de diciembre de 2015, 14:36:52 (UTC-6), Stefan Karpinski >>>> escribió: >>>>> >>>>> In Julia 0.4 anonymous functions are non-generic (in 0.5 they will, >>>>> however, be generic), so that's one way to create a non-generic function. >>>>> Aside from anonymous functions, the only non-generic are the builtins, >>>>> defined in C code using the add_builtin_func function: >>>>> >>>>> $ ack add_builtin_func src >>>>> src/builtins.c >>>>> 1196:static void add_builtin_func(const char *name, jl_fptr_t f) >>>>> 1204: add_builtin_func("is", jl_f_is); >>>>> 1205: add_builtin_func("typeof", jl_f_typeof); >>>>> 1206: add_builtin_func("sizeof", jl_f_sizeof); >>>>> 1207: add_builtin_func("issubtype", jl_f_subtype); >>>>> 1208: add_builtin_func("isa", jl_f_isa); >>>>> 1209: add_builtin_func("typeassert", jl_f_typeassert); >>>>> 1210: add_builtin_func("throw", jl_f_throw); >>>>> 1211: add_builtin_func("tuple", jl_f_tuple); >>>>> 1214: add_builtin_func("getfield", jl_f_get_field); >>>>> 1215: add_builtin_func("setfield!", jl_f_set_field); >>>>> 1216: add_builtin_func("fieldtype", jl_f_field_type); >>>>> 1217: add_builtin_func("nfields", jl_f_nfields); >>>>> 1218: add_builtin_func("isdefined", jl_f_isdefined); >>>>> 1221: add_builtin_func("arrayref", jl_f_arrayref); >>>>> 1222: add_builtin_func("arrayset", jl_f_arrayset); >>>>> 1223: add_builtin_func("arraysize", jl_f_arraysize); >>>>> 1226: add_builtin_func("applicable", jl_f_applicable); >>>>> 1227: add_builtin_func("invoke", jl_f_invoke); >>>>> 1230: add_builtin_func("apply_type", jl_f_instantiate_type); >>>>> 1231: add_builtin_func("_apply", jl_f_apply); >>>>> 1232: add_builtin_func("kwcall", jl_f_kwcall); >>>>> 1233: add_builtin_func("_expr", jl_f_new_expr); >>>>> 1234: add_builtin_func("svec", jl_f_svec); >>>>> >>>>> >>>>> You can determine the same list from the Julia side by this >>>>> not-so-obvious code: >>>>> >>>>> julia> unique(filter(x->isa(x,Function) && isa(x.env,Symbol), >>>>> map(s->Base.(s), filter(s->isdefined(Base,s), names(Base, true, true))))) >>>>> 22-element Array{Any,1}: >>>>> issubtype >>>>> is >>>>> _apply >>>>> _expr >>>>> applicable >>>>> apply_type >>>>> arrayref >>>>> arrayset >>>>> arraysize >>>>> fieldtype >>>>> getfield >>>>> invoke >>>>> isa >>>>> isdefined >>>>> kwcall >>>>> nfields >>>>> setfield! >>>>> svec >>>>> throw >>>>> tuple >>>>> typeassert >>>>> typeof >>>>> >>>>> >>>>> On Sun, Dec 27, 2015 at 2:57 PM, Ray Toal <[email protected]> wrote: >>>>> >>>>>> In the REPL >>>>>> >>>>>> >>>>>> *julia> **methods(is)* >>>>>> >>>>>> *ERROR: ArgumentError: argument is not a generic function* >>>>>> >>>>>> * in methods at reflection.jl:180* >>>>>> >>>>>> >>>>>> and ditto for isa and typeof and perhaps others. >>>>>> >>>>>> Two quick questions: >>>>>> >>>>>> - Is it possible for the programmer to create nongeneric >>>>>> functions in Julia? >>>>>> - If not, is there a complete (at least up to the current release >>>>>> version of the language) list of nongeneric functions? >>>>>> >>>>>> >>>>>> >>>>>> >>>>> >>
