Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Вытянуть данные из DBGrid, оптимальное решение?? 
:(
    Опции темы
vrska
Дата 29.3.2010, 22:29 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 3
Регистрация: 4.3.2010

Репутация: нет
Всего: нет



Задача: Сделать планировщик задач.
Используется: delphi2010 , sqlite, zeoslib, ehlib(DBGridEh).

Есть база
user posted image

Очень напрягает опрашивать базу каждую секунду + когда база загружается в DBGridEh1, он скролится от первой записи к последний каждую секунду. 
Есть ли более человеческое решение данной задачи?  smile 

Ниже 2 кода, одинакого по функционалу(как я понял), найдены на этом форуме ;)

код1
Код

procedure TForm1.Timer2Timer(Sender: TObject);
begin
  i:=0;
  with DBGridEh1.DataSource.DataSet do
  begin
    First;
    while not Eof do
    begin
      if FieldByName('time').AsString = TimeToStr(Now) then
      ShellExecute(Handle, 'open', PChar(FieldByName('exec').AsString), nil, nil, SW_SHOW);
      Next;
      i:=i+1;
    end;
  end;
end;


код2
Код

procedure TForm1.Timer2Timer(Sender: TObject);
begin
  DBGridEh1.DataSource.DataSet.First;
  for i := 0 to DBGridEh1.DataSource.DataSet.RecordCount-1 do
  begin
    if DBGridEh1.DataSource.DataSet.FieldByName('time').AsString = TimeToStr(Now) then
      ShellExecute(Handle, 'open', PChar(DBGridEh1.DataSource.DataSet.FieldByName('exec').AsString), nil, nil, SW_SHOW);
  DBGridEh1.DataSource.DataSet.Next;
  end;
end;


Заранее спасибо
ЗЫ: До этого никогда не кодил и не открывал делфи  smile 
PM MAIL   Вверх
chip_and_dayl
Дата 29.3.2010, 23:39 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 603
Регистрация: 22.4.2007
Где: Украина, Киев

Репутация: 2
Всего: 9



Не понял зачем в первом коде переменная И

Добавлено через 5 минут и 15 секунд
По логике работы они в принципе одинаковые. Но первый вариант есть более лучшим (не в плане быстродействия).
По оптимизации могу сказать одно, отключи видимость передвижения курсора по записям smile Во-первых глаза мозолить не будет, во-вторых быстродействие должно возрасти (хотя это чисто мое сугубое наблюдение)

Добавлено через 10 минут и 42 секунды
А еще в цикле не помешает application.processmessages программа не будет виснуть, особенно когда цикл

Это сообщение отредактировал(а) chip_and_dayl - 29.3.2010, 23:40


--------------------
Фсё будет хорошо!!!
PM MAIL Skype   Вверх
VictorTsaregorodtsev
Дата 29.3.2010, 23:50 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 274
Регистрация: 28.7.2006

Репутация: 1
Всего: 8



У писавших такой код - ошибки в ДНК. Если на каждой итерации цикла вычислять одно и то же - конечно будет тормозить.

В первом варианте TimeToStr(Now) вычисляется каждый раз - можно вне цикла однократно присвоить её результат локальной переменной, и потом пользоваться последней.
FieldByName('time') тоже ищется каждый раз. Вне цикла один раз найти и сохранить указатель на поле в  локальной переменной - при перемещении по строкам таблицы указатель останется актуальным.
Сравнение строк - как бы там тоже не возникало создания (через конструктор) и уничтожения "невидимых" строк (с Борланда станется...)

Второй вариант - на каждой итерации вычисляется DBGridEh1.DataSource.DataSet.RecordCount, каждая "точка" - это, считайте, вызов функции и возврат значения оттуда. Да и не для каждого формата баз данных RecordCount хранится в базе (в dbf-формате не хранится, в ранних версиях VCL тоже не определялся и потом не хранился - а каждый раз вычислялся заново как бы не прогоном до конца базы и обратно на текущую запись). Т.е. цикл от конца к началу крутить можно, а от начала к концу с постоянным опросом RecordCount - тормоза.
DBGridEh1.DataSource.DataSet.FieldByName - аналогично.
Ну и всё сказанное для первого варианта ко второму тоже применимо.

Конкретно по синтаксису улучшений тутошние паскалисты подскажут (я сишник).

Ну и сама архитектура приложения вызывает вопросы (насчет опроса базы каждую секунду) - это уже vrska пинок. При записи в базу (да и нафига база - обычный текстовый файл сойдет) сначала просто сортировать задания по времени, а потом ждать до наступления момента первого задания в списке (т.е. к базе не ходить, в локальной переменной дату-время держать), в момент же наступления события - делать, что нужно, после чего удалять первую запись и брать время следующей как ориентир для "пробуждения".
PM MAIL WWW   Вверх
Frees
Дата 30.3.2010, 08:39 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 2233
Регистрация: 2.12.2005
Где: Екатеринбург

Репутация: 23
Всего: 54



точность до секунд - лишнее, минуты за глаза,  храни время как TDateTime а не как строки.




--------------------
Кольцов Виктор Владимирович
PM MAIL ICQ   Вверх
former
Дата 30.3.2010, 12:06 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


MEMS Expert
***


Профиль
Группа: Завсегдатай
Сообщений: 1166
Регистрация: 1.3.2006
Где: Россия

Репутация: 7
Всего: 17



