Implementacja słownika

Implementacja słownika
A6
  • Rejestracja:około 14 lat
  • Ostatnio:około 14 lat
  • Postów:21
0

Mam problem w jednym zadaniu, w którym trzeba zaimplementować klasę Słownik<K,V> (oczywiście nie wykorzystując klas bibliotecznych).

Mój kod:

Kopiuj
namespace ConsoleApplication8
{
    class Slownik<K, V> where K: IComparable
    {
        public K klucz;
        public V wartosc;
        Slownik<K, V> poprzedni;
        Slownik<K, V> nastepny;

        public void dodaj(K klucz, V wartosc)
        {
            if (CO TUTAJ WSTAWIC?)
            {
                this.klucz = klucz;
                this.wartosc = wartosc;

                this.poprzedni = new Slownik<K, V>();
                this.nastepny = new Slownik<K, V>();
                     
            }

            else
            {
                if (this.klucz.CompareTo(klucz) < 0)
                    this.nastepny.dodaj(klucz, wartosc);
                else
                    this.poprzedni.dodaj(klucz, wartosc);
            }
        }
    }



    class Program
    {
        static void Main(string[] args)
        {
            Slownik<int, string> test = new Slownik<int,string>();
            test.dodaj(1, "asia");
            test.dodaj(2, "basia");
          
            Console.ReadKey();
        }
    }
}

i nie wiem teraz co wstawić w warunku if'a. Chciałoby się wstawić this.klucz == 0, ale nie można.
Prosiłbym o pomoc.
Z góry dzięki.

edytowany 1x, ostatnio: madmike
A6
  • Rejestracja:około 14 lat
  • Ostatnio:około 14 lat
  • Postów:21
0

może coś takiego? : this.poprzedni == null && this.nastepny == null

Deti
  • Rejestracja:ponad 22 lata
  • Ostatnio:ponad 9 lat
0

Zastanów się dobrze, co chcesz osiągnąć .. bo twój słownik coś dziwnie wygląda. Jak ma ten słownik działać? Co reprezentuje?


A6
  • Rejestracja:około 14 lat
  • Ostatnio:około 14 lat
  • Postów:21
0

No w sumie teraz już chyba działa. Słownik ma dodawać nowe elementy.
A czemu mówisz że dziwnie wygląda?

Kurde analizuję to no i faktycznie z tym warunkiem (this.nastepny == null oraz this.poprzedni == null) śmiga wyśmienicie, wszystko tak jak miało być.

edytowany 1x, ostatnio: arek686451990
somekind
Moderator
  • Rejestracja:około 17 lat
  • Ostatnio:około 3 godziny
  • Lokalizacja:Wrocław
0

Co to jest klucz, wartosc, poprzedni i nastepny w tym słowniku? IMHO nie ma to żadnego sensu.

edytowany 1x, ostatnio: somekind
A6
  • Rejestracja:około 14 lat
  • Ostatnio:około 14 lat
  • Postów:21
0

No jak: klucz i wartosc to jest po prostu klucz i wartosc w słowniku przecież a poprzedni i następny to referencje do poprzedniego i nastepnego elementu w słowniku. Wszyscy mówią że to nie ma sensu to chociaż powiedzcie co jest źle... albo jak powinno być.

ŁF
Moderator
  • Rejestracja:ponad 22 lata
  • Ostatnio:5 dni
0

to, co zrobiłeś, to jest lista, a nie słownik.


deus
Konkretnie niezbyt udana próba stworzenia listy asocjacyjnej, formy 'słownika dla ubogich'. Gdyby nie dwukierunkowość to przysiągłbym, że ktoś tutaj za dużo w Lispie pisał.
msm
Administrator
  • Rejestracja:około 16 lat
  • Ostatnio:5 miesięcy
1

to, co zrobiłeś, to jest lista, a nie słownik.

A tam, przesadzasz. Tak jakby napisać że ArrayList to nie lista tylko tablica. Kolekcje rozpoznaje się po interfejsie a nie implementacji.

@autor - dodaj wcale nie zadziała - zastanów się co się stanie dla kodu

Kopiuj
test.dodaj(1, "asia");
test.dodaj(2, "basia");

