2009-10-27 21 views
7

Szukam dobrej klasy lub funkcji liczenia słów. Kiedy kopiuję i wklejaję coś z Internetu i porównuję je z moim algorytmem obliczania liczby słów i MS Word, zawsze jest on wyłączony o nieco ponad 10%. Myślę, że to za dużo. Czy wiecie o dokładnym algorytmie liczenia słów w języku C#.Algorytm liczenia słów w języku C#

+1

Czy Twój algorytm jest zawsze zbyt wysoki lub zbyt niski? Czy to się różni? – Larsenal

+1

Czy liczą się tylko słowa, czy też wklejacie również znaczniki. – joshperry

+2

Dlaczego używasz liczby słów MS Word jako punktu odniesienia dla dokładności? Subtelne różnice w tym, co liczy się jako "słowo", mogą powodować znaczne różnice w liczbie słów. 10% nie jest zaskoczeniem. To, co widzisz, jest prawdopodobnie idealnie dokładne, ale tylko trochę inne. –

Odpowiedz

6

String.Split według predefiniowanych znaków. Używaj znaków interpunkcyjnych, spacji (usuń wiele spacji) i innych znaków, które określasz jako "podział słów".

Czego próbujesz?

Widziałem, że poprzedni użytkownik został przybity do linków, ale tutaj jest kilka przykładów użycia wyrażenia regularnego lub dopasowania znaków. Nadzieję, że to pomaga, i nikt nie ucierpi X-)

String.Split Method (Char[])

Word counter in C#

C# Word Count

+0

nie dla linków, zamiast dla googling oczywiste linki w/brak wartości dodać wniesione – zvolkov

+0

ok, punkt wzięty. –

+1

Przywołanie Nie zapomnij o opcji _StringSplitOptions.RemoveEmptyEntries_ w -_Split_ w przeciwnym razie "słowo1, słowo2" lub "słowo1? Słowo2" będą liczone jako 3 słowa! –

8

Jak @astander sugeruje, można zrobić String.split następująco:

string[] a = s.Split(
    new char[] { ' ', ',', ';', '.', '!', '"', '(', ')', '?' }, 
    StringSplitOptions.RemoveEmptyEntries); 

Przekazując tablicę znaków, można dzielić na wiele przerw wyrazów. Usunięcie pustych wpisów uniemożliwi odliczanie słów innych niż słowa.

+3

To jest świetne, ale powinieneś także uwzględnić nowe znaki. Jeśli wpiszesz słowo, naciśnij klawisz Enter, wpisz słowo, naciśnij klawisz Enter, zwróci wartość 0. Jedno z przeciążeń dla Split() pozwala na utworzenie tablicy łańcuchów znaków, dzięki czemu możesz zmienić tę tablicę na ciągi znaków i dodaj Environment.Newline (lub "\ r \ n" i \ n "). –

+2

Jeśli twoje wejście nie zawiera bardzo ograniczonego formatowania, prawdopodobnie będziesz potrzebować szerszej sieci - rozważ klatki kręte i kątowe, myślniki (chociaż może to powodować fałszywe alarmy) i inne znaki interpunkcyjne. –

1

Należy również sprawdzić newlines, tabs i non-breaking spaces. Najlepiej jest skopiować tekst źródłowy do postaci i zastąpić wszystkie znaki nowej linii, tabulatory i znaki kończące zdanie spacjami. Następnie podziel łańcuch na spacje.

1

Właśnie miał ten sam problem w ClipFlair, gdzie potrzebne do obliczenia WPM (słów na minutę) dla filmu napisy, więc wpadłem na następujący:

można zdefiniować ten statyczny metoda rozszerzenia w klasie statycznej, a następnie dodaj klauzulę using do przestrzeni nazw tej klasy statycznej w dowolnej klasie, która musi używać tej metody rozszerzenia. Metoda rozszerzenie jest wywoływana za pomocą s.WordCount(), gdzie s jest ciągiem znaków (identyfikator [zmienna/stała] lub dosłowny)

public static int WordCount(this string s) 
{ 
    int last = s.Length-1; 

    int count = 0; 
    for (int i = 0; i <= last; i++) 
    { 
    if (char.IsLetterOrDigit(s[i]) && 
     ((i==last) || char.IsWhiteSpace(s[i+1]) || char.IsPunctuation(s[i+1]))) 
     count++; 
    } 
    return count; 
} 
4

użyć wyrażenia regularnego, aby znaleźć słowa (np [\ w] +) i po prostu policzyć zapałki

public static Regex regex = new Regex(
    "[\\w]+", 
RegexOptions.Multiline 
| RegexOptions.CultureInvariant 
| RegexOptions.Compiled 
); 

regex.Match (_someString) .Count

1

Oto okrojona wersja kodu klasy C# i wykonane do liczenia słów, Azji słowy, charaters itd. to jest prawie taki sam jako Microsoft Word. Opracowałem oryginalny kod do liczenia słów dla dokumentów Microsoft Word.

using System; 
    using System.Collections.Generic; 
    using System.Linq; 
    using System.Text; 
    using System.Text.RegularExpressions; 
    namespace BL { 
    public class WordCount 
    { 

    public int NonAsianWordCount { get; set; } 
    public int AsianWordCount { get; set; } 
    public int TextLineCount { get; set; } 
    public int TotalWordCount { get; set; } 
    public int CharacterCount { get; set; } 
    public int CharacterCountWithSpaces { get; set; } 


    //public string Text { get; set; } 

    public WordCount(){} 

    ~WordCount() {} 


    public void GetCountWords(string s) 
    { 
     #region Regular Expression Collection 
     string asianExpression = @"[\u3001-\uFFFF]"; 
     string englishExpression = @"[\S]+"; 
     string LineCountExpression = @"[\r]+"; 
     #endregion 


     #region Asian Character 
     MatchCollection asiancollection = Regex.Matches(s, asianExpression); 

     AsianWordCount = asiancollection.Count; //Asian Character Count 

     s = Regex.Replace(s, asianExpression, " "); 

     #endregion 


     #region English Characters Count 
     MatchCollection collection = Regex.Matches(s, englishExpression); 
     NonAsianWordCount = collection.Count; 
     #endregion 

     #region Text Lines Count 
     MatchCollection Lines = Regex.Matches(s, LineCountExpression); 
     TextLineCount = Lines.Count; 
     #endregion 

     #region Total Character Count 

     CharacterCount = AsianWordCount; 
     CharacterCountWithSpaces = CharacterCount; 

     foreach (Match word in collection) 
     { 
      CharacterCount += word.Value.Length ; 
      CharacterCountWithSpaces += word.Value.Length + 1; 
     } 

     #endregion 

     #region Total Character Count 
     TotalWordCount = AsianWordCount + NonAsianWordCount; 
     #endregion 
    } 
} 
}