> For the complete documentation index, see [llms.txt](https://overleaf-pro.ayaka.space/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://overleaf-pro.ayaka.space/latex/fi/syvalliset-artikkelit/54-what-is-a-tex-token-list.md).

# Mikä on TeX-tokenlista

## Eli mikä ihme on "TeX-tokeniluettelo"?

Yhdessä [edellinen artikkeli](/latex/fi/syvalliset-artikkelit/53-what-is-a-tex-token.md)—myös osa tätä [matalan tason TeX-yksityiskohdista kertovaa sarjaa](/latex/fi/syvalliset-artikkelit/01-a-new-series-of-articles-tex-tokens-and-related-concepts-but-why-and-how.md)—tutkimme prosesseja, joiden kautta TeX skannaa `.tex` tiedostosi luodakseen uusia tokeneita: tarkastelimme TeX-tokenin perusluonnetta ja sitä, miten TeX luo niitä (katso [Mikä on "TeX-token"?](/latex/fi/syvalliset-artikkelit/53-what-is-a-tex-token.md)).

Tässä jatkoartikkelissa tarkastelemme *tokenuetteloa*t: mitä ne ovat ja miten TeX-moottorit luovat/käyttävät niitä. Tokenuetteloiden ymmärtäminen voi olla hankalaa, koska ne on tallennettu syvälle TeXin sisuksiin: nämä yksityiskohdat on piilotettu käyttäjältä — vaikka nykyään näin ei aina ole, jos ohjelmoit LuaTeXilla edistyneemmin. Toistaiseksi voit kuitenkin alkaa ajatella tokenuetteloita TeXin tapana tallentaa kokonaislukuarvojen sarja, jossa jokainen kokonaisluku on token, joka on johdettu merkistä tai komennosta, jonka TeX oli lukenut syötetiedostostasi.

Tokenuetteloilla on keskeinen rooli TeXin sisäisessä toiminnassa, usein yllättävillä tavoilla, kuten komentojen `\uppercase` ja `\lowercase`. Yksi erityisen tärkeä tokenuetteloiden käyttötarkoitus on makrojen tallentaminen ja suorittaminen, jota tarkastelemme yksityiskohtaisesti tämän sarjan tulevassa artikkelissa.

### TeX saa syötteensä tiedostoista ja tokenuetteloista

TeX-moottoreilla on kolme syötteen lähdettä — kaksi niistä saatat tuntea:

* levylle tallennetut fyysiset tekstitiedostot;
* teksti, jonka käyttäjä kirjoittaa terminaaliin (komentoriville);

mutta sillä on myös kolmas tapa lukea/hankkia syötettä: tokenuettelot!

Tokenuettelot ovat käytännössä TeXin käyttämä sisäinen tiedontallennuspaikka sen toiminnan osana. Koska TeXin tokenuettelot toimivat aiemmin luotujen tokeneiden "varastona", on järkevää, että TeX voi käyttää niitä uudelleen toisena syötteen lähteenä. Kun on tarpeen ottaa seuraava syöte jostakin tietystä tokenuettelosta (tai TeXille käsketään tehdä niin), TeX keskeyttää tilapäisesti syötteen lukemisen fyysisestä tiedostosta (eli luomisen *uusia tokeneita*) ja siirtyy hankkimaan syötteensä *olemassa olevista tokeneista*: muistipaikasta, johon tokenuettelo on tallennettu. Selvää on, että tokenuettelon kohdalla tokeneiden skannaus + luonti on jo tapahtunut, joten TeXin tarvitsee vain katsoa kutakin listan tokenia ja päättää, mitä tehdä kullekin.

Nopeana esimerkkinä matalan tason (TeXin primitiivi) `\toks` komento antaa sinun luoda tokenilistan, jonka TeX tallentaa muistiin myöhempää uudelleenkäyttöä varten:

```latex
\toks100={Hello}
```

Näiden tokeneiden hakemiseksi (eli jotta TeX käsittelisi niitä seuraavana syötteen lähteenään) antaisit komennon kuten

```latex
\the\toks100
```

Tämä saa TeXin siirtymään uusien tokeneiden luomisesta syötetiedostostasi siihen, että se ottaa seuraavan syötteensä sieltä, minne nuo tokenit (joiden luominen tapahtui `\toks`) on tallennettu — niin sanotussa *token-rekisteriä* joka on vain TeXin tuntema sisäinen muistipaikka (tässä se on rekisteri 100).

Lisäksi tokenuetteloita voidaan luoda sisäisesti lennosta useilla TeX-komennoilla. Yksi esimerkki on komento `\jobname` joka luo sarjan merkkitokeneita — yhden tokenin jokaista merkkiä kohden sen päätiedoston nimessä, jota TeX käsittelee. Toinen esimerkki on `\string` komento; esimerkiksi

```latex
\string\mymacro
```

luo sarjan merkkitokeneita jokaiselle kirjaimelle nimen `\mymacro`—mukaan lukien alkuperäinen `\` merkki. Tarkastelemme joitakin "tokeneita tuottavia komentoja" lähemmin tämän artikkelin lopussa.

## Tokenuettelo: selitetty analogian avulla

Ellei sinulla ole ohjelmointitaustaa ja/tai jonkin verran tietojenkäsittelytieteen tuntemusta, "tokenuettelot" voivat olla jokseenkin hämärä käsite ja ehkä hieman hämmentäväkin. Jos kuitenkin haluat oppia kirjoittamaan TeX-/LaTeX-makroja hyvin, hyvä ymmärrys aiheista kuten TeX-tokenit, tokenuettelot ja kategoriakoodit (`\catcode`) osoittautuu erittäin hyödylliseksi.

Tässä osiossa käytämme analogiaa selittääksemme/kuvataksemme TeX-tokenuettelon keskeiset ideat/periaatteet: miten TeX tallentaa tokeneita muistiin. Kannattaa käyttää aikaa tämän lukemiseen, koska tokenuettelot ovat *perustavanlaatuinen* osa TeXiä, ja ne kannattaa ymmärtää hieman tarkemmin.

### Tokenuettelot: analogia (ajatuskoe)

Käymme läpi "ajatuskokeen" luodaksemme pohjan TeX-tokenuetteloiden ymmärtämiselle. Kuvittele, että sinulla olisi käytössäsi suuri joukko säiliöitä, kuten satoja peltirasioita — emme voi käyttää sanaa "box" kuvaamaan ajatuskokeemme säiliöitä, koska "box" tarkoittaa tietenkin TeXissä hyvin tarkkaa asiaa, joka ei liity tähän keskusteluumme. Kutsukaamme siis säiliöitämme "Tins", jossa jokainen Tin:

* siinä on ulkopuolelle painettu yksilöllinen tunnistenumero;
* on (sisäisesti) jaettu kahteen lokeroon.

Nämä kaksi lokeroa on suunniteltu seuraavasti:

* vasen lokero sisältää esineen, jonka haluat laittaa Tiniin;
* oikea lokero on tarkoitettu pitämään paperilappua, johon voit kirjoittaa yhden numeron: toisen Tinin tunnistenumeron.

![testi](/files/7ba113881c11663745b2c4d4db8c812d8c640544)

Oletetaan, että sinulla on esimerkiksi 5 esineen kokoelma ja haluat tallentaa sen näihin Tineihin; mutta valitettavasti kukin Tin voi pitää vain yhden tallennettavaa lajia olevan esineen.

Yksinkertaisuuden vuoksi oletetaan, että haluamme tallentaa 5 värillistä ympyrää:

![{{{alt}}}](/files/536f297fa915436a75667dfd06ce39a427344611)

Lisäksi, kun palaat hakemaan nuo esineet tallennusjärjestelmästäsi (Tins), nuo esineet *täytyy* on voitava hakea/löytää tietyssä järjestyksessä — siinä järjestyksessä, jossa ne tallennettiin: tuo järjestys on säilytettävä. Miten tämän voi toteuttaa?

Voimme hyödyntää sitä, että jokaisessa Tinissä:

* on ulkopuolelle kiinnitetty yksilöllinen tunnistenumero;
* on 2 lokeroa — joista vain yhtä käytämme esineemme säilyttämiseen, kun taas toisessa on paperilappu, johon on kirjoitettu toisen Tinin numero.

Oletetaan, että jokainen Tin on tyhjä — mutta mikään ei estä avaamasta mitä tahansa Tiniä tarkistaaksesi, onko se tyhjä; jos ei ole, kokeile seuraavaa, kunnes löydät tyhjän Tinin.

Voisimme tehdä seuraavasti. Laita ensimmäinen esineemme (tummanvihreä ympyrä) yhteen Tineistämme (esim. Tin 124) ja kirjoita tämän ensimmäisen Tinin numero muistiin — sillä ei ole väliä, mikä numero sillä ensimmäisellä Tinillä on, ainoastaan sillä, että kirjoitamme sen jonnekin ylös ja säästämme myöhempää käyttöä varten.

![{{{alt}}}](/files/818cd52c48ed44e4d2f3d9bfd934f58bb82fd0f6)

Etsi toinen Tin — mikä tahansa Tinin numero (esim. Tin 432) — ja kirjoita sen numero muistiin. Kirjoita tuon toisen Tinin (432) numero paperilapulle ja aseta tuo lappu *ensimmäiseen Tiniin* (Tin 124). Laitamme toisen esineemme (vaaleanvihreä ympyrä) toiseen Tiniin. Tilanne on siis tällä hetkellä seuraava:

* kirjoitettu lappu — ei tallennettuna Tiniin — jossa sanotaan, että ensimmäinen Tin on numero 124 (se sisältää ensimmäisen esineemme);
* Tin 124:ään olemme lisänneet toisen lapun, jossa sanotaan, että seuraava esine löytyy Tinistä 432.

Käytännössä olemme *linkittäneet* ensimmäiset kaksi Tiniämme: tiedämme, mistä aloittaa (Tin 124), ja että Tin 124:ssä oleva lappu kertoo, mikä Tin sisältää seuraavan esineen (Tin 432).

![{{{alt}}}](/files/b70ded4667be25c82232c2f22b24f067268fdf9a)

Sitten löydämme kolmannen Tinin, kirjoitamme sen numeron (esim. Tin 543) paperilapulle ja laitamme sen *toiseen* Tiniin (numero 432). Sitten laitamme kolmannen esineemme (punainen ympyrä) kolmanteen Tiniin.

Nyt olemme linkittäneet kolme Tiniä peräkkäin: lähtöpisteemme, Tin 124 (tummanvihreä ympyrä) → Tin 432 (vaaleanvihreä ympyrä)→ Tin 543 (punainen ympyrä) →…

![{{{alt}}}](/files/e57bb4642057a81c1a7eac110dd3ca3cc8a07fd4)

Toista tämä prosessi kahden viimeisen esineen (vaaleansininen ja tummansininen ympyrä) kohdalla käyttäen Tiniä 213 (vaaleansininen ympyrä) ja Tiniä 102 (tummansininen ympyrä).

![{{{alt}}}](/files/e2f7c9ad0eddb660f82912a0c71703864ae859b9)

Nyt kaikki 5 Tiniä on linkitetty yhteen (käyttäen kunkin Tinin numeerista tunnistetta), ja pystymme hakemaan kaikki tallennetut esineemme — oikeassa järjestyksessä — käymällä yksinkertaisesti jokaisessa Tinissä vuorollaan, poistamalla oman esineemme ja katsomalla lappua, joka kertoo, mikä Tin sisältää seuraavan esineemme.

### Entä listamme viimeinen esine (Tin 102)?

Miksi meidän pitäisi olla erityisen huolissamme juuri tästä? Tähän asti olemme tallentaneet jokaisen esineen Tiniin yhdessä lapun kanssa, joka kertoo, mikä Tin sisältää seuraavan esineen: mitä tuon lapun pitäisi sanoa listamme viimeisen esineen kohdalla — koska seuraavaa Tiniä ei ole.

Kun saavumme viimeiseen esineeseen (Tiniin), on oltava ilmeistä, että tämä Tin (joka sisältää viimeisen esineen) on listamme viimeinen esine — meidän ei tarvitse etsiä toista Tiniä, koska sellaista ei ole. Yksi tapa tehdä tämä on asettaa "erityinen" Tinin numero viimeisen Tinin (102) sisään. Voimme käyttää mitä tahansa numeroa, kunhan valitsemme yksilöllisen numeron, joka ei ole minkään todellisen Tinin numero — esimerkiksi "Tin -1", "Tin 0": sillä ei ole väliä, kunhan tiedämme, että "Tin -1" tai "Tin 0" jne. kertoo meille heti, että etsintä on lopetettava: meidän ei tarvitse etsiä enempää Tinejä, koska tämä on viimeinen, eikä enempää esineitä ole haettavana.

### Esineistä ja Tineistä tokeneihin ja TeXiin

Nyt meidän on siirryttävä analogiastamme kuvausta kohti, joka on lähempänä TeXin todellisuutta. Ensinnäkin, sen sijaan että tallentaisimme erivärisiä ympyröitä mielikuvituksellisiin Tineihimme, on selvää, että voisimme ajatella noiden Tinsien tallentavan TeX-tokeneita: pelkkiä kokonaislukuja. Tämä on analogiamme siirtämisen helpompi osa ohjelmiston (TeXin) maailmaan. Mutta mikä olisi fyysisten numeroitujen Tinsiemme, joissa on "lokerot", ohjelmallinen vastine?

Emme halua mennä liian syvälle ohjelmointikäsitteisiin, mutta voit ajatella Tinsiemme edustavan muutamaa tietokoneen muistissa olevaa tavua, jotka on "pakattu" kätevään tallennusyksikköön. Analogiamme numeerinen tunniste kullekin Tiniille voidaan nähdä tietokoneen muistin sisäisenä sijaintina, jossa kukin pieni muistipaketti sijaitsee. Itse TeXissä näitä pieniä tallennuspaketteja kutsutaan "memory wordeiksi" — termi, joka heijastaa aikaa/aikakautta, jolloin TeX luotiin (1970-luku). Nämä "memory wordit" ovat TeXissä käytetty perusrakennuspalikka, mutta meidän ei tarvitse käsitellä niitä tässä enempää — lisätietoja kaipaava voi viitata artikkeliin [kirjoittajan henkilökohtaisessa blogissa](http://www.readytext.co.uk/?p=3537).

Tietokoneohjelmoinnin termein sitä, mistä olemme puhuneet, kutsutaan [*linkitetty lista*](https://en.wikipedia.org/wiki/Linked_list): TeX-tokeniluettelo on linkitetty lista, joka on rakennettu TeXin tallennussäiliöistä nimeltä *muistisanat* joissa kutakin muistisanaa voidaan käyttää tallentamaan:

* a *arvo*: tokenin arvo (kokonaisluku);
* a *linkki*: seuraavan tokenin sisältävän seuraavan muistisanan muistipaikka.

## Missä TeX käyttää tokenuetteloita?

Kaikkialla! Näin on, koska TeX-/LaTeX-makron määrittely (esim. LaTeX-komento) tallennetaan (hieman erikoistuneena) tokenuettelon muotona — erikoistuneena siinä mielessä, että se sisältää tokeneita, joita et näe "tavallisissa" tokenuetteloissa (liittyen makroparametrien täsmäyttämiseen jne.). Älä huoli tästä, sillä käsittelemme noita yksityiskohtia tulevassa artikkelissa.

### Esimerkkimakro

Makron voi ajatella koostuvan kolmesta osasta:

```
\def\<macro name><parameter text>{<replacement text>}
```

Huomaa, että `\def` olisit voinut käyttää `\edef`, `\gdef` tai `\xdef`.

**Huomautus LaTeX-käyttäjille**: Tässä määrittelemme makroja käyttäen raakaa, matalan tason TeX-komentoja (nimeltään *primitiiveistä*). LaTeX-käyttäjille tutumpaa on luoda makroja LaTeXin avulla `\newcommand` (joka itsessään on makro).

Kun pyydät TeXiä luomaan (määrittelemään) makron, se luo tokenin, joka edustaa `<makron nimi>` ja *tokenuetteloa* joka edustaa yhdistettyä `<parametriteksti>` ja `<korvausteksti>`. TeX tallentaa kaiken huolellisesti niin, että token, joka edustaa `<makron nimi>` on linkitetty tokenuetteloon, joka edustaa sen määritelmää (`<parametriteksti>` ja `<korvausteksti>`).

Esimerkiksi, jos määrittelemme `\mymacro` näin:

```latex
\def\mymacro abc #1 defz{I typed "#1"!}
```

Näemme, että sen osat ovat:

* `<makron nimi>` = `mymacro`
* `<parametriteksti>` = `abc #1 defz`
* `<korvausteksti>` = `I typed "#1"!`

Voisit esimerkiksi kutsua `\mymacro` näin:

```latex
\mymacro abc THIS TEXT defz
```

josta seuraa `I typed "THIS TEXT"!` ladottuna — `abc` ja `defz` olet *sisällä* ladotaan. `abc` ja `defz` ovat merkkitokeneiden sarjoja, joita käytetään *rajaamaan* makroparametri `#1` ja jotka TeX imee sisäänsä ja hylkää, kun makrokutsusi on käsitelty onnistuneesti.

Kun määrittelit `\mymacro`, tallennetussa olevien tokeneiden kuvio toimii "mallipohjana", jonka avulla TeX voi päätellä:

* mitkä syötteesi tokenit ovat erotintokeneita;
* mitkä syötteesi tokenit todella muodostavat makrosi parametrin/parametrit (tässä se, mitä käytät kohdassa `#1` kutsussasi `\mymacro`).

Sinun täytyy kutsua `\mymacro` seuraavalla: `<parametriteksti>` siten, että siinä on samat erottimet kuin ne, joita käytettiin sen määrittelyssä — tähän sisältyy merkkierottimien käyttäminen samoilla kategoriakoodeilla. Jos erotinmerkit `<parametriteksti>` joita käytetään kutsumaan `\mymacro` ovat erilaiset kuin ne, joita käytettiin sen määrittelyssä (muistiin tallennettu "mallipohja"), TeX voi mennä melko sekaisin — kun se yrittää käsitellä `\mymacro` se ei pystyisi vastaamaan muistissaan tallentamaansa "mallipohjaa".

Kun TeX näkee, että kutsut makroa, se skannaa syöteteksisi luodakseen uusia tokeneita ja yrittää token tokenilta sovittaa ne tokenuetteloon `<parametriteksti>` mallipohja, joka on tallennettu osaksi makrosi määritelmää. Jos syöteteksissäsi käytetyt erottimet tuottavat tokeneiden sarjan, joka ei vastaa "mallipohjaan" tallennettuja tokeneita, TeX antaa yleensä virheen.

TeX on hyvin tarkka — muista, että merkkitokenit ovat yhdistelmä merkkikoodista ja kategoriakoodista: jos muutat merkin kategoriakoodia, saat kyseisestä merkistä eri tokenarvon.

Oletetaan, että muuttaisimme merkin kategoriakoodin `z` esimerkiksi arvoon 12 — tavallisesti se on 11 — ja yrittäisimme kutsua makroamme näin:

```latex
\catcode`z=12
\mymacro abc THIS TEXT defz more text here...
```

Tällä kertaa se ei toimi, koska merkin `z` kategoriakoodi on muuttunut. Näet virheen kuten tämän:

```latex
Karkaava argumentti?
THIS TEXT defz
! Kappale päättyi ennen kuin \mymacro oli valmis.
<luetaan uudelleen>
\par
l.22
```

Kun TeX lukee ja skannaa `z` tiedostoihin `defz` se ei tunnista sitä muodostavan loppua `\mymacro`’n `<parametriteksti>` syötetiedostossasi käytetyn. Aina siihen asti kunnes se näki tuon virheellisen `z` TeX oli sovittanut oikein ensimmäiset 3 merkkiä `def` mutta tuo `z` (kategoriakoodilla 12) sekoittaa TeXin skannauksen. Oletetaan, että `z` sillä oli kategoriakoodi 11, kun me *määrittelimme* `\mymacro`: se johtaisi tokenarvoon 256×11 + 122 = 2938, joka tallennettaisiin osaksi `\mymacro`n määritelmää (eli tallennettaisiin osaksi "mallipohjaa"). Kuitenkin kategoriakoodilla 12, `z` luo nyt tokenarvon 256×12 + 122 = 3194. Koska tokenarvo (kohdalle `z`) joka luetaan syötteestäsi (arvo 3194) ei vastaa `z`-tokenia, joka sisältyy tallennettuun `<parametriteksti>` tokenuettelon mallipohjaan (arvo 2938), TeX jatkaa syötteesi skannaamista. TeX jatkaa makrosi jälkeen seuraavan tekstin skannaamista (*lisää tekstiä tähän* ...) etsiäkseen lisätokeneita — yrittäen sovittaa tallennetun mallipohjan syötteestäsi löytyviin tokeneihin. Se ei todennäköisesti löydä oikeaa tokenkuviota, ja seurauksena on virheitä, kun TeX "ylittää" syötteesi ja lukee virheellisesti ylimääräistä tekstiä luodakseen lisätokeneita — noita ylimääräisiä tokeneita ei olisi pitänyt lukea tässä vaiheessa, ja ne lähes varmasti aiheuttavat virheen.

Käsittelemme tätä yksityiskohtaisemmin tulevassa artikkelissa.

## Tokenuetteloiden muita käyttötapoja

Muita tokenuetteloiden luomiseen/tallentamiseen käytettäviä komentoja ovat:

```latex
\toks<n>={...}
\everypar={...}
\everymath={...}
\everydisplay={...}
\everyhbox={...}
\everyvbox={...}
\output={...}
\everyjob={...}
\everycr={...}
\errhelp={...}
```

Jokainen näistä komennoista luo tokenuettelon aaltosulkeiden ‘{...}’ sisällä olevista merkeistä ja komennoista, ja tuo tokeneiden lista on tarkoitettu käytettäväksi uudelleen tietyissä tilanteissa. Esimerkiksi, `\everypar={...}` luo ja tallentaa joukon tokeneita (tokenuettelon), jonka TeX lisää syötteeseen juuri ennen kuin se aloittaa uuden kappaleen.

## Piilotetut tokenuetteloiden käyttötavat: esimerkkejä

Tässä viimeisessä osiossa tarkastelemme joitakin käytännön esimerkkejä tokenuetteloiden käytöstä tavoilla, joita et ehkä odottaisi.

### Esimerkki 1: \uppercase{...} ja \lowercase{....} — tilapäiset tokenuettelot

Tokenuetteloiden luomista varten annettujen selkeiden komentojen lisäksi on tilanteita, joissa TeX luo piilotetun ja tilapäisen sisäisen tokenuettelon suorittaakseen jonkin erityiskäsittelyn. Muista, että kun TeX lukee/käsittelee syötemerkkejäsi/-komentoja, ne muutetaan tokeneiksi: perusrakennuspalikaksi, jonka kanssa TeX-moottorit toimivat.

Hyvä esimerkki ovat komennot `\uppercase{...}` tai `\lowercase{...}` koska niiden toiminta voi ensi kohtaamisella olla melko hämmentävää. Kun ymmärrät, mitä ne tekevät — syvemmällä TeXissä ja käyttäjälle näkymättömissä — niiden toiminta on paljon helpompi ymmärtää.

Oletetaan, että sinulla on yksinkertainen kirjainsarja, jonka haluat muuttaa suuraakkosiksi — esim. abcde ja muuntaa sen ABCDE:ksi. No, se onnistuu helposti TeXin `\uppercase` komento:

```latex
\uppercase{abcde}
```

tuottaa `ABCDE`. Oletetaan nyt, että haluaisimme tallentaa tämän yksinkertaisen kirjainsarjan myöhempää käyttöä varten — eli emme halua tulostaa sitä heti, joten käytämme TeXin ainoaa *sisäistä* mekanismia — ei ulkoista (tiedosto)mekanismia — datan tallentamiseen: käytä tokenuetteloa. Voimme tehdä sen joko luomalla makron tai käyttämällä nimenomaista tokenuettelokomentoa:

```latex
\toks100={abcde}
\def\mychars{abcde}
```

Sitten jossain vaiheessa saatat päättää haluavasi käyttää kirjainsarjaasi uudelleen, mutta tällä kertaa suuraakkosina; joten yrität

```latex
\uppercase{\the\toks100}
```

ja

```latex
\uppercase{\mychars}
```

Mutta valitettavasti kumpikaan näistä ei toimi. Miksi?

### Salaiset tokenuettelot!

Ymmärtääkseen, miten komennot `\uppercase{...}` `\lowercase{...}` todella toimivat, minun piti kurkistaa TeXin sisäisiin mekanismeihin, joten seuraava selitys perustuu siihen.

Kun TeX havaitsee jommankumman `\uppercase{<material>}` tai `\lowercase{<material>}` syötteessäsi, ensimmäinen asia, jonka TeX tekee, on luoda (tilapäinen) sisäinen tokenuettelo `materiaalista` sellaisista merkeistä, jotka on suljettu niiden jälkeen tulevien `\uppercase{...}` tai `\lowercase{...}` komentojen väliin — tuo tilapäinen tokenuettelo on TeXin sisäinen.

Keskeinen ja ratkaiseva seikka sen ymmärtämisessä, miten `\uppercase{<material>}` ja `\lowercase{<material>}` itse asiassa toimivat, on se, että kaikki siinä olevat komennot tai makrot `materiaalista` eivät ole *laajennettu*: TeX vain luo tokeneita merkkien ja komentojen perusteella, jotka on sijoitettu `{...}`. Käytön aikana `\uppercase{<material>}` tai `\lowercase{<material>}` mitään aaltosulkeiden sisällä ei suoriteta: se muutetaan yksinkertaisesti tokeneiksi.

Kohdan `materiaalista` sisällä `{...}` on muunnettu (tilapäiseksi) tokenuetteloksi, TeX palaa sitten uudelleen jokaiseen tuon listan tokeniin ja testaa, onko se *merkkiä* token vai *komento* token (käyttäen tokenin numeerista arvoa). Jos TeX havaitsee merkkitokenin, se muokkaa tuota tokenia säätääkseen merkin kirjainkokoa (sen mukaan, onko `\uppercase` tai `\lowercase` käsiteltävänä). TeX yksinkertaisesti sivuuttaa kaikki komentotokennet eikä "katso sisään" niihin nähdäksensä, mitä ne edustavat tai sisältävät (esim. makro, joka sisältää merkkejä) — ne ohitetaan yksinkertaisesti: vain merkkitokenit todella käsitellään/niihin vaikutetaan kirjainkokoa muuttavissa operaatioissa.

Joten esimerkiksi, jos annamme TeX-komennon kuten `\uppercase{abcde}` TeX luo tokenuettelon `abcde` joka sisältää vain merkkitokeneita: ne kaikki säädetään luomaan sarja muokattuja tokeneita, jotka edustavat A:ta, B:tä, C:tä, D:tä ja E:tä. Nuo muokatut tokenit syötetään takaisin TeXin syöteprosessoriin, mikä johtaa siihen, että `ABCDE` ladotaan. Jos kuitenkin olemme tallentaneet merkkimme *makron sisään*—esimerkiksi `\def\mychars{abcde}`—ja yritämme muuntaa ne suuraakkosiksi näin:

```latex
\uppercase{\mychars}
```

silloin se epäonnistuu ja ladotaan abcde — ei ABCDE kuten ehkä odottaisit. Jos sitten yritämme tallentaa merkkimme tokenuetteloon kuten `\toks0={abcde}` ja teemme `\uppercase{\the\toks0}` silloin jälleen `\uppercase` epäonnistuu, koska tokenuettelo koostuu kokonaan tokeneista, joihin `\uppercase`.

Jos otamme esimerkiksemme makromme, `\mychars`, kun TeX havaitsee `\uppercase` syötteessä, TeX hakee merkityksen `\uppercase` ja suorittaa sen toiminnon, luoden tilapäisen tokenuettelon `{\mychars}`. Selvää on, että tuo tilapäinen tokenuettelo sisältää vain yhden tokenin, joka ei ole merkkitoken vaan joka edustaa makrokomentoamme `\mychars`: näin ollen, kun `\uppercase`, sitä tokenia sivuutetaan —`\mychars` ei edusta merkkitokenia. Kuten edellä todettiin, kun `\uppercase` on tehnyt työnsä, tilapäinen tokenuettelo (jonka loi `\uppercase`) syötetään takaisin TeXin täyteen syötteenkäsittely- (skannaus-) mekanismiin. Kun TeX lukee tuon tokenuettelon uudelleen, se havaitsee tokenin, joka edustaa meidän `\mychars` makroamme, jonka TeX suorittaa (laajentaa) ja joka luo sarjan merkkejä ladottavaksi abcde — yhä pienaakkosina, koska ne oli "kääritty" makron sisään ja siten näkymättömiä `\uppercase`.

Kun TeX on tutkinut uudelleen tilapäisen tokenuettelon, joka luotiin `\uppercase{...}` tai `\lowercase{...}`, ja käsitellyt mahdolliset merkkitokenit, se siirtyy käyttämään tuota tilapäistä tokenuetteloa syötteensä lähteenä: ladottaen merkkejä (käsiteltyjä merkkitokeneita) ja suorittaen komentoja ja makroja.

### Miten tämä voidaan korjata?

Koska `\uppercase{...}` tai `\lowercase{...}` vaikuttaa vain merkkitokeneihin, meidän on löydettävä tapa "pakottaa purkamaan" makromme sisältämät merkit `\mychars` (tai sisältyvät `\toks` rekisteriin) ennen kuin `\uppercase{...}` tai `\lowercase{...}` toimii siihen. "Purkamalla" tarkoitamme oikeastaan TeXin prosessia *laajennus*:

* korvata TeX-/LaTeX-komento *sarjalla* tokeneita *joista tuo komento* (*esim. makro*) *koostuu,* tai
* tuottaen tokeneiden sarjan, jonka komento on suunniteltu *luomaan*. Yksi esimerkki komennosta, joka luo tokeneita, on `\jobname`, joka tuottaa sarjan merkkitokeneita, jotka edustavat käsiteltävän pääTeX-tiedoston nimeä.

#### Matalamman tason taikuutta: scantoks(..., ...)

Tässä kurkistamme todella TeXin sisäisten toimintojen synkempiin nurkkiin, joten voit ohittaa tämän osion, ellei yksityiskohtien penkominen miellytä…

Kun TeX havaitsee `\uppercase` tai `\lowercase` syötevirrassa, se suorittaa sisäisen funktion nimeltä `scantoks(..., ...)` jonka tehtävänä on luoda tokenuettelo käyttäen avaus-‘{’ ja lopetus-‘}’ -merkkien välissä olevia osia — kuten todettiin, tuo tokenuettelo tutkitaan myöhemmin merkkitokeneiden havaitsemiseksi (ja sitten säätämiseksi), jotta merkkien kirjainkoko voidaan muuttaa tarvittaessa. Huomaa tarkasti, että viittaamme `scantoks(..., ...)` sisäiseen funktioon, joka on rakennettu TeX-moottoreiden lähdekoodiin — tässä sitä ei tarkoiteta ohjaussekvenssin nimenä.

Työnsä osana, `scantoks(..., ...)` voidaan määrätä laajentamaan tai olemaan laajentamatta rakentamaansa tokenuetteloa, ja `\uppercase` ja (`\lowercase`) se ei laajenna tokeneita: se vain luo ne ja asettaa ne tokenuetteloon.

Yksi ensimmäisistä asioista, jotka `scantoks(..., ...)` sen täytyy tehdä, on tarkistaa avaus-‘{’ (tai mikä tahansa merkki, jonka `\catcode` kategoriakoodi on 1), koska sen on varmistettava, ettei käyttäjä ole tehnyt syntaksivirhettä ja unohtanut avaus-‘{’:ää (tai mitään merkkiä, jonka kategoriakoodi on 1) — sillä kategoriakoodin 1 omaava merkki tarvitaan rajaamaan tokenoitavien kohteiden listan alku.

Ja tässä on juju: avaus-‘{’:n etsimisen tehtävä käynnistää `scantoks(..., ...)` TeXin laajennusprosessin, mikä tarkoittaa, että seuraavat esimerkit toimivat:

```latex
\let\ob={
\uppercase\ob abcde}
\def\obb{\ob}
\uppercase\obb xyz}
```

Otetaan esimerkiksi `\obb`, makro, se tunnistetaan *laajeneva komento* ja TeX laajentaa sen asianmukaisesti ( `scantoks(..., ...)` funktion kautta) etsiessään avausaaltosulkua (mitä tahansa merkkiä, jonka kategoriakoodi on 1). Tämä tarkoittaa, että voimme käyttää "`\expandafter` kikkaa" saavuttaaksemme tavoitteemme "purkaa" merkkimme makromme sisältä — eli laajentaa sen. Huomaa, että `\expandafter` kuuluu myös luokkaan *laajeneva komento*, joten TeX käsittelee sen tässä ja antaa sen tehdä työnsä osana avaus-‘{’:n (tai minkä tahansa merkin, jonka kategoriakoodi on 1) metsästystä.

So, if you define:

```latex
\toks0={abcde}
\def\mychars{abcde}
```

And do this:

```latex
\uppercase\expandafter{\mychars}
\uppercase\expandafter{\the\toks0}
```

molemmissa tapauksissa näet nyt ABCDE:n ladottuna, koska `\expandafter` aiheuttaa "purkamisen" (laajentamisen) kohteelle `\mychars` ja `\the\toks0`—molemmat johtavat siihen, että `\uppercase` näkee merkkitokeneiden virran, jota ne voivat käsitellä muuttaakseen kirjainkokoa.

### Esimerkki 2: \string — lisää tilapäisiä tokenuetteloita

Sisäisesti TeX luokittelee `\string` yhdeksi niin sanotuista "muunna"-komennoistaan: suorittaa toiminnon "muunna tekstiksi". Se `\string` komento on suunniteltu muuntamaan merkkiyksikkö ihmisen luettavaksi tekstiversioksi—eli ladottamaan ihmisen luettava merkkijono, josta kyseinen merkkiyksikkö alun perin luotiin.

Esimerkiksi `\string\hello` luo väliaikaisen token-listan, joka sisältää merkit \\, h, e, l, l, o — kyllä, jopa alkuperäisen ‘\’:n mukaan lukien. Kun token-lista on luotu, TeX lukee sen sitten uudelleen, ja komennon “`\hello`” teksti ladotaan—kyllä, mukaan lukien ‘\’, jos valitset oikean fontin…

Saatat ihmetellä, miten/miksi TeX voi ladota escape-merkin, kun sitä yleensä käytetään laukaisemaan TeXin jäsennin luomaan komentotoken: miksei se tee niin tässä? Vastaus liittyy kategoriakoodeihin: yleensä ‘\’-merkin catcode on 0 (escape-merkki), mutta kun `\string` se luo sisäisen token-listansa, se tekee hieman toisin. Kun se luo merkkitoken-listan, se antaa kaikille merkeille paitsi välilyönnille kategoriakoodin 12; välilyönnille annetaan catcode 10—muista, että merkkitokenit lasketaan kaavalla 256 x catcode + ASCII-arvo. Kun TeX siis lukee uudelleen (syöttää) väliaikaisen token-listan, jonka `\string` joka on generoitu `\hello`, TeX *ei näe escape-merkkiä* koska ‘\’-token laskettiin catcode 12:lla eikä 0:lla: TeX käsittelee ‘\’:tä vain tavallisena merkkinä ja ladottaa sen.

Tarkkaan ottaen meidän pitäisi ehkä huomata, että TeX ei itse asiassa luo escape-merkeille tokenia silloin, kun se tunnistaa ne syötteessä. Kun se on tunnistanut merkin, որի kategoriakoodi on 0, kyseistä merkkiä käytetään vain “laukaisemaan” ohjaussekvenssitokenin luominen: kun se on saanut TeXin tekemään sen, escape-merkki on tehnyt tehtävänsä eikä sitä enää huomioida.

### Tekninen huomautus

Komento nimeltä `\showtokens{...}` (e-TeX-moottorin esittelemä) voi näyttää token-listoja (lokitiedostossa). e-TeX-käsikirjasta:

> Komento `\showtokens{<token list>}` näyttää token-listan ja mahdollistaa sellaisten suureiden näyttämisen, joita ei voi näyttää komennolla `\show` tai `\showthe`, esim.:
>
> ```latex
> \showtokens\expandafter{\jobname}
> ```

## Yhteenvetona

TeX-lähdekoodin kohdassa 291 (katso sivu 122 teoksesta [TeX: The Program](https://www.amazon.co.uk/Computers-Typesetting-TeX-Program-TEX/dp/0201134373)) Knuth kuvaa token-listan seuraavasti:

> “Token-lista on yksisuuntaisesti linkitetty yhden sanan solmujen lista muistissa, jossa jokainen sana sisältää tokenin ja linkin. Makromäärittelyt, ulostusrutiinimäärittelyt, merkinnät, `\write-komennon` tekstit ja muutamat muut asiat TeX muistaa token-listojen muodossa, yleensä niiden edellä on solmu, jonka viitemäärä on sen “token\_ref\_count”-kentässä.”

Ensimmäisellä lukemalla tämä ei ehkä ollut helppo ymmärtää, mutta toivottavasti se alkaa nyt tuntua hieman järkevämmältä.


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter, and the optional `goal` query parameter:

```
GET https://overleaf-pro.ayaka.space/latex/fi/syvalliset-artikkelit/54-what-is-a-tex-token-list.md?ask=<question>&goal=<endgoal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is optional and describes the broader end goal you are ultimately trying to accomplish on behalf of the user. GitBook uses it to tailor the answer towards what is most useful for that goal.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
