Gibt es in c # einen Algorithmus zum Singularisieren - Pluralisieren eines Wortes?


106

Gibt es in c # einen Algorithmus zum Singularisieren - Pluralisieren eines Wortes (auf Englisch) oder gibt es eine .net-Bibliothek, um dies zu tun (möglicherweise auch in verschiedenen Sprachen)?

Antworten:


182

Sie haben auch den System.Data.Entity.Design.PluralizationServices.PluralizationService .

UPDATE : Alte Antwort verdient Aktualisierung. Es gibt jetzt auch Humanizer: https://github.com/MehdiK/Humanizer


2
Hmmm, dürfen Sie eine Design-DLL neu verteilen oder nur verwenden? Ich frage das, weil ich weiß, dass die Lizenz für DevExpress die Weiterverteilung von .design-DLLs verbietet.
Pierre-Alain Vigeant

58
Das Öffnen des Codes mit ILSpy zeigt eine Klasse namens EnglishPluralizationService, in der viele Ausnahmefälle definiert sind und die eine interessante Lektüre ermöglicht. Ich mag besonders 'Pneumonoultramicroscopicsilicovolcanoconiosis', die ich ständig in meinen Entitätsmodellen verwende ... 8o)
MrKWatkins

7
Ich kann mir vorstellen, wie das hinzugefügt wurde. Ein Tester hat einen Fehler beim Entwickler gemeldet, der besagt, dass er für dieses Wort nicht funktioniert. Dev hat es behoben. Beide lachten miteinander.
Merlinbeard

2
@ MrKWatkins Klingt eher nach 'supercalifragilisticexpialidocious'
Corstian Boerman

1
Humanizer ist eine großartige Empfehlung. Ich hatte natürlich 15% davon selbst implementiert, bevor ich herausfand, dass es existiert.
Casey

18

Ich kann es für Esperanto tun, ohne Sonderfälle!

string plural(string noun) { return noun + "j"; }

Für Englisch wäre es nützlich, sich mit den Regeln für reguläre Pluralformen von Substantiven sowie für unregelmäßige Pluralformen von Substantiven vertraut zu machen . Es gibt einen ganzen Wikipedia-Artikel über den englischen Plural , der möglicherweise auch einige hilfreiche Informationen enthält.


5
Sie sollten es werfen lassen, wenn Sie ein Verb oder Adverb übergeben!
Timwi

1
@Matt: Natürlich ist dies für den Nominativfall angemessen; Ich vertraue darauf, dass die Ausweitung dieser Methode auf den Akkusativ für einen klugen Leser unkompliziert ist.
Greg Hewgill

14

Die meisten ORMs haben einen Stich drauf, obwohl sie im Allgemeinen nicht perfekt sind. Ich weiß, dass Castle eine Inflector-Klasse hat, in der Sie wahrscheinlich herumstöbern können. Es "perfekt" zu machen ist jedoch keine leichte Aufgabe (englische "Regeln" sind keine wirklichen Regeln :)), daher hängt es davon ab, ob Sie mit einem "vernünftigen Schätz" -Ansatz zufrieden sind.


Auf Ihren Vorschlag hin habe ich nach "Inflector" gesucht und dieses andrewpeters.net/inflectornet gefunden , das im Grunde das gleiche sein sollte wie das des Schlosses
Ronnie

4
Eigentlich ist es nicht im Grunde das gleiche, es ist identisch.
David Pfeffer

12

Ich habe in Java betrogen - ich wollte in der Lage sein, eine korrekte Zeichenfolge für "Es gab n etwas (e)" zu erstellen, also schrieb ich Folgendes. wenig überladene Dienstprogrammmethode:

static public String pluralize(int val, String sng) {
    return pluralize(val,sng,(sng+"s"));
    }

static public String pluralize(int val, String sng, String plu) {
    return (val+" "+(val==1 ? sng : plu)); 
    }

so aufgerufen

System.out.println("There were "+pluralize(count,"something"));
System.out.println("You have broken "+pluralize(count,"knife","knives"));

Dies deckt zwar nur einen kleinen Teil der Grammatik ab, berücksichtigt jedoch keine Wörter wie Quiz, Partys, Hälften, Mäuse, Indizes usw. Es ist ein guter erster Stich, aber es gibt viele andere Regeln, die wahrscheinlich zuerst verarbeitet werden sollten .
Jeremy S

4
@ Jeremy: Warum nicht?: Println ("Sie haben bestanden" + SingularPlural (Anzahl, "Quiz", "Quiz") + "bisher")
Lawrence Dol

Ich könnte die Frage anders interpretieren. Ich denke, der Algorithmus sollte die Pluralform ohne einen Hinweis des Entwicklers bestimmen, während Ihre Methode die Aufgabe auferlegt, zu wissen, was die Pluralform für den Entwickler ist.
Jeremy S

3
@Jeremy: Daher führt das "Ich habe betrogen ..." - führt nicht zu einer Ablehnung.
Lawrence Dol

1
Einverstanden. Ich denke auch, dass die bereitgestellten Informationen nützlich waren, weshalb keine Ablehnung von mir kam. Ich stimme im Allgemeinen nicht nach dem Vorbild des "One Man's Junk ..." ab.
Jeremy S

10

