> > > > I sometimes just use #- to comment out a function or method > > > > (as opposed to #| ... |#). Is this legal ANSI Common Lisp? > > > > I'm running Allegro 6.0 which is happy with the #- form > > > > with no explicit feature mentioned. MCL complains when > > > > loading the same file.
> [snip ...]
> > > So, the bottom line is:
> > > Fix your code, if you want it to be portable...
> > This may indeed be the bottom line, but unless/until we get clarification > > from Larry Kramer as to what he was trying to do and assuming, we will not > > know if it is programmer error or a bug in MCL.
> Erik in the first reply to my posting identified exactly what > I was trying to do and why it was incorrect. Basically, I > was being lazy and misunderstood the spec in terms of > feature expressions. I was trying to comment out a function using > #-, assuming that since it was followed by whitespace, it would > be taken as some sort of universal "ignore what follows." (Don't > know how I came upon this idea...)
OK, thanks for the clarification. I was wrong in my guess as to what you were trying to do. The most commonly used (though not foolproof) method of such commenting is to use a feature that you don't expect to be defined in your lisp.
> The form following a #- (irrespective of whitespace as Duane points out) > is read as the feature expression. As 24.1.2.1 in the spec reads, > feature expressions should be a boolean combination of features.
> Here's an example of what I (incorrectly) was doing, > in order to textually retain the first definition of > func, while using the second definition:
> #- > (defun func () <some-code-here>)
> (defun func () <new-definition-of-code-here>)
> Bottom line, here's what I'll do in the future:
> #| > (defun func () <some-code-here>) > |#
> (defun func () <new-definition-of-code-here>)
In cases where you are defining a new version of the same function, but want to keep the old one around in case the new one breaks your testing badly, you might want to consider the #-never / #+never trick that we use; it allows rapid switching back and forth. So, for example,
#+never (defun func () <this is the old code>)
#-never (defun func () <this is the newer, experimental code>)
> I'll leave it up to others to decide whether Allegro or > MCL should've barfed in the first place. (Sorry, my colleague > is not in yet today, so I don't have access to the exact error > that MCL gave, although I do remember that it reported it as > a "syntax error.")
The answer is, it is undefined - you _cannot_ count on either behavior.
As for why Allegro CL doesn't barf on #-(some-random-symbol), I'll take you through it:
1. Allegro CL defines a number of functional extensions to Feature Extensions. The most notable example is :version>= - it allows conditional reading of a form based on the version nuumber of Allegro CL. So, for example,
will only define the function foo if in an Allegro CL of version 6.2 or greater.
2. Note the preliminary test for :allegro-version>= - this test is recommended for portable code, because the AND expression should kick out of any lisp that doesn't have :allegro-version>= on the *features* list, so the version>= expression should never be evaluated. This allows these extensions to be used in source code that is ported between Allegro CL and other CLs.
3. Next, because Feature Expressions are recursively defined, the expression (version>= 6 2) is itself a Feature Expression. You wouldn't want to say #(version>= 6 2) (defun foo () 'foo) in portable code, but it is legal with our extension.
4. Finally, the decision not to call out an error when a Feature Expression is not recognized was made based on a Good Neighbor policy: if our reader reads a Feature Expression it doesn't recognize, chances are that it is some other implementation's own extension, and chances are again that the actual feature was meant for that implementation only, so we interpret it that way and count the Feature Expression as having failed.
Kent Pitman already pointed out elsewhere in this thread that there is a Lisp called NIL, and :nil is a perfectly valid feature, and thus is not a good feature to use as a never-defined feature.
The world rejoiced as Erik Naggum <e...@naggum.no> wrote:
> * Paul F. Dietz > | Doesn't this feature expression always fail: (or) > | and this one always succeed: (and)?
> Good catch! This is a much better way than to use random names.
> Norwegian offers a useful word to remember this. "Avisand" is > used for an untrue news item (avis = newspaper, and = duck), often > abbreviated to just "and". #-(and) could be read as "ignore this > mistake". Maybe.
OK, so this means it's necessary to be literate in Norwegian to understand _wrong_ Lisp code?
I think that makes a whole lot of flame wars make totally a lot more sense... -- (reverse (concatenate 'string "gro.gultn@" "enworbbc")) http://cbbrowne.com/info/oses.html They are called computers simply because computation is the only significant job that has so far been given to them. -- Louis Ridenour
Erik Naggum <e...@naggum.no> wrote: > I disagree profoundly. I think Paul's observation is insightful and clever. > Although a naive reader may be stumped upon seeing (or) used for `nilī, > (and) used for `tī, (+) for 0, and (*) for 1, I imagine it would yield a > very pleasant, mathematical realization of the trivial case for these > operators. I certainly smiled in appreciation upon reading Paul's > article. > Once internalized, this becomes an idiom that is not at all obscure.
It is clever, but strange. Until you posted this, my intuition thought that (or), if it yielded anything, should yield true, and (and) false.
Now, I see that it's getting the identity of the operator, which makes a kind of sense, but I'm not sure I'd ever guess it. I don't see any reason why using an operator with no arguments should necessarily return anything. Is this is the spec, or is there some mathematical basis/use that I'm missing?
Michael
-- Michael Sullivan Business Card Express of CT Thermographers to the Trade Cheshire, CT mich...@bcect.com
mich...@bcect.com (Michael Sullivan) writes: > Erik Naggum <e...@naggum.no> wrote:
> > I disagree profoundly. I think Paul's observation is insightful and clever.
> > Although a naive reader may be stumped upon seeing (or) used for `nilī, > > (and) used for `tī, (+) for 0, and (*) for 1, I imagine it would yield a > > very pleasant, mathematical realization of the trivial case for these > > operators. I certainly smiled in appreciation upon reading Paul's > > article.
> > Once internalized, this becomes an idiom that is not at all obscure.
> It is clever, but strange. Until you posted this, my intuition thought > that (or), if it yielded anything, should yield true, and (and) false.
> Now, I see that it's getting the identity of the operator, which makes a > kind of sense, but I'm not sure I'd ever guess it. I don't see any > reason why using an operator with no arguments should necessarily return > anything. Is this is the spec, or is there some mathematical basis/use > that I'm missing?
You can define operators any way you want, of course. But as it turns out, it is often useful to define operators in a way that they return a neutral element when applied to zero arguments. For instance,
\sum_{i=1}^n i = n(n+1) / 2
is true even for 0, if you define an empty sum to be zero,
\prod_{i=1}^n i = n!
is true even for 0 if you define an empty product to be one. There are many more examples. 0 is the neutral element for addition, 1 for multiplication. Now,
(and x y) is always the same as (and t x y)
and
(or x y) is always the same as (or nil x y).
That's why I'd expect (or) to be nil, and (and) to be t.
Also, you might argue: ``If (and) was false, then there should be one argument of AND which is false (but there isn't)''. And ``If (or) was true, there should be one argument of OR that is true (but there isn't).''
Something like that.
Regards, -- Nils Goesche "Don't ask for whom the <CTRL-G> tolls."
(Occasionally I have used things like LOSER, LOSSAGE, UNIMPLEMENTED, NEVER, and ALWAYS, but only temporarily -- not in real code.)
How about just testing *FEATURES* in the SYSDCL (whatever your implementation does for that) to make sure that :IGNORE isn't there? You won't compile or load on platforms that have defined that feature, but at least there will be no mystery.
Here's a can of worms for ya: Maybe a good practice would be to say that feature names should always be qualified names (like Java packages). That's not a complete suggestion, of course; let's play with this idea.
In article <ubs7tqpy6....@dtpq.com>, Christopher C. Stacy <cst...@dtpq.com> wrote:
>I have always used #+IGNORE and #+DEBUG.
>(Occasionally I have used things like LOSER, LOSSAGE, UNIMPLEMENTED, >NEVER, and ALWAYS, but only temporarily -- not in real code.)
>How about just testing *FEATURES* in the SYSDCL (whatever your >implementation does for that) to make sure that :IGNORE isn't there? >You won't compile or load on platforms that have defined that feature, >but at least there will be no mystery.
>Here's a can of worms for ya: Maybe a good practice would be to say >that feature names should always be qualified names (like Java packages). >That's not a complete suggestion, of course; let's play with this idea.
Instead of putting restrictions on the names of legit features, I would use something like
<programmer-name>-sez-ignore-this
(where <programmer-name> is a metavariable of course) for the bogus feature name that marks the #+ comment.
It is instantly recognizable as a comment to the code-browsing eye, and it lets one track down who's responsible for the comment. It is also highly unlikely, even unlikelier than are `ignore' and `debug', to be in *features*. I doubt that even Kent Pitman at his most counterexample-happy can find a scenario where symbols like this have good reason to be in *features*.
Michael Sullivan wrote: > Erik Naggum <e...@naggum.no> wrote:
>> I disagree profoundly. I think Paul's observation is insightful and clever.
>> Although a naive reader may be stumped upon seeing (or) used for `nilī, >> (and) used for `tī, (+) for 0, and (*) for 1, I imagine it would yield a >> very pleasant, mathematical realization of the trivial case for these >> operators. I certainly smiled in appreciation upon reading Paul's >> article.
>> Once internalized, this becomes an idiom that is not at all obscure.
> It is clever, but strange. Until you posted this, my intuition thought > that (or), if it yielded anything, should yield true, and (and) false.
> Now, I see that it's getting the identity of the operator, which makes a > kind of sense, but I'm not sure I'd ever guess it. I don't see any > reason why using an operator with no arguments should necessarily return > anything. Is this is the spec, or is there some mathematical basis/use > that I'm missing?
> Michael
One thing that I noticed while reading this is that if you consider the above functions to be the binary operators of a group, then the result of not giving the function any arguments is the identity element. But you don't need to know anything about groups to see the pattern:
(or nil n) => n (and t n) => n (+ 0 n) => n (* 1 n) => n
(I only picked this up because one of the things that I am studying at the moment is group theory...)
* Erik Naggum | Once internalized, this becomes an idiom that is not at all obscure.
* Frode Vatvedt Fjeld | Isn't this statement is true by definition?
No. You can internalize something that still remains obscure, not only to others, but to yourself. That is, some things never progress beyond passive vocabulary. Some image that you understand when you meet it, but it takes effort to /remember/ how works, is not used. #-(and) immediately makes so much sense that it becomes part of your active vocabulary. I think of this the same way I think of string theory (not the character strings :). It is very hard for me to read and follow, and my brain just drops it after a few months so I no longer even remember that I grasped something when I pick up a new paper. There is no lack of understanding on my part when I immerse myself in it for the umpteenth time, but it runs counter to my intuition in a weird way that makes me always stand outside and look in. I have not yet been able to /enter/ the world of string theory in a way that stays with me when I put down another excellent article or book on it.
| Anything one takes the trouble to internalize becomes obvious.
If you can say this, you have only tried with easy things. The curse of high intelligence is that you think /all/ things are easy and are unprepared for the really hard things. People of lesser intelligence have been used to dealing with things they do not understand all their lives, and they have learned to deal with this in ways that very smart people can never dream of grasping. The kinds of things that you /cannot/ wrap your head around are the real defining attributes of your intelligence.
| But in this case and context I don't see any reason to take that trouble.
I think you are still looking at it from outside. That (+) => 0, etc, are such marvelously elegant things that I embrace them immediately.
| And also, I believe that even if (and) and (or) are internalized as general | concepts, #+ignore would still be more readable as a commenting mechanism.
Not if you think about it, which you should. "Conditionalize this expression on the presence of the feature called IGNORE" is /actually/ obscure -- but you have internalized it in /spite/ of its meaning. I think it is much better to have a real feature and conditionalize on its absence. E.g., in Allegro CL source, I would much rather see #-allegro than #+ignore. In comforming code, you could write #-common-lisp and know that it would never be read because if you write Common Lisp at all, it /will/ be present.
I used to not care about #+ignore, but now I do not care /for/ it. It is a misguided abuse of the feature mechanism that overloads natural language semantics on the name of a feature and that conflates several concept spaces in /unnatural/ ways. If you think /in/ Common Lisp, you would not invent this thing. You would invent #+(or) or #-common-lisp, instead.
-- Erik Naggum, Oslo, Norway
Act from reason, and failure makes you rethink and study harder. Act from faith, and failure makes you blame someone and push harder.
* Christopher C. Stacy | How about just testing *FEATURES* in the SYSDCL (whatever your | implementation does for that) to make sure that :IGNORE isn't there? | You won't compile or load on platforms that have defined that feature, | but at least there will be no mystery.
How about testing for something you know is there, instead? That way, you are actually always safe.
-- Erik Naggum, Oslo, Norway
Act from reason, and failure makes you rethink and study harder. Act from faith, and failure makes you blame someone and push harder.
* Duane Rettig | Another way to look at it: If I had a CL program and it suddenly broke because | I loaded in a module that pushed :scheme onto the *features* list, then I would | have much less justification for being upset than if I had been using #+ignore | or #+never and someone just stupidly pushed one of these onto *features*.
FWIW, I think it is stupid to rely on names out of your control. Since you control a whole bunch of features yourself, there are many ways to ensure that you test for something that you know is there instead of believe will not be there. For the "future" case, you could also use a future version of Allegro CL. Suppose you will never have code for Allegro CL 10.0 while you are working on Allegro CL 6.3 and 7.0 and perhaps 8.0. You could write
#+(version>= 10 0) for-further-study
to signal to your developers that this is way into the future. You could also use this mechanism to ensure that features were included in a future version despite the cvs branch it was inserted on. Going through the code to find places where a future version were specified would be a good way of ensuring that those future things were indeed brought into the present.
Using a feature like debug-<package> would be OK, however, since it would presumably be code that would actually be processed if you requested debugging of that package.
This discussion has changed my view on #+ignore and the like. From not having an opinion on it to having an actual opinion on it, I have come to think it is wrong to use /any/ non-existing feature as a marker that some code should not be processed, and in particular that overloading natural language semantics on formal constructs is a form of intellectual sloppiness that should be avoided.
-- Erik Naggum, Oslo, Norway
Act from reason, and failure makes you rethink and study harder. Act from faith, and failure makes you blame someone and push harder.
* Duane Rettig | The most commonly used (though not foolproof) method of such commenting is | to use a feature that you don't expect to be defined in your lisp.
Argh! This is so dumb. Think about it. You remove a truly large fraction of your vocabulary from possible feature names. Think of all the synonyms that various programmers will use for this out of the misguided notion that feature names "mean" something. They should have the meaning that the thing they /name/ have. If you want to exclude something, you should do so based on something you /can/ know, not something you /hope/ you may know, but are only guessing about. In this age of multiculturalism and such, consider the mess if you run the whole gamut of Roget's-equivalents in all languages where people use Common Lisp, and you find that there is a significant risk of naming your feature something that "means" something in some other language, and obvious words can no longer be used for features because some idiot may have used it for a conditional. That is just /wrong/. Let me put this intensely: Never say #+never!
I think Franz Inc code should use #-franz or something, and portable code should use #-common-lisp to exclude code that is never going to be parsed. This if fool-proof. If someone steals your code and they do not define the franz feature in time, you also get the extra benefit of taking revenge.
If your application includes a feature symbol on `*features*ī, then you can use that symbol to exclude code, too. E.g., if you write an application that pushes the (legal) feature lex-nemini-facit-injuriam on `*features*ī, you actually /know/ that this feature will be there in your application, and since you control this yourself, you can use #-lex-nemini-facit-injuriam to argue that some code violates this feature, i.e., it would do injury if that feature was absent.
-- Erik Naggum, Oslo, Norway
Act from reason, and failure makes you rethink and study harder. Act from faith, and failure makes you blame someone and push harder.
* Michael Sullivan | Is this is the spec, or is there some mathematical basis/use that I'm | missing?
I guess the latter. I have talked about this with a few people (irc) and unmathematical people do not even understand that (+) => 0 and (*) => 1.
The spec is quite clear that `andī, `orī and a few other obvious identity candicates return their identity value. That is, (operator argument) is identical to (operator (operator) argument), which has as a corrollary precisely that (operator argument) is identical to argument. This is very sound mathematically. That there are such hidden gems in Common Lisp delight me just as much as grokking some mathematical concept.
-- Erik Naggum, Oslo, Norway
Act from reason, and failure makes you rethink and study harder. Act from faith, and failure makes you blame someone and push harder.
>>>>> On 24 Aug 2002 04:28:13 +0000, Erik Naggum ("Erik") writes:
Erik> * Christopher C. Stacy Erik> | How about just testing *FEATURES* in the SYSDCL (whatever your Erik> | implementation does for that) to make sure that :IGNORE isn't there? Erik> | You won't compile or load on platforms that have defined that feature, Erik> | but at least there will be no mystery.
Erik> How about testing for something you know is there, instead? Erik> That way, you are actually always safe.
It's just because I want the good names IGNORE and DEBUG to be mine.
> It would be weird for () not to mean CL:NIL, but [...about :NIL]
Sure. I was just wondering if the feature expression evaluator (EXT:FEATUREP in CMUCL) is required to treat CL:NIL as a symbol and not as an empty list, which would be invalid.
(CMUCL draws the line between conses and atoms, allowing even non-symbols as features.)
Erik Naggum <e...@naggum.no> wrote: > * Michael Sullivan > | Is this is the spec, or is there some mathematical basis/use that I'm > | missing?
> I guess the latter. I have talked about this with a few people (irc) and > unmathematical people do not even understand that (+) => 0 and (*) => 1. > The spec is quite clear that `andī, `orī and a few other obvious identity > candicates return their identity value. That is, (operator argument) is > identical to (operator (operator) argument), which has as a corrollary > precisely that (operator argument) is identical to argument. This is very > sound mathematically. That there are such hidden gems in Common Lisp > delight me just as much as grokking some mathematical concept.
Yes, after seeing Nils's post and thinking about it some more, I realized this make writing certain kinds of operators/functions much more elegant than having blank operators return nil, or error in some way. Maybe one of these days I should actually read the spec.
Michael
-- Michael Sullivan Business Card Express of CT Thermographers to the Trade Cheshire, CT mich...@bcect.com
Erik Naggum <e...@naggum.no> writes: > * Duane Rettig > | Another way to look at it: If I had a CL program and it suddenly broke because > | I loaded in a module that pushed :scheme onto the *features* list, then I would > | have much less justification for being upset than if I had been using #+ignore > | or #+never and someone just stupidly pushed one of these onto *features*.
> FWIW, I think it is stupid to rely on names out of your control.
The very fact that we use the *features* list automatically puts it into that category, although it is not _completely_ out of our control.
The basic problem with *features* is that it has no official registry of names. And I don't think anyone ever intended such a thing, and if I'm correct then *features* was never intended to be a perfectly controllable thing.
Within a specific set of sources, features aid in the ability for the programmer not to have to change his source code as much. As the source code expands its scope in many directions, the conditionalizations allow for such expansions in an orderly manner.
- One direction that source can take (for example, in code we use internally) is that new architectures are added to the list for which the source is applicable. Whether or not the source must be changed to add these new architectures is dependent on how clever we were in specifying the feature; specific enough to clarify the feature, and general enough to include all architectures. So, for example, some code that says
is much more likely to left alone when adding a new architecture than
#+(or sparc hp ibm sgi) (foo) #+(or x86 alpha) (bar) #-(or sparc hp ibm sgi x86 alpha) (error)
even though the same thing is intended in both versions.
- Another more public way that source code is conditionalized is with the use of brand identifiers. This is where *features* could use a registery, but probably never will. Publically available (or private, but shared) source has been around for a long time in the Lisp world, and various vendors have had to work out how to identify each lisp:
Two examples of ambiguous names I can recal are #+gcl and #+ccl. The former might be either "Golden Common Lisp" or "GNU Common Lisp". And I may be misremembering, but I think I've seen at least one piece of source conditionalized for Corman Lisp whose #+ccl clashed with the older "Corral Common Lisp" (which I believe eventually became MCL).
These ambiguities usually don't last long, but it either takes vendors changing their standard branding *features*, or users changing their source code. The latter is much harder to do when the source is widely shared.
By the way, in another article elsewhere on this thred you mentioned that we should use #-franz for conditionalization. We can't do that, because that would break conditionaliztions for another, older lisp called "Franz Lisp"...
> Since you > control a whole bunch of features yourself, there are many ways to ensure > that you test for something that you know is there instead of believe will > not be there.
Yes, you mentioned this also in that other article and I had though of it at about the same time - How about:
(push :comment *features*)
...
#-comment (foo)
as a way to always guarantee success in ignoring the code?
> For the "future" case, you could also use a future version of > Allegro CL. Suppose you will never have code for Allegro CL 10.0 while you > are working on Allegro CL 6.3 and 7.0 and perhaps 8.0. You could write
> #+(version>= 10 0) for-further-study
> to signal to your developers that this is way into the future. You could > also use this mechanism to ensure that features were included in a future > version despite the cvs branch it was inserted on. Going through the code > to find places where a future version were specified would be a good way of > ensuring that those future things were indeed brought into the present.
If we were going to do that, I would not want to use 10, since that could be only 5 or 10 years down the road, which is short enough that it is not a guarantee, but long enough that I would not want to have to remember back that far to the time when we generated that code, and _why_ we conditionalized it that way. If we are going to really remove probabilities, let's go with most-positive-fixnum instead of 10. :-)
> Using a feature like debug-<package> would be OK, however, since it would > presumably be code that would actually be processed if you requested > debugging of that package.
But packages, like features, are not registered, and thus are not guaranteed to be unique. The problem thus remains that someone else could push the same feature for a different purpose in their source code. If there is a requirement that that source work in the same lisp, then source code changes are already required, anyway. To tie the feature to the package name centralizes the problem (a Good Thing) but the same amount of source code may have to be changed if, for example, the package names clash.
> This discussion has changed my view on #+ignore and the like. From not > having an opinion on it to having an actual opinion on it, I have come to > think it is wrong to use /any/ non-existing feature as a marker that some > code should not be processed, and in particular that overloading natural > language semantics on formal constructs is a form of intellectual sloppiness > that should be avoided.
I share your concern, but not your opinion, because of my own experience in what works and what doesn't work in the conditonalization world of lisp code, and although there are pitfalls to features lists, some are more likely to occur than others, and #+ignore is not one of them that is as likely to be a problem.
> > * Duane Rettig > > | Another way to look at it: If I had a CL program and it suddenly broke because > > | I loaded in a module that pushed :scheme onto the *features* list, then I would > > | have much less justification for being upset than if I had been using #+ignore > > | or #+never and someone just stupidly pushed one of these onto *features*.
> > FWIW, I think it is stupid to rely on names out of your control.
> The very fact that we use the *features* list automatically puts it into > that category, although it is not _completely_ out of our control.
> The basic problem with *features* is that it has no official registry of > names. And I don't think anyone ever intended such a thing, and if I'm > correct then *features* was never intended to be a perfectly controllable > thing.
> Within a specific set of sources, features aid in the ability for the > programmer not to have to change his source code as much. As the source > code expands its scope in many directions, the conditionalizations allow > for such expansions in an orderly manner.
> - One direction that source can take (for example, in code we use internally) > is that new architectures are added to the list for which the source is > applicable. Whether or not the source must be changed to add these new > architectures is dependent on how clever we were in specifying the feature; > specific enough to clarify the feature, and general enough to include all > architectures. So, for example, some code that says
* "Paul F. Dietz" <di...@dls.net> | Somehow one should be able to use this idiom: | | #+#.(predicate-evaluating-to-a-feature-expression) ... | | instead of having to preload attributes of the system as symbols pushed onto | the *feature* list.
A useful extension to the feature scheme would be to treat any form whose car was not the defined `andī, `orī and `notī as a macro to be expanded. That way, a feature expression could evaluate to (or) or (and) transparently if the macro returned just `nilī or `tī, too, hiding what appears to trigger some irrational aesthetics factor that considers #+ignore OK even though it totally confuses the semantic spaces of feature names and natural languages.
-- Erik Naggum, Oslo, Norway
Act from reason, and failure makes you rethink and study harder. Act from faith, and failure makes you blame someone and push harder.
* Duane Rettig wrote: > The basic problem with *features* is that it has no official > registry of names. And I don't think anyone ever intended such a > thing, and if I'm correct then *features* was never intended to be a > perfectly controllable thing.
But it's very easy to invent names which essentially are known to be controlled. We use a domain prefix for almost everything - an idea borrowed from Java via, I think, Franz's hierarchical package name documentation. So all our features start COM.CLEY (or ORG.TFEB depending on which hat I have on). I actually use a mixed convention of <system-name>/qualifier, so I'd probably use, say: :COM.CLEY.WELD/NEVER as a `never' feature (I have :COM.CLEY.WELD/DEBUG for stuff that should be processed only if I want verbose debugging, say). Similarly we use prefixed package names (but not the / convention, not sure why).
I figure if someone else starts pushing features with names beginning COM.CLEY, then they deserve what they get - and similarly if we started using COM.FRANZ, say.
If you use names prefixed by a DNS domain that you own, it seems to me that you don't need a global registry, because DNS provides it.
Tim Bradshaw <t...@cley.com> writes: > * Duane Rettig wrote: > > The basic problem with *features* is that it has no official > > registry of names. And I don't think anyone ever intended such a > > thing, and if I'm correct then *features* was never intended to be a > > perfectly controllable thing.
> But it's very easy to invent names which essentially are known to be > controlled. We use a domain prefix for almost everything - an idea > borrowed from Java via, I think, Franz's hierarchical package name > documentation. So all our features start COM.CLEY (or ORG.TFEB > depending on which hat I have on). I actually use a mixed convention > of <system-name>/qualifier, so I'd probably use, say: > :COM.CLEY.WELD/NEVER as a `never' feature (I have :COM.CLEY.WELD/DEBUG > for stuff that should be processed only if I want verbose debugging, > say). Similarly we use prefixed package names (but not the / > convention, not sure why).
> I figure if someone else starts pushing features with names beginning > COM.CLEY, then they deserve what they get - and similarly if we > started using COM.FRANZ, say.
> If you use names prefixed by a DNS domain that you own, it seems to me > that you don't need a global registry, because DNS provides it.
This is essentially the solution I've been using. At one point I was naming my packages/features things like TFB.GARNET-EXTENSIONS. I stopped when you yourself posted a reply to one of my c.l.l articles that began the quoted text from me with "I wrote..." (because your newsreader recognized my/your initials). Unfortunately, for completely general-purpose things (ie, not tied to a product associated with a shorter domain name), I end out with some attrociously long names: eg, EDU.BERKELEY.OCF.TFB.GARNET-EXTENSIONS. For packages, I can use nicknames, but for features, it gets ugly. It's not just the length (I always edit code in 100-column windows), really it's the ability to scan code and see the names. When I scan names prefixed like this, I see the domain name part. Maybe I'll try using / after the domain part -- it seems to emphasize the important part better.
-- /|_ .-----------------------. ,' .\ / | No to Imperialist war | ,--' _,' | Wage class war! | / / `-----------------------' ( -. | | ) | (`-. '--.) `. )----'