Skip to content

Debug Non c'è spazio per un nuovo problema di write

Restate sintonizzati perché in questo post troverete il risultato che cercate.

Soluzione:

Senza un esempio minimo di lavoro (MWE) si tratta solo di supposizioni, ma se il documento ha acronimi definiti o voci di glossario all'interno dell'elemento document e si è aggiornato alla versione 4.0, è necessaria una scrittura aggiuntiva. Il motivo è il seguente:

Le versioni 3.07¹ e successive scrivono l'ambiente name, description e symbol nei file di glossario esterni (oltre al campo sort ). I problemi sono molteplici:

  1. I comandi fragili all'interno di questi campi devono essere protetti, altrimenti si verifica un errore quando il comando viene scritto nel file. Per ovviare a questo problema, glossaries si è fatto in modo che il campo sanitize che in pratica convertiva il contenuto di questi campi in un elenco di lettere, quindi, per esempio, se si aveva cite nel campo description questo verrebbe convertito da una macro nei cinque caratteri cit e e. Ora è possibile scrivere in modo sicuro nel file di glossario, ma se si tenta di visualizzare il carattere description in un altro punto del documento, si otterrebbe "cite" nel PDF (o, più comunemente, "-cite", poiché il font serif predefinito visualizza il carattere come un trattino).

  2. Qualsiasi occorrenza di makeindex o xindy devono essere evase. Questo viene fatto con glossaries ma più lungo è il carattere name, descriptione symbol più lungo è il tempo necessario per farlo, quindi rallenta la creazione del documento.

  3. makeindex ha un buffer limitato e una descrizione lunga può superarlo.

  4. Può essere richiesto uno stile di glossario personalizzato che dovrebbe visualizzare altri campi, ma questi non sono accessibili se la voce non è stata definita.

