---------------------------------------------------------------------------
Pname.h, Version 1.1, 10 May 2001, copyright 2001, by Neil Cerutti
(cerutti@together.net)

Aggiornata alla libreria 6/11 e tradotto in italiano da Marco Falcinelli. 2006.

Questa  la documentazione per pname.h, una libreria con cui potrete
potenziare il riconoscimento dei nomi degli oggetti operata dalla
libreria standard di Inform, riducendo di gran lunga la necessit di andare
a scrivere routine in parse_name.  Contiene le seguenti sezioni:

    INTRODUZIONE
    INSTALLAZIONE e USO
    D&R
    OPERATORI
    PARSING
    NOTE TECNICHE
    PAROLE RISERVATE
    DISTRIBUZIONE
    NESSUNA GARANZIA
    RINGRAZIAMENTI SPECIALI
    CRONOLOGIA DELLE VERSIONI

---------------------------------------------------------------------------
INTRODUZIONE

Se il vostro gioco include oggetti con lo stesso nome nel medesimo luogo
(ad esempio, un Giardino che contiene ARANCE da SUCCO ed una SPREMUTA DI
ARANCE), avrete gi incontrato il problema di come far capire al parser a quale oggetto 
ci si riferisce, ad esempio: ESAMINA SUCCO o ESAMINA SPREMUTA descriver
rispettivamente o l'arancia o la spremuta, ma ESAMINA ARANCE far si che
il parser richieda di essere pi precisi e di specificare a quale oggetto ci
si riferisce. Per evitare di infastidire il giocatore -- che potrebbe
considerare 'ovvio' che in questo caso ci si riferisca al frutto -- sarete
costretti a rimpiazzare le propriet name di questi oggetti (con le loro
semplici liste di parole di dizionario) con propriet pi complesse
parse_name;  incluse routine personalizzare che possono diventare piuttosto
difficili da scrivere e da verificare.

La libreria pname.h definisce una nuova propriet, pname (abbreviazione
per phrase name), con un aspetto ed un funzionamento simile alla propriet
standard name: esntrambe contengono una lista di parole di dizionario.
Naturalmente, in una propriet pname l'ordine delle parole  significativo,
e attraverso degli operatori speciali '.p' '.or' e '.x'  possibile 
includere una maggiore adattabilit della vostra lista. Nella maggior
parte dei casi dove la propriet name standard non  sufficiente, potrete
rimpiazzarla con una propriet pname, invece di scrivere una routine
nella propriet parse_name. Per esempio, per risolvere il problema
sopra indicato, tutto ci di cui avete bisogno :

    Object  esempio_frutta "arancie da succo"
      with  pname '.x' 'succo' 'arance',
            ... ;

    Object  esempio_bibita "spremuta di arance"
      with  pname '.x' 'arance' 'succo',
            ... ;

Questa  tutto, una propriet pname  come una propriet name che ha
una migliore capacit di definire 'frasi' -- sequesze di parole -- che
migliorano la possibilit di un oggetto di essere selezionato dal parser
nel momento in cui il giocatore scrive le parole corrispondenti.
Nel far ci si propone come alternativa facile, flessibile e veloce 
rispetto all'uso di parse_name.

---------------------------------------------------------------------------
INSTALLAZIONE e USO

Per inserire questa libreria nel vostro programma, dovete fare tre cose:

1.  Aggiungere quattro linee verso l'inizio del vostro codice (prima di includere
    Parser.h).
     
    Replace MakeMatch;
    Replace Identical;
    Replace NounDomain;
    Replace TryGivenObject;

2.  Includere il file pname.h subito dopo aver incluso Parser.h.

    Include "Parser";
    Include "pname.h";

3.  Aggiungere la propriet pname a quegli oggetti che lo richiedono.

