Pomoc - Szukaj - Użytkownicy - Kalendarz
Pełna wersja: JavaScript: Odmiana polskich słów pzez przypadki według liczby
Forum PHP.pl > Forum > Gotowe rozwiązania
SmokAnalog
Hej,

w ostatnim projekcie potrzebowałem kodu, który odmieniałby słowa przez przypadki według liczby, czyli np.
  1. Mam 12 psów.
  2. Bajka o 71 krasnoludkach.
  3. Nie piłem od 100 lat.

Tworzenie tej funkcji było dobrą zabawą i wymagało analizy jak zmieniają się przypadki w zależności od kontekstu. Odkryłem, że mianownik, biernik i wołacz przy niektórych liczbach zmieniają się w dopełniacz. Pozostałe przypadki nie zmieniają się wcale.

A oto owoc mojej rozkminy:
[JAVASCRIPT] pobierz, plaintext
  1. function getWordForm(wordObject, context, number) {
  2. var toGenitive = ["nominative", "accusative", "vocative"],
  3. absolute = Math.abs(number),
  4. validForm = "";
  5.  
  6. if (toGenitive.indexOf(context) > -1 && absolute !== 1 && (absolute % 10 <= 1 || absolute % 10 >= 5 || (absolute % 100 >= 11 && absolute % 100 <= 19))) {
  7. validForm = wordObject.plural.genitive;
  8. } else {
  9. validForm = wordObject[absolute === 1 ? "singular" : "plural"][context];
  10. }
  11.  
  12. return validForm;
  13. }
[JAVASCRIPT] pobierz, plaintext


I przykład użycia:
[JAVASCRIPT] pobierz, plaintext
  1. var dog = {
  2. singular: {
  3. nominative: "pies",
  4. genitive: "psa",
  5. dative: "psu",
  6. accusative: "psa",
  7. instrumental: "psem",
  8. locative: "psie",
  9. vocative: "psie"
  10. },
  11. plural: {
  12. nominative: "psy",
  13. genitive: "psów",
  14. dative: "psom",
  15. accusative: "psy",
  16. instrumental: "psami",
  17. locative: "psach",
  18. vocative: "psy"
  19. }
  20. };
  21.  
  22. console.log("Mam 4 " + getWordForm(dog, "accusative", 4));
  23. console.log("Piszę książkę o 30 " + getWordForm(dog, "locative", 30));
  24. console.log("Idę na spacer z moim " + getWordForm(dog, "instrumental", 1));
  25. console.log("Nie zniosę 101 " + getWordForm(dog, "genitive", 101) + " w moim domu!");
[JAVASCRIPT] pobierz, plaintext


Obiekt słowa zawiera wszystkie przypadki, więc można się dowolnie bawić kontekstem i liczbą. Można też wzbogacić funkcję o opcję automatycznego wyświetlania liczby przed słowem, żeby się nie powtarzać.

Podoba Wam się? smile.gif
flashdev
Bardzo ciekawe smile.gif
Nie spodziewałem się, że da się coś takiego napisać w tak krótkim kodzie. Nie ma żadnych wyjątków od tych reguł?

Ahhh, już rozumiem. Obiekt dog trzeba podać, myślałem że funkcja go potrafi obliczyć na podstawie słowa "pies". Mimo wszystko przydatne smile.gif
mmaaciek
Publikuję wersję skróconą, która wystarcza w większości przypadków. Można ją używać dla mianownika, biernika i wołacza (do pozostałych przypadków wystarczy rozróżniać tylko liczbę pojedynczą i mnogą):
[JAVASCRIPT] pobierz, plaintext
  1. function odmiana(liczba, pojedyncza, mnoga, mnoga_dopelniacz) {
  2. liczba = Math.abs(liczba); // tylko jeśli mogą zdarzyć się liczby ujemne
  3. if (liczba === 1) return pojedyncza;
  4. var reszta10 = liczba % 10;
  5. var reszta100 = liczba % 100;
  6. if (reszta10 > 4 || reszta10 < 2 || (reszta100 < 15 && reszta100 > 11))
  7. return mnoga_dopelniacz;
  8. return mnoga;
  9. }
[JAVASCRIPT] pobierz, plaintext

Użycie:
[JAVASCRIPT] pobierz, plaintext
  1. var liczba_psow = 4;
  2. console.log("Mam " + liczba_psow + " " + odmien(liczba_psow, 'psa', 'psy', 'psów'));
  3. var liczba_krasnoludkow = 30;
  4. console.log("Oto " + liczba_krasnoludkow + " " + odmien(liczba_krasnoludkow, 'krasnoludek', 'krasnoludki', 'krasnoludków'));
  5. var liczba_lat = 101;
  6. console.log(liczba_lat + " " + odmien(liczba_lat, 'rok', 'lata', 'lat') + " w moim domu!");
[JAVASCRIPT] pobierz, plaintext
To jest wersja lo-fi głównej zawartości. Aby zobaczyć pełną wersję z większą zawartością, obrazkami i formatowaniem proszę kliknij tutaj.
Invision Power Board © 2001-2024 Invision Power Services, Inc.