Topic structure was derived from the titles and abstracts of 600 records, of which 600 contained abstracts of at least 40 words and were retained for analysis. Text was Unicode-normalised (NFKC), lower-cased and tokenised; adjacent word pairs occurring at least 2 times with a pointwise mutual information of at least 3.0 were merged into phrase tokens. Tokens were reduced to stems with the Porter algorithm (PorterStemmer, NLTK) and filtered against the NLTK English stop-word list (n = 198), a built-in list of academic boilerplate stems (n = 51) and 0 project-specific stop words; tokens shorter than 3 characters were discarded.
Terms occurring in at least 2 documents were retained as candidate nodes. For each of the 965877 candidate term pairs, the null hypothesis of independent occurrence was tested with a one-sided (right-tail) hypergeometric test, and p-values were corrected for multiple comparisons with the Benjamini–Hochberg false discovery rate procedure at α = 0.05. Pairs surviving correction with a binary Pearson correlation above ρ = 0.3 were retained, yielding a validated co-occurrence network of 1337 terms and 1762 edges.
Topics were identified by Louvain community detection on the validated network, with edges weighted by ρ and a fixed random seed of 42, producing 385 communities (modularity Q = 0.944).
Documents were assigned to topics by a second one-sided hypergeometric test of the overlap between each document's validated terms and each topic's term set, corrected with the Bonferroni procedure at α = 0.01; a document may be assigned to several topics or to none. 211 documents received at least one assignment and 389 received none. A further Bonferroni-corrected test at the same α identified 14 documents whose vocabulary drew significantly on the validated term set as a whole; these are reported separately as general documents.