Ecco un esempio di un programma Inform che usa questa libreria:

    Constant Story "PROVA";
    Constant Headline "^E' solo una prova^^";

    Replace MakeMatch;      ! /---- aggiunte queste linee prima di Parser.h
    Replace Identical;      ! |
    Replace NounDomain;     ! |
    Replace TryGivenObject; !<'

    Include "Parser";
    Include "pname.h";      ! <---- aggiunta questa linea dopo Parser.h
    Include "VerbLib";

    ...

    Object  canna "canna da pesca"
      with  description "Una canna da pesa in carbonio...",
            pname '.x' 'carbonio' '.x' 'pesca' 'canna',
            ... ;

    Object  rete "rete da pesca"
      with  description "Una rete da pesca in nylon...",
            pname '.x' 'nylon' '.x' 'pesca' 'rete',
            ... ;

    Object  pesca "pesca"
      with  description "Una bella e succosa pesca...",
            name 'pesca',
            ... ;

    ...

Una propriet pname definisce una o pi frasi che possono riferirsi
al dato oggetto, usando le parole di dizionario e semplici operatori.
Per esempio, consideriamo la dichiarazione di pname per la canna da
pesca:

            pname '.x' 'carbonio' '.x' 'pesca' 'canna',

La propriet pname dell'oggetto canna "canna da pesca" contiene una
frase in cui le parole 'carbonio' e 'pesca' sono aggettivi facoltativi 
mente 'canna'  il sostantivo vincolante. Nel parsing, la propriet 
genera una 'frase che corrisponda' -- un segnale che incrementa la 
possibilit che l'oggetto sia scelto senza la necessit di una ulteriore
richiesta al giocatore -- in risposta agli input: CANNA DA PESCA IN CARBONIO,
CANNA IN CARBONIO, CANNA DA PESCA, e CANNA. 


---------------------------------------------------------------------------
D&R

D:  In cosa si differenzia la propriet pname dalla propriet name?

R:  In una propriet pname, l'odine in cui appaiono le parole crea differenza
    nel processo di selezione dell'oggetto a cui ci si riferisce.  Nella propriet
    name, l'odine delle parole non importa.

    Inoltre, potete includere operatori nella vostra propriet pname per
    aiutare il parsing ad essere pi preciso. La propriet name  sempre
    e completamente generica.


D:  Non posso gi fare questo tipo di lavoro usando una routine parse_name?

