web-dev-qa-db-fra.com

Lemmatisation java

Je cherche un lemmatisation implementation pour l'anglais en Java. J'en ai déjà trouvé quelques-uns, mais il me faut quelque chose qui nécessite peu de mémoire (1 Go de haut). Merci. Je n'ai pas besoin d'un stemmer.

22
Ilija

La bibliothèque Stanford CoreNLP Java contient un lemmatiseur qui nécessite peu de ressources, mais je l’ai exécuté sur mon ordinateur portable avec <512 Mo de RAM.

Pour l'utiliser:

  1. Téléchargez les fichiers jar ;
  2. Créez un nouveau projet dans l'éditeur de votre choix/créez un script ant qui inclut tous les fichiers jar contenus dans l'archive que vous venez de télécharger;
  3. Créez une nouvelle Java comme indiqué ci-dessous (d'après l'extrait de code du site de Stanford);
import Java.util.Properties;

public class StanfordLemmatizer {

    protected StanfordCoreNLP pipeline;

    public StanfordLemmatizer() {
        // Create StanfordCoreNLP object properties, with POS tagging
        // (required for lemmatization), and lemmatization
        Properties props;
        props = new Properties();
        props.put("annotators", "tokenize, ssplit, pos, lemma");

        // StanfordCoreNLP loads a lot of models, so you probably
        // only want to do this once per execution
        this.pipeline = new StanfordCoreNLP(props);
    }

    public List<String> lemmatize(String documentText)
    {
        List<String> lemmas = new LinkedList<String>();

        // create an empty Annotation just with the given text
        Annotation document = new Annotation(documentText);

        // run all Annotators on this text
        this.pipeline.annotate(document);

        // Iterate over all of the sentences found
        List<CoreMap> sentences = document.get(SentencesAnnotation.class);
        for(CoreMap sentence: sentences) {
            // Iterate over all tokens in a sentence
            for (CoreLabel token: sentence.get(TokensAnnotation.class)) {
                // Retrieve and add the lemma for each Word into the list of lemmas
                lemmas.add(token.get(LemmaAnnotation.class));
            }
        }

        return lemmas;
    }
}
35
Chris

La réponse de Chris à propos du Standford Lemmatizer est excellente! Absolument magnifique. Il avait même inclus un pointeur sur les fichiers jar, je n'avais donc pas à chercher sur Google.

