Methode member - Problem mit Klammern/else



  • Hier mal der Code mit Tags und korrekt eingerueckt, sonst kann das keiner lesen (ich hoffe zumindest, dass ich die Einrueckung richtig hibekommen abe):

    template <typename E> 
    bool DoubleHashing<E>::member ( const E& e ) const
    { 
    
    	size_t key; 
    	size_t pos; 
    
    	key = hashValue<E>(e); 
    	pos = key % nmax; 
    
    	if(status[pos] == filled)
    	{ 
    		if (values[pos] == e)
    			return true; 
    		else
    		{ 
    			size_t seckey; 
    			size_t newpos; 
    
    			seckey = 4*((hashValue<E>(e))%10); 
    
    			newpos = (pos + seckey) % nmax; 
    
    			while (newpos != pos)
    			{
    				if (status[newpos] == empty)
    					return false; 
    				else
    				{ 
    					if(status[newpos] == filled)
    						if (values[newpos] == e)
    							return true; 
    					else
    						newpos = (newpos + seckey) % nmax; 
    				} 
    			} 
    
    			return false; 
    		} 
    	} 
    }
    

    Hat er auch gesagt mit welchem else es ein Problem gibt?



  • danke ich hab das eigentlich e alles eingerückt gehabt nur hat das die seite nicht übernommen! sry dafür!

    ne hat er mir nicht gesagt und ich bin echt schon am verzweifeln!

    die ganze methode soll einen wert suchen der in meiner hashing tabelle ist oder auch nicht ist! info am rande habe bei der add methode double hashing genommen!



  • Ja, du kannst einige deiner else's weglassen.
    Wenn du in einer If-Anweisung ein return hast, was definitiv ausgeführt wird, brauchst du das auf das If folgende else nicht, denn der Code im entsprechenden Else Block wird doch nach ende des if's sowieso nicht ausgeführt, du bist ja schon mit return aus der Funktion raus.

    Also lässt sich folgendes:

    bool func(bool foo)
    {
        if (foo)
            return true;
        else
            return false;
    }
    

    zu:

    bool func(bool foo)
    {
        if (foo)
            return true;
    
        return false;
    }
    

    kürzen.

    Das nächste wäre noch, dass du, wenn if(status[pos] == filled) false zurückgibt du nichts returnst.

    So, hab den auf die schnelle mal ein wenig gekürzt. Ich hoff ich hab nichts ausversehn rausgelöscht 😶

    template <typename E>
    bool DoubleHashing<E>::member ( const E& e ) const {
    
        size_t key;
        size_t pos;
    
        key = hashValue<E>(e);
    
        pos = key % nmax;
    
        if(status[pos] == filled)
        {
            if (values[pos] == e) return true;
    
            size_t seckey;
            size_t newpos;
    
            seckey = 4*((hashValue<E>(e))%10);
    
            newpos = (pos + seckey) % nmax;
    
            while (newpos != pos)
            {
                if (status[newpos] == empty) return false;
    
                if(status[newpos] == filled)
                {
                    if (values[newpos] == e) return true;
                }
                else newpos = (newpos + seckey) % nmax;
            }
    
            return false;
        }
    }
    


  • ok funkt doch nicht bekomme diese fehlermeldung

    DoubleHashing.h: In member function ‘bool DoubleHashing<E>::member(const E&) const [with E = TestKey]’:
    DoubleHashing.h:230: warning: control reaches end of non-void function

    Methode member( key )
    Ergebnis (erwartet) false
    Ergebnis true
    Container-Inhalt (erwartet) (empty)
    Container::print() HashTable[ n=0 nmax=50000 values= ]



  • template <typename E> 
    bool DoubleHashing<E>::member ( const E& e ) const 
    { 
    
        size_t key; 
        size_t pos; 
    
        key = hashValue<E>(e); 
        pos = key % nmax; 
    
        if(status[pos] == filled) 
        { 
            if (values[pos] == e) 
                return true; 
            else 
            { 
                size_t seckey; 
                size_t newpos; 
    
                seckey = 4*((hashValue<E>(e))%10); 
    
                newpos = (pos + seckey) % nmax; 
    
                while (newpos != pos) 
                { 
                    if (status[newpos] == empty) 
                        return false; 
                    else 
                    { 
                        if(status[newpos] == filled) 
                            if (values[newpos] == e) 
                                return true; 
                        else 
                            newpos = (newpos + seckey) % nmax; 
                    } 
                } 
            } 
        } 
        return false; // return hier ?
    }
    

    Das wäre das einzige was mir grad einfällt.. Aber da ich keine Ahnung habe was das Programm macht kann ich Logikfehler echt nicht gut beheben..



  • Ihr Container sollte mit simpletest (in der Lernplattform verfügbares Testprogramm) compiliert und ausgiebig getestet worden sein. Das Einfügen und Finden von 100000 Objekten und die Verarbeitung von Objekten vom Typ Person (siehe Unterlagen) sollte kein Problem sein. Andernfalls ist ein Hochladen kaum erfolgversprechend.

    Unsere Professoren haben uns einen Container bereitgestellt und wir solln jz die Methoden add und member implementieren.

    ich habe doublehashing gewählt.

    meine add methode funktioniert soweit wie gesagt nur ein problem mit member!



  • Ich bin Matrix... schrieb:

    Also lässt sich folgendes:

    bool func(bool foo)
    {
        if (foo)
            return true;
        else
            return false;
    }
    

    zu:

    bool func(bool foo)
    {
        if (foo)
            return true;
    
        return false;
    }
    

    ja, das noch weiter zu kürzen scheint mir auch unmöglich... return foo; 🙄



  • ja, das noch weiter zu kürzen scheint mir auch unmöglich...

    Es ging mir nicht um die Funktionsweise der Funktion - sie ist total sinnlos - es ging mir rein ums Prinzip bzw. der Möglichkeit des Weglassens eines else . Inwieweit diese Funktion sich nochmehr vereinfachen lässt bzw. überhaupt einen Sinn hat ist für dieses Ziel nicht relevant.



  • DarkShadow44 schrieb:

    template <typename E> 
    bool DoubleHashing<E>::member ( const E& e ) const 
    { 
    
        size_t key; 
        size_t pos; 
    
        key = hashValue<E>(e); 
        pos = key % nmax; 
    
        if(status[pos] == filled) 
        { 
            if (values[pos] == e) 
                return true; 
            else 
            { 
                size_t seckey; 
                size_t newpos; 
    
                seckey = 4*((hashValue<E>(e))%10); 
    
                newpos = (pos + seckey) % nmax; 
    
                while (newpos != pos) 
                { 
                    if (status[newpos] == empty) 
                        return false; 
                    else 
                    { 
                        if(status[newpos] == filled) 
                            if (values[newpos] == e) 
                                return true; 
                        else 
                            newpos = (newpos + seckey) % nmax; 
                    } 
                } 
            } 
        } 
        return false; // return hier ?
    }
    

    Das wäre das einzige was mir grad einfällt.. Aber da ich keine Ahnung habe was das Programm macht kann ich Logikfehler echt nicht gut beheben..

    Ich schreibe den Code mal um. Ganz ohne auf den Inhalt zu achten.

    Erstmal Auto-Einrücker benutzen.

    template <typename E>
    bool DoubleHashing<E>::member ( const E& e ) const
    {
    
        size_t key;
        size_t pos;
    
        key = hashValue<E>(e);
        pos = key % nmax;
    
        if(status[pos] == filled)
        {
            if (values[pos] == e)
                return true;
            else
            {
                size_t seckey;
                size_t newpos;
    
                seckey = 4*((hashValue<E>(e))%10);
    
                newpos = (pos + seckey) % nmax;
    
                while (newpos != pos)
                {
                    if (status[newpos] == empty)
                        return false;
                    else
                    {
                        if(status[newpos] == filled)
                            if (values[newpos] == e)
                                return true;
                            else
                                newpos = (newpos + seckey) % nmax;
                    }
                }
            }
        }
        return false; // return hier ?
    }
    

    Die tiefe Einrückung des tiefsten else ist schon erschreckend.

    Dann nehme ich mir das erste if und bringe die unmittelbare Wirkung dichter an die Abfrage.

    template <typename E>
    bool DoubleHashing<E>::member ( const E& e ) const
    {
        size_t key;
        size_t pos;
    
        key = hashValue<E>(e);
        pos = key % nmax;
    
        if(status[pos] != filled)
            return false;
    
        if (values[pos] == e)
            return true;
        else
        {
            size_t seckey;
            size_t newpos;
    
            seckey = 4*((hashValue<E>(e))%10);
    
            newpos = (pos + seckey) % nmax;
    
            while (newpos != pos)
            {
                if (status[newpos] == empty)
                    return false;
                else
                {
                    if(status[newpos] == filled)
                        if (values[newpos] == e)
                            return true;
                        else
                            newpos = (newpos + seckey) % nmax;
                }
            }
        }
        return false; // return hier ?
    }
    

    Noch ein nutzloses else wegmachen...

    template <typename E>
    bool DoubleHashing<E>::member ( const E& e ) const
    {
        size_t key;
        size_t pos;
    
        key = hashValue<E>(e);
        pos = key % nmax;
    
        if(status[pos] != filled)
            return false;
    
        if (values[pos] == e)
            return true;
    
        size_t seckey;
        size_t newpos;
    
        seckey = 4*((hashValue<E>(e))%10);
    
        newpos = (pos + seckey) % nmax;
    
        while (newpos != pos)
        {
            if (status[newpos] == empty)
                return false;
            else
            {
                if(status[newpos] == filled)
                    if (values[newpos] == e)
                        return true;
                    else
                        newpos = (newpos + seckey) % nmax;
            }
        }
        return false; // return hier ?
    }
    

    Definitionen später machen.

    template <typename E>
    bool DoubleHashing<E>::member ( const E& e ) const
    {
        size_t pos = key % nmax;
    
        if(status[pos] != filled)
            return false;
    
        if (values[pos] == e)
            return true;
    
        size_t key = hashValue<E>(e);
    
        size_t seckey = 4*((hashValue<E>(e))%10);
    
        size_t newpos = (pos + seckey) % nmax;
    
        while (newpos != pos)
        {
            if (status[newpos] == empty)
                return false;
            else
            {
                if(status[newpos] == filled)
                    if (values[newpos] == e)
                        return true;
                    else
                        newpos = (newpos + seckey) % nmax;
            }
        }
        return false; // return hier ?
    }
    

    Noch ein else weg.

    template <typename E>
    bool DoubleHashing<E>::member ( const E& e ) const
    {
        size_t pos = key % nmax;
    
        if(status[pos] != filled)
            return false;
    
        if (values[pos] == e)
            return true;
    
        size_t key = hashValue<E>(e);
    
        size_t seckey = 4*((hashValue<E>(e))%10);
    
        size_t newpos = (pos + seckey) % nmax;
    
        while (newpos != pos)
        {
            if (status[newpos] == empty)
                return false;
            if(status[newpos] == filled)
                if (values[newpos] == e)
                    return true;
                else
                    newpos = (newpos + seckey) % nmax;
        }
        return false; // return hier ?
    }
    

    Und gleich noch eins.

    template <typename E>
    bool DoubleHashing<E>::member ( const E& e ) const
    {
        size_t pos = key % nmax;
    
        if(status[pos] != filled)
            return false;
    
        if (values[pos] == e)
            return true;
    
        size_t key = hashValue<E>(e);
    
        size_t seckey = 4*((hashValue<E>(e))%10);
    
        size_t newpos = (pos + seckey) % nmax;
    
        while (newpos != pos)
        {
            if (status[newpos] == empty)
                return false;
            if(status[newpos] == filled)
                if (values[newpos] == e)
                    return true;
                newpos = (newpos + seckey) % nmax;
        }
        return false; // return hier ?
    }
    

    Hier (und nur hier) muß ich was über das Programm wissen. Gibt es nur filled und empty als Status? Ich nehme an, ja. Dann geht

    template <typename E>
    bool DoubleHashing<E>::member ( const E& e ) const
    {
        size_t pos = key % nmax;
    
        if(status[pos] != filled)
            return false;
    
        if (values[pos] == e)
            return true;
    
        size_t key = hashValue<E>(e);
    
        size_t seckey = 4*((hashValue<E>(e))%10);
    
        size_t newpos = (pos + seckey) % nmax;
    
        while (newpos != pos)
        {
            if (status[newpos] == empty)
                return false;
            if (values[newpos] == e)
                return true;
            newpos = (newpos + seckey) % nmax;
        }
        return false; // return hier ?
    }
    

    Mal ein paar Leerzeilen weg.

    template <typename E>
    bool DoubleHashing<E>::member ( const E& e ) const
    {
        size_t pos = key % nmax;
        if(status[pos] != filled)
            return false;
        if (values[pos] == e)
            return true;
        size_t key = hashValue<E>(e);
        size_t seckey = 4*((hashValue<E>(e))%10);
        size_t newpos = (pos + seckey) % nmax;
        while (newpos != pos)
        {
            if (status[newpos] == empty)
                return false;
            if (values[newpos] == e)
                return true;
            newpos = (newpos + seckey) % nmax;
        }
        return false; // return hier ?
    }
    

    Jetzt hat der äußere Kram eine gewisse Ähnlichkeit mit dem Kram innerhalb der Schleife. Sollten sie etwa auch was ähnliches machen?

    Ah, noch gleicher machen.

    template <typename E>
    bool DoubleHashing<E>::member ( const E& e ) const
    {
        size_t pos = key % nmax;
        if(status[pos] == empty)
            return false;
        if (values[pos] == e)
            return true;
        size_t key = hashValue<E>(e);
        size_t seckey = 4*((hashValue<E>(e))%10);
        size_t newpos = (pos + seckey) % nmax;
        while (newpos != pos)
        {
            if (status[newpos] == empty)
                return false;
            if (values[newpos] == e)
                return true;
            newpos = (newpos + seckey) % nmax;
        }
        return false; // return hier ?
    }
    

    Schau, rätsel, guck...
    Ah, die while-Schleife war evtl eine ungeschickte Wahl.
    newpos = (pos + seckey) % nmax
    direkt vor der Schleife und als Weiterschaltungsausdruck, das riecht nach einem dreiviertel Takt unwinding, um die Bedingung an den Anfang (ins while) zu kriegen.

    Da mache ich erstmal for(;;) draus, um frei winden zu können.

    template <typename E>
    bool DoubleHashing<E>::member ( const E& e ) const
    {
        size_t pos = key % nmax;
        if(status[pos] == empty)
            return false;
        if (values[pos] == e)
            return true;
        size_t key = hashValue<E>(e);
        size_t seckey = 4*((hashValue<E>(e))%10);
        size_t newpos = (pos + seckey) % nmax;
        for(;;)
        {
            if (newpos == pos)
                break;
            if (status[newpos] == empty)
                return false;
            if (values[newpos] == e)
                return true;
            newpos = (newpos + seckey) % nmax;
        }
        return false; // return hier ?
    }
    

    *kurbel*

    template <typename E>
    bool DoubleHashing<E>::member ( const E& e ) const
    {
        size_t pos = key % nmax;
        if(status[pos] == empty)
            return false;
        if (values[pos] == e)
            return true;
        size_t key = hashValue<E>(e);
        size_t seckey = 4*((hashValue<E>(e))%10);
        size_t newpos = pos;
        for(;;)
        {
            newpos = (newpos + seckey) % nmax;
            if (newpos == pos)
                break;
            if (status[newpos] == empty)
                return false;
            if (values[newpos] == e)
                return true;
        }
        return false; // return hier ?
    }
    

    *kurbel*

    template <typename E>
    bool DoubleHashing<E>::member ( const E& e ) const
    {
        size_t pos = key % nmax;
        if(status[pos] == empty)
            return false;
        size_t key = hashValue<E>(e);
        size_t seckey = 4*((hashValue<E>(e))%10);
        size_t newpos = pos;
        for(;;)
        {
            if (values[newpos] == e)
                return true;
            newpos = (newpos + seckey) % nmax;
            if (newpos == pos)
                break;
            if (status[newpos] == empty)
                return false;
        }
        return false; // return hier ?
    }
    

    *kurbel*

    template <typename E>
    bool DoubleHashing<E>::member ( const E& e ) const
    {
        size_t pos = key % nmax;
        size_t key = hashValue<E>(e);
        size_t seckey = 4*((hashValue<E>(e))%10);
        size_t newpos = pos;
        for(;;)
        {
            if (status[newpos] == empty)
                return false;
            if (values[newpos] == e)
                return true;
            newpos = (newpos + seckey) % nmax;
            if (newpos == pos)
                break;
        }
        return false; // return hier ?
    }
    

    So, jetzt wissen wir auch, was loop-winding ist.

    Die Laufbedingung ist jetzt unten. Also do-Schleife.

    {
        size_t pos = key % nmax;
        size_t key = hashValue<E>(e);
        size_t seckey = 4*((hashValue<E>(e))%10);
        size_t newpos = pos;
        do
        {
            if (status[newpos] == empty)
                return false;
            if (values[newpos] == e)
                return true;
            newpos = (newpos + seckey) % nmax;
        }while (newpos != pos);
        return false; // return hier ?
    }
    

    Noch eine Doppelberechnung weg.

    template <typename E>
    bool DoubleHashing<E>::member ( const E& e ) const
    {
        size_t key = hashValue<E>(e);
        size_t pos = key % nmax;
        size_t seckey = 4*key%10;
        size_t newpos = pos;
        do
        {
            if (status[newpos] == empty)
                return false;
            if (values[newpos] == e)
                return true;
            newpos = (newpos + seckey) % nmax;
        }while (newpos != pos);
        return false; // return hier ?
    }
    

    Umnennen.

    template <typename E>
    bool DoubleHashing<E>::member ( const E& e ) const
    {
        size_t key = hashValue<E>(e);
        size_t startpos = key % nmax;
        size_t seckey = 4*key%10;
        size_t newpos = pos;
        do
        {
            if (status[newpos] == empty)
                return false;
            if (values[newpos] == e)
                return true;
            newpos = (newpos + seckey) % nmax;
        }while (newpos != startpos);
        return false; // return hier ?
    }
    
    template <typename E>
    bool DoubleHashing<E>::member ( const E& e ) const
    {
        size_t key = hashValue<E>(e);
        size_t startpos = key % nmax;
        size_t seckey = 4*key%10;
        size_t pos = startpos;
        do
        {
            if (status[pos] == empty)
                return false;
            if (values[pos] == e)
                return true;
            pos = (pos + seckey) % nmax;
        }while (pos != startpos);
        return false; // return hier ?
    }
    

    Klappt doch.



  • Alle lokalen Variablen außer pos kannste auch noch const-en.



  • Wenn Du noch

    size_t startpos = key % nmax;
        size_t seckey = key % (nmax-2);
    

    machst und sowohl nmax-2 als auch nmax Primzahlen sind, haste laut Knuth praktisch keine Kollissionshäufungen (Cluster).


Anmelden zum Antworten