Policz błędy ortograficzne w tekście; zminimalizuj liczbę błędów ortograficznych w kodzie

28

Napisz program lub funkcję, która pobiera dwa dane wejściowe:

  1. Wiadomość tekstowa
  2. Słownik języka angielskiego, jak się pojawia w tym pliku Github (zawierający około 60000 słów)

i wyświetla liczbę błędów ortograficznych w komunikacie (patrz definicja i przypadki testowe poniżej).

Możesz otrzymać słownik jako parametr swojej funkcji, jako wstępnie zdefiniowany plik, który program spodziewa się znaleźć, jako zakodowane dane w kodzie lub w inny rozsądny sposób.


Twój kod powinien wyglądać jak wiadomość tekstowa z minimalną liczbą błędów ortograficznych. Więc obliczysz wynik swojego kodu, wprowadzając go do siebie jako dane wejściowe.

Zwycięzcą jest kod, który ma najniższy wynik (minimalny możliwy wynik to 0). Jeśli istnieje kilka odpowiedzi o tym samym wyniku, o zwycięzcy decyduje rozmiar kodu (w znakach). Jeśli dwie odpowiedzi są nadal powiązane, zwycięzcą jest ta wcześniejsza.


W razie potrzeby można założyć, że komunikat wejściowy to ASCII (bajty 32 ... 126) z znakami nowej linii zakodowanymi w konwencjonalny sposób (1 bajt „10” lub 2 bajty „13 10”) i niepuste. Jeśli jednak kod zawiera znaki spoza ASCII, powinien również obsługiwać dane wejściowe spoza ASCII (aby mógł obliczyć swój wynik).

Znaki są podzielone na następujące klasy:

  • Litery a ... z oraz A ... Z
  • Biała spacja (zdefiniowana tutaj jako znak spacji lub znak nowej linii)
  • Interpunkcja . , ; : ! ?
    • Zakończenie zdania . ! ?
  • Śmieci (cała reszta)

Słowo jest zdefiniowany jako ciąg liter, który jest maksymalny (tj poprzedzone ani nie występuje litera).

Zdanie jest zdefiniowany jako sekwencja maksymalnej znaków, które nie są zdanie kończy.

Postać jest błędem w pisowni, jeśli narusza którąkolwiek z zasad pisowni:

  1. Litera musi należeć do słowa w słowniku (lub innymi słowy: każde słowo o długości N, które nie pojawia się w słowniku, liczy się jako N błędów ortograficznych)
  2. Pierwszy znak w zdaniu, ignorując początkowe białe znaki, musi być wielką literą
  3. Wszystkie litery muszą być małe, z wyjątkiem tych określonych w poprzedniej regule
  4. Znak interpunkcyjny jest dozwolony tylko po literze lub śmieciach
  5. Znak nowej linii jest dozwolony tylko po znaku kończącym zdanie
  6. Znaki białych znaków są niedozwolone na początku wiadomości i po znakach białych znaków
  7. Nie powinno być śmieci (lub innymi słowy: każdy znak śmieci się liczy jest błędem pisowni)

Ponadto ostatnie zdanie musi być puste lub zawierać dokładnie jeden znak nowej linii (tzn. Wiadomość powinna kończyć się znakiem kończącym zdanie i opcjonalnym znakiem nowej linii - nazwijmy to regułą 8).

Przypadki testowe (poniżej każdej postaci znajduje się reguła, którą narusza; po =>jest wymagana odpowiedź):

Here is my 1st test case!!
           711           4                => 4

main(){puts("Hello World!");}
2   777    883     3     77 78            => 12

  This message starts with two spaces
66                                   8    => 3

What ? No apostrophe's??
     4              71 4                  => 4

  Extra   whitespace   is   BAD!
66      661111111111 66   66333           => 21

Several
lines?
Must be used only to separate sentences.
                                          => 1 (first linebreak is en error: rule 5)

"Come here," he said.
73         7                              => 3 (sentence starts with '"', not 'C')
anatolig
źródło
2
Spodziewałem się wielu luk, ale zdawało się, że je wszystkie pokryłeś. +1 ode mnie
Nathan Merrill,
4
Myślę, że SPL jest tutaj zwycięzcą.
Gurupad Mamadapur
2
. Gertruda jest jeszcze lepsza. Polecenia są dowolnymi zdaniami, liczy się tylko liczba słów i średnia długość słów.
Rainer P.
Kiedy to zobaczyłem, pomyślałem „Jabłkowy”. Nie mam jednak komputera Mac.
PurkkaKoodari
1
@PeterTaylor Nie chcę, aby zasady stały się zbyt skomplikowane. Twój przypadek testowy jest w porządku; Dodałem go do mojego postu.
anatolyg

Odpowiedzi:

6

Perl 6 , 134 błędów ortograficznych

my token punctuation {<[.,;:!?]>}
my \text = slurp; my \mistakes=[]; for split /\.|\!|\?/, text { for .trim.match: :g, /<:letter>+/ -> \word { (append mistakes, .comb when none words slurp pi given lc word) or (push mistakes, $_ if ((.from or word.from) xor m/<[a..z]>/) for word.match: :g, /./) }}
append mistakes, comb / <after \s | <punctuation>> <punctuation> | <!before <punctuation> | <:letter> | \s> . | <!after \.|\!|\?> \n | [<before ^> | <after \s>] \s /, text; say mistakes.Numeric

Z dodatkową spacją dla czytelności:

my token punctuation {<[.,;:!?]>}
my \text = slurp;
my \mistakes=[];
for split /\.|\!|\?/, text {
    for .trim.match: :g, /<:letter>+/ -> \word {
        (append mistakes, .comb when none words slurp pi given lc word)
        or
        (push mistakes, $_ if ((.from or word.from) xor m/<[a..z]>/) for word.match: :g, /./)
    }
}
append mistakes, comb /
  <after \s | <punctuation>> <punctuation>
  | <!before <punctuation> | <:letter> | \s> .
  | <!after \.|\!|\?> \n
  | [<before ^> | <after \s>] \s
/, text;
say mistakes.Numeric

Uwagi:

  • Oczekuje słownika w pliku o nazwie 3.14159265358979 w bieżącym katalogu roboczym.
  • Jedyną inspirowaną częścią jest linia
    append mistakes, .comb when none words slurp pi given lc word,
    reszta jest dość zła. Ale może może służyć przynajmniej jako podstawa dla lepszych rozwiązań ... :)
smls
źródło
4
Najbardziej czytelny kod perla w historii
Kritixi Lithos