Wtedy test.następny.poprzedni != test, a test.następny.poprzedni.następny.poprzedni` wyrzuci NullPointer bo .następny.poprzedni.następny = null.

ŁF
"rozpoznaje się po interfejsie a nie implementacji" - zastanów się nad tym raz jeszcze
msm
Że niby znowu coś źle wyraziłem? Chodziło mi o http://en.wikipedia.org/wiki/Abstract_data_type
Deti
No to fajny słownik ze złożonością O(n) przy wyciąganiu Value :)
somekind
Moderator
  • Rejestracja:około 17 lat
  • Ostatnio:około 3 godziny
  • Lokalizacja:Wrocław
0
MSM napisał(a)

A tam, przesadzasz. Tak jakby napisać że ArrayList to nie lista tylko tablica. Kolekcje rozpoznaje się po interfejsie a nie implementacji.

Czyli słowniki implementuje się jako dwukierunkowe listy par klucz-wartość? Przecież to jest co najmniej dziwne.

edytowany 1x, ostatnio: somekind
Zobacz pozostałe 8 komentarzy
somekind
Nie homoseksualizm tylko gynandromorfizm.
deus
Gynvaela w to nie mieszaj :P
somekind
A nie wiedziałem, że ten nick to od tego... Ciekawe czy on o tym wie. :P
deus
Od czasu jak o tym na JM napisano to już tak :D
somekind
A tego to nie czytałem.
A6
  • Rejestracja:około 14 lat
  • Ostatnio:około 14 lat
  • Postów:21
0

No to jak się implementuje?

somekind
Moderator
  • Rejestracja:około 17 lat
  • Ostatnio:około 3 godziny
  • Lokalizacja:Wrocław
0

Mi się wydawało, że jako tablicę (dynamiczną zapewne) par klucz-wartość + parę myków na zwiększenie wydajności.

msm
Administrator
  • Rejestracja:około 16 lat
  • Ostatnio:5 miesięcy
1
somekind napisał(a)

Mi się wydawało, że jako tablicę (dynamiczną zapewne) par klucz-wartość + parę myków na zwiększenie wydajności.

Ja bym zrobił raczej (dla szybkości) posortowany kopiec list składających się z par hash klucza-wartość :P , ale ogólnie masz rację.

edytowany 7x, ostatnio: msm
somekind
Hashe wypadałoby trzymać w oddzielnej tablicy, a oryginalne wartości zostawiać. I nie psuć kolejności, no chyba że to ma być SortedDictionary.
ŁF
to po co te hashe, skoro do niczego nie służą?
somekind
Co do niczego nie służy?
msm
@sk - pewnie masz rację... @ŁF - do wyszukiwania binarnego, szybkiego porównywania i po to żeby GetHashCode() się nie nudził.
ŁF
hashe. po co chcesz je gdziekolwiek trzymać? wiesz jak działa tablica haszująca?
somekind
Nie wiem czy mam racje, może źle myślę, w takim razie proszę o nakierowanie na poprawny tok rozumowania.
ŁF
bardzo dużym uproszczeniu: masz klucz k i wartość w. funkcja mieszająca/hashująca na podstawie klucza k zwraca jakąś liczbę (hash). liczba ta modulo ilość miejsc w słowniku to indeks w tablicy, gdzie wyląduje wartość w. dobrze jeszcze przewidzieć możliwość kolizji i skończenia się miejsca w tablicy. chcesz potem wyciągnąć wartość dla klucza? funkcja mieszająca modulo rozmiar tablicy zwraca indeks elementu, zwracasz ten element i już. teoretycznie stała złożoność obliczeniowa niezależnie od ilości danych.
ŁF
@msm - do wyszukiwania binarnego nie potrzebujesz hasha, bo równie dobrze możesz użyć oryginalnego klucza (choć owszem, dla długich kluczy hash przyspieszy porównywanie). GetHashCode() ma się nie nudzić? prooszę...
somekind
@ŁF - ok, tu pełna zgoda. A czy przechowywanie hashy w oddzielnej tablicy nie ułatwi wykrywania kolizji?
ŁF
nie. w jaki sposób by miało?
somekind
Zaraz, bo nie wiem już czy o tym samym piszemy. Kolizja wynika z dzielenie hasha przez modulo czy nazywasz tak po prostu duplikat?
ŁF
to pierwsze. polecam lekturę np. wiki - http://pl.wikipedia.org/wiki/Tablica_mieszaj%C4%85ca. w przypadku kolizji do decyzji o nadpisaniu/dodaniu elementu wystarczy oryginalna wartość klucza. pamiętaj, że hash waży, a klucz i tak trzymamy, bo może do czegoś będzie potrzebny użytkownikowi. jeśli jednak z pewnych powodów nie chcemy pamiętać klucza, to owszem, możemy trzymać pełen hash (o ile takim dysponujemy), a osobna tablica na to jest zbędna.
somekind
Nie lubimy tutaj wikipedii, wg niej nie isteniejemy. ;) Pytam, bo jednocześnie oglądam implementację Dictionary w .NET i zastanawiam się, czemu oni mają tam tablicę na hashe. (No chyba, że czegoś zupełnie nie rozumiem.)
ŁF
szczegóły implementacyjne. zbędna nie oznacza niemożliwa do użycia.

Zarejestruj się i dołącz do największej społeczności programistów w Polsce.

Otrzymaj wsparcie, dziel się wiedzą i rozwijaj swoje umiejętności z najlepszymi.