R:  Non allo stesso modo, non facilmente, e non cos velocemente.
    (Inoltre, non preoccupateci se non avete capito esattamente come
    funzionano le routine parse_name ... non ne userete molte se
    includerete questa libreria.)

    Per esempio, supponiamo che il vostro gioco contenga dei fondi di caff 
    e un caff:
    
        Object  coffee "caff"
          with  name 'caff',
                description "Caldo, forte e amaro.",
                ... ;

        Object  coffee_fondi "fondi di caff"
          with  name 'fondi' 'caff',
                description "I resti maleodoranti delle tue ricerche nel preparare
		la bevanda perfetta.",
                ... ;

    naturalmente, il parser non riuscir mai a capire nominando il caff nel comando
    a quale dei due oggetti ci si riferisca se sono entrambi in scope.:

        Puoi vedere un caff e dei fondi di caff qui.
        
        >ESAMINA IL CAFFE
        Cosa intendi, il caff o i fondi di caff?

        >IL CAFFE
        Cosa intendi, il caff o i fondi di caff?

    Il caff  un oggetto a cui non ci si pu pi riferire! La soluzione tradizionale
    a questo problema  quella di mettere una routine parse_name nell'oggetto
    fondi di caff, che forzi il gioco ad associare mai la parola CAFFE
    da sola all'oggetto fondi.

        Object  coffee_fondi "fondi di caff"
          with  parse_name [ wd;
                    wd = NextWord();
                    if (wd == 'fondi' && NextWord() == 'caff') 
                      return 2;
                    else if (wd == 'fondi') 
                      return 1;
                    else 
                      return 0;
                    ],
                description "I resti maleodoranti... ",
                ... ;

    Questa soluzione funziona benissimo quando entrambi gli oggetti sono in scope:

        Puoi vedere un caff e dei fondi di caff qui.
        
        >ESAMINA IL CAFFE
        Caldo, forte e amaro.

        >ESAMINA I FONDI DI CAFFE
        I resti maleodoranti... 

    Ma c' ancora una trappola. Questa soluzione non funziona quando i fodni di caff
    sono in scope ma non il caff, causando frustrazione al giocatore nel momento in cui
    un comando assolutamente chiaro e non ambiguo viene respinto:

        Puoi vedere dei fondi di caff qui.

        >ESAMINA CAFFE
        Non vedi niente del genere qui.

    In questo caso, la routine parse_name  troppo restrittiva.  Una routine pi
    flessibile dovrebbe sapere che, quando il caff non  in scope, allora pu
    riconoscere la parola CAFFE da sola e riferirsi ai fondi di caff. Potete
    sistemare questo problema migliorando la vostra parse_name, ma inciderete
    sulle performance:

        Object  coffee_fondi "fondi di caff"
          with  name 'caff' 'fondi',
                parse_name [ wd;
                    if (~~TestScope(coffee)) 
                      return -1; ! usa name invece
                    wd = NextWord();
                    if (wd == 'fondi' && NextWord() == 'caff') 
                      return 2;
                    else if (wd == 'fondi') 
                      return 1;
                    else 
                      return 0;
                    ],
                description "I resti maleodoranti... ",
                ... ;

    Ecco, la routine parse_name applicata solo quando il caff non  in scope.
    Comunque, chiamare TestScope() incide sulle prestazioni del gioco;
    ciamarla dall'interno di una routine parse_name  molto costoso in termini 
    di risorse, e ci rallenter sensibilmente la velocit di esecuzione del
    gioco anche su cumputer piuttosto potenti.

    La situazione, gi non buona, diventa peggiore se un altro oggetto ambiguo
    (ad esempio un macina caff) viene aggiunta al gioco; sarete in quel
    caso costretti a modificare tutta la vostra routine parse_name.

    Ma, l'aiuto  a portata di mano! Usando pname.h, potrete semplicemente scrivere:

        Object  coffee "caff"
          with  name 'caff',
                description "Caldo, forte e amaro. ",
                ... ;

        Object  coffee_fondi "fondi di caff"
          with  pname '.x' 'caff' 'fondi',
                description "I resti maleodoranti... ",
                ... ;

        Object  coffee_macina "macina caff"
          with  pname '.x' 'caff' 'macina',
                description "Un piccolo macina caff in legno magnificamente decorato,... ",
                ... ;


Q:  FORTE!  Cos devo usare la propriet pname in utti i miei oggeti giusto?

R:  Non  necessario. Dovreste usare la propriet pname solo quando il problema
    dei termini ambigui si palesa. Non vi  vantaggio ad usare pname quando
    il normale sistema di riconoscimento di Inform  sufficiente. Per esempio,
    se nel vostro gioco avete un "tavolo di legno" ed un "cavolo verde" la propriet
    name  capace di distinguere tra essi e usare pname sarebbe uno spreco.


D:  Ho definito una propriet pname per la bacchetta nera da Avventura:

        Object  black_rod "bastone nero con una stella arrugginita in punta"
          with  pname 'bastone' 'nero',
                ... ;

    Dal momento che sia le parole 'nero' e 'bastone', sono richieste in questa frase, la 
    sola parola BASTONE e la frase NERO BASTONE non verranno mai associati al mio oggetto.
    Vero?
    
R:  Dipende; l'oggetto potrebbe ancora finire per essere quello pi probabile nella scelta
    del parsing tra quelli che sono in scope. Ricordare che la propriet pname agisce solo
    come un _aiuto_ nel processo che elimina le ambiguit. Se l'input del giocatore
    non  ambiguo allora il parser seleziona il bastone nero anche se la frase 'nero'
    'bastone' non corrisponde all'input. L'associazione della frase in pname.h non
     restrittivo; invece, esso applica dei bonus nel processo che toglie le ambiguit
    in modo tale che la frase venga associata al giusto oggetto.


D:  Oh. Allora cosa  una frase, e cos' l'associazione di una phrase?

