On 2012-03-30 14:46:19 +0000, Andrei Alexandrescu
<SeeWebsiteForEmail@erdani.org> said:
> Destroy!
Since you're asking…
One thing the current system avoids is unresolvable symbols. If two
symbol name clashes, you just qualify them fully and it'll always be
unambiguous. For instance:
.std.algorithm.sort(…)
Now, if std.algorithm becomes both a module and a package, you could
have both a sort function and a sort submodule with no way to
distinguish between the two, even when fully qualified. I think this is
why D does not allow modules to have the same name as packages.
I understand that you try to work around this problem by inventing a
.std.algorithm.package scope. Then you make it's content imported
automatically inside the .std.algorithm scope for backward
compatibility (and convenience). The problem is that if
.std.algorithm.package contains a sort function and there is also a
module called std.algorithm.sort, the fully-qualified name of that
'sort' module will become ambiguous. Moreover, whether the
fully-qualified name .std.algorithm.sort is ambiguous or not depends on
what modules were imported, which is not a very desirable behaviour.
So to make sure there is no unresolvable fully-qualified names, when
importing std.algorithm.sort the compiler should make sure that no
symbol called 'sort' already exist in the .std.algorithm scope (which
includes the symbols in .std.algorithm.package and all other packages
inside std.algorithm). This is clearly untenable.
- - -
I recognize the need. If I may, I'll propose something simpler:
1. allow both std/algorithm.d and std/algorithm/sort.d to exist
2. importing std.algorithm.sort will also implicitly import
std.algorithm (if it exists) and std (if it exists)
3. if any symbol of std.algorithm clash with the std.algorithm.sort
module name, you get an error when importing std.algorithm.sort.
Effectively, importing std.algorithm.sort becomes synonymous to
importing std, std.algorithm, and std.algorithm.sort. This is what's
needed to detect clashes in fully-qualified names.
The only issue now (beside a few more imports) is that if std.algorithm
imports any of its submodule it becomes a circular import. That's
usually fine in D, but not when you have module constructors.
--
Michel Fortin
michel.fortin@michelf.com
On Fri, Mar 30, 2012 at 05:35:25PM -0400, Jonathan M Davis wrote:
[...]
>.
[...]
+1.
I also have my doubts about the wisdom of std.sort implicitly binding to
std.algorithm.sort. It's nice syntactic sugar in the short term, but as
Jonathan points out, it can cause headaches in the long term. I say we
should hold off on that part of the proposal.
T
--
Microsoft is to operating systems & security ... what McDonalds is to gourmet cooking.
On 3/30/12 10:46 PM, Andrei Alexandrescu wrote:
> Starting a new thread from one in announce:
>
>
>
> Please comment, after which Walter will approve. Walter's approval means
> that he would approve a pull request implementing DIP16 (subject to
> regular correctness checks).
Great. Large modules are my main complaint about D. :-)
If I correctly understand the second part (because I couldn't understand
the text in the proposal until I read some comments here), then it makes
sense. Is it like this?
sort(...) -> search sort in every module out there
std.sort(...) -> search sort in every module that's in the std package
If both std.algorithm.sort and std.path.sort exist, or something like
that, then you would anyway get a clash so you'd have to fully qualify it.
But if std.algorithm.sort and foo.bar.sort and you'd import both:
import std.algorithm.package;
import foo.bar.package;
and you'd wanted to use both, then it could be convenient:
std.sort(...)
foo.sort(...)
Though I wonder if this indeed happens a lot. That's why I would wait
until there's a real need for it. The main complaint people have is not
having a way to import all files in a directory, which is the first
point, but I never heard a complaint about the second point.
Also, I think it would make sense to change the first part to this:
* If the compiler sees a request for importing "foo.bar" and "foo/bar"
is a directory, then automatically look for the file
"foo/bar/package.d". *If it doesn't exist, automatically expand the
import to import all files under that directory.* If both "foo/bar.d"
and "foo/bar/" exists, compilation halts with an error.
That way you have convenience and safety. Most of the time people just
put in package.d a list of all the files in that directory. Maybe
sometimes (not sure) people restrict that list to some modules. And in
those cases you can just restrict the list in package.d
Please, it's the year 2012. Compilers need to be smarter. Save people
some typing time. You save them typing all the imports. But then you
make them typing them in that pacakge.d file. Hmm....
----------
Chris NS

