I have been looking in Rakudo source for the implementation of require, first out of curiosity and second because I wanted to know if it was returning something.
I looked up sub require and it returned this hit, which actually seems to be the source for require, but it's called sub REQUIRE_IMPORT. It returns Nil and is declared as such, which pretty much answers my original question. But now my question is: Where's the mapping from that sub to require? Is it really the implementation for that function? Are there some other functions that are declared that way?
require is not a sub, but rather a statement control (so, in the same category of things like use, if, for, etc.) It is parsed by the Perl 6 grammar and there are a few different cases that are accepted. It is compiled in the Perl 6 actions, which has quite a bit to handle.
Much of the work is delegated to the various CompUnit objects, which are also involved with use/need. It also has to take care of stubbing symbols that the require will bring in, since the set of symbols in a given lexical scope is fixed at compile time, and the REQUIRE_IMPORT utility sub is involved with the runtime symbol import too.
The answer to your question as to what it will evaluate to comes at the end of the method:
$past.push($<module_name>
?? self.make_indirect_lookup($longname.components())
!! $<file>.ast);
Which means:
If it was a require Some::Module then evaluate to a lookup of Some::Module
If it was a require $file style case, evaluate to the filename
Related
Reading Idris2 code I've seen several cases of functions "decorated" with %inline and also %tcinline I've been searching for a clear explanation about it but haven't found anything except that it "can" be used for giving some "hints" to help on foreign calls, but it's not clear what's the main purpose of it and when it should be used or when should not be used.
Additionally it would be really good to know if these "decorators" which happen to start with % have any common purpose.
From the change log:
New function flag %tcinline which means that the function should be inlined for the purposes of totality checking (but otherwise not inlined). This can be used as a hint for totality checking, to make the checker look inside functions that it otherwise might not.
From the documentation on pragmas:
%inline Instruct the compiler to inline the following definition when it is applied. It is generally best to let the compiler and the backend you are using optimize code based on its predetermined rules, but if you want to
force a function to be inlined when it is called, this pragma will force it.
I prefer working with files that are less than 1000 lines long, so am thinking of breaking up some Erlang modules into more bite-sized pieces.
Is there a way of doing this without expanding the public API of my library?
What I mean is, any time there is a module, any user can do module:func_exported_from_the_module. The only way to really have something be private that I know of is to not export it from any module (and even then holes can be poked).
So if there is technically no way to accomplish what I'm looking for, is there a convention?
For example, there are no private methods in Python classes, but the convention is to use a leading _ in _my_private_method to mark it as private.
I accept that the answer may be, "no, you must have 4K LOC files."
The closest thing to a convention is to use edoc tags, like #private and #hidden.
From the docs:
#hidden
Marks the function so that it will not appear in the
documentation (even if "private" documentation is generated). Useful
for debug/test functions, etc. The content can be used as a comment;
it is ignored by EDoc.
#private
Marks the function as private (i.e., not part of the public
interface), so that it will not appear in the normal documentation.
(If "private" documentation is generated, the function will be
included.) Only useful for exported functions, e.g. entry points for
spawn. (Non-exported functions are always "private".) The content can
be used as a comment; it is ignored by EDoc.
Please note that this answer started as a comment to #legoscia's answer
Different visibilities for different methods is not currently supported.
The current convention, if you want to call it that way, is to have one (or several) 'facade' my_lib.erl module(s) that export the public API of your library/application. Calling any internal module of the library is playing with fire and should be avoided (call them at your own risk).
There are some very nice features in the BEAM VM that rely on being able to call exported functions from any module, such as
Callbacks (funs/anonymous funs), MFA, erlang:apply/3: The calling code does not need to know anything about the library, just that it's something that needs to be called
Behaviours such as gen_server need the previous point to work
Hot reloading: You can upgrade the bytecode of any module without stopping the VM. The code server inside the VM maintains at most two versions of the bytecode for any module, redirecting external calls (those with the Module:) to the most recent version and the internal calls to the current version. That's why you may see some ?MODULE: calls in long-running servers, to be able to upgrade the code
You'd be able to argue that these points'd be available with more fine-grained BEAM-oriented visibility levels, true. But I don't think it would solve anything that's not solved with the facade modules, and it'd complicate other parts of the VM/code a great deal.
Bonus
Something similar applies to records and opaque types, records only exist at compile time, and opaque types only at dialyzer time. Nothing stops you from accessing their internals anywhere, but you'll only find problems if you go that way:
You insert a new field in the record, suddenly, all your {record_name,...} = break
You use a library that returns an opaque_adt(), you know that it's a list and use like so. The library is upgraded to include the size of the list, so now opaque_adt() is a tuple() and chaos ensues
Only those functions that are specified in the -export attribute are visible to other modules i.e "public" functions. All other functions are private. If you have specified -compile(export_all) only then all functions in module are visible outside. It is not recommended to use -compile(export_all).
I don't know of any existing convention for Erlang, but why not adopt the Python convention? Let's say that "library-private" functions are prefixed with an underscore. You'll need to quote function names with single quotes for that to work:
-module(bar).
-export(['_my_private_function'/0]).
'_my_private_function'() ->
foo.
Then you can call it as:
> bar:'_my_private_function'().
foo
To me, that communicates clearly that I shouldn't be calling that function unless I know what I'm doing. (and probably not even then)
Suppose I have a function (in Kotlin over Java):
fun <E> myFun() = ...
where E is a general type I know nothing about. Can I determine within this function whether there exists an extension function E.extFun()? And if so, how?
I very much doubt this is possible.
Note that extension functions are resolved statically, at compile time.
And that they're dependent on the extension function being in scope, usually via a relevant import. In particular, it's possible to have more than one extension function with the same name for the same class, as long as they're defined in different places; the one that's in scope will get called.
Within your function, you won't have access to any of that context. So even if you use reflection (which is the usual, and much-abused, ‘get out of jail free card’ for this sort of issue), you still won't be able to find the relevant extension function(s). (Not unless you have prior knowledge of where they might be defined — but in that case, you can probably use that knowledge to come up with a better approach.)
So while I can't say for certain, it seems highly unlikely.
Why do you want to determine this? What are you trying to achieve by it?
Where in the VB6/VBA project references do Array(), LBound(), and UBound() come from..? When I'm typing in code, they don't appear in the Autocomplete list (ctrl+space), they don't get autocompleted, and they must be typed out completely before the text editor recognizes them. And only when a left-parenthesis is typed will ToolTipText pop up with the command syntax. Also, they do not appear anywhere in Object Explorer.
There's probably a basic concept in play here that I'm not aware of. And it makes me wonder, what other commands/statements/keywords are hidden in the same way..? Is there a list somewhere..? I googled for info but didn't find anything, probably because I don't know what I'm looking for and using the wrong search terms.
I ask these questions because I have the habit of prefixing many VB6 built-in functions like this: VBA.Left(), VBA.Len, VBA.Instr(), and so on. But I can't figure out what reference prefeix to use with Array(), LBound(), and UBound(), or perhaps they're so basic to VB6 that they don't have one.
I do this prefixing because years ago I was working on a large project, and there were functions I was trying to use with the same name in different reference libraries. I was a newbie and it took me a while to figure out, and it was causing tremendous problems since the functions were just NOT working the way I thought they were supposed to. It was then that I developed the prefixing habit after I figured it out. It's just easier that way, and always ensures the expected functions are being used.
The reason that they don't appear as IntelliSense options (and also why they don't appear in the Object Browser) is that they aren't declared in the VBE7.dll typelib for some reason that's beyond me. The Array function is implemented in the .dll as rtcArray. The utility of knowing that is dubious, in that its sole argument is a ParamArray, which means that if you called it directly from VBE7.dll you would need to create an array to have it feed you back the same array... This partially explains why it isn't on the typelib - a COM call would need to do the same thing, and the marshaling would basically be doing the same thing as what you'd expect the function to return.
LBound and UBound don't even appear as functions in the export table, so my guess is that they are handled more like "keywords" than first class functions internally. This makes some sense, in that it's fairly trivial to check the bounds of a SAFEARRAY if you have a pointer to the automation struct (you just index into the rgsabound array at the end of it and read the cElements and lLbound from it. Again a guess, but I'd assume that this allows for flexibility in letting LBound and UBound function with both fixed length and variable length arrays. In the fixed case, the array is basically managed as a block of memory with an indexer (more like a VT_CARRAY than a VT_SAFEARRAY). I'd imagine that handling this internally was easier or more convenient than providing first-class functions.
You won't find Debug in the Object Browser either, nor its methods Assert and Print.
You won't find Statements that are used like methods, like Open, Close, Get and Put, which is why you don't get any Intellisense when you use those statements, and the syntax must be memorized.
You will find Load and Unload as members of VBA.Global, but it's not clear what they belong to otherwise, and their arguments are late-bound Objects. The VBA documentation states that Load and Unload are Statements, even though the Object Browser shows them as Methods.
Keep in mind that you can move the order of references and it will make a difference. Try moving VBA to the top or near the top of your list of references. I believe that if something else also defines a BASIC keyword, it steals it, in a sense. I once had Right disappear and because I was not aware of the order of references, had to change all references of Right to VBA.Right. It's possibly the same with the ubound, lbound, or array.
I'm working on an iOS app using C and Objective-C, and I want to write a very small piece of code that will be executed thousands of times from more than one place. Is it safe to make this an inline function and be sure that it will always be expanded (I won't ever be taking its address) or should I make it a macro? The code is small and it will be executed very frequently, so I'd like to make sure I won't end up with thousands of function calls for it, but still I'd like the type safety of the function approach if possible...
If you want to be sure that a function is inlined, make it "extern inline" (this is a GNU-C feature). Such functions are only used for inlining; the compiler will never generate a "real" function for it. Thus, if the inlining fails, you should be getting linker errors. I assume clang has "inherited" this feature.
In general, always use inline instead of macros, if possible. There's a reason why many C-compilers had it for ages, and C++ finally added it as a core feature; it makes things a lot safer and reliable to use. There are still things that need macros, but those are few and far between.
Yes, you should use an inline function over a macro.
The performance will be identical to a macro (the code is inline, after all) and you'll get type safety as well.
N.B., this assumes that your function is simple enough for the compiler to inline. gcc's -Winline option warns if this isn't the case; not sure what flags do the same on your platform.
Also see this post for cases when you might prefer a macro (e.g., deferred evaluation)--but based on your question it sounds like inline function is the clear choice.
I may be wrong, but I understand a compiler can only inline functions which are in the same source file. If your inline function is in file A and you're trying to use it elsewhere, it cannot be inlined, unless the linker does link-time optimization.
This is because the compiler only compiles one C file at a time into one object file. It cannot obtain the inlined function from another object file, because firstly, it may not yet have been compiled and secondly, it wouldn't know which object file to look for anyway.