CLT131: Tekstityökalut 2012, yhdeksäs luento
Tommi A Pirinen
tommi.pirinen+clt131@helsinki.fi
Helsingin yliopisto
Kieliteknologian oppiaine, Nykykielten laitos
31. tammikuuta 2012
Asialista
1 Tehtävät
2 Teoriaa
3 Menetelmät ja työkalut
1. Frekvenssien laskenta
Perusratkaisuhelppo, muuttujat eivät tuoneet ongelmia
luvun poimintauniq -c:n tulosteesta (taiwc -l tiedosto -tulosteesta) grepillä tai tr:llä ja headilla säätämällä
2. Virkkeistys
Perusratkaisu ei paljoa tuo muutosta tuttuihin menetelmiin, esim.
sedillä välimerkin ja sanavälin yhdistelmät välimerkiksi ja rivinvaihdoksi
pari helpohkoa parannusta:
vain suurakkosta ja sanaväliä edeltävät isot välimerkit katkotaan suuraakkoset (edelleen) varminta saada joko luettelemalla [ABC...ÅÄÖ]tai luokalla[[:upper:]], eritoten[A-Z]jo voi tuottaa suomen asetuksilla myös pienet kirjaimet
lisäksi tunnetut pisteelliset lyhenteet voi suojata väliaikaisesti muuttamalla lyhenteiden pisteet muiksi (ehkä vain ei
suuraakkosen edeltä?)
otsikoiden joutuminen osaksi seuraavaa virkettä estetään sinänsä samalla taktiikalla kuin edellisen tehtävä lyhenteet, mutta valinta ei aivan triviaalia
3. Haukut
suora ratkaisu helpohko perustaa esim. bigrammiskriptiin tai muodostaa kahden sanan hakulauseke
myös saneistetusta aineistosta ilman bigrammiskriptiä voi saada kontekstia grepin kontekstivalitsimilla
jatkoparannuksina esim. haukkujen hakulauseketta voi parannella verbiketjut, relaatiorakenteet jne.
4. taulukon yhdistelyt
join tuotti jonkin verran hankaluuksia, eikä se sinänsä hyvin yleinen tai korvaamaton työkalu olekaan
helpoiten pääsi tarkkaavaisesti seuraamalla joinin toimintaehtoja ja käytöstä
siis; yhdistettävien sarakkeiden pitäisi olla järjestyksessä, esim.
pidetään kaikkien taulukkojen sanesarakkeet järjestyksessä ja yhdistellään ne keskenään
suoraan kolmen taulukon yhdistämisessä on huomattava, että yhdistelty sarake hyppää ensimmäiseksi; ensimmäisen
yhdistämisen tuloksessa saneet ovat siis sarakkeessa 1 eikä 2 tämä voidaan suoraan lennostakin yhdistää kolmanteen frekvenssilistaan ilmoittamalla sarakkeeksi se 1, ja tiedostonimeksi -, joka tarkoittaa |:a.
8.3. Harjoitustyöstä
Ohjeita ja arvostelukriteerejä on verkkosivuilla
http://www.ling.helsinki.fi/kit/2011s/clt131/
priv/harjoitustyo.shtml Harjoitustyön osaset:
Skriptit
kirjoitelma, josta käy ilmi:
I ”tutkimuskysymys”, lähtöoletus, tavoite tms.
I menetelmät
I aineisto
I lopputulos
käyttöohje ja esimerkkiajo
”esitelmä” käsittää 2—15 minuuttia
Asialista
1 Tehtävät
2 Teoriaa
3 Menetelmät ja työkalut
AWK-kieli
AWK-kieli on täysimittainen ohjelmointikieli, jolla tyypillisesti operoidaan riveihin ja sarakkeisiin (tai sanoihin) jaettua dataa AWKin nimi tulee sen keksijöiden nimien alkukirjaimista, Aho, W...
ja Kernighan
kuten tästä voi arvella, AWKin varsinainen komentokieli on hyvin samannäköinen kuin C (R. Kernighanin tunnetumpi
ohjelmointikieli)
aiheena awk olisi varmasti kokonaisen kurssin mittainen, tässä katsotaan hyvin laveasti paria komentoa ja yleistä syntaksia
Awkin perusrakennuspalikat 1: yleinen rakenne ja käytös
Awk kuten bashkin sisältää muuttujia, joihin voi tallentaa tietoa kuten numeroita ja merkkijonoja
Awk käsittelee tiedostoja rivi riviltä ja jakaa rivin automaattisesti sarakkeisiin, joista voi puhua muuttujalla$1( tämän rivin ensimmäinen sarake) jne.
Awk tietää myös paljon muita asioita, kuten sarakkeiden määrän rivillä muuttujassaNF(number of fields) rivien määränNR(number of records) jne., näitä kun kirjoittaa lähes minne tahansa
AWK-koodissa niin ne toimivat vastaavan arvona (lisätietoja ks.
man gawk)
Uusia muuttujia voi asetella itse, kuten bashissakin, yhtäsuuruusmerkilläyksi=1.
Awk-komennot koostuvat tyypillisesti kahdesta osasta:
hakuehdoista ja komennoista
ne kirjoitetaangawk ’hakuehdot {komento; komento;
Awkin perusrakennuspalikat 2: hakuehdot
hakuehdoissa voi kuvata varsin monenlaisia asioita:
I koko riviä koskevaa säännöllistä hakulauseketta:/lauseke/
I jotain rivin kenttää koskevaa hakulauseketta:$1 ~/lauseke/
I sarakkeeseen liittyvää muuta vertailua$1 > 1000(suurempi kuin tuhat jos lukuarvo)$2 == "kissa"(täsmälleen yhtäläinen)
I huom! ”hakuehto” voi olla myös$2 = "kissa", se tarkoittaa
”aseta sarakkeen 2 arvoksi "kissa”’, yleinen virhe uusille C- ja AWK-ohjelmoijille!
I sarakkeita voi myös vertailla keskenään$2 < $3
I erikoismerkinnöilläBEGIN(aluksi) jaEND(lopuksi)
I hakuehtoja voi yhdistellä keskenään loogisilla operaattoreilla&&ja,
||tai,?:jos-niin-muutoin,!ei:
I erityisen hyödyllinen on useampaa riviä koskeva hakuehtopari:
/ekarivi/,/vikarivi, joka kaappaa rivit ekarivi-lausekkeesta vikarivi-lausekkeseen käsiteltäväksi
Awkin perusrakennuspalikat 3: toiminnot
toiminnoissa on käytössä laajahko ohjelmointikieli joka sisältää kaikkea: matematiikka, tulostusta, merkkijonojenkäsittelyä, käyttöjärjestelmäkutsuja, . . . . Muistetaan toimintojen syntaksi {toiminto; toiminto; ...;}:
I yleisintä on käyttää tulostustoimintoaprint, sellaisenaan se tulostaa koko rivin
I komennoille annetaan sulkeissa parametrilistoja, esim. print tulostaa kenttiä jotka sille antaaprint($3, $1)(tulostaa ensimmäisen ja kolmannen kentän)
I aritmetiikkaa hoidetaan enimmäkseen samoin kuin muilla ohjelmilla:+, -, *, /, esim:print(($1 + 1) / 10000) tulostaa ensimmäisen kentän
I printiä hienovaraisempi tulostuskomento onprintf, jolle kerrotaan tulostusmuotoilujaprintf("sanan %s todnäk olikin %g
\n", $2, $1/100);(vaatii aika paljon opettelua, mutta on varsin kätevä)
I myös muuttujia voi käsitellä toiminnossa:rivit = rivit + 1;
(kasvattaa omaa rivilaskuria)
Asialista
1 Tehtävät
2 Teoriaa
3 Menetelmät ja työkalut
Kokeillaan rakennella awkeja näistä osasista
rakennuskaava komentoriviltähän oli:gawk ’hakuehdot {komento; komento; ...;}’:
I haetaan kissat-rivit tulostettaviksi:gawk ’/kissa/ {print}’
I mutta vain jos kissa piilee kolmannessa saneessa:gawk ’$3
~/kissa/ {print}’
I etsitään että toinen sarake on tasan ”paukkaa”gawk ’$2 ==
"paukkaa"{print}
I tehdään ekan sarakkeen prosenttilaskurigawk ’{printf("%g
%%\n", $1/100);}
Monimutkaisemmat skriptit usein tehdään tiedostoon
gawk -f skripti.awk skripti.awk:
1 BEGIN {kissoja = 0;}
2 /kissa/ {kissoja = kissoja + 1;}
3 END {print("Tiedostossa", FILENAME, "oli nyt", kissoja, "kissaa")}
muita esimerkkejä?