Russian Qt Forum

Qt => Общие вопросы => Тема начата: gil9red от Май 13, 2013, 22:02



Название: Автоматическое сохранение
Отправлено: gil9red от Май 13, 2013, 22:02
Здравствуйте!
Делаю программу "менеджер электронных заметок".
Встал вопрос как лучше всего сделать автоматическое сохранение изменений.

У меня такая идея: поставить общий на всю прогу таймер сохранения
ну скажем раз в 5 минут
  • У этого таймера есть список заметок, которых нужно сохранить
  • Когда какая нибудь заметка изменяется, она сигналит об этом, таймер перехватывает ее сигнал и добавляет ее в список
  • Повторяющиеся заметки будут удалены - останется только 1 экземпляр, но останется последний добавленный
  • Когда весь список опустеет, таймер выключается
  • Когда, в отключенном состоянии, таймер отлавливает сигнал, добавляет в список заметку, испустившую сигнал и запускается
  • Когда время таймера истечет, происходит сохранение данных всех заметок в списке

Ваши идеи :)


Название: Re: Автоматическое сохранение
Отправлено: Bepec от Май 13, 2013, 22:10
Стоит ли таймер запускать? Может проще сохранять при изменении? У вас явно будет не более 200 заметок (ширина экрана поделённая на строку читаемого формата, примерно). Стоит ли из-за них делать общий таймер и прочая? К тому же с таймером связана опасность не успеть сохранить при, скажем, быстром отключении питания через минуту.

Т.е. у вас полюбому будет функционал сохранения "как есть" мгновенно. Зачем тогда таймер?


Название: Re: Автоматическое сохранение
Отправлено: Majestio от Май 13, 2013, 22:19
Сохранение в момент завершения редактирования - лучший вариант. Смысла откладывать сохранение на N минут нет никакого.


Название: Re: Автоматическое сохранение
Отправлено: gil9red от Май 13, 2013, 22:21
У меня и так сейчас стоит сохранение при любом "чохе" :)
при редактировании содержимого заметок, при изменении цвета, при изменении заголовка, при изменении размера, при изменении положения на экрана и т.д. и т.п.

Причем все эти сохранения идут в внешний файл. А конкретно - каждая заметка имеет собственный файл
Хочется увеличить скорость работы программы :)

Вот и думаю, может что то с автосохранением изменений сделать )


Название: Re: Автоматическое сохранение
Отправлено: Bepec от Май 13, 2013, 22:46
Вы сделайте автосохранение с таймером. Таймер не на "общее сохранение", а на "3 секунды после последнего изменения".


Название: Re: Автоматическое сохранение
Отправлено: gil9red от Май 13, 2013, 22:48
Т.е. после каждого изменения, создавать таймер, который эти изменения сохранит через определенный короткий промежуток времени?  :)


Название: Re: Автоматическое сохранение
Отправлено: Majestio от Май 13, 2013, 23:00
Понятие "увеличить скорость программы" надо бы уточнить. Если речь идет о притормаживании UI во время сохранения, так делать это отдельным от GUI потоком (через тот же singleShot таймера). Если речь идет о пересчетах ... ну не знаю, реализуйте узкие части на асме ... хотя судя по специфике программы, вероятно речь идет о первом.


Название: Re: Автоматическое сохранение
Отправлено: gil9red от Май 14, 2013, 05:39
Ясно :)
Я тоже подумал о QTimer::singleShot()  :)


Название: Re: Автоматическое сохранение
Отправлено: Bepec от Май 14, 2013, 06:34
Хотя на мой взгляд у вас что-то в архитектуре наверно. Сохранение даже десятка файлов по десятку мегабайт не вызывает трудностей. Что-то у вас не чисто :P


Название: Re: Автоматическое сохранение
Отправлено: Old от Май 14, 2013, 06:43
Причем все эти сохранения идут в внешний файл. А конкретно - каждая заметка имеет собственный файл
Хочется увеличить скорость работы программы :)
А чем вас не устраивает скорость? Даже если программа будет сохранять каждое изменение еще в 10 архивных файлах, тормозить ничего не должно. Что там за объемы, считанные байты?
Не хотите записывать каждый "чих", ждите пока пользователь перестанет вносить изменения несколько секунд и сохраняйте. Ну и конечно, не забывайте сохранить все изменения, если пользователь закрывает программу раньше.


