import HTML.App as Html - elm

The elm tutorial at http://guide.elm-lang.org/architecture/user_input/buttons.html has these lines:
import Html exposing (Html, button, div, text)
import Html.App as Html
I do not understand what the name Html references as the result of these imports. Is it Html.App or the function from Html package? And why.

import Html exposing (Html)
exposes the identifier Html in two different namespaces.
The Html coming from the brackets part is a type. It's qualified name is Html.Html and it can only appear in Type signatures.
The Html module which can only appear as a qualifier. Hence you could write Html.img and this refers to the part immediately after the import keyword.
Finally,
import Html.App as Html
imports the Html.App module and also gives it a local alias of Html. These don't shadow each other but as long as the actual function names are different in each module the compiler will resolve these correctly for you.
I generally avoid aliasing to the same thing since it makes the code confusing for me. But the compiler deals with it no problem.

Here is my understanding...
if Html is used alone then it refers to a type defined
inside of Html module, and it can be used alone because
it is exposed by import directive.
(i.e. Html.Html)
Html.xx (xx is arbitrary, whichever Html.App module exposes)
is xx exposed by module Html.App (i.e. Html.App.xx).
And it cannot be used alone, because it is not imported with
name spacing with a word Html.
Note that, a period . can only be name-spacing operator if
the left-side word starts with a capital letter.
And, only value (has to starts with a lower-case letter) can have properties, where . can also be used.
(ModuleName.TypeName vs recordValue.property)
So, it is not ambiguous.
But, if two modules expose same name
(e.g. Html.xx and Html.App.xx)
, then xx can become ambiguous
and compiler would complain.
for example, when Html modules is imported with exposing (..)
I hope it makes sense...

TL;DR:
If there is just Html, it's the type (originally Html.Html).
But if there's . after it, it's a module name and you can take definitions from both Html and Html.App modules by doing Html.something.
More in detail:
The result of import Html is that you can access Html.whateverHtmlExposes.
The result of the exposing (Html, button, div, text) is that you can write
Html instead of Html.Html (the type),
button instead of Html.button (function),
etc.
The result of import Html.App would be that you can access Html.App.whateverHtmlAppExposes, BUT because of the as Html part you can now write it like Html.whateverHtmlAppExposes.
Don't worry about conflicts - the compiler will warn you in that case:
-- NAMING ERROR ---------------------------------------------------------- C.elm
This usage of variable `A.x` is ambiguous.
9| Html.text A.x
^^^
Maybe you want one of the following?
A.x
B.x
Detected errors in 1 module.
Here I have imported B as A, both modules have x exposed:
A.elm
module A exposing (x)
x = "x from A"
B.elm
module B exposing (x)
x = "x from B"
C.elm
module C exposing (..)
import A
import B as A
import Html
main = Html.text A.x

import Html.App as App
Its basically importing the application from html package. These functions will help you set up an Elm program that follows the Elm Architecture, a pattern for creating great code that stays great as your project grows.

Related

How to import theorems from Coq.Numbers.NatInt.NZDiv?

In this doc link there are useful theorems about division. I tried importing it using Require Import in CoqIDE 8.9.0, however while the import succeeds, the following code fails with The reference div_lt_upper_bound was not found in the current environment.
Require Import Coq.Numbers.NatInt.NZDiv.
Check div_lt_upper_bound.
I tried downloading the source code for the file and manually importing it via Load, but then I get the following message with no further explanation (the first line is in red):
Application of a functor with too few arguments.
Interactive Module Type DivMod started
div is declared
modulo is declared
Module Type DivMod is defined
Interactive Module Type DivModNotation started
Module Type DivModNotation is defined
Module Type DivMod' is defined
Interactive Module Type NZDivSpec started
div_mod is declared
mod_bound_pos is declared
Module Type NZDivSpec is defined
Module Type NZDiv is defined
How do I load those theorems properly? Why did the previous methods not work?
The quick answer is that you are looking at the Module Type (see Print NZDivProp.).
The actual usage is simple, e. g.
Require Import Arith.
Check Nat.div_lt_upper_bound.
(*
Nat.div_lt_upper_bound
: forall a b q : nat, b <> 0 -> a < b * q -> a / b < q
*)

Can I import just one declaration from an F# module?