Cependant, une de ses lignes de code comportait une erreur de syntaxe (il a en quelque sorte inversé les parenthèses fermantes et le point-virgule de fin de la ligne commençant par "lemmas.add ...), et il a oublié d'inclure les importations.

En ce qui concerne l'erreur NoSuchMethodError, elle est généralement causée par le fait que cette méthode n'est pas rendue publique, mais si vous regardez le code lui-même (à http://grepcode.com/file/repo1.maven.org/maven2/com .guokr/stan-cn-nlp/0.0.2/edu/stanford/nlp/util/Generics.java? av = h ) n’est pas le problème. Je soupçonne que le problème se situe quelque part dans le chemin de génération (j'utilise Eclipse Kepler, il n'y a donc aucun problème à configurer les 33 fichiers jar que j'utilise dans mon projet).

Ci-dessous, ma correction mineure du code de Chris, ainsi qu'un exemple (mes excuses à Evanescence pour le massacre de leurs paroles parfaites):

import Java.util.LinkedList;
import Java.util.List;
import Java.util.Properties;

import edu.stanford.nlp.ling.CoreAnnotations.LemmaAnnotation;
import edu.stanford.nlp.ling.CoreAnnotations.SentencesAnnotation;
import edu.stanford.nlp.ling.CoreAnnotations.TokensAnnotation;
import edu.stanford.nlp.ling.CoreLabel;
import edu.stanford.nlp.pipeline.Annotation;
import edu.stanford.nlp.pipeline.StanfordCoreNLP;
import edu.stanford.nlp.util.CoreMap;

public class StanfordLemmatizer {

    protected StanfordCoreNLP pipeline;

    public StanfordLemmatizer() {
        // Create StanfordCoreNLP object properties, with POS tagging
        // (required for lemmatization), and lemmatization
        Properties props;
        props = new Properties();
        props.put("annotators", "tokenize, ssplit, pos, lemma");

        /*
         * This is a pipeline that takes in a string and returns various analyzed linguistic forms. 
         * The String is tokenized via a tokenizer (such as PTBTokenizerAnnotator), 
         * and then other sequence model style annotation can be used to add things like lemmas, 
         * POS tags, and named entities. These are returned as a list of CoreLabels. 
         * Other analysis components build and store parse trees, dependency graphs, etc. 
         * 
         * This class is designed to apply multiple Annotators to an Annotation. 
         * The idea is that you first build up the pipeline by adding Annotators, 
         * and then you take the objects you wish to annotate and pass them in and 
         * get in return a fully annotated object.
         * 
         *  StanfordCoreNLP loads a lot of models, so you probably
         *  only want to do this once per execution
         */
        this.pipeline = new StanfordCoreNLP(props);
    }

    public List<String> lemmatize(String documentText)
    {
        List<String> lemmas = new LinkedList<String>();
        // Create an empty Annotation just with the given text
        Annotation document = new Annotation(documentText);
        // run all Annotators on this text
        this.pipeline.annotate(document);
        // Iterate over all of the sentences found
        List<CoreMap> sentences = document.get(SentencesAnnotation.class);
        for(CoreMap sentence: sentences) {
            // Iterate over all tokens in a sentence
            for (CoreLabel token: sentence.get(TokensAnnotation.class)) {
                // Retrieve and add the lemma for each Word into the
                // list of lemmas
                lemmas.add(token.get(LemmaAnnotation.class));
            }
        }
        return lemmas;
    }


    public static void main(String[] args) {
        System.out.println("Starting Stanford Lemmatizer");
        String text = "How could you be seeing into my eyes like open doors? \n"+
                "You led me down into my core where I've became so numb \n"+
                "Without a soul my spirit's sleeping somewhere cold \n"+
                "Until you find it there and led it back home \n"+
                "You woke me up inside \n"+
                "Called my name and saved me from the dark \n"+
                "You have bidden my blood and it ran \n"+
                "Before I would become undone \n"+
                "You saved me from the nothing I've almost become \n"+
                "You were bringing me to life \n"+
                "Now that I knew what I'm without \n"+
                "You can've just left me \n"+
                "You breathed into me and made me real \n"+
                "Frozen inside without your touch \n"+
                "Without your love, darling \n"+
                "Only you are the life among the dead \n"+
                "I've been living a lie, there's nothing inside \n"+
                "You were bringing me to life.";
        StanfordLemmatizer slem = new StanfordLemmatizer();
        System.out.println(slem.lemmatize(text));
    }

}

Voici mes résultats (j'ai été très impressionné; il a attrapé des "tels quels" (parfois) et a fait presque tout le reste à la perfection):

Démarrer Stanford Lemmatizer

Ajout d'annotateur tokenize

Ajout de l'annotateur ssplit

Ajout d'annotateur pos

Lire le modèle de balise POS à partir de edu/stanford/nlp/models/pos-tagger/english-left3words/english-left3words-distsim.tagger ... done [1.7 sec].

Ajout du lemme d'annotateur

[comment pourriez-vous être, voyez-vous, dans, mon œil, comme, ouvrez-vous, porte,?, vous menez, moi, vers le bas, dans, mon cœur, où, je suis devenu, engourdi , sans, a, âme, mon, esprit, dors, quelque part, froid, jusqu’à ce que, tu trouves, il, là, et, conduis-le, retour, maison, toi, réveille-toi, moi, haut, dedans, appelle, mon, nom, et, sauve, je, de, la, sombre, tu as, dit, mon sang, et, courais, avant, je, deviendrais, défais, tu, sauverais, je, de, rien, je suis presque devenu, vous, soyez, apportez, je, à, vie, maintenant, que, je sais, quoi, je, être, sans, vous, pouvez, simplement avoir laisse, je, tu respire, dans, je, et fais, je, réel, gelé, à l'intérieur, sans, tu, touche, sans, tu, amour, , chérie, seulement, tu, sois, la, vie, parmi les morts, je suis, je vis, je vis, un mensonge ", il n'y a rien, à l'intérieur de toi, sois, apporte, je, à la vie.]

17
Tihamer

Vous pouvez essayer l'API gratuite Lemmatizer ici: http://twinword.com/lemmatizer.php

Faites défiler la liste pour trouver le point de terminaison Lemmatizer.

Cela vous permettra d'obtenir des "chiens" pour "chiens", des "capacités" pour "capacités".

Si vous transmettez un paramètre POST ou GET appelé "texte" avec une chaîne semblable à "plante parcourue":

// These code snippets use an open-source library. http://unirest.io/Java
HttpResponse<JsonNode> response = Unirest.post("[ENDPOINT URL]")
.header("X-Mashape-Key", "[API KEY]")
.header("Content-Type", "application/x-www-form-urlencoded")
.header("Accept", "application/json")
.field("text", "walked plants")
.asJson();

Vous obtenez une réponse comme celle-ci:

{
  "lemma": {
    "plant": 1,
    "walk": 1
  },
  "result_code": "200",
  "result_msg": "Success"
}
0
Joseph Shih