Название: Re: Автоматическое сохранение
Отправлено: gil9red от Май 14, 2013, 16:33
В общем нашел ошибку и исправил :)
С архитектурой все ок! Дело в моих кривых руках годичной давности - когда только-только начал изучать всерьез программирование :D

Дело в том что навесив на события изменения размера и положения на экране, сохранение соответствующих параметров подложил себе большууую свинью - сдвиг хоть на миллиметр (образно) вызывает функцию сохранения, при сдвиге на большем расстоянии - больше десятка подряд (я точно не считал) и из-за этого возникали "артефакты"

Создал таймер, который сработает 1 раз:
Код:
timerAutosavePosition = new QTimer();
timerAutosavePosition->setSingleShot(true);
timerAutosavePosition->setInterval(intervalAutosave);

connect(timerAutosavePosition, SIGNAL(timeout()),
           this, SLOT(savePosition()));

а в функциях-событиях (moveEvent и resizeEvent) вызываю нужные таймеры
Код:
timerAutosavePosition->start(); 
вызов start() без параметров сбрасывает таймер
таким образом, изменения будут сохранены только после того, как с последнего изменения пройдет intervalAutosave времени  :)

Ну как то так :)
Это еще только доработка  - что то мне не нравится в этом - но она уже доказала свою эффективноть  :)


Название: Re: Автоматическое сохранение
Отправлено: Bepec от Май 14, 2013, 16:42
Это нормально.

Ненравится потому, что в промежуток таймера могут потеряться данные. Это можно исправить, если добавить приоритеты для сохранения.
Аля:
низкий приоритет - состояние окон, 10 секунд.
средний приоритет - цвет или там ещё что,  5 секунд.
высокий приоритет - сами записи, их содержимое. Незамедлительное сохранение.

PS если и потеряете, то самое ценное останется.
 


Название: Re: Автоматическое сохранение
Отправлено: gil9red от Май 14, 2013, 16:48
То что вы описали, уже есть =)
Самое важное и/или мало вызываемое сразу сохраняется  :)

Остается проблема только с сохранением текста.

У меня сохранение текста происходит в момент его изменения.
Причем сохраняется весь текст.
А т.к. используется rich text, то сам сохраняемый текст вдобавок нагружается тегами html.

Можно ли как то оптимизировать такое сохранение? :)


Название: Re: Автоматическое сохранение
Отправлено: Bepec от Май 14, 2013, 17:10
Чесслово я не понимаю вашей проблемы :D

Текст < 700 символов сохраняется мгновенно. 

Неужели у вас ВОООТ такое вот полотнище заметок? В случае текстЭдита сохранение должно идти с минимальной, но задержкой. 3 секунды после последнего введённого символа хватит, я думаю.


Название: Re: Автоматическое сохранение
Отправлено: gil9red от Май 14, 2013, 19:23
Кто уж знает будущего пользователя  :)
Вдруг ему вздумается все тома "войны и мира" засунуть в заметку :D
а из-за одного символа записывать 100500 символов... :)
Цитировать
В случае текстЭдита сохранение должно идти с минимальной, но задержкой. 3 секунды после последнего введённого символа хватит, я думаю.

Спасибо, так и сделаю :)


Название: Re: Автоматическое сохранение
Отправлено: Majestio от Май 14, 2013, 19:36
Создал таймер, который сработает 1 раз:
Код:
timerAutosavePosition = new QTimer();
timerAutosavePosition->setSingleShot(true);
timerAutosavePosition->setInterval(intervalAutosave);

connect(timerAutosavePosition, SIGNAL(timeout()),
           this, SLOT(savePosition()));

Это жи монстер у тя вышел!  ;D

... Может сохранение делать вот так:

QTimer::singleShot(2000,this,SLOT(SlotSuperSave()));

 ::)


Название: Re: Автоматическое сохранение
Отправлено: Bepec от Май 14, 2013, 19:53
Конечно так запись выглядит проще, но непонятнее для новичков ;)


