Russian Qt Forum

Qt => Вопросы новичков => Тема начата: Soulq от Май 18, 2011, 13:28



Название: Qhash?
Отправлено: Soulq от Май 18, 2011, 13:28
Не могли бы вы объяснить работа с QHash? Почитал http://doc.qt.nokia.com/latest/qhash.html не понял :о
Как добавлять элемент? как записывать ключ?
Например я хочу чтобы ключ был аски код строки. Как избавляться от коллизии?
Вот написал чуток кода. думаю не правильно
Код
C++ (Qt)
...// работа с файлом
unsigned mykey;
   int c;
   int t=0;
   QHash <int,QString> myHash;
   while(fgets(result_string,sizeof(result_string),file)){
       i++;
       if(result_string[strlen(result_string)-1] == '\n'){
           result_string[strlen(result_string)-1]='\0';
       }
 
       c = strlen(result_string)-1;
       mykey = 1;
       while(c != -1){
           if(c != 0 )
               mykey = (mykey * toascii(result_string[c]) * c);
           else
               mykey = (mykey * toascii(result_string[c]));
           c --;
       }
       mykey = (mykey * strlen(result_string)) & 100000;
       while(myHash[mykey].isEmpty() == false){
            //t++;
            //std::cout << "LOLOLOL";
           QHash
 
       }
       std::cout<<"MyKey = " << mykey << " ";
       myHash[mykey] = result_string;
       std::cout << result_string <<"\n";
   }
std::cout << "Q = " << t << "\n";
std::cout << i;
}


Название: Re: Qhash?
Отправлено: GreatSnake от Май 18, 2011, 13:56
Код
C++ (Qt)
QString rs( result_string );
myHash[ qHash( rs ) ] = rs;
или
Код
C++ (Qt)
QHash< QString, bool > myHash;
myHash[ QString( result_string ) ] = true;


Название: Re: Qhash?
Отправлено: Soulq от Май 18, 2011, 14:09
Код
C++ (Qt)
QString rs( result_string );
myHash[ qHash( rs ) ] = rs;
или
Код
C++ (Qt)
QHash< QString, bool > myHash;
myHash[ QString( result_string ) ] = true;
Спасибо. Буду дальше писать :)


Название: Re: Qhash?
Отправлено: GreatSnake от Май 18, 2011, 14:15
Для чтения файла лучше используй QTextStream::readLine().


Название: Re: Qhash?
Отправлено: twp от Май 18, 2011, 14:17
может более подходящий контейнер в данном случае QSet<QString>


Название: Re: Qhash?
Отправлено: GreatSnake от Май 18, 2011, 14:21
может более подходящий контейнер в данном случае QSet<QString>
+1

Хотя, QHash< QString, bool > =  QSet<QString > :)


Название: Re: Qhash?
Отправлено: Soulq от Май 18, 2011, 14:54
может более подходящий контейнер в данном случае QSet<QString>
нее, мне надо реализовать словарь.


Название: Re: Qhash?
Отправлено: Igors от Май 18, 2011, 15:38
нее, мне надо реализовать словарь.
А какой тогда смысл в ключе "кода" строки? Делайте просто
Код
C++ (Qt)
QHash <QString, QString> dictionary;  // напр английское слово - ключ, русское - значение
 
// или так если несколько вариантов перевода
QHash <QString, QStringList> dictionary;
 


Название: Re: Qhash?
Отправлено: Soulq от Май 18, 2011, 16:08
нее, мне надо реализовать словарь.
А какой тогда смысл в ключе "кода" строки? Делайте просто
Код
C++ (Qt)
QHash <QString, QString> dictionary;  // напр английское слово - ключ, русское - значение
 
// или так если несколько вариантов перевода
QHash <QString, QStringList> dictionary;
 
Ой извиняюсь, мне надо словарь-то для проверки орфографии. Я высчитываю ключ и смотрю то ли слово. Если я буду хранить только ключ то у меня может попасться другое слово с таким же кешом. Вот.

И еще как можно вывести все слова из кеша в text_edit?


Название: Re: Qhash?
Отправлено: twp от Май 18, 2011, 16:41
Ой извиняюсь, мне надо словарь-то для проверки орфографии. Я высчитываю ключ и смотрю то ли слово. Если я буду хранить только ключ то у меня может попасться другое слово с таким же кешом. Вот.

И еще как можно вывести все слова из кеша в text_edit?
т.е. фактически проверяется наличие слова в хеше?