Ich habe dafür in .net (C #) eine winzige Bibliothek namens Pluralizer erstellt (nicht überraschend).

Es soll mit ganzen Sätzen arbeiten, so etwas wie String.Format.

Es funktioniert im Grunde so:

var target = new Pluralizer();
var str = "There {is} {_} {person}.";

var single = target.Pluralize(str, 1);
Assert.AreEqual("There is 1 person.", single);

// Or use the singleton if you're feeling dirty:
var several = Pluralizer.Instance.Pluralize(str, 47);
Assert.AreEqual("There are 47 people.", several);

Es kann auch viel mehr als das. Lesen Sie mehr darüber in meinem Blog . Es ist auch in NuGet verfügbar.



4
Ja, diese Bibliothek verwendet nur einzelne Wörter und nur Substantive (obwohl Pluralizer diese Klasse intern verwendet). Diese Bibliothek erleichtert das Schreiben ganzer Sätze. Weitere Beispiele finden Sie in meinem Blog. Pluralizer.Instance.Pluralize ("{She} {geht} zu {ihrem | ihrem}} Zuhause.", 5)
Jay Querido

Shaun Wilson - Mein Computer ist derzeit in Teilen. Ich beeile mich, es wieder in Betrieb zu nehmen und werde es innerhalb von ein oder zwei Tagen aktualisieren. In der Zwischenzeit nuget.org/packages?q=pluralizer
Jay Querido

8

Ich habe einen zusammen mit dem Rails-Pluralizer zusammengeschlagen. Sie können meinen Blog-Beitrag hier oder auf Github hier sehen

output = Formatting.Pluralization(100, "sausage"); 

3
Danke für das Teilen. Ich bin froh, dass ich mich nicht auf eine andere Versammlung beziehen musste.
Hofnarwillie

1
Einfach und schön!, Aber es fehlt die Singularize- Funktionalität
amd

5

Da die Frage für C # war, ist hier eine nette Variation der Software Monkey-Lösung (wieder ein bisschen "Cheat", aber für mich wirklich die praktischste und wiederverwendbarste Art, dies zu tun):

    public static string Pluralize(this string singularForm, int howMany)
    {
        return singularForm.Pluralize(howMany, singularForm + "s");
    }

    public static string Pluralize(this string singularForm, int howMany, string pluralForm)
    {
        return howMany == 1 ? singularForm : pluralForm;
    }

Die Verwendung ist wie folgt:

"Item".Pluralize(1) = "Item"
"Item".Pluralize(2) = "Items"

"Person".Pluralize(1, "People") = "Person"
"Person".Pluralize(2, "People") = "People"

3

Subsonic 3 hat eine InflectorKlasse, die mich beeindruckt hat, indem sie sich Personin verwandelt hat People. Ich habe einen Blick auf die Quelle geworfen und festgestellt, dass sie mit einer fest codierten Liste natürlich ein wenig schummelt, aber das ist wirklich die einzige Möglichkeit, dies auf Englisch zu tun und wie Menschen es tun - wir erinnern uns an den Singular und den Plural jedes Wortes und wenden nicht nur eine Regel an . Da es nicht männlich / weiblich (/ neutral) gibt, um die Mischung zu ergänzen, ist es viel einfacher.

Hier ist ein Ausschnitt:

AddSingularRule("^(ox)en", "$1");
AddSingularRule("(vert|ind)ices$", "$1ex");
AddSingularRule("(matr)ices$", "$1ix");
AddSingularRule("(quiz)zes$", "$1");

AddIrregularRule("person", "people");
AddIrregularRule("man", "men");
AddIrregularRule("child", "children");
AddIrregularRule("sex", "sexes");
AddIrregularRule("tax", "taxes");
AddIrregularRule("move", "moves");

AddUnknownCountRule("equipment");

Es erklärt einige Wörter, die keine Pluraläquivalente haben, wie das Ausrüstungsbeispiel. Wie Sie wahrscheinlich sehen können, wird es einfach Regexdurch $ 1 ersetzt.

Update:
Es scheint, dass Subsonic Inflectordie CastleInflector ActiveRecord- Klasse infiziert !


2

MSDN enthält nicht viel Dokumentation zur spezifischen Verwendung der PluralizationService-Klasse. Hier ist eine Unit-Test-Klasse (NUnit), um die grundlegende Verwendung zu veranschaulichen. Beachten Sie den seltsamen Testfall unten, der zeigt, dass der Service nicht perfekt ist, wenn es um nicht standardmäßige Pluralformen geht.

[TestFixture]
public class PluralizationServiceTests
{
    [Test]
    public void Test01()
    {
        var service = PluralizationService.CreateService(CultureInfo.CurrentCulture);

        Assert.AreEqual("tigers", service.Pluralize("tiger"));
        Assert.AreEqual("processes", service.Pluralize("process"));
        Assert.AreEqual("fungi", service.Pluralize("fungus"));

        Assert.AreNotEqual("syllabi", service.Pluralize("syllabus")); // wrong pluralization
    }
}


1

Verwenden der Northwind-Beispieldatenbank von Microsoft:

 System.Data.Entity.Design.PluralizationServices.PluralizationService.CreateService(new System.Globalization.CultureInfo("en-US"));

Singularize singularisiert nicht "Order_Details" Es gibt "Order_Details" mit dem sam Ende zurück. Was ist die Arbeit um?


1
Dies ist eine Frage, keine Antwort auf eine Frage ... aber Pluralize () und Singularize () funktionieren nur mit Wörterbuchwörtern. Es gibt eine Möglichkeit, Wörter mit ICustomPluralizationMapping.AddWord hinzuzufügen, aber zumindest für mich war dies keine sehr gute Lösung, wenn Sie möglicherweise viele nicht reale Wörter wie Codenamen haben.
Tordal

@tordal Danke, genau dafür bin ich zu dieser Frage gekommen
Chad
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.