Название: Re: Автоматическое сохранение
Отправлено: gil9red от Май 14, 2013, 20:02
Создал таймер, который сработает 1 раз:
Код:
timerAutosavePosition = new QTimer();
timerAutosavePosition->setSingleShot(true);
timerAutosavePosition->setInterval(intervalAutosave);

connect(timerAutosavePosition, SIGNAL(timeout()),
           this, SLOT(savePosition()));

Это жи монстер у тя вышел!  ;D

... Может сохранение делать вот так:

QTimer::singleShot(2000,this,SLOT(SlotSuperSave()));

 ::)

А таймер QTimer::singleShot будет обновляться при его повторном вызове? )
Проверил, что нет :)

Поэтому пусть лучше будет "монстр", но работающий :)


Название: Re: Автоматическое сохранение
Отправлено: Majestio от Май 14, 2013, 20:13
Поэтому пусть лучше будет "монстр", но работающий :)

Это как? В момент вызова он отрабатывает 1 раз - чере 2 сек вызовет слот.
Нужно еще сохранение - еще раз вызовешь.
Он же и есть single! - его задача активировать через n сек новый тред.


Название: Re: Автоматическое сохранение
Отправлено: gil9red от Май 14, 2013, 20:27
В том то и дело =)
Такие вызовы его помещаются в очередь и выполнятся друг за дружком, и вызовут лаги, поэтому и был использован тот "монстр", который активировался и вызывал слот сохранения только тогда, когда с последнего изменения прошло некоторое время. Например, 1 секунда =)

Теперь никаких лагов )))


Название: Re: Автоматическое сохранение
Отправлено: Majestio от Май 14, 2013, 20:32
Теперь никаких лагов )))

Странно, а почему лаги были? Вернее в чем заключались? Если приложение в трех сторонних тредах пишет в три файла ... GUI тред же свободен во время записи?


Название: Re: Автоматическое сохранение
Отправлено: Bepec от Май 14, 2013, 20:39
Лаги при записи. Причём скорее всего сохранение идёт из ГУИ потока, что обосновано - при правильной архитектуре никаких потоков ненадо, это не особо ёмкие операции.


Название: Re: Автоматическое сохранение
Отправлено: Majestio от Май 14, 2013, 20:55
Лаги при записи. Причём скорее всего сохранение идёт из ГУИ потока, что обосновано - при правильной архитектуре никаких потоков ненадо, это не особо ёмкие операции.

Не согласен. Любые заметные по времени манипуляции с ресурсами крайне желательно выносить в отдельные потоки. Гуевое дело - управлять. Пусть ГУИ прогрессбар рисует какой или % записаного в статус строке обновляет, но операции кроме как отлова управления - гуй делать ниче не должен!


Название: Re: Автоматическое сохранение
Отправлено: Bepec от Май 14, 2013, 21:08
Вы, понятно дело, специалист наверняка в этой области и я боюсь даже спорить :D

Но... Но создание потока, синхронизация, взаимодействие всех заметок с потоком выйдет затратнее и ненадёжнее, чем простое и моментальное сохранение в основном потоке.

PS пока у многих, кто не пробовал многопоточность имеется "авторитетное" мнение, что чем больше потоков, тем лучше.


Название: Re: Автоматическое сохранение
Отправлено: gil9red от Май 14, 2013, 21:26
Согласен =)
Потоки вещь конечно клевая, но муторная :)
В крайнем случаи, буду функции сохранения выносить в отдельный поток через QFuture и QtConcurrent :)
Но сомневаюсь что это пригодится :)


Название: Re: Автоматическое сохранение
Отправлено: Majestio от Май 14, 2013, 21:50
Вы, понятно дело, специалист наверняка в этой области и я боюсь даже спорить :D

А зря!  ;D

