Ack... I obviously am just not understanding packages. I look at how
the maths lib is written and it "exports" most of the things (lists
them in L). But that means (sign) is defined. So if I also use some
other library that defines a function (sign)... there's a name
conflict which I thought package was supposed to help avoid. So... I'm
confused.
Here's some more evidence of my confusedness. I'm using the clojure
port. I put the following in a file:
(package mypackage- []
(define main -> (output "hello"))
(define test X Y -> (+ X (* 789 (/ 1 5))))
(define doit -> (time (test 5 5)))
)
At the REPL:
(69-) (load "Test.shen")
mypackage-main
mypackage-test
mypackage-doit
run time: 0.07400000000006912 secs
loaded
(70-) (mypackage-test 5 5)
162.8
(71-) (mypackage-doit)
get-time does not understand the parameter mypackage-run
So... I take it that time is actually a macro? and it results in the
use of the symbol run which doesn't exist here. So, I have to exclude
it from the prefixing so the first line should be:
(package mypackage- [run]
Is that right?
Ah, thanks. I still have questions about packages:
It mentions that internal symbols are "hidden", but I can still access
them by including the package prefix on them, so how are they
"hidden"?
Test1.shen:
(package mypackage1- [commonName]
(define commonName -> (output "1"))
)
Test2.shen:
(package mypackage2- [commonName]
(define commonName -> (output "2"))
)
How can I access both versions of commonName? REPL session below
showing how loading the second overwrites the first.
Perhaps I need to take a step back and ask: if I'm writing a package
in a file and it needs to depend on various libraries, what is the
proper way of importing them?
I could see how one could possibly call (load filename), magically
figure out what package it just loaded, use (external pkgname) on that
and prepend a qualifier to all those symbols selectively maybe, but
that would need to run at compile time...
Shen 2010, copyright (C) 2010 Mark Tarver
www.lambdassociates.org, version 3.1
running under Clojure, implementation: Clojure 1.4.0-beta5 [jvm 1.6.0_26]
port 0.1.4 ported by Håkan Råberg
(0-) (load "Test.shen")
commonName
run time: 0.028999999999999915 secs
loaded
(1-) (commonName)
1"1"
(2-) (load "Test2.shen")
commonName
run time: 0.023999999999997357 secs
loaded
(3-) (commonName)
2"2"
But that's not what I asked. I want to know how I can access both at
the same time.
> Symbols that are declared external are supposed to be freely usable by
> all packages.
But what if they conflict? Thousands of people making various
libraries are going to export the same symbol name because they are
intended to be used. And when I need to use both libraries at the same
time, how do I do that?
maths already exports all its functions. So, if that convention is
followed, there are going to be a lot of conflicts.
Is this only a problem in the REPL or unpackaged program? You
mentioned something about how a package could access other packages in
a qualified way and so a packaged program could access both at the
same time?
How does one package state that it depends on another package so that
other package will be loaded and it's symbols become available (when
we're NOT working at the REPL)?
In short, I guess my question is: how does one write and organize an
application in Shen, like when I'm writing an application that may
have 10's or 100's of packages that have various dependencies with
each other and other libraries.
For that matter, is there even a way to run Shen outside the REPL yet.
Sorry... I read every page under Learning Shen and at least most of
the Shen Standard doc, if there is something else I should read
through that answers these questions, let me know.
Let's say P1 and P2 both have external symbol S. At this point, could
we prepend all P1's external symbols with "p1-" so when we run:
(load "P2.shen")
it doesn't redefine the prepended symbols and then we prepend all P2's
symbols with "p2-" and then...
> .......
> (load "Pn.shen")
> (package my-package- (append L (external P1) .... (external Pn))
And then here we list the prepended symbol lists (instead of just
(external P#)) we created above? So, now in our package we can access
both p1-S and p2-S.
The above would give us the "qualified import" functionality available
in many languages.
Thanks for your patience in helping me understand.
I was suggesting that as a proposal of how we might be able to solve
the problem. I need to access a function with the same name in P1 and
P2 from within my package P3. If you're saying that's impossible... it
makes no sense.
For example, right now I have a workspace open in which there are 1977
methods named "read" across all libraries. The likelihood that at some
point I'll need to access two of those from the same package is very
high. You might suggest they should not be declared external? But then
it's the case of whatever library author "gets there first"? For
example, maths exports the sign symbol. So that means that all future
users of Shen should never declare sign to be external or else others
won't be able to use their package at the same time as the maths
package?
I'm sorry to keep pursuing this, but this is really not making sense
to me. All other languages I have used provide a way to import things
from other packages and deal with conflicting names. So, I'm really
confused by the suggestion that that would not be possible.
It's many libraries--hundreds. And since they are written by different
authors, there's no way to coordinate who is "allowed" to externalize
"read" and who is not. As soon as one person has done so in Shen, he
makes it impossible for anyone else to do it.
> supposed to get into that awful state. Providing support tools for
> people to do bad things was not my goal. Library management means
> avoiding that mess.
So avoiding externalizing at all? Then why have that feature?
> What I'm saying is that it makes no sense to maintain a library where
> this happens because the point of making a symbol external is that you
> are saying 'This is unique and can be used freely in the REPL'.
But that is just one library author. There will be thousands of
library authors. And as soon as one of them externalizes a name, it
means that noone else can.
And I'm not talking about the REPL. The REPL is not really interesting
to me. It's useful during development, but you don't write
applications that way, do you? I understand Shen is kind of limited to
the REPL right now, but I'm looking forward to how I can write big
complex applications with it. And package/namespace management is a
crucial part of any such undertaking.
> I actually would incline to 'systemf' all external symbols of a package
> so that any programmer who did overwrite one definition with another
> in loading packages would raise an error and be required to actually
> change the code he is loading.
In what I'm discussing, you can't change the code you're loading. It's
written by someone
else, it's binary, it's not your code. That's like telling me I need
to go change the maths library every time I run into a conflict,
except I might not even have the source code to the library so it
would be impossible for me to change it even if I wanted to.
On Apr 6, 4:59 pm, Joel Shellman <j...@mentics.com> wrote:
> > The basic answer is that Shen does not have it because I would regard
> > it as extremely undesirable to have 1977 functions called 'read'
> > external across a library.
>
> It's many libraries--hundreds. And since they are written by different
> authors, there's no way to coordinate who is "allowed" to externalize
> "read" and who is not. As soon as one person has done so in Shen, he
> makes it impossible for anyone else to do it.
What you need here is a library management tool, not a package
management tool, to ensure that externalised symbols remain unique
within the library.
> So avoiding externalizing at all? Then why have that feature?
Because basic bread-and-butter functions like 'tan' are more usefully
invoked in that form rather than 'maths-lib-tan'. We try to avoid
cluttering up the namespace with auxiliary functions like 'tan-help'
etc.
> In what I'm discussing, you can't change the code you're loading. It's
> written by someone
> else, it's binary, it's not your code. That's like telling me I need
> to go change the maths library every time I run into a conflict,
> except I might not even have the source code to the library so it
> would be impossible for me to change it even if I wanted to.
The library is open source BSD.