Название: Re: Qhash?
Отправлено: Soulq от Май 18, 2011, 16:42
Ой извиняюсь, мне надо словарь-то для проверки орфографии. Я высчитываю ключ и смотрю то ли слово. Если я буду хранить только ключ то у меня может попасться другое слово с таким же кешом. Вот.

И еще как можно вывести все слова из кеша в text_edit?
т.е. фактически проверяется наличие слова в хеше?
совершенно верно


Название: Re: Qhash?
Отправлено: twp от Май 18, 2011, 16:52
тогда чем не подошел QSet<QString>? ключ не нужно вычислять, просто проверяешь наличие слова в контейнере через QSet::contains()
но тут возникает другая проблема - одно и тоже слово можно написать несколькими вариантами, например слово код:
Код, КОД, код
в QHash как и в QSet это будут разные слова. Т.е нужно делать QString::toUpper() или QString::toLower()




Название: Re: Qhash?
Отправлено: Fat-Zer от Май 18, 2011, 16:54
совершенно верно
тогда хватит QSet'а... а если объём словаря большой, то лучше свою структуру на основе дерева использовать.


Название: Re: Qhash?
Отправлено: Soulq от Май 18, 2011, 17:15
тогда чем не подошел QSet<QString>? ключ не нужно вычислять, просто проверяешь наличие слова в контейнере через QSet::contains()
но тут возникает другая проблема - одно и тоже слово можно написать несколькими вариантами, например слово код:
Код, КОД, код
в QHash как и в QSet это будут разные слова. Т.е нужно делать QString::toUpper() или QString::toLower()
совершенно верно
тогда хватит QSet'а... а если объём словаря большой, то лучше свою структуру на основе дерева использовать.
Сейчас попробую.
Насчет toLower() - это да)

А добавлять и проверять наличие как?
что-то вроде:
Код
C++ (Qt)
mySet.insert(rs);
 
?


Название: Re: Qhash?
Отправлено: twp от Май 18, 2011, 17:21
в ассистенте все есть  ;)
Код:
// Here's an example QSet with QString values:

 QSet<QString> set;
// To insert a value into the set, use insert():

 set.insert("one");
 set.insert("three");
 set.insert("seven");
// Another way to insert items into the set is to use operator<<():
 set << "twelve" << "fifteen" << "nineteen";
// To test whether an item belongs to the set or not, use contains():

 if (!set.contains("ninety-nine"))


Название: Re: Qhash?
Отправлено: Soulq от Май 18, 2011, 17:31
в ассистенте все есть  ;)
Код:
// Here's an example QSet with QString values:

 QSet<QString> set;
// To insert a value into the set, use insert():

 set.insert("one");
 set.insert("three");
 set.insert("seven");
// Another way to insert items into the set is to use operator<<():
 set << "twelve" << "fifteen" << "nineteen";
// To test whether an item belongs to the set or not, use contains():

 if (!set.contains("ninety-nine"))
Да-да я уже разобрался, еще раз спасибо.
 


Название: Re: Qhash?
Отправлено: Soulq от Май 20, 2011, 08:38
А какая скорость поиска элемента у qset?


Название: Re: Qhash?
Отправлено: twp от Май 20, 2011, 11:16
http://doc.qt.nokia.com/latest/containers.html#algorithmic-complexity (http://doc.qt.nokia.com/latest/containers.html#algorithmic-complexity)


Название: Re: Qhash?
Отправлено: Igors от Май 20, 2011, 12:01
А какая скорость поиска элемента у qset?
http://doc.qt.nokia.com/latest/containers.html#algorithmic-complexity (http://doc.qt.nokia.com/latest/containers.html#algorithmic-complexity)
Не так уж много понятно из этой ссылки :) Наверное лучше ответить своими словами, напр: qset(qhash) предназначен/заточен для быстрой вставки/поиска. Как он это делает - совсем непросто и разбираться можно долго, но во всяком случае это те классы что нужны.


Название: Re: Qhash?
Отправлено: twp от Май 20, 2011, 12:10
Думаю предпочтительней, в первую очередь дать почитать первоисточник, тогда многие вопросы могут отпасть сами собой. Кроме того сравнительная таблица может дать больше инфы для размышления :)