R:  Una phrase  una stringa di parole di dizionario in una propriet pname,
    con la possibilit che contenga degli operatori.
    Pi di una frase pu apparire in una singola propriet pname se sono separate
    dall'operatore di separazione di frase '.p'.

    Un phrase match avviene quando le parole di input del giocatore incontrano
    una delle frasi specificate in una propriet pname. Se avviene la corrispondenza,
    l'oggetto riceve un bonus durante il processo di eliminazione delle ambiguita
    effettuato dal parsing.


Q:  pname.h  compatibile con Glulx? In altre parole, posso usare pname.h in un
    programma Inform progettato per essere compilato per la nuova Glulx virtual
    machine?

R:  Si.


Q:  OK. Sono convinto che pname.h mi semplificher la vita. Ma quali sono gli svantaggi 
    di usare pname.h nel mio programma, se ve ne sono?

A:  Il pi grande svantaggio  che pname.h sostituisce alcune routine importanti
    che sono parte integrante della libreria di Inform. Vi state vincolando
    all'uso di una specifica versione della Libreria usando pname.h, e ogni modifica
    che fate a queste routine nella vostra copia sar sovrascritta da pname.h.
    Questa versione di pname.h  progettata per la versione della Libreria mostrata
    in cima a questo documento, ed  molto probabile che diventi incompatibile
    con future o passate versioni.

    Uno svantaggio di pi piccola portata  che pname.h non assolve del tutto
    alla sua promessa di eliminare l'uso di routine in parse_name. Probabilmente
    dovrete ancora andare a scrivere alcune di esse; leggete le NOTE TECNICHE pi
    in basso.

    Uno svanttaggio ancora pi piccolo  che usa uno del numero limitato di attributi 
    messi a disposizione da Inform.

---------------------------------------------------------------------------
OPERATORI

La propriet pname prende una lista delle parole di dizionario poste tra
apici, allo stesso modo in cui lo fa la propriet name. La prima differenza
 che alcune di queste parole possono essere operatori per pname
'.p', '.or', e '.x' che sono qui di seguito definiti.

'.p' operatore di separazione di phrase

    Usato per separare le dichiarazioni di frasi in una propriet pname.
    Ogni cosa dopo di esso e fino alla fine della propriet o del prossimo
    separatore di frase  interpretato come una singola frase.

    Tutte le propriet pname cominciano con un implicito '.p' se non si
    provvede ad alcun operatore di separazione di frase. Usando questo
    operatore, potete dichiarare pi di una frase per lo stesso oggetto.
    Ad esempio:

        pname 'vecchia' 'lampada' 'bronzo' '.p' 'luce' 'abbagliante'

    definisce due frasi: 'vecchia' 'lampada' 'bronzo' e 'luce' 'abbagliante'.
    Dovrebbe generare una associazione per gli input VECCHIA LAMPADA DI BRONZO
    e LUCE ABBAGLIANTE, ma non per LUCE BRONZO o LAMPADA ABBAGLIANTE.

'.or' operatore or

    Un operatore binario usato nella frase per mostrare che certe parole
    in una frase possono essere sostituite con altre parole. Per esempio:

        pname 'bibita' 'gassata' '.or' 'frizzante' 

    dovrebbe generare una associazione di frasi per gli input BIBITA GASSATA e
    BIBITA FRIZZANTE. Potete inserire assieme quante parole volete con questo operatore.
    Per esempio:

        pname 'bibita' 'frizzante' '.or' 'gassata' '.or' 'bollicine' '.or' 'effervescente' 

    Una associazione alla frase dovrebbe essere il risultato a tutti i seguenti input:
    BIBITA GASSATA, BIBITA FRIZZANTE, BIBITA CON BOLLICINE e BIBITA EFFERVESCENTE.
    Ma non dovrebbe esserci associazione per nessuno dei seguenti input:
    BIBITA, BIBITA GASSATA GASSATA, BIBITA GASSATA CON BOLLICINE, BIBITA FRIZZANTE GASSATA,
    BIBITA FRIZZANTE o GASSATA.