(http://ic.pics.livejournal.com/andrey_zorin/12800503/340/340_original.jpg)

Но... Но создание потока, синхронизация, взаимодействие всех заметок с потоком выйдет затратнее и ненадёжнее, чем простое и моментальное сохранение в основном потоке.

"ненадёжнее" - это зависит от доверия к реализации QThread, QMutex, QMutexLocker

Если простое и моментальное - до полу секунды, согласен. А если 7 или даже 8?! :o

А с таймерами что с singlShot, что с повторяемым - все равно будут засады. Таймера выполняются в том потоке, где вызваны и где есть обработка событий.

Допустим выйдет portable версия - на глухой флэшке GUI будет лагать неподецки. Выход простой - использовать  QThread::exec() для потока-сохранятеля, общую очередь того, что нужно сохранять, доступ к очереди организовать через мьютексы. Я бы сделал именно так.



Название: Re: Автоматическое сохранение
Отправлено: gil9red от Май 14, 2013, 21:56
Я только учусь (с) :D


Название: Re: Автоматическое сохранение
Отправлено: Bepec от Май 14, 2013, 22:12
Кхм. Вообще по хорошему надо не мучаться с потоками, а писать всё в sqlite базу данных. И никаких потоков не надо и сложности не будет совершенно.
Запись за 0,00018 с вполне удовлетворяет всем требованиям.

А потоки коварны. Простейшая ошибка может выскочить через месяц или парочку. Доверие к Qt есть. Доверие к рукам, пишущим код - минимальное ;)

PS на данный момент флешки быстрее жёстких дисков. А запись в 7 секунд на SSD - это гигабайт с лишним думаю :)

PPS ради интереса с HDD на SSD скинул двухгиговую библиотечку - время копирования 14 секунд :D


Название: Re: Автоматическое сохранение
Отправлено: Majestio от Май 14, 2013, 22:29
Кхм. Вообще по хорошему надо не мучаться с потоками, а писать всё в sqlite базу данных.
Вот использование БД одобрям! Это действительно и упростит и ускорит запись.

А потоки коварны. Простейшая ошибка может выскочить через месяц или парочку.

В данном случае действий минимум:

1) Запуск/остановка потока
2) Захват/отдача ресурса (вектора заданий)
3) Выполнение единичного действия в потоке

Путаться негде. Можно конечно нагромоздить по типу а-ла рандеву языка Ада ... но это будет как из миномета по колорадским жукам)

PPS ради интереса с HDD на SSD скинул двухгиговую библиотечку - время копирования 14 секунд :D

У меня есть флешка на 128М ... раритет! Думал у меня одного на всей планете осталась такая, а-н нет ... черз одного, двух у бухгалтерш. Жысть - она разная)


Название: Re: Автоматическое сохранение
Отправлено: Bepec от Май 15, 2013, 06:39
Как говорил один мой знакомый - не лежи впереди паровоза :D

Пока что в данной ситуации у автора имеется нормальная десктопная программа с нормальным быстродействием.
Про развитие в "портабельность", "синхронизацию со всеми устройствами", "поддержку дискет и CD" мы не говорим.

Но так то - можно попробовать вообще сделать простейшую вещь. Поставить QDataWidgetMapper и соединить каждую заметку с базой :D Интересно тормозить будет?


Название: Re: Автоматическое сохранение
Отправлено: LEO от Май 15, 2013, 08:06
Делал запись с автосохранением по вводу инфы в Sqlite базу через QDataWidgetMapper, тормозов не замечал :)


Название: Re: Автоматическое сохранение
Отправлено: Majestio от Май 15, 2013, 08:13
В том-то и дело, что ...
Такие вызовы его помещаются в очередь и выполнятся друг за дружком, и вызовут лаги
... без дискет и флешек. Не знаю, но приходится верить, что его синглшоты вызывают лаги. Да ланна, думаю вопрос уже имеет кучу решений, выбирай не хочу.


Название: Re: Автоматическое сохранение
Отправлено: panAlexey от Май 15, 2013, 16:16
А у нас есть какой-нить раздел типа "полезные программы форумчан"?
Я бы себе присмотрел пару софтин по заметкам, выбрал бы какую-нить.


Название: Re: Автоматическое сохранение
Отправлено: Bepec от Май 15, 2013, 17:01
Нету. У меня имеются некоторые полезные программы, но все они в стадии "криво валко стенко шаталко - один разработчик меня понимает" :P


Название: Re: Автоматическое сохранение
Отправлено: panAlexey от Май 16, 2013, 00:18
Да вот жешь...
хочется нечто вроде "Exiland Assistant (http://www.exiland-soft.com/ru/)", наковырял запчастей а склеять времени маловато.
Может устроим гроупваре?


Название: Re: Автоматическое сохранение
Отправлено: Bepec от Май 16, 2013, 07:12
Посмотрю что за программка.