Suppose I have a module like this:
module Foo
let x = 1
let y = 2
Now I can use this module like this:
module Bar
let z = Foo.x + Foo.y
Is it possible to import a definition from Foo such that it does not need to be qualified?
Something like:
module Bar
import x from Foo // Not real code
let z = x + Foo.y // x need not be qualified
Note that I do not want to import everything from Foo
You cannot, there is no direct F# equivalent to the ES6 import { ... } from 'Module' syntax. F# supports organizing code into both modules and namespaces, but both modules and namespaces are 'imported' in their entirety with the open keyword. As mentioned in the comments, you can use local bindings to simplify qualified access to values (such as let exchangeRange = Conversions.Currency.UsdToCadExchangeRate) or type aliases to simplify qualified access to types (type Converter = Conversions.Currency.CurrencyConverter).
In addition, modules can be marked with the [<AutoOpen>] attribute to make their contents accessible without qualified access, or the [<RequireQualifiedAccess>] attribute to make their contents accessible only when qualified, even if the module is referenced in an open expression.
See this MSDN article for more information.

Two Modules, both exporting the same name

There are two packages I want to use: CorpusLoaders.jl, and WordNet.jl
CorpusLoaders.SemCor exports sensekey(::SenseTaggedWord)
WordNet exports sensekey(::DB, ::Synset, ::Lemma)
I want to use both sensekey methods.
Eg
for some mixed list of items: mixedlist::Vector{Union{Tuple{SenseTaggedWord},Tuple{DB, Synset,Lemma}}.
Ie the items in the list are a mixture of 1-tuples of SenseTaggedWord, and3 tuples of DB, Synset, and Lemma.
for item in mixedlist
println(sensekey(item...)
end
should work.
This example is a little facetious, since why would I be mixing them like this.
But, hopefully it serves for illustrating the problem in the general case.
Trying to using CorpusLoaders.SemCor, WordNet to bring in both results in WARNING: both WordNet and Semcor export "sensekey"; uses of it in module Main must be qualified.
Manually importing both: import CorpusLoaders.SemCor.sensekey; import WordNet.sensekey results in WARNING: ignoring conflicting import of Semcor.sensekey into Main
What can be done? I want them both, and they don't really conflict, due to multiple-dispatch.
Given that CorpusLoaders.jl is a package I am writing I do have a few more options, since I could make my CorpusLoaders.jl depend on WordNet.jl.
If I did do than then I could say in CorpusLoaders.jl
import WordNet
function WordNet.sensekey(s::SenseTaggedWord)...
and that would make them both work.
But it would mean requiring WordNet as a dependency of CorpusLoaders.
And I want to know how to solve the problem for a consumer of the packages -- not as the creator of the packages.
tl;dr qualify the functions when using them in your script via their module namespace, i.e. CorpusLoader.sensekey() and WordNet.sensekey()
Explanation
My understanding of your question after the edits (thank you for clarifying) is that:
You have written a package called CorpusLoaders.jl, which exports the function sensekey(::SenseTaggedWord)
There is an external package called WordNet.jl, which exports the function sensekey(::DB, ::Synset, ::Lemma)
You have a script that makes use of both modules.
and you are worried that using the modules or "importing" the functions directly could potentially create ambiguity and / or errors in your script, asking
how can I write my CorpusLoaders package to prevent potential clashes with other packages, and
how can I write my script to clearly disambiguate between the two functions while still allowing their use?
I think this stems from a slight confusion how using and import are different from each other, and how modules create a namespace. This is very nicely explained in the docs here.
In essence, the answers are:
You should not worry about exporting things from your module that will clash with other modules. This is what modules are for: you're creating a namespace, which will "qualify" all exported variables, e.g. CorpusLoaders.sensekey(::SenseTaggedWord).
When you type using CorpusLoaders, what you're saying to julia is "import the module itself, and all the exported variables stripped from their namespace qualifier, and bring them into Main". Note that this means you now have access to sensekey as a function directly from Main without a namespace qualifier, and as CorpusLoaders.sensekey(), since you've also imported the module as a variable you can use.
If you then try using the module WordNet as well, julia very reasonably issues a warning, which essentially says:
"You've imported two functions that have the same name. I can't just strip their namespace off because that could create problems in some scenarios (even though in your case it wouldn't because they have different signatures, but I couldn't possibly know this in general). If you want to use either of these functions, please do so using their appropriate namespace qualifier".
So, the solution for 2. is:
you either do
using CorpusLoaders;
using WordNet;
, disregarding the warning, to import all other exported variables as usual in your Main namespace, and access those particular functions directly via their modules as CorpusLoaders.sensekey() and WordNet.sensekey() each time you need to use them in your script, or
you keep both modules clearly disambiguated at all times by doing
import CorpusLoaders;
import WordNet;
and qualify all variables appropriately, or
in this particular case where the function signatures don't clash, if you'd really like to be able to use the function without a namespace qualifier, relying on multiple dispatch instead, you can do something like what FengYang suggested:
import CorpusLoaders;
import WordNet;
sensekey(a::SenseTaggedWord) = CorpusLoader.sensekey(a);
sensekey(a::DB, b::Synset, c::Lemma) = WordNet.sensekey(a, b, c);
which is essentially a new function, defined on module Main, acting as a wrapper for the two namespace-qualified functions.
In the end, it all comes down to using using vs import and namespaces appropriately for your particular code. :)
As an addendum, code can get very unwieldy with long namespace qualifiers like CorpusLoader and WordNet. julia doesn't have something like python's import numpy as np, but at the same time modules become simple variables on your workspace, so it's trivial to create an alias for them. So you can do:
import CorpusLoaders; const cl = CorpusLoaders;
import Wordnet; const wn = WordNet;
# ... code using both cl.sensekey() and wn.sensekey()
In this case, the functions do not conflict, but in general that is impossible to guarantee. It could be the case that a package loaded later will add methods to one of the functions that will conflict. So to be able to use the sensekey for both packages requires some additional guarantees and restrictions.
One way to do this is to ignore both package's sensekey, and instead provide your own, dispatching to the correct package:
sensekey(x) = CorpusLoaders.sensekey(x)
sensekey(x, y, z) = WordNet.sensekey(x,y,z)
I implemented what #Fengyang Wang said,
as a function:
function importfrom(moduleinstance::Module, functionname::Symbol, argtypes::Tuple)
meths = methods(moduleinstance.(functionname), argtypes)
importfrom(moduleinstance, functionname, meths)
end
function importfrom(moduleinstance::Module, functionname::Symbol)
meths = methods(moduleinstance.(functionname))
importfrom(moduleinstance, functionname, meths)
end
function importfrom(moduleinstance::Module, functionname::Symbol, meths::Base.MethodList)
for mt in meths
paramnames = collect(mt.lambda_template.slotnames[2:end])
paramtypes = collect(mt.sig.parameters[2:end])
paramsig = ((n,t)->Expr(:(::),n,t)).(paramnames, paramtypes)
funcdec = Expr(:(=),
Expr(:call, functionname, paramsig...),
Expr(:call, :($moduleinstance.$functionname), paramnames...)
)
current_module().eval(funcdec) #Runs at global scope, from calling module
end
end
Call with:
using WordNet
using CorpusLoaders.Semcor
importfrom(CorpusLoaders.Semcor, :sensekey)
importfrom(WordNet, :sensekey)
methods(sensekey)
2 methods for generic function sensekey:
sensekey(db::WordNet.DB, ss::WordNet.Synset, lem::WordNet.Lemma)
sensekey(saword::CorpusLoaders.Semcor.SenseAnnotatedWord
If you wanted to get really flash you could reexport the DocString too.

Exposing and importing a data constructor from another module

In my Elm program I want to define a type in one module:
MyModule.elm:
module MyModule exposing (MyType)
type MyType = Constr1 String | Constr2 Int
and construct a value of this type in another module:
Main.elm:
import MyModule exposing (MyType)
import Html exposing (text)
main =
let x = Constr1 "foo" in
text "hello"
When I build this with:
elm-package install elm-lang/html && elm-make Main.elm
I get:
NAMING ERROR ------------------------------------------------------- Main.elm
Cannot find variable `Constr1`
6| let x = Constr1 "foo" in
^^^^^^^
Detected errors in 1 module.
If I use (..) in both exposing clauses, this compiles fine, but I would like to know how to express that I want to expose the constructors.
Side note: I would also like to know where I should have found this in the docs.
You can specify which constructors to expose like this:
module MyModule exposing (MyType(Constr1, Constr2))
All constructors of a type can be exposed using (..) notation:
module MyModule exposing (MyType(..))
And if you don't want to expose any constructors (meaning you have other exposed functions that create values of your type, you specify only the type:
module MyModule exposing (MyType, otherFunctions)
There is community documentation around this topic at elm-community.github.io/elm-faq

Import module into current scope?

The modules have very long names (they make names of the imported functions three times longer then needed), for example: mapconcat looks Project.Utils.mapconcat is there any way to import this function and use it w/o fully qualifying it by the module name?
You can always do :
var x = Project.Utils.mapconcat;
// now use x in place of mapconcat
PS: you can use the import statement to create an alias for a module
import pu = Project.Utils;
// now:
pu.mapconcat
This is assuming Utils is a module name (and not a class).