'.x' operatore facoltativo

    Un operatore univoco e prefisso, che introduce una parola di dizionario
    che pu essere facoltativa in una frase. La prima parola di dizionario alla
    destra di un operatore '.x'  interpretata come facoltativa. Per esempio:

            pname 'bottone' 'distributore' '.x' 'bibite' 

    denota che la parola 'gassate'  facoltatica nella suddetta frase. Generer
    una associazione di frase per gli input BOTTONE del DISTRIBUTORE di BIBITE e
    BOTTONE del DISTRIBUTORE. 

    Si possono inserire quante parole facoltative si vogliono; tutte le parole dell'input
    che si associano alle parole nella stringa di opzioni verranno associate, in un ordine qualsiasi.
    Per esempio:

            pname 'calzoncini' '.x' 'neri' '.x' 'bagno' 
    
    Generer una associazione di frase per tutti i seguenti input:
    CALZONCINI, CALZONCINI NERI, CALZONCINI NERI DA BAGNOS, CALZONCINI DA BAGNO,
    CALZONCINI DA BAGNO NERI and CALZONCINI DA BAGNO DA BAGNO NERI NERI DA BAGNO.
    Nessuna associazione di frase verr fatta per: NERI, BAGNO o PICCOLI CALZONCINI.

    Una propriet pname che contiene tutte parole facoltative agir esattamente
    come una propriet name standard.

---------------------------------------------------------------------------
PARSING

il parser pname.h conta il numero di parole nell'input che appaiono nella 
propriet pname di un dato oggetto. Registra inoltre se accade di associare
o meno un input con una qualsiasi delle frasi specificate per l'oggetto.
Se il numero totale di parole che si associano  uguale alla frase pi
lunga possibile da associare, allora l'oggetto viene contrassegnato per 
aver incontrato l'associazione di una frase nell'input.
Un oggetto con una propriet name  trattato come se avesse una propriet
pname in cui tutte le parole sono facoltative -- pertanto ogni corrispondenza
risulta in una associazione di frase. Se un oggetto a sia una propriet name 
che una pname, pname effettivamente maschera l'esistenza di una propriet
name dal parser. Lo stesso dicasi per le routine parse_name. Se avete una
routine parse_name in un oggetto con una propriet pname, parse_name non
verr richiamato durante il parsing.

Next, during an early phase of Inform's disambiguation process, from all
the objects that match at least one word in the input, only the ones that
match the most consecutive words in the input are retained.

Finally, among the objects that matched the most words, only the ones that
generated a phrase match are retained (unless none of them generated a
phrase match, in which case they are all retained).

Thus, it's possible for an object that generates no phrase matches to be
selected as the most likely.  In the coffee table example in the Q&A section
above, when the coffee was not in scope and the player specified only
COFFEE, even though the single word COFFEE does not produce a phrase
match for the coffee table, the coffee table is still deemed the most
likely object by the parser because it matched a word in the input.

Here's a longer example and a more detailed explanation.

The starting location of _Uncle Zebulon's Will_ by Magnus Olsson has some
troubling parsing problems.  There's a garden, a garden path, and a garden
shed all in scope at once.  Using pname phrases, you can solve the problem
by making 'garden' optional for the garden path and the garden shed:

    Object  garden "garden"
      with  name 'garden',
            description "The garden...",
            ... ;

    Object  path "garden path"
      with  pname '.x' 'garden' 'path',
            description "The path...",
            ... ;

    Object  shed "garden shed"
      with  pname '.x' 'garden' 'shed',
            description "The shed...",
            ... ;

The following table shows phrase matches and word matches for several
possible inputs and explains which object results.

                    Words   
Input       Object  Matched Phrase match?
----------- ------- ------- ------------------------
GARDEN
            garden: 1       yes
            path:   1       no
            shed:   1       no
            -------------------
            result: garden


SHED
            garden: 0       no
            path:   0       no
            shed:   1       no
            -------------------
            result: shed


GARDEN SHED
            garden: 1       yes
            path:   0       no
            shed:   2       yes
            -------------------
            result: shed [it matched the most words - on that basis, it
                          would have won even if it had not generated a
                          phrase match]

PATH
            garden: 0       no
            path:   1       yes
            shed:   0       no
            -------------------
            result: path


GARDEN PATH
            garden: 1       yes
            path:   2       yes
            shed:   1       no
            -------------------
            result: path