Цитата(VictorTsaregorodtsev @  29.3.2010,  23:50 Найти цитируемый пост)
Ну и сама архитектура приложения вызывает вопросы (насчет опроса базы каждую секунду) - это уже vrska пинок. При записи в базу (да и нафига база - обычный текстовый файл сойдет) сначала просто сортировать задания по времени, а потом ждать до наступления момента первого задания в списке (т.е. к базе не ходить, в локальной переменной дату-время держать), в момент же наступления события - делать, что нужно, после чего удалять первую запись и брать время следующей как ориентир для "пробуждения". 

VictorTsaregorodtsev, при таком варианте в один момент времени может быть выполнено только одно задание. А если автору нужно выполнять несколько заданий в несколько потоков в один момент времени?


--------------------
Достаточно снизить уровень мышления, чтобы иные почувствовали почву под ногами.
PM MAIL   Вверх
vrska
Дата 30.3.2010, 12:12 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 3
Регистрация: 4.3.2010

Репутация: нет
Всего: нет



Цитата(Frees @ 30.3.2010,  08:39)
точность до секунд - лишнее, минуты за глаза

если запуск файла запланирован в 12:00:00
проверка была в 11:59:50 и будет в 12:00:10, получается файл не запустится. я не прав? 

VictorTsaregorodtsev
Спасиба за конструктивную критику, это приветствуется.
На сколько я понял вы имели ввиду сделать так

Код

procedure TForm1.Timer2Timer(Sender: TObject);
var
timenow: string;
begin
  timenow := TimeToStr(Now);
  with DBGridEh1.DataSource.DataSet do
  begin
    First;
    while not Eof do
    begin
      if FieldByName('time').AsString = timenow then
      ShellExecute(Handle, 'open', PChar(FieldByName('exec').AsString), nil, nil, SW_SHOW);
      Next;
    end;
  end;
end;


т.е. присвоил TimeToStr(Now) переменную timenow, но разве она не вычисляется каждую секунду как было в коде до этого? timenow тоже стоит в процедуре таймера, который обновляется каждую секунду. Или я что то не понимаю.

Добавлено через 4 минуты и 13 секунд
Приветствуются конкретные примеры. Возможно кто то решит задачу за небольшое вознаграждение  smile 
PM MAIL   Вверх
Frees
Дата 30.3.2010, 12:39 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 2233
Регистрация: 2.12.2005
Где: Екатеринбург

Репутация: 23
Всего: 54



Цитата(vrska @  30.3.2010,  15:12 Найти цитируемый пост)
проверка была в 11:59:50 и будет в 12:00:10, получается файл не запустится. я не прав? 

смотря как проверять будеш наличие задачи
проверяй раз в минуту с последнего времени проверки до конца текущей минуты
тогда не пропустиш

Добавлено @ 12:53
я делаю это вот так

Код

Query1.SQL :=  'SELECT ID FROM ЗАДАЧИ WHERE' + 
          '    ВРЕМЯ_ЗАДАЧИ > :BEGIN' + 
          '    AND  ВРЕМЯ_ЗАДАЧИ <= :END'

FLastRemindTime: TDateTime;

procedure TForm1.Timer1Timer(Sender: TObject);
var
  tm: TDateTime;
  v: Variant;
begin
  tm := IncMinute(RoundDateTime(Now), 1);
  if FLastRemindTime = tm then
    Exit;
  with Query1 do
  begin
      Close;
      ParambyName('BEGIN').Value := FLastRemindTime;
      ParambyName('END').Value := tm;      
      ExecQuery;                
      FLastRemindTime := tm;
      while not Eof then
      begin
        //Выполнием заданеи
        Next;
      end;
  end
 end; 


хотя идея VictorTsaregorodtsev, мне тоже пнравилась возможно переделаю

Это сообщение отредактировал(а) Frees - 30.3.2010, 13:27


--------------------
Кольцов Виктор Владимирович
PM MAIL ICQ   Вверх
Frees
Дата 30.3.2010, 12:54 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 2233
Регистрация: 2.12.2005
Где: Екатеринбург

Репутация: 23
Всего: 54



RoundDateTime - функция отбрасывает секунды


--------------------
Кольцов Виктор Владимирович
PM MAIL ICQ   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
Правила форума "Delphi: Базы данных и репортинг"
Vit
Петрович

Запрещено:

1. Публиковать ссылки на вскрытые компоненты

2. Обсуждать взлом компонентов и делиться вскрытыми компонентами


Обязательно указание:

1. Базы данных (Paradox, Oracle и т.п.)

2. Способа доступа (ADO, BDE и т.д.)


  • Литературу по Дельфи обсуждаем здесь
  • Действия модераторов можно обсудить здесь
  • С просьбами о написании курсовой, реферата и т.п. обращаться сюда
  • Вопросы по реализации алгоритмов рассматриваются здесь
  • 90% ответов на свои вопросы можно найти в DRKB (Delphi Russian Knowledge Base) - крупнейшем в рунете сборнике материалов по Дельфи
  • Вопросы по SQL и вопросы по базам данных не связанные с Дельфи задавать здесь

FAQ раздела лежит здесь!


Если Вам помогли и атмосфера форума Вам понравилась, то заходите к нам чаще! С уважением, Vit, Петрович.

 
1 Пользователей читают эту тему (1 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | Delphi: Базы данных и репортинг | Следующая тема »


 




[ Время генерации скрипта: 0.0760 ]   [ Использовано запросов: 21 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.