Название: Организация произвольного построчного чтения
Отправлено: Spark от Июль 19, 2013, 10:17
Создаю слайдшоу. Имена карточек берутся из списка по порядку, построчно - http://www.prog.org.ru/topic_25276_15.html
Необходимо организовать режим Random (случайное чтение), учитывая, что список может быть большим (тысяч сто). Т.е список надо перемешать и затем выдавать по порядку (что бы не было повторов). Подскажите как это организовать? Рад любой помощи.
Название: Re: Организация произвольного построчного чтения
Отправлено: kambala от Июль 19, 2013, 12:01
1) быстрый способ: засунуть строки в хэш или множество и извлекать оттуда, получится такой себе не очень рандомный рандом 2) нормальный способ: генерировать случайный индекс через qrand(), извлекать по нему строку, помещать индекс во множество для проверки уникальности
Название: Re: Организация произвольного построчного чтения
Отправлено: Igors от Июль 19, 2013, 12:58
2) нормальный способ: генерировать случайный индекс через qrand(), извлекать по нему строку, помещать индекс во множество для проверки уникальности
Проще перемешать сами элементы контейнера напр C++ (Qt) QStringList lst; ... for (int i = 0; i < lst.size(); ++i) lst.swap(qrand() % lst.size(), qrand() % lst.size());
А потом брать подряд
Название: Re: Организация произвольного построчного чтения
Отправлено: m_ax от Июль 19, 2013, 13:57
C++ (Qt) QStringList list; ... std::random_shuffle(list.begin(), list.end());
Название: Re: Организация произвольного построчного чтения
Отправлено: kambala от Июль 19, 2013, 13:59
да уж, надо изучить STL получше
Название: Re: Организация произвольного построчного чтения
Отправлено: Igors от Июль 19, 2013, 14:12
C++ (Qt) QStringList list; ... std::random_shuffle(list.begin(), list.end());
Это заметно хуже предыдущего варианта (см описание QList::swap)
Название: Re: Организация произвольного построчного чтения
Отправлено: m_ax от Июль 19, 2013, 14:35
C++ (Qt) QStringList list; ... std::random_shuffle(list.begin(), list.end());
Это заметно хуже предыдущего варианта (см описание QList::swap) Это Ваше очередное заблуждение.. Давайте посмотрим на тесты: C++ (Qt) #include <iostream> #include <list> #include <algorithm> #include <QStringList> #include <ctime> #include <chrono> template <unsigned N> void initList(QStringList & list) { for (unsigned i = 0; i < N; ++i) { list << QString::number(i); } } int main() { using namespace std::chrono; const unsigned Num = 1000000; QStringList list; initList<Num>(list); high_resolution_clock::time_point t1 = high_resolution_clock::now(); std::random_shuffle(list.begin(), list.end()); high_resolution_clock::time_point t2 = high_resolution_clock::now(); duration<double> time_span = duration_cast<duration<double>>(t2 - t1); std::cout << "random_shuffle: " << time_span.count() << " seconds." << std::endl; t1 = high_resolution_clock::now(); for (int i = 0; i < list.size(); ++i) { list.swap(qrand() % list.size(), qrand() % list.size()); } t2 = high_resolution_clock::now(); time_span = duration_cast<duration<double>>(t2 - t1); std::cout << "igors: " << time_span.count() << " seconds." << std::endl; return 0; }
Результаты у меня такие (3 испытания) Bash random_shuffle: 0.172468 seconds. igors: 0.403365 seconds. random_shuffle: 0.1679 seconds. igors: 0.350107 seconds. random_shuffle: 0.162135 seconds. igors: 0.362432 seconds.
Результаты ясно говорят, что random_shuffle эффективнее более чем в два раза..
Название: Re: Организация произвольного построчного чтения
Отправлено: Old от Июль 19, 2013, 14:53
Результаты ясно говорят, что random_shuffle эффективнее более чем в два раза..
А время на изучение почему ваш тест не выводит, так сказать на поиск и рыскатню? :)
Название: Re: Организация произвольного построчного чтения
Отправлено: m_ax от Июль 19, 2013, 15:03
Результаты ясно говорят, что random_shuffle эффективнее более чем в два раза..
А время на изучение почему ваш тест не выводит, так сказать на поиск и рыскатню? :) ;D Моё лицо упало на пол, потом я долго долго плакал)
Название: Re: Организация произвольного построчного чтения
Отправлено: Igors от Июль 19, 2013, 15:09
Результаты ясно говорят, что random_shuffle эффективнее более чем в два раза..
У меня др результаты (gcc/icc практически одинаковы) random_shuffle: 298 ms. igors: 126 ms.
Немного изменил Ваш пример т.к. не имею С++ 11. На всякий случай вот полный текст C++ (Qt) #include <iostream> #include <algorithm> #include <QtGUI> template <unsigned N> void initList(QStringList & list) { for (unsigned i = 0; i < N; ++i) { list << QString::number(i); } } int main() { const unsigned Num = 1000000; QStringList list; initList<Num>(list); QTime t1 = QTime::currentTime(); std::random_shuffle(list.begin(), list.end()); std::cout << "random_shuffle: " << t1.elapsed() << " ms." << std::endl; t1 = QTime::currentTime(); for (int i = 0; i < list.size(); ++i) list.swap(i, qrand() % list.size()); std::cout << "igors: " << t1.elapsed() << " ms." << std::endl; return 0; }
Перемещать данные не есть хорошо/грамотно - нужно перемещать указатели. И здесь еще так-сяк с имплисит шарой
Название: Re: Организация произвольного построчного чтения
Отправлено: m_ax от Июль 19, 2013, 15:16
С Вашим модифицированным вариантом результаты у меня: Bash random_shuffle: 163 ms. igors: 229 ms. random_shuffle: 159 ms. igors: 229 ms. random_shuffle: 192 ms. igors: 233 ms.
gcc 4.6.3 Architecture: x86_64 CPU(s): 1 On-line CPU(s) list: 0 Thread(s) per core: 1 Vendor ID: AuthenticAMD CPU MHz: 1808.327
Название: Re: Организация произвольного построчного чтения
Отправлено: Igors от Июль 19, 2013, 15:33
С Вашим модифицированным вариантом результаты у меня:
??? Не знаю. Я уже и тесты поменял местами, добавил srand и qsrand - все то же самое gcc/icc 32/64. debug/release. Вот последний вариант (хотя принципиальной разницы никакой) C++ (Qt) #include <iostream> #include <algorithm> #include <QtGUI> template <unsigned N> void initList(QStringList & list) { for (unsigned i = 0; i < N; ++i) { list << QString::number(i); } } int main() { const unsigned Num = 1000000; QStringList list; initList<Num>(list); qsrand(0); QTime t2 = QTime::currentTime(); for (int i = 0; i < list.size(); ++i) list.swap(i, qrand() % list.size()); std::cout << "igors: " << t2.elapsed() << " ms." << std::endl; srand(0); QTime t1 = QTime::currentTime(); std::random_shuffle(list.begin(), list.end()); std::cout << "random_shuffle: " << t1.elapsed() << " ms." << std::endl; return 0; }
Название: Re: Организация произвольного построчного чтения
Отправлено: Old от Июль 19, 2013, 15:35
А версии и разработчики stl думаю отличаются существенно. У вас даже стандарты разные.
Название: Re: Организация произвольного построчного чтения
Отправлено: Old от Июль 19, 2013, 16:41
Проверил у себя, последний тест: igors: 83 ms. random_shuffle: 59 ms.
g++ (GCC) 4.8.1 Architecture: x86_64 CPU op-mode(s): 32-bit, 64-bit Byte Order: Little Endian CPU(s): 4 On-line CPU(s) list: 0-3 Thread(s) per core: 1 Core(s) per socket: 4 Socket(s): 1 NUMA node(s): 1 Vendor ID: AuthenticAMD CPU family: 16 Model: 4 Model name: AMD Phenom(tm) II X4 945 Processor Stepping: 2 CPU MHz: 800.000 BogoMIPS: 6030.87 Virtualization: AMD-V L1d cache: 64K L1i cache: 64K L2 cache: 512K L3 cache: 6144K NUMA node0 CPU(s): 0-3
Название: Re: Организация произвольного построчного чтения
Отправлено: Spark от Июль 19, 2013, 17:18
Спасибо за помощь. Понял пока только в каком направлении двигаться, остальное не понял :). Но наверное на изучение вопроса придется потратить ночь. Из того, что понял. - Надо создать: C++ (Qt) QStringList lst;
- Далее каким то образом перетащить в него все пункты с текстового файла. - Затем перемешать: C++ (Qt) for (int i = 0; i < lst.size(); ++i) lst.swap(qrand() % lst.size(), qrand() % lst.size());
В списке (колонке) 100.000 пунктов. Тормозить не будет?
Название: Re: Организация произвольного построчного чтения
Отправлено: Igors от Июль 19, 2013, 17:41
Проверил у себя, последний тест:
То что великий и могучий std сэкономил мне аж одну(!) строку не компенсирует того что подход неверен в принципе. Возьмем структурку поприличнее, у меня разницв в 20 раз, (не привожу цифры из соображений тактичности :)) C++ (Qt) #include <iostream> #include <algorithm> #include <QtGUI> struct CData { CData( void ) { vec.resize(10); std::fill(vec.begin(), vec.end(), "test"); } std::vector <std::string> vec; }; int main() { const int Num = 1000 * 1000; QList <CData> list; for (int i = 0; i < Num; ++i) list.push_back(CData()); qsrand(0); QTime t2 = QTime::currentTime(); int limit = list.size(); for (int i = 0; i < limit; ++i) list.swap(i, qrand() % limit); std::cout << "igors: " << t2.elapsed() << " ms." << std::endl; srand(0); QTime t1 = QTime::currentTime(); std::random_shuffle(list.begin(), list.end()); std::cout << "random_shuffle: " << t1.elapsed() << " ms." << std::endl; return 0; }
Название: Re: Организация произвольного построчного чтения
Отправлено: Igors от Июль 19, 2013, 17:43
В списке (колонке) 100.000 пунктов. Тормозить не будет?
Нет, не забудьте только вызвать qsrand до того, иначе каждвй раз результат перемешивания будет новый
Название: Re: Организация произвольного построчного чтения
Отправлено: m_ax от Июль 19, 2013, 17:51
Проверил у себя, последний тест:
Возьмем структурку поприличнее, у меня разница в 20 раз, (не привожу цифры из соображений тактичности :)) В 20 раз? У Вас либо какая то сильно кривая stl, либо она на вас держит зуб) У меня результаты такие: Bash igors: 226 ms. random_shuffle: 736 ms.
одного порядка..
Название: Re: Организация произвольного построчного чтения
Отправлено: Old от Июль 19, 2013, 17:59
иначе каждвй раз результат перемешивания будет новый
одинаковый он будет.
Название: Re: Организация произвольного построчного чтения
Отправлено: kambala от Июль 19, 2013, 18:07
компилятор от студии 2012, процессор i7-2600K 3.4 GHz, release сборка: igors: 14 ms. random_shuffle: 864 ms. igors: 15 ms. random_shuffle: 741 ms..
Название: Re: Организация произвольного построчного чтения
Отправлено: m_ax от Июль 19, 2013, 18:09
компилятор от студии 2012, процессор i7-2600K 3.4 GHz, release сборка: igors: 14 ms. random_shuffle: 864 ms. igors: 15 ms. random_shuffle: 741 ms.. Понятно всё.. В c++11 у std::vector есть move конструктор и move assignment оператор. Этим всё объясняется..
Название: Re: Организация произвольного построчного чтения
Отправлено: Spark от Июль 19, 2013, 18:14
В списке (колонке) 100.000 пунктов. Тормозить не будет?
Нет, не забудьте только вызвать qsrand до того, иначе каждвй раз результат перемешивания будет новый А остальные пункты верны? Т.е в целом правильно понял и двигаться в этом порядке? Если да, то для меня сейчас важен второй пункт - как перегнать текст в QStringList? Тема для меня относительно новая. Т.е. надо организовать цикл как в предыдущей теме и добавлять пункты, что то вроде этого?: C++ (Qt) QStringList lst; do { itemStr = fileStream.readLine(); trimmedStr = itemStr.trimmed(); lst = +trimmedStr; } while( !fileStream.atEnd() );
Название: Re: Организация произвольного построчного чтения
Отправлено: Spark от Июль 19, 2013, 18:33
Или так: C++ (Qt) QStringList lst; while(!fileStream.atEnd()) { lst.append(fileStream.readLine()); }
Название: Re: Организация произвольного построчного чтения
Отправлено: m_ax от Июль 19, 2013, 18:45
Вы и дальше собираетесь всё методом тыка постигать? C++ (Qt) QFile file("in.txt"); if (!file.open(QIODevice::ReadOnly | QIODevice::Text)) return; QTextStream in(&file); QStringList list = in.readAll().split(QRegExp("[\\s\n]"), QString::SkipEmptyParts);
Название: Re: Организация произвольного построчного чтения
Отправлено: kambala от Июль 19, 2013, 19:07
не слишком будет сурово для ста тысяч строк? построчно читать пооптимальнее будет. где-то помню даже была тема, где сравнивались разные подходы к чтению большого текстового файла.
Название: Re: Организация произвольного построчного чтения
Отправлено: m_ax от Июль 19, 2013, 19:17
не слишком будет сурово для ста тысяч строк? построчно читать пооптимальнее будет. где-то помню даже была тема, где сравнивались разные подходы к чтению большого текстового файла.
Думаете сто тысяч это много? Сейчас проверим..
Название: Re: Организация произвольного построчного чтения
Отправлено: Spark от Июль 19, 2013, 19:31
Спасибо! Вроде как перегнать удалось настроить. 100.000 считывает вроде мгновенно. Теперь организовать разобраться с считыванием с QStringList и можно буде проверить с реальными 100.000 слайдами и вообщее рандомит ли :). До утра еще время есть у меня. Час 2-3 :).
Название: Re: Организация произвольного построчного чтения
Отправлено: m_ax от Июль 19, 2013, 19:39
не слишком будет сурово для ста тысяч строк? построчно читать пооптимальнее будет. где-то помню даже была тема, где сравнивались разные подходы к чтению большого текстового файла.
Думаете сто тысяч это много? Сейчас проверим.. Вобщем создал файлик 100000 строк.. Размер порядка 1 метра. Короче, на таких объёмах можно пока не беспокоиться)
Название: Re: Организация произвольного построчного чтения
Отправлено: Spark от Июль 19, 2013, 20:21
Спасибо! Разобрался. Проверил два варианта: C++ (Qt) if ( file.open( QFile::ReadOnly | QIODevice::Text ) ) { QTextStream fileStr( & file ); QStringList list = fileStr.readAll().split(QRegExp("[\\s\n]"), QString::SkipEmptyParts); for (int i = 0; i < list.size(); ++i) list.swap(qrand() % list.size(), qrand() % list.size()); foreach (QString itm, list) { if(slideShowPopupAction->isChecked())winPopup->slideTranslationFor( itm ); QEventLoop loop2; QTimer::singleShot(cfg.preferences.slideShowTimer, &loop2, SLOT(quit())); loop2.exec(); } file.close(); }
C++ (Qt) if ( file.open( QFile::ReadOnly | QIODevice::Text ) ) { QTextStream fileStr( & file ); QStringList list; while(!fileStr.atEnd()) { list.append(fileStr.readLine()); } for (int i = 0; i < list.size(); ++i) list.swap(qrand() % list.size(), qrand() % list.size()); foreach (QString itm, list) { if(slideShowPopupAction->isChecked())winPopup->slideTranslationFor( itm ); QEventLoop loop2; QTimer::singleShot(cfg.preferences.slideShowTimer, &loop2, SLOT(quit())); loop2.exec(); } file.close(); }
Тормоза не обнаружены. 100,000 реальных слайдов заводятся мгновенно. Какой вариант предпочтительней? Учитывая, что список вполне может быть и на 200,000 и на 300,000.
Название: Re: Организация произвольного построчного чтения
Отправлено: Spark от Июль 19, 2013, 20:26
Осталось решить маленький баг. Если ставить таймер показа большим (допустим час), а после ставить маленький (допустим 5 сек), то придется ждать час. Причина ясна. Как избавиться, не прерывая последовательность обработки спика? Или все таки придется пересмотреть механизм показа слайд? Так полагаю таймер можно зациклить с коротким дискретным значением. Но как от этого пострадает точность? И грамотная ли это реализация? Может прервать цикл можно иным более правильным способом?
Название: Re: Организация произвольного построчного чтения
Отправлено: Igors от Июль 20, 2013, 09:24
2m_aх Не могу объяснить противоположные результаты. Может qrand заметно медленнее std::rand? Если нетрудно - проверьте (с QStringList)
Название: Re: Организация произвольного построчного чтения
Отправлено: m_ax от Июль 20, 2013, 10:32
2m_aх Не могу объяснить противоположные результаты. Может qrand заметно медленнее std::rand? Если нетрудно - проверьте (с QStringList)
Если использовать Мерсен Твистер, то результаты практически совпадают. C++ (Qt) using namespace std::chrono; const unsigned Num = 1000000; QStringList list; initList<Num>(list); std::mt19937 gen; high_resolution_clock::time_point t1 = high_resolution_clock::now(); std::random_shuffle(list.begin(), list.end(), std::bind(std::uniform_int_distribution<int>(0, Num-1), gen)); high_resolution_clock::time_point t2 = high_resolution_clock::now(); duration<double> time_span = duration_cast<duration<double>>(t2 - t1); std::cout << "random_shuffle: " << time_span.count() << " seconds." << std::endl; t1 = high_resolution_clock::now(); for (int i = 0; i < list.size(); ++i) { list.swap(i, qrand() % list.size()); } t2 = high_resolution_clock::now(); time_span = duration_cast<duration<double>>(t2 - t1); std::cout << "igors: " << time_span.count() << " seconds." << std::endl;
Bash random_shuffle: 0.237838 seconds. igors: 0.27764 seconds.
Название: Re: Организация произвольного построчного чтения
Отправлено: m_ax от Июль 20, 2013, 11:09
Если в обоих алгоритмах использовать один и тот же генератор, то результаты также практически совпадают..
Скорее всего дело в реализации swap в c++11.
Название: Re: Организация произвольного построчного чтения
Отправлено: Old от Июль 20, 2013, 11:13
Если в обоих алгоритмах использовать один и тот же генератор, то результаты также практически совпадают..
В c++11 у std::vector есть move конструктор и move assignment оператор. Этим всё объясняется..
В c++11 и std::swap из-за этого эффективней и отпадает необходимость использовать встроенный из списка QList.
Название: Re: Организация произвольного построчного чтения
Отправлено: m_ax от Июль 20, 2013, 11:21
Если в обоих алгоритмах использовать один и тот же генератор, то результаты также практически совпадают..
В c++11 у std::vector есть move конструктор и move assignment оператор. Этим всё объясняется..
В c++11 и std::swap из-за этого эффективней и отпадает необходимость использовать встроенный из списка QList. Да, если у того, кто хранится в списке есть move конструктор)
Название: Re: Организация произвольного построчного чтения
Отправлено: Spark от Июль 20, 2013, 17:51
В принципе доделал организацию слайдшоу. Функционирует как задумал. Спасибо за помощь. Оцените критическим взглядом и если не в тягость посоветуйте, как оптимизировать. Как организация таймера? Достаточно ли будет точен?... Связи: C++ (Qt) // Slide slideShowButton = new QToolButton ( navToolbarBefore ); slideShowButton->setIcon( QIcon (":/icons/show.png") ); slideShowButton->setToolTip( tr( "Slideshow Play/Pause" ) ); slideShowButton->setCheckable(true); slideShowButton->setChecked(false); slideShowButton->setContextMenuPolicy( Qt::CustomContextMenu ); navToolbarBefore->addWidget( slideShowButton ); zeroActionSlideShow = navToolbarBefore->addWidget( slideShowButton ); zeroActionSlideShow->setVisible( cfg.preferences.slideshowButtonVisible ); slideShowTimerAction = new QAction( tr( "Set Timer" ), this ); slideShowRandomAction = new QAction( tr( "Random" ), this ); slideShowRandomAction->setCheckable(true); slideShowRandomAction->setChecked(cfg.preferences.slideShowRandom); slideShowPopupAction = new QAction( tr( "Popup Window" ), this ); slideShowPopupAction->setCheckable(true); slideShowPopupAction->setChecked(cfg.preferences.slideShowPopup); slideShowPopupOnTopAction = new QAction( tr( "Popup Window On Top" ), this ); slideShowPopupOnTopAction->setCheckable(true); slideShowPopupOnTopAction->setChecked(cfg.preferences.alwaysOnTopPopup); slideShowGrandAction = new QAction( tr( "Grand Window" ), this ); slideShowGrandAction->setCheckable(true); slideShowGrandAction->setChecked(cfg.preferences.slideShowGrand); sendToTranslateLineAction = new QAction( tr( "Send To Translate Line" ), this ); sendToTranslateLineAction->setCheckable(true); sendToTranslateLineAction->setChecked(cfg.preferences.sendToTranslateLine); slideShowGrandOnTopAction = new QAction( tr( "Grand Window On Top" ), this ); slideShowGrandOnTopAction->setCheckable(true); slideShowGrandOnTopAction->setChecked(cfg.preferences.alwaysOnTop); slideShowOpenAction = new QAction( tr( "Open" ), this ); slideShowQuitAction = new QAction( tr( "Stop" ), this ); slideShowPlay = false; slideShowPause = true; slideShowStop = false; connect( slideShowButton, SIGNAL( toggled( bool ) ), this, SLOT( slideShowOn( bool ) ) ); connect( slideShowButton, SIGNAL( customContextMenuRequested( const QPoint & ) ), this, SLOT( contextToolbarSlideShowButton( const QPoint & ) ) ); connect( slideShowTimerAction, SIGNAL( triggered() ), this, SLOT(slideShowTimer())); connect( slideShowRandomAction, SIGNAL( triggered( bool ) ), this, SLOT( slideShowRandomTriggered( bool ) ) ); connect( slideShowPopupAction, SIGNAL( triggered( bool ) ), this, SLOT( slideShowPopupTriggered( bool ) ) ); connect( slideShowPopupOnTopAction, SIGNAL( triggered( bool ) ), this, SLOT( slideShowOnTopTriggered( bool ) ) ); connect( slideShowGrandAction, SIGNAL( triggered( bool ) ), this, SLOT( slideShowGrandTriggered( bool ) ) ); connect( sendToTranslateLineAction, SIGNAL( triggered( bool ) ), this, SLOT( sendToTranslateLineTriggered( bool ) ) ); connect( slideShowGrandOnTopAction, SIGNAL( triggered( bool ) ), this, SLOT( on_alwaysOnTop_triggered( bool ) ) ); connect( slideShowOpenAction, SIGNAL( triggered() ), this, SLOT( openNewSlideShow() ) ); connect( slideShowQuitAction, SIGNAL( triggered() ), this, SLOT( slideShowQuit() ) );
Функционал: C++ (Qt) void MainWindow::slideShowOn(bool on) { if(!on) { slideShowPause = true; return; } else if(slideShowPlay && slideShowPause) { slideShowPause = false; return; } else { if(!cfg.preferences.slideShowPopup && !cfg.preferences.slideShowGrand) { slideShowPopupAction->setChecked(true); cfg.preferences.slideShowPopup = true; } slideShowStop = false; slideShowPlay = true; slideShowPause = false; QString importPath; if( cfg.contentExportPath.isEmpty() ) importPath = QDir::homePath(); else { importPath = QDir::fromNativeSeparators( cfg.contentExportPath ); if( !QDir( importPath ).exists() ) importPath = QDir::homePath(); } QString fileName = QFileDialog::getOpenFileName( this, tr( "Slideshow content from file" ), importPath, tr( "Text files (*.txt);;All files (*.*)" ) ); if( fileName.size() == 0) { slideShowButton->setChecked(false); return; } QFileInfo fileInfo( fileName ); QString contentName = fileInfo.baseName(); QFile file( fileName ); slideShowOnTopTriggered( cfg.preferences.alwaysOnTopPopup ); int n(0); for(;;) { // Count n=0; if ( file.open( QFile::ReadOnly ) ) { char buf[1024]; qint64 lineLength; forever { lineLength = file.readLine(buf, sizeof(buf)); if (lineLength > 0) { ++n; } else if (lineLength == -1) { break; } } file.close(); } slideShowName.setNum(n); slideShowName = contentName + "/" + slideShowName; if(slideShowRandomAction->isChecked()) { if ( file.open( QFile::ReadOnly | QIODevice::Text ) ) { QTextStream fileStr( & file ); QStringList list; if(slideShowGrandAction->isChecked())setWindowTitle( slideShowName + "/Random" ); if(slideShowPopupAction->isChecked())winPopup->setWindowTitle( slideShowName + "/Random" ); while(!fileStr.atEnd()) { list.append(fileStr.readLine()); } for (int i = 0; i < list.size(); ++i) list.swap(qrand() % list.size(), qrand() % list.size()); foreach (QString itm, list) { do { QEventLoop loop; QTimer::singleShot(0, &loop, SLOT(quit())); loop.exec(); // Нормально стопим паузу для экстренного выхода программы if(slideShowStop)break; } while(slideShowPause); if(slideShowGrandAction->isChecked())showTranslationFor( itm ); if(sendToTranslateLineAction->isChecked())translateLine->setText( itm ); if(slideShowPopupAction->isChecked())winPopup->slideTranslationFor( itm ); for(int i=1; i<=cfg.preferences.slideShowTimer/1000; ++i) { QEventLoop loop3; QTimer::singleShot(1000, &loop3, SLOT(quit())); loop3.exec(); } if(!cfg.preferences.slideShowRandom)break; if(slideShowStop)break; } file.close(); } } if(!slideShowStop) { if ( file.open( QFile::ReadOnly | QIODevice::Text ) ) { QTextStream fileStream( & file ); QString itemStr; if(slideShowGrandAction->isChecked())setWindowTitle( slideShowName ); if(slideShowPopupAction->isChecked())winPopup->setWindowTitle( slideShowName ); do { do { QEventLoop loop; QTimer::singleShot(0, &loop, SLOT(quit())); loop.exec(); if(slideShowStop)break; } while(slideShowPause); itemStr = fileStream.readLine(); if( fileStream.status() >= QTextStream::ReadCorruptData ) break; trimmedStr = itemStr.trimmed(); if( trimmedStr.isEmpty() ) continue; if(slideShowGrandAction->isChecked())showTranslationFor( trimmedStr ); if(sendToTranslateLineAction->isChecked())translateLine->setText( trimmedStr ); if(slideShowPopupAction->isChecked())winPopup->slideTranslationFor( trimmedStr ); for(int i=1; i<=cfg.preferences.slideShowTimer/1000; i++) { QEventLoop loop3; QTimer::singleShot(1000, &loop3, SLOT(quit())); loop3.exec(); } if(cfg.preferences.slideShowRandom)break; if(slideShowStop)break; } while( !fileStream.atEnd() ); } file.close(); } if(slideShowStop)break; } } } void MainWindow::quitApp() { slideShowStop = true; qApp->quit(); } void MainWindow::openNewSlideShow() { slideShowStop = true; slideShowOn(true); } void MainWindow::slideShowTimer() { TimerDialog *dialog = new TimerDialog( cfg ); dialog->setWindowFlags(Qt::WindowStaysOnTopHint); dialog->show(); } void MainWindow::slideShowRandomTriggered( bool checked ) { cfg.preferences.slideShowRandom = checked; } void MainWindow::slideShowPopupTriggered( bool checked ) { cfg.preferences.slideShowPopup = checked; if(cfg.preferences.slideShowRandom) { winPopup->setWindowTitle( slideShowName + "/Random"); } else { winPopup->setWindowTitle( slideShowName); } } void MainWindow::slideShowGrandTriggered( bool checked ) { cfg.preferences.slideShowGrand = checked; if(cfg.preferences.slideShowRandom) { setWindowTitle( slideShowName + "/Random"); } else { setWindowTitle( slideShowName); } } void MainWindow::sendToTranslateLineTriggered( bool checked ) { cfg.preferences.sendToTranslateLine = checked; } void MainWindow::slideShowQuit() { slideShowButton->setChecked(false); slideShowPlay = false; slideShowPause = true; slideShowStop = true; } void MainWindow::contextToolbarSlideShowButton( const QPoint &pos) { QMenu * slideMenu = new QMenu( this ); slideMenu->addAction( slideShowTimerAction ); slideMenu->addAction( slideShowRandomAction ); slideMenu->addSeparator(); slideMenu->addAction( slideShowPopupAction ); slideMenu->addAction( slideShowPopupOnTopAction ); slideMenu->addSeparator(); slideMenu->addAction( slideShowGrandAction ); slideMenu->addAction( sendToTranslateLineAction ); slideMenu->addAction( slideShowGrandOnTopAction ); slideMenu->addSeparator(); slideMenu->addAction( slideShowOpenAction ); slideMenu->addAction( slideShowQuitAction ); slideMenu->exec( slideShowButton->mapToGlobal( pos ) ); }
Виджет Таймер: C++ (Qt) #include <QtGui> #include "timerslide.hh" TimerDialog::TimerDialog( Config::Class &cfg_, QWidget *parent ) : QDialog( parent ), cfg(cfg_) { setWindowTitle(tr("Timer")); setMinimumWidth(210); setHoursLabel = new QLabel(tr("Hours:")); setHoursSpinBox = new QSpinBox(); setHoursSpinBox->setValue(cfg.preferences.slideShowTimer/3600000); setHoursSpinBox->setMinimum(0); setHoursSpinBox->setMaximum(12); setMinutesLabel = new QLabel(tr("Minutes:")); setMinutesSpinBox = new QSpinBox(); setMinutesSpinBox->setValue(cfg.preferences.slideShowTimer%3600000/60000); setMinutesSpinBox->setMinimum(0); setMinutesSpinBox->setMaximum(60); setSecondsLabel = new QLabel(tr("Seconds:")); setSecondsSpinBox = new QSpinBox(); setSecondsSpinBox->setValue(cfg.preferences.slideShowTimer%3600000%60000/1000); setSecondsSpinBox->setMinimum(1); setSecondsSpinBox->setMaximum(60); setSecondsSpinBox->setFocus(); setOkButton = new QPushButton(tr("Ok")); setOkButton->setToolTip( tr( "Set Timer" ) ); QGridLayout *timerLayout = new QGridLayout; timerLayout->addWidget(setHoursLabel, 0, 0); timerLayout->addWidget(setHoursSpinBox, 0, 1); timerLayout->addWidget(setMinutesLabel, 1, 0); timerLayout->addWidget(setMinutesSpinBox, 1, 1); timerLayout->addWidget(setSecondsLabel, 2, 0); timerLayout->addWidget(setSecondsSpinBox, 2, 1); timerLayout->addWidget(setOkButton, 3, 0, 1, 2); QHBoxLayout *mainLayout = new QHBoxLayout; mainLayout->addLayout(timerLayout); setLayout(mainLayout); connect(setOkButton, SIGNAL(clicked()), this, SLOT(setOkButtonClicked())); } void TimerDialog::setOkButtonClicked() { int valtHours = setHoursSpinBox->value(); int valMinutes = setMinutesSpinBox->value(); int valSeconds = setSecondsSpinBox->value(); cfg.preferences.slideShowTimer = valtHours*60*60*1000+valMinutes*60*1000+valSeconds*1000; close(); }
Название: Re: Организация произвольного построчного чтения
Отправлено: gil9red от Июль 20, 2013, 19:11
Проще было бы заценить, если бы скинули исходный код :)
Название: Re: Организация произвольного построчного чтения
Отправлено: Spark от Июль 20, 2013, 19:31
Проще было бы заценить, если бы скинули исходный код :)
Однако, здесь весь исходный код самой организации слайдшоу. И качество этой части меня интересует в первую очередь. С остальным все в порядке.
Название: Re: Организация произвольного построчного чтения
Отправлено: Spark от Июль 20, 2013, 21:01
Маленький косячок остался. В момент показав слайда, курсор мыши меняется. Подскажите, что за это отвечает?
Название: Re: Организация произвольного построчного чтения
Отправлено: thechicho от Июль 20, 2013, 21:43
C++ (Qt) QStringList list = in.readAll().split(QRegExp("[\\s\n]"), QString::SkipEmptyParts);
для чего \\s? если в строке будет пробел, будет ошибка. с флагом QIODevice::Text достаточно C++ (Qt) split("\n", QString::SkipEmptyParts)
Название: Re: Организация произвольного построчного чтения
Отправлено: m_ax от Июль 20, 2013, 21:57
C++ (Qt) QStringList list = in.readAll().split(QRegExp("[\\s\n]"), QString::SkipEmptyParts);
для чего \\s? если в строке будет пробел, будет ошибка. с флагом QIODevice::Text достаточно C++ (Qt) split("\n", QString::SkipEmptyParts)
Для того чтобы обрезать лишние пробелы в начале и конце строки. (предполагается, что в середине строки пробелов нет).
Название: Re: Организация произвольного построчного чтения
Отправлено: thechicho от Июль 20, 2013, 22:00
функционал убил. это чем надо думать, чтобы такое придумать) такое чувство, что код писался с целью запутывания кого-то для чего-то. несколько раз вподряд чтение одного и того же файла :) самое убойное, что сразу бросилось в глаза ;D do { QEventLoop loop; QTimer::singleShot(0, &loop, SLOT(quit())); loop.exec(); // Нормально стопим паузу для экстренного выхода программы if(slideShowStop)break; } while(slideShowPause); в более общие моменты не хочу даже вникать, жжешь)
Название: Re: Организация произвольного построчного чтения
Отправлено: thechicho от Июль 20, 2013, 22:05
//Для того чтобы обрезать лишние пробелы в начале и конце строки. (предполагается, что в середине строки пробелов нет). тогда уж в начале и конце файла. не буду спрашивать, откуда им там взяться) при split("\n", QString::SkipEmptyParts) QString::SkipEmptyParts - убирает пробелы в конце остаются в начале. C++ (Qt) QStringList list = in.readAll().trimmed().split("\n", QString::SkipEmptyParts);
Название: Re: Организация произвольного построчного чтения
Отправлено: Spark от Июль 20, 2013, 22:14
самое убойное, что сразу бросилось в глаза ;D
Однако, с чувством юмора у вас туговато. Кроме того, по этой проблеме вразумительного ответа профи не дали. Так или иначе этот пункт решен. По остальному - спасибо на добром слове. Замечания учту. Будем набираться опыт.
Название: Re: Организация произвольного построчного чтения
Отправлено: thechicho от Июль 20, 2013, 22:23
//Однако, с чувством юмора у вас туговато не всем харизма дана как Путину
я ничего доброго не сказал. код ужасен. это притом что я сам не заморачиваюсь сейчас насчет читаемости своего кода, т.к. мало опыта еще.
//Кроме того, по этой проблеме вразумительного ответа профи не дали. какая проблема? когда мне нужно было как-то сделать паузу, я использовал сигнал-слот if (slideShowPause) { QEventLoop loop; connect(this, SIGNAL(wakeUp()), &loop, SLOT(quit())); loop.exec(); } ... connect(play, SIGNAL(clicked()), this, SIGNAL(wakeUp()));
хотя в данном контексте можно просто написать. connect(play, SIGNAL(clicked()), &loop, SLOT(quit()));
я делал паузу в другом потоке. это пример, чтобы иметь представление как можно сделать паузу.
Название: Re: Организация произвольного построчного чтения
Отправлено: Spark от Июль 21, 2013, 04:20
я ничего доброго не сказал. код ужасен. это притом что я сам не заморачиваюсь сейчас насчет читаемости своего кода, т.к. мало опыта еще.
Через два года я бы уже начал стесняться говорить. Сомневаюсь, что через пару месяцев вы делали что то серьезное. А по поводу паузы. Во первых сам по себе ваш ответ говорит подобное. Опыта у вас, действительно, пока еще маловато, для того, что бы с ходу понять, почему пришлось именно так сделать. Вы профи сначала реализуйте свое подобное, когда столкнетесь с проблемами я посмеюсь. Нравится вам код или нет меня это мало волнует. А вот сами по себе замечания для меня полезны (просто можно было обойтись без сарказма). Я то воспользуюсь критикой и достаточно быстро оптимизирую, а в следующий раз учту, спасибо вам за это, но вот поумнеете ли вы, это вопрос еще.
Название: Re: Организация произвольного построчного чтения
Отправлено: Igors от Июль 21, 2013, 07:20
2Spark "не кормите тролля" :)
Название: Re: Организация произвольного построчного чтения
Отправлено: thechicho от Июль 21, 2013, 08:42
да, ты сучонок нагл и упорот. в игнор :)
|