---------------------------------------------------------------------------
TECHNICAL NOTES

I recommend you use only the latest version of the Inform Library.
You may use either the standard version by Graham Nelson or Andrew
Plotkin's cross-platform port for compiling Glulx files.

The pname parser considers as indistinguishable any two objects that have
equivalent name properties and duplicate pname properties. To be
indistinguishable, the name property of the two objects must be equivalent:
every word in one must appear somewhere in the other (See Nelson, Graham:
_The Inform Designer's Manual_, 3rd Ed, Section 25). pname properties
must be identical.

The pname property is additive. That means that pname properties inherit
the pname property of their parent class. The way this works in practice
is: the pname properties of the instance and its parent classes are
concatenated into a list and that list is assigned to the instance as its
pname property. When a name property is created through inheritance, the
order in which the properties are concatenated doesn't matter. However,
since the order of the words in a pname property is important, you need to
understand the order of inheritance.

Inheritance start with the instance and works its way back up through its
parent classes.

     Class Rod with pname 'rod' '.or' 'wand';
     
     Rod black_rod with pname '.x' 'black;

     Rod blue_rod with pname '.x' 'blue';

After compilation, the black rod's pname property is 

     '.x' 'black' 'rod' '.or' 'wand'
     
and the blue rod's is 

     '.x' 'blue' 'rod' '.or' 'wand'.

For multiple inheritance, the order in which the list is created is
equivalent to the order the classes are declared in the class clause of the
inheriting object.

    Class Rod with pname 'rod';

    Class Wand with pname 'wand';

    Object black_rod
     class Rod Wand
     with pname '.x' 'black';

In this case the pname property of the black_rod is 

     '.x' 'black' 'rod' 'wand'
     
which is probably not what you wanted! You have to be careful. 

If you don't want pname properties of Class objects to have a chance of
interfering with pname properties of its intances, you can include a phrase
separator operator in the declaration.

     Class Rod with pname '.p' 'rod';

     Class Wand with pname '.p' 'wand';

     Object black_rod
      class Rod Wand
      with pname 'black';

The black_rod, after compilation, will have a pname property of 'black'
'.p' 'rod' '.p' 'wand', in other words, a pname property which contains
three one-word phrases.

If a class contains a name property then it will be masked by the existence
of any instances that contain a pname property. pname_verify will print
warnings in this case (see DEBUGGING).

You may use plural flagged dictionary words in your pname properties, and
they will be recognized by the pname parser.  A plural dictionary word is
defined with a //p on the end (for example, 'dogs//p').  If the parser sees
one, it knows that the player may be referring to more than one object.
(See: Nelson, Section 25.)

There are some uses for parse_name routines that pname.h doesn't cover. A
parse_name must be used to dynamically change the name of an object during
the course of a game.  In addition, a parse_name routine may be needed by a
class of similar objects in order to be explicit about what is
indistinguishable and what isn't. As noted in the PARSING section above, do
not try to have a parse_name and a pname in the same object. They do not
coexist happily.

---------------------------------------------------------------------------
DEBUGGING

This package contains a useful set of debugging diagnostic statements for
times when thorny parsing issues arise (they were also of great help while
debugging this package!); these are compiled only if DEBUG is defined.  The
parser trace level must be set to 7 or higher for full phrase parsing
diagnostics to print (See: Nelson, Section 30), although trace level 5 is
enough to show which objects produced phrase matches.

Due to speed and algorithmic simplicity concerns, pname.h does not do error
checking for bad pname declarations during parsing. To ameliorate this
shortcoming, pname.h provides a pname_verify routine.  When DEBUG is
defined, you may call pname_verify() in your Initialise() routine to verify
the pname properties in your objects.  Here's what I suggest:

    [ Initialise;
        #ifdef DEBUG;
        pname_verify();
        #endif;
        ! etc...
    ];

pname_verify loops over all the game objects and reports errors and
warnings for pname properties it finds suspect. The game is aborted if any
errors are reported.

pname_verify report a warning if it finds 'x', 'p', or 'or' in a
pname property, since they are most likely typos for '.x', '.p' and '.or',
respectively.

pname_verify also reports a warning for objects with pname property and a
name or parse_name property, because a pname property masks both the
parse_name and name properties from the parser.

You can call pname_verify with 'true' as its argument to suppress these
warning messages:

    pname_verify(true); ! suppress warnings

---------------------------------------------------------------------------
RESERVED WORDS

In addition to the identifiers reserved by Inform and the standard Library,
pname.h defines the following.  You mustn't use any of the following words
in a program that Includes pname.h, except as documented here.

Globals:            matches_in_match_list

Constants:          PHRASE_OP           '.p'
                    OR_OP               '.or'
                    OPT_OP              '.x'

                    You may use any of these constants in your program
                    but you must not try to define them yourself.


Routines:           _pn_pname
                    _pn_matchPhrase
                    _pn_inpWord
                    _pn_inpLen
                    _pn_TryGivenObject

    additionally, if DEBUG is defined:     

                    pname_verify
                    _pn_printInpWord
                    _pn_printPhrase
                    _pn_isOp
                    _pn_error
                    _pn_warning

                    You shouldn't call any of the above routines in your
                    program except for pname_verify.

Attributes:         phrase_matched

                    This is used internally by the pname parser to mark
                    objects for which a phrase match has been detected.

Standard Library routines:
                    
                    MakeMatch
                    Identical
                    NounDomain
                    TryGivenObject

                    These Library routines are replaced in pname.h so
                    don't try to replace them yourself. If you want to hack
                    one of these routine in a program that includes pname.h
                    you will need to hack pname.h instead.

---------------------------------------------------------------------------
DISTRIBUTION

You may use the header file pname.h in any Inform program.  You may
distribute source code which uses pname.h, but you may not distribute
pname.h with your source code except as described below.

The header file pname.h itself may only be distributed if this
documentation file, pname.txt, is included and pname.h is not modified in
any way.  This documentation file, 'pname.txt' may not be altered without
the permission of the author, Neil Cerutti <cerutti@together.net>, except
if the contents remain unchanged.  It is permissible to adapt it to a
different file format, e.g., HTML, PDF, PS, however and I don't consider
such adaptation to be an alteration.

You may distribute compiled game files which include pname.h.  You may also
distribute compiled game files which include an altered version of pname.h.

---------------------------------------------------------------------------
NO WARRANTY

Because this software is distributed without charge, you assume the
entire responsibility for determining whether the program fits your
needs and whether it is correct and/or complete.

Neil Cerutti, and any distributors of this software specifically disclaim
any and all warranties, expressed or implied, including but not limited to
implied warranties of merchantability and fitness for a particular purpose,
with regard to this software. In no event will the author or any
distributor of this software be liable to you for any damages, including
lost profits, lost savings, or other incidental or consequential damages
arising out of the use or inability to use this software, even if any of
these parties has been advised of the possibility of such damages, or for
any claim by any other party.

---------------------------------------------------------------------------
SPECIAL THANKS 

Thanks to Roger Firth who submitted an unsolicited re-organization of this
file that helped transform it from a specification into documentation. His
rewrites were invaluable in writing this documentation.

Thanks to Marnie Parker and David Cornelson, who both looked at very early
drafts of this document and gave good advice and asked good questions, which
helped streamline and clarify the design of pname.h, which was originally
much more complex.

Thanks to Andrew Plotkin for donating the code for the cross-platform (Z
and Glulx) versions of Identical, TryGivenObject, MakeMatch and ParseNoun
from his cross-platform port of Inform Library 6/10.

---------------------------------------------------------------------------
VERSION HISTORY

1.0  18 April 2001
  Initial release

1.1  10 May 2001
  o  Fixed bug that caused to the parser to never generate a phrase match
	for a phrase in which an optional word was followed by the same
	consecutive word, or in an '.or' clause, e.g., '.x' 'card' 'card'.

	The phrase '.x' 'card' 'card' will now generate a 1 word phrase match
	for the input CARD and an N word phrase match for input containing N
	instances of the word CARD, i.e., CARD CARD CARD CARD would cause a 4
	word phrase match.