>
> I'm not sure whether I favor them losing or keeping their "friend" status.
>
There's always the "package" access specifier.
On Saturday, 31 March 2012 at 06:39:07 UTC, Nick Sabalausky wrote:
> .
>>
>
> There's always the "package" access specifier.
True, though it bears revisiting in its own right. I've never
been completely satisfied with the horizontal visibility, and
would have preferred 'package' be defined as "visible within
current package, *and subpackages* of the current." But now I'm
getting a bit off-topic.
On Sat, 31 Mar 2012 01:46:19 +1100, Andrei Alexandrescu
<SeeWebsiteForEmail@erdani.org> wrote:
> Starting a new thread from one in announce:
>
>
>
We solved this issue in the Euphoria Programming language by introducing
the concept of 'public include'.
The 'include' directive is similar to DPL's 'import' directive. Normally
when a file (module) is included, its public identifiers are *only*
visible to the including module and not further module up the include
tree. However, if a module is 'public include'd then its public
identifiers are set up *as if* they were actually declared in the
including module rather than the included module.
Thus if Euphoria's module called datetime.e gets too large, we split it
into, say two or three new modules and replace the code in datetime.e with
corresponding 'public include' statements, thus making it a type of
package definition. This means that existing application code does not
have to be modified and future code can choose to include either the
entire package called datetime.e or individual modules that go into making
that package.
From the POV of a developer, creating a package out of what was a module
is transparent. They do not even know or have to care in order to use it.
There are no complicated access rules that can one day trip people up.
We made one tweak to the public identifier declaration though to cater for
situations in which an identifier which was currently local to a module,
but when moved to a new module when the original was transformed to a
package, still had to be visible to the code in the package file but
invisible to code including the package. We created the 'export' qualifier
on an identifier declaration to signal such an item.
Original module code ...
function to_seconds(datetime x) /* A local function to the module */
public function local_to_gmt(datetime x) /* A publicly exposed function
*/
New module code ...
export function to_seconds(datetime x) /* A function visible to the
package file only */
public function local_to_gmt(datetime x) /* A publicly exposed function
*/
This means that application that include the package datetime.e will not
see to_seconds() but code in the datetime.e will see it, and
local_to_gmt() will be seen by the application code and the package code.
--
Derek Parnell
Melbourne, Australia.
On Friday, 30 March 2012 at 14:46:16 UTC, Andrei Alexandrescu
wrote:
> Starting a new thread from one in announce:
>
>
>
> Please comment, after which Walter will approve. Walter's
> approval means that he would approve a pull request
> implementing DIP16 (subject to regular correctness checks).
>
>
> Destroy!
>
> Andrei
Hooray! I was loudly complaining about this issue for years. I'm
glad this is finally going to be taken care of.
1. Regarding naming - as others mentioned it's inconvenient for
sorting. How about changing the file extension instead of the
name? e.g have a "algorithm.package" instead of "algorithm.d"?
The compiler could even ignore the name of the file as long as it
has the proper extension - check for existence of "*.package".
The compiler should enforce that there's at most one such package
file to prevent ambiguities - regardless of the chosen naming
scheme.
2. Regarding documentation - I'd encourage (via a D style
guideline) putting the overview of the package in this file. A
tool such as Ruby's codnar would nicely compliment the reference
generated by DDoc. see
for details.
3. std.algorithm should be deprecated and eventually removed. All
code *is* essentially algorithms and as such importing this
module makes as much sense as doing:
import code; // generic much?
4. regarding the look-up rules - I'm unsure about this part of
the proposal. Others already voiced concerns about issues this
might bring.
On Sat, 31 Mar 2012 13:06:36 +0200, Timon Gehr <timon.gehr@gmx.ch> wrote:
>.
That already works, doesn't it?