Parlis text-mining

Naast de gestructureerde data zijn ook alle platte tekst bestanden van de tweede kamer vrijgegeven. Middels deze naar tekst geconverteerde bestanden gaan we onderzoeken welke woorden in de documenten het meest voorkomen. Je hebt dan van alle documenten de woord-frequentie in je database, die je weer kan koppelen aan de gestructureerde data of metadata zoals zaken, activiteiten, enz.

Let op: dit is een snelle tutorial om je bekend te maken met tekst mining. Text-mining vereist in de praktijk veel snellere algoritmes dan onderstaande. Je server zal ook tegen een stootje moeten kunnen. Zorg voor veel RAM, CPU’s en minstens 30 Gigabyte hardeschijfruimte. Voer ook geen queries uit in een productie omgeving.

Hieronder wordt text-mining in vier stappen uitgelegd.

Stap 1:

Je kunt het best de tekst bestanden downloaden en vervolgens uitpakken naar een aparte folder:

Wget http://data.appsvoordemocratie.nl/txt/txt.tar.gz

Gunzip txt.tar.gz

Tar xvf txt.tar


Stap 2:

We maken 2 scripts aan die bestand voor bestand de woorden aftelt:

Script 1 (compute_freq.sh)

#!/bin/sh

find ./txt -name “*” -exec sh -c “sh compute_filefreq.sh {}”  \;

Wat lastig is met zoveel bestanden (100k+) is dat linux niet goed kan omgaan met zoveel bestanden in één map. Als je probeert de bestanden te hernoemen of te kopieëren, dan zal je al snel ‘too many arguments’ zien. Find zoekt bestanden één voor één op en voert daar een programma op uit.

Script 2 (compute_filefreq.sh)

#!/bin/sh

# $1 = file name

cat $1  | tr [:punct:] ‘ ‘| tr [:cntrl:] ‘ ‘ | tr [:digit:] ‘\n’  | tr [:blank:] ‘\n’ |awk ‘{if(length($0) > 8){print $0}}’ | tr ‘[:upper:]‘ ‘[:lower:]‘ | sort |  uniq -c |  awk ‘{print “‘`basename $1 .txt.gz`’”, $0}’ | tr ‘ ‘ ‘\t’ >> /root/parlis/miningtxt/word_freq.tsv

mv $1 /root/parlis/miningtxt/cptd

Het bestand wordt afgedrukt met ‘cat’ commando. Vervolgens filteren we met het commando ‘tr’ interpunctie, controletekens, cijfers. Ook zetten we alle spaties, die de woorden scheiden, om naar de einderegel code ‘\n’. Er is nu een lijst met op elke regel een woord of een serie spaties.

We filteren met ‘awk’ alle woorden met 8 of meer letters eruit (in verband met de performance).We zetten alle hoofdletters om naar kleine letters en sorteren de hele lijst alfabetisch met het commando ‘sort’. Met het commando ‘uniq –c’ worden alle herhalende woorden geteld en verwijderd. Het commando ‘awk’ voegt aan het einde van elke regel, die nu bestaat uit een woord en een aantal, de naam van het tekst-bestand toe.

Stap 3:

Inladen in de database kan met de volgende (My)SQL instructie:

CREATE TABLE IF NOT EXISTS `parlis`.`Document_WordFrequencyCount`(`ID`VARCHAR(64) NOT NULL,
`Aantal` INT NOT NULL,`Woord`VARCHAR(4000) NOT NULL ,
INDEX (ID)
);
LOAD DATA LOCAL INFILE ‘word_freq.newtsv’ INTO TABLE
`parlis`.`Document_WordFrequencyCount`
FIELDS TERMINATED BY ‘ ‘ ENCLOSED BY ” ESCAPED BY ‘\\’
LINES TERMINATED BY ‘\n’ STARTING BY ” IGNORE 0 LINES;

Merk op dat de volgende conversie instructie zorgt dat er tabs worden ingevoegd in het bestand:

tr ‘ ‘ ‘\t’

Bij het importeren in de database bleek dat deze niet helemaal goed stonden. Dit is opgelost met:

awk ‘{print $1, $2, $3}’ word_freq.tsv > word_freq.new.tsv

Je kunt dit ook direct doen door het ‘tr’ commando te vervangen met de ‘awk’ instructie.

Stap 4:

Het eindresultaat is een tekst bestand met per woord de frequenties. Echter de uitdaging is natuurlijk om deze te koppelen aan bijvoorbeeld Zaken en Activiteiten. Het volgende script kan worden gebruikt voor de berekening van de frequenties:

SELECT `Woord`, SUM(Aantal) as `Aantal_Keer`
FROM `Document_WordFrequencyCount`
GROUP BY `Woord`
ORDER BY SUM(Aantal) DESC
INTO OUTFILE ‘/tmp/word_freq_all.tsv’
FIELDS TERMINATED BY ‘ ‘
ENCLOSED BY ”
LINES TERMINATED BY ‘\n’;

Let op: bij het dumpen naar andere folders dan de ‘/tmp’ map ontstaan foutmeldingen. Dit kan dus niet zomaar aangepast worden.

Let op 2: Voor 8 letters en meer is er al een vrije schijfruimte van 5.3 GB nodig. Dit is natuurlijk slechts een uitleg van de principes van text-mining. Beter is om technologie, die geschikt is voor bigdata , zoals Hadoop te gebruiken. Hadoop deelt het probleem in stukken op en loopt er dan in blokken door heen.

Text-mining in beeld gebracht

Hieronder zie je de frequenties van de meest voorkomende woorden in beeld gebracht in een grafiek.

Dit is niet de eerste keer dat er woord frequenties zijn gemaakt op basis van alle tweede kamer stukken. Het is nu wel de eerste keer dat ook jij er ook mee aan de slag kan! Succes!