Per ovviare a questi problemi, la versione 4.0 ha modificato il modo in cui le informazioni sulle voci vengono scritte nel file di glossario. Ora solo la voce sort e glossentry{etichetta} sono scritti nel file. È poi compito dello stile del glossario definire glossentry in modo da accedere alle informazioni pertinenti usando comandi come glsentrydesc. In questo modo non ci si preoccupa più di usare comandi fragili, perché non vengono scritti nel file. (Il comando sort viene automaticamente sanificato per impostazione predefinita e l'etichetta non può comunque contenere comandi fragili). Dato che le informazioni di indicizzazione sono ora in una stringa più corta, è molto più veloce eseguire l'escape di xindy/makeindex (nel caso in cui compaiano, per esempio, nella stringa sort o nell'etichetta della voce). E non c'è bisogno di preoccuparsi di superare i caratteri makeindex(a meno che non si abbia un valore di ordinamento o un'etichetta eccessivamente lunghi).

C'è però un inconveniente in questo approccio: tutte le voci devono essere definite quando il glossario viene visualizzato, in modo che glossentry accedere ai campi pertinenti. Se il glossario viene visualizzato alla fine del documento, questo non è un problema, ma spesso gli utenti preferiscono avere un elenco di acronimi o notazioni nella parte iniziale. Per ovviare a questo problema e per garantire la compatibilità con le versioni precedenti, glossaries modifica la definizione di newglossaryentry all'inizio dell'elemento document in modo che le informazioni sul glossario siano scritte in un file temporaneo jobname.glsdefsche viene poi inserito all'inizio del documento nella successiva esecuzione di LaTeX.

In questo modo si garantisce che le informazioni sulla voce siano disponibili quando si visualizza il glossario, ma c'è lo svantaggio di una scrittura aggiuntiva, possono verificarsi problemi di espansione e qualsiasi modifica alle definizioni non viene rilevata fino all'esecuzione successiva. Il see non funziona perché non è salvata in un campo (attiva semplicemente il riferimento incrociato quando la voce è definita) e quindi non viene scritta nel campo .glsdefs e quindi non viene scritto nel file .glsdefs . Ciò significa anche che i termini definiti usando newacronym vengono convertiti in una normale definizione di voce, il che può causare problemi al meccanismo di abbreviazione.

Si vedano anche gli svantaggi della definizione delle voci nell'ambiente del documento nel file glossaries nel manuale utente.

MWE1:

documentclass{article}

usepackage{glossaries}

makeglossaries

newglossaryentry{sample}{name={sample},description={an example}}

begin{document}

gls{sample}.

printglossaries

end{document}

Qui glossaries definisce due scritture: una per l'elemento .ist e una per il file .glo .

MWE2:

documentclass{article}

usepackage[acronym]{glossaries}

makeglossaries

newglossaryentry{sample}{name={sample},description={an example}}
newacronym{xyz}{XYZ}{long form}

begin{document}

gls{sample}. gls{xyz}.

printglossaries

end{document}

Qui glossaries definisce tre scritture: una per l'elemento .ist , una per il file glo e una per il file .acn file.

MWE3:

documentclass{article}

usepackage[acronym]{glossaries}

makeglossaries

begin{document}

newglossaryentry{sample}{name={sample},description={an example}}
newacronym{xyz}{XYZ}{long form}

gls{sample}. gls{xyz}.

printglossaries

end{document}

Qui glossaries definisce quattro scritture: una per l'elemento .ist , una per il file .glo e una per il file .acn e uno per il file .glsdefs file.

MWE4:

documentclass{article}

usepackage[acronym,index,symbols,numbers]{glossaries}

makeglossaries

begin{document}

newacronym{xyz}{XYZ}{long form}

gls{xyz}.

printglossaries

end{document}

Qui glossaries definisce sette scritture: .ist, .glo, .acn, .idx (da index ), .nlo (dall'opzione numbers ), .slo (dall'opzione symbols e .glsdefs (perché newacronym si trova nell'opzione document ).

Il glossaries-extra fornisce l'opzione docdef=restricted che consente la definizione dei documenti, ma non crea il file .glsdefs . Ciò significa che i termini devono essere definiti prima che i glossari vengano visualizzati, ma significa anche che un file aggiuntivo write non è necessario.

MWE5:

documentclass{article}

usepackage[acronym,docdef=restricted]{glossaries-extra}

makeglossaries

setabbreviationstyle[acronym]{long-short}

begin{document}

newglossaryentry{sample}{name={sample},description={an example}}
newacronym{xyz}{XYZ}{long form}

gls{sample}. gls{xyz}.

printglossaries

end{document}

Ora ci sono tre scritture: una per l'elemento .ist uno per il file .glo e una per il file .acn file.

Come ridurre al minimo il numero di nuovi file writes

  1. Spostare tutte le istanze di newglossaryentry (e newacronym che utilizza newglossaryentry) al preambolo o a un file che viene caricato nel preambolo tramite input o loadglsentries (non usare include).
  2. Assicurarsi di non aver definito un glossario che non si intende utilizzare. Ad esempio:

    documentclass{article}
    
    usepackage[acronym]{glossaries}
    
    makeglossaries
    
    newacronym{xyz}{XYZ}{long form}
    
    begin{document}
    
    gls{xyz}.
    
    printglossaries
    
    end{document}
    

    Qui glossaries definisce tre nuove scritture: una per il glossario .ist , una per il file .glo e una per il file .acn ma uno di questi (.glo) non viene utilizzato. Questo è uno spreco di un file write quindi sopprimere l'elemento main utilizzando l'opzione nomain opzione del pacchetto:

    usepackage[nomain,acronym]{glossaries}
    
  3. Se non è necessario apportare ulteriori modifiche al file .ist , si consenta l'uso di glossaries di generarlo alla prima compilazione:

    documentclass{article}
    
    usepackage[nomain,acronym]{glossaries}
    
    makeglossaries
    
    newacronym{xyz}{XYZ}{long form}
    
    begin{document}
    
    gls{xyz}.
    
    printglossaries
    
    end{document}
    

    Quindi sopprimere la sua creazione aggiungendo noist al documento:

    documentclass{article}
    
    usepackage[nomain,acronym]{glossaries}
    
    noist
    makeglossaries
    
    newacronym{xyz}{XYZ}{long form}
    
    begin{document}
    
    gls{xyz}.
    
    printglossaries
    
    end{document}
    

    Ora glossaries definisce solo una nuova scrittura per l'elemento .acn .

  4. Utilizzare il file savewrites per il pacchetto. Utilizza una sola scrittura per il file .ist e per tutti i pacchetti .glo, .acn (ma non per il file .glsdefs ). Con questa opzione glossaries memorizza tutte le informazioni del glossario in token fino alla fine del documento e poi itera attraverso ogni glossario e scrive su ogni file di glossario riutilizzando lo stesso registro di scrittura. Questo rallenta la costruzione del documento, ma a condizione che si definiscano tutte le voci nel preambolo glossaries definisce solo un registro di scrittura.

    Questo metodo è soggetto alla routine di output asincrono di TeX e può causare l'errata localizzazione delle voci.

    Questa opzione rallenta la compilazione perché ogni volta che si fa riferimento a una voce (usando comandi come gls o glsadd) le informazioni vengono aggiunte a un registro di token. Alla fine del documento, glossaries itera attraverso ogni glossario definito e scrive il contenuto del registro dei token associato nel file del glossario esterno. Questa operazione richiede più tempo rispetto alla semplice scrittura di una riga ogni volta che si usa un comando come gls o glsadd. Il tempo necessario dipende dal numero di volte in cui si fa riferimento a ciascuna voce.

A partire da glossaries versione 4.04, c'è un'altra opzione che non crea nuovi file, poiché l'ordinamento e l'indicizzazione sono effettuati da TeX anziché da un'applicazione di indicizzazione esterna:

documentclass{article}

usepackage[acronym]{glossaries}

makenoidxglossaries

newglossaryentry{sample}{name={sample},description={an example}}
newacronym{xyz}{XYZ}{long form}

begin{document}

gls{xyz}. gls{sample}.

printnoidxglossaries

end{document}

Crea solo il file standard .log e .aux (così come il file .pdf/.dvi ). In questo caso, newglossaryentry e newacronym sono stati resi comandi di solo preambolo, quindi non c'è alcun comando .glsdefs . Tuttavia, questo metodo è molto inefficiente, ha difficoltà con le voci gerarchiche e può ordinare solo in base all'insieme latino di base. È quindi sconsigliato, se non come ultima risorsa.

Il glossaries-extra mette a disposizione altri due metodi che non utilizzano alcun metodo write registri:

Utilizza semplicemente printunsrtglossary (o printunsrtglossaries) per visualizzare i glossari. In questo modo si itera semplicemente su tutte le voci definite (che quindi devono essere definite per prime). Non c'è un ordinamento e non ci sono elenchi di posizioni.

documentclass{article}

usepackage{glossaries-extra}

newglossaryentry{zoo}{name={zoo},description={sample description}}
newglossaryentry{aardvark}{name={aardvark},description={sample description}}

begin{document}

gls{aardvark}.

printunsrtglossaries

end{document}

Non ci sono write creati qui, ma il glossario è in ordine di definizione e include entrambe le voci anche se solo una è stata usata nel documento.

L'altra opzione è quella di utilizzare glossaries-extra con bib2gls. Questo comporta una leggera modifica a quanto descritto sopra. Le voci sono ora definite in un file .bib . Ad esempio, entries.bib:

@entry{zoo,name={zoo},description={sample description}}
@entry{aardvark,name={aardvark},description={sample description}}

Il file del documento ha ora bisogno del file record e GlsXtrLoadResources per specificare l'opzione .bib :

documentclass{article}

usepackage[record]{glossaries-extra}

GlsXtrLoadResources[src=entries]% terms defined in entries.bib

begin{document}

gls{aardvark}.

printunsrtglossaries

end{document}

Questo non definisce alcun file write (tutte le informazioni sono scritte nel file .aux ma ora solo la voce indicizzata (aardvark) appare nel glossario, il glossario è ordinato e le voci hanno elenchi di localizzazione. (Anche se in questo caso c'è solo una voce).

Il processo di creazione del documento (supponendo che il file del documento si chiami myDoc.tex) è:

pdflatex myDoc
bib2gls myDoc
pdflatex myDoc

(Sostituire pdflatex con xelatex ecc.). Se si desidera un gruppo di lettere, è necessario l'opzione --group (o -g):

bib2gls --group myDoc

Funziona in modo diverso dal selettore makeindex/xindy approccio. bib2gls legge le informazioni richieste dal file .aux e crea un file con le definizioni delle voci che viene inserito da GlsXtrLoadResources. Le voci vengono ordinate prima di scrivere le loro definizioni e vengono incluse solo quelle indicizzate nel documento. Questo significa che il glossario può essere visualizzato semplicemente usando printunsrtglossariescome nell'esempio precedente. bib2gls crea un file di trascrizione (.glg) e uno .glstex per ogni comando di risorsa (GlsXtrLoadResources) ma nessun write per i file di glossario.

C'è una tabella che confronta i vari metodi nel file glossaries manuale d'uso.

A titolo di confronto, bib2gls viene fornito con alcuni documenti di esempio, tra cui sample-multi2.tex che contiene 14 glossari e 1 indice. Il documento main è soppresso con nomain, il glossario dell'indice viene creato con l'opzione index e i restanti glossari vengono creati con newglossary*:

usepackage[record,% use bib2gls
 section,% use section* for glossary headings
 postdot,% insert dot after descriptions in glossaries
 nomain,% don't create 'main' glossary
 index,% create 'index' glossary
 nostyles,% don't load default styles
% load and patch required style packages:
 stylemods={list,mcols,tree,bookindex}
]{glossaries-extra}

newglossary*{bacteria}{Bacteria}
newglossary*{markuplanguage}{Markup Languages}
newglossary*{vegetable}{Vegetables}
newglossary*{mineral}{Minerals}
newglossary*{animal}{Animals}
newglossary*{chemical}{Chemical Formula}
newglossary*{baseunit}{SI Units}
newglossary*{measurement}{Measurements}
newglossary*{film}{Films}
newglossary*{book}{Books}
newglossary*{person}{People}
newglossary*{mediacontrol}{Media Control Symbols}
newglossary*{information}{Information Symbols}
newglossary*{weather}{Weather Symbols}

Il documento carica hyperref, quindi questo significa che un registro di scrittura (@outlinefile) viene creato per hyperref's .out in aggiunta ai registri di scrittura standard @mainaux e @partaux definiti dal kernel LaTeX. (Se si aggiunge un indice, si crea un registro di scrittura aggiuntivo per il parametro .toc ).

Se il documento viene modificato per utilizzare makeindex/xindyrichiederebbe 1 registro di scrittura per il file di stile e uno per ogni glossario (compreso l'indice) = 1 + 15 = 16. Con i 2 registri definiti dal kernel e da hyperrefper i segnalibri del PDF, questo significa che il documento richiederebbe 19 registri di scrittura (o 20 se il registro .glsdefsse le definizioni del glossario vengono spostate nel file document ).

Con bib2gls solo i 2 registri definiti dal kernel e hyperref's .out vengono creati per un totale di 3 registri di scrittura, il che rappresenta un risparmio significativo.

In termini di file temporanei associati, ci sono i file standard .aux e .log e hyperref's .out . Con makeindex/xindy c'è anche il file di stile e tre file per glossario (input, output e transcript), per un totale di 2 (.aux e .log) + 1 (.out) + 1 (.ist/.xdy) + 3 × 15 = 49.

Con bib2gls, c'è la trascrizione .glg e 1 .glstex per GlsXtrLoadResources. Il numero di comandi di risorse non è correlato al numero di glossari. Un comando di risorse può elaborare più glossari (se hanno le stesse impostazioni) o un glossario può richiedere più comandi di risorse (se è diviso in blocchi ordinati indipendentemente). Nel caso di sample-multi2.tex ci sono 9 comandi di risorse, quindi il numero totale di file temporanei associati = 2 (.aux e .log) + 1 (.out) + 1 (.glg) + 9 (.glstex) = 13. (Il risultato sample-multi2.pdf è disponibile anche su CTAN).

Quindi utilizzando bib2gls non solo elimina la necessità di registri di scrittura associati ai glossari, ma può anche ridurre il numero totale di file temporanei.


¹ Le versioni tra la 3.07 e la 4.0 erano sperimentali e non sono state caricate su CTAN.

Il problema con morewrites e la versione filecontents è il modo in cui filecontents definisce un elemento newwrite utilizzando [email protected][email protected]write e bypassando il parametro morewrites meccanismo.

Qui c'è una versione hackerata che uso e che bypassa il problema. Bruno o Scott Pakin devono risolvere il problema a livello di pacchetto.

Vi mostriamo i commenti e le valutazioni degli utenti

Se accetti, puoi lasciare una dichiarazione su ciò che ti ha colpito di questo post.



Utilizzate il nostro motore di ricerca

Ricerca
Generic filters

Lascia un commento

Il tuo indirizzo email non sarà pubblicato.