Название: Re: Qhash?
Отправлено: Igors от Май 20, 2011, 12:28
Думаю предпочтительней, в первую очередь дать почитать первоисточник, тогда многие вопросы могут отпасть сами собой. Кроме того сравнительная таблица может дать больше инфы для размышления :)
Реально первая очередь будет и последней, а до размышлений дело не дойдет. Просто получена новая порция поверхностных знаний - вот и все. Понимаю что не нужно (да и невозможно) вникать во все до мелочей, многое надо просто использовать - это нормально. Но все же иногда интересно "а как же работает напр тот же QHash". Я открывал исходники но понял далеко не все.  Если можете объяснить принципиальный алгоритм на котором построен QHash - буду благодарен.


Название: Re: Qhash?
Отправлено: Fat-Zer от Май 20, 2011, 12:32
Реально первая очередь будет и последней, а до размышлений дело не дойдет. Просто получена новая порция поверхностных знаний - вот и все. Понимаю что не нужно (да и невозможно) вникать во все до мелочей, многое надо просто использовать - это нормально. Но все же иногда интересно "а как же работает напр тот же QHash". Я открывал исходники но понял далеко не все.  Если можете объяснить принципиальный алгоритм на котором построен QHash - буду благодарен.
всегда считал, что и там, и в QSet обычная хеш-таблица... или я не прав?


Название: Re: Qhash?
Отправлено: Igors от Май 20, 2011, 12:37
всегда считал, что и там, и в QSet обычная хеш-таблица... или я не прав?
Понятно что QSet сводится к тому же QHash. Понятно для чего нужен хеш и как его использовать. Я спрашиваю как он устроен. Ну напр. std::set - красно-черное дерево, поиск - спуск, вставка - балансировка. А здесь как?


Название: Re: Qhash?
Отправлено: Fat-Zer от Май 20, 2011, 12:45
Понятно что QSet сводится к тому же QHash. Понятно для чего нужен хеш и как его использовать. Я спрашиваю как он устроен. Ну напр. std::set - красно-черное дерево, поиск - спуск, вставка - балансировка. А здесь как?
большой массив, qHash вычисляет индекс в этом массиве, в котором должен хранится элемент. остаётся два вопроса:
1) что делать, если для нескольких элементов одинаковый индекс ака коллизии
2) когда расширять табицу
в общем тыц (http://ru.wikipedia.org/wiki/Хеш-таблица)


Название: Re: Qhash?
Отправлено: Igors от Май 20, 2011, 13:25
большой массив, qHash вычисляет индекс в этом массиве, в котором должен хранится элемент. остаётся два вопроса:
1) что делать, если для нескольких элементов одинаковый индекс ака коллизии
2) когда расширять табицу
в общем тыц (http://ru.wikipedia.org/wiki/Хеш-таблица)
А что собственно "тыц"?  :) Это из той же оперы что и предыдущая ссылка - хороша чтобы иметь общее понятие, но не более того. Кто такой "большой массив"? Что. если я вставил 2 ключа напр 1 и 10000, так уже 10К элементов полетели? Вряд ли, слишком тупо. Также популярный/практический вопрос - а почему итератор хеша не выдает элементы в отсортированном порядке (в отличие от QMap)?


Название: Re: Qhash?
Отправлено: Soulq от Май 20, 2011, 13:37
Вроде почитал сет ищет за логарифм :)


Название: Re: Qhash?
Отправлено: Fat-Zer от Май 20, 2011, 14:57
Кто такой "большой массив"?
обычный массив, алоцированный в хипе или список не очень больших массивов... это детали реализации... там хоть std::vector хоть QList может быть бекэндом... на самом деле используется обычный массив в хипе...
Что. если я вставил 2 ключа напр 1 и 10000, так уже 10К элементов полетели?
нет, хеш функция потом берётся по модулю количества значений в массиве.
Вряд ли, слишком тупо. Также популярный/практический вопрос - а почему итератор хеша не выдает элементы в отсортированном порядке (в отличие от QMap)?
очевидно - значения в хеш таблице хранятся по другому порядку (значения хеш функции % размер массива)
Вроде почитал сет ищет за логарифм :)
кто-то вас обманывает... QSet - ищет за о(1) в лучшем случае, и за о(n) в худшем... а вот std::set за лагорифм, ибо иснован на деревьях...


Название: Re: Qhash?
Отправлено: twp от Май 20, 2011, 19:18
Кому интересно вот (http://doc.qt.nokia.com/qq/qq19-containers.html) описание реализации основных контейнеров Qt.