Форум по Delphi программированию

Delphi Sources



Вернуться   Форум по Delphi программированию > Все о Delphi > Базы данных
Ник
Пароль
Регистрация <<         Правила форума         >> FAQ Пользователи Календарь Поиск Сообщения за сегодня Все разделы прочитаны

Ответ
 
Опции темы Поиск в этой теме Опции просмотра
  #1  
Старый 10.04.2007, 18:04
Тимониссимо Тимониссимо вне форума
Прохожий
 
Регистрация: 10.04.2007
Сообщения: 15
Репутация: 10
По умолчанию Delphi 7 + access + excel = out of memory

В общем, программер я плохой, но диплом писать надо...
Смысл проги такой: есть таблица access со стат данными про предприятия (7 показателей за каждый квартал с 2000 по 2006 год, итого, 1000 строк и ок. 200 столбцов).
Соединяюсь через ado, Делаю выборку из таблицы (выбрать предприятия опред. отрасли и района). Данные отображаются в dbgrid. Далее перегоняю в обычный массив.
Затем создаю E:=CreateOleObject('Excel.Application'); Пергоняю из массива в ячейки активной книги.
В итоге, после увеличения файла подкачки до 1 Гб прога начала работать (Athlon 2.0, 512 озу). Exe-ник соответственно тоже не запускается на средник по мощности компах.
Не могу также при перегоне из массива в excel заполнить одну ячейки в строке (заголовки к таблице) - в этом случае гига оперативы не хватает!
Короче, подскажите, что делать, плз!!!
Вот код программы:

var
Form1: TForm1;
nachalo, konec, kolzap, i, j: integer;
e,sheet:variant;
mas_data: array [1..10000, 1..10000] of real;
mas_data2: array [1..10000, 1..10000] of real;
mas_data3: array [1..10000, 1..5] of string;
odna_firma: string;
mas_pokaz: array [1..7] of string = ('Прибыль','Отгрузка','Обор. активы','Собст. кап.','заим. кап','бюдж. зад','кратк. зад');

implementation

uses Unit2;

{$R *.dfm}

procedure TForm1.Button1Click(Sender: TObject);
begin
with unit2.DataModule2.ADOQuery1 do
begin
Active:=false;
sql.Clear;
sql.Add('select * ');
sql.Add('from alldata'); //+unit1.Form1.Edit1.Text+
sql.add('where region like ''117%''');
active:=true;
unit1.Form1.Edit2.Text:=inttostr(unit1.Form1.DBGri d1.DataSource.DataSet.RecordCount);
end;
end;
procedure TForm1.Button2Click(Sender: TObject);
begin
with unit2.DataModule2.ADOQuery1 do
begin
Active:=false;
datamodule2.ADOQuery1.Parameters.ParamByName('kodt own1').Value:=0;
datamodule2.ADOQuery1.Parameters.ParamByName('kodt own2').Value:=10000000000;
datamodule2.ADOQuery1.Parameters.ParamByName('otr1 ').Value:=0;
datamodule2.ADOQuery1.Parameters.ParamByName('otr2 ').Value:=100000;
active:=true;
unit1.Form1.Edit2.Text:=inttostr(unit1.Form1.DBGri d1.DataSource.DataSet.RecordCount);
end;
end;

procedure TForm1.Button3Click(Sender: TObject);
var
perem, otrasl: string;
perem2, perem1, k, pi,pj: integer; // для города
otr1, otr2:integer; //для отрасли

begin
perem:=unit1.Form1.DBLookupComboBox1.Text; // считали название города
with unit2.DataModule2.ADOQuery_town do //выбираем код города в соотв. с выбранным названием
begin
active:=false;
sql.Clear;
sql.Add('select * from soato');
sql.Add('where name like '''+perem+'''');
active:=true;
end;
perem:=unit2.DataModule2.ADOQuery_town.Fields[0].AsString; //считываем код города
if form1.CheckBox1.Checked=false then
begin
perem2:=strtoint(perem)+1999;
perem1:=strtoint(perem)-1;
end
else
begin
perem2:=strtoint(perem)+1;
perem1:=strtoint(perem)-1;
end;
//----------- закончили с городом -----------------//
otrasl:=unit1.Form1.DBLookupComboBox2.Text;
with unit2.DataModule2.ADOQuery_otrasl do
begin
active:=false;
sql.Clear;
sql.Add('select * from okonh');
sql.Add('where name like '''+otrasl+'''');
active:=true;
end;
otrasl:=unit2.DataModule2.ADOQuery_otrasl.Fields[0].AsString; //считали отрасль
if form1.CheckBox2.Checked=false then
begin
otr1:=strtoint(otrasl)-1;
otr2:=strtoint(otrasl)+999;
end
else
begin
otr1:=strtoint(otrasl)-1;
otr2:=strtoint(otrasl)+1;
end;
//otr1:=0;
//otr2:=100000;
//-------------- закончили с отраслью -------------//

with unit2.DataModule2.ADOQuery1 do
begin
Active:=false;
datamodule2.ADOQuery1.Parameters.ParamByName('kodt own1').Value:=perem1;
datamodule2.ADOQuery1.Parameters.ParamByName('kodt own2').Value:=perem2;
datamodule2.ADOQuery1.Parameters.ParamByName('otr1 ').Value:=otr1;
datamodule2.ADOQuery1.Parameters.ParamByName('otr2 ').Value:=otr2;
// unit1.Form1.Edit2.Text:=unit2.DataModule2.ADOQuery 1.SQL.GetText;
active:=true;
unit1.Form1.Edit2.Text:=inttostr(unit1.Form1.DBGri d1.DataSource.DataSet.RecordCount);
end;

//------------ начинаем отбор по периоду ----------------//
kolzap:=unit1.Form1.DBGrid1.DataSource.DataSet.Rec ordCount;
nachalo:=(strtoint(form1.ComboBox2.Text)-2000)*28+7*(strtoint(form1.ComboBox1.Text));
konec:=(strtoint(form1.ComboBox4.Text)-2000)*28+7*(strtoint(form1.ComboBox3.Text)+1)-1;
//---- создаем книгу excel ----//
E:=CreateOleObject('Excel.Application');
e.workbooks.add(-4167);
e.workbooks[1].worksheets[1].name:='лист1';
sheet:=e.workbooks[1].worksheets['лист1'];
//------ считываем dbgrid (только 7 показателей) -----------------------//
sheet.cells[1,1]:='код ОКПО';
sheet.cells[1,2]:='Регион';
sheet.cells[1,3]:='Тип';
sheet.cells[1,4]:='Отрасль';
sheet.cells[1,5]:='Название';
sheet.cells[1,6]:='Адрес';
k:=7;
//------ заголовки первый прогон -------//

pi:=strtoint(form1.ComboBox1.Text);
pj:=strtoint(form1.ComboBox2.Text);
sheet.range['A1:Gs1'].font.bold:=true;
with unit2.DataModule2.ADOQuery1 do
begin
first;
for i:=1 to kolzap do
begin
mas_data2[i,1]:=fields[0].AsFloat; sheet.cells[i+1,1]:=mas_data2[i,1];
mas_data2[i,2]:=fields[1].AsFloat; sheet.cells[i+1,2]:=mas_data2[i,2];
mas_data2[i,3]:=fields[2].AsFloat; sheet.cells[i+1,3]:=mas_data2[i,3];
mas_data2[i,4]:=fields[3].AsFloat; sheet.cells[i+1,4]:=mas_data2[i,4];
mas_data3[i,1]:=fields[4].AsString; sheet.cells[i+1,5]:=mas_data3[i,1];
mas_data3[i,2]:=fields[5].AsString; sheet.cells[i+1,6]:=mas_data3[i,2];
k:=7;
for j:=(nachalo-1) to (konec-1) do
begin
mas_data[i,j]:=fields[j].AsFloat;
sheet.cells[i+1,k]:=mas_data[i,j];
k:=k+1;
end;
moveby(1);
end;
end;
//-------------- выгружаем нужное в excel -----------------//
if form1.CheckBox3.Checked=true then
e.visible:=true;
end;

procedure TForm1.Edit4KeyUp(Sender: TObject; var Key: Word;
Shift: TShiftState);
begin
with unit2.DataModule2.ADOQuery_firms do
begin
active:=false;
sql.clear;
sql.Add('select alldata.name');
sql.Add('from alldata');
sql.Add('where name like ''%'+unit1.Form1.Edit4.Text+'%''');
active:=true;
end;
end;
Ответить с цитированием
  #2  
Старый 10.04.2007, 18:16
Аватар для mav_c
mav_c mav_c вне форума
Активный
 
Регистрация: 26.03.2007
Адрес: Москва
Сообщения: 287
Репутация: 30
По умолчанию

Пиши напрямую из датасэта в Exel
__________________
---------------------------------------------
Программирование - не профессия, а стиль жизни
Ответить с цитированием
  #3  
Старый 10.04.2007, 18:28
Тимониссимо Тимониссимо вне форума
Прохожий
 
Регистрация: 10.04.2007
Сообщения: 15
Репутация: 10
По умолчанию

Цитата:
Сообщение от mav_c
Пиши напрямую из датасэта в Exel

Не получится, так как мне нужно предварительно массив обработать
(кроме семи показателей будут еще несколько производных)

Или как то можно обычный массив загнать в dataset ?
Ответить с цитированием
  #4  
Старый 11.04.2007, 05:48
Аватар для Aristarh Dark
Aristarh Dark Aristarh Dark вне форума
Модератор
 
Регистрация: 07.10.2005
Адрес: Москва
Сообщения: 2,906
Версия Delphi: Delphi XE
Репутация: выкл
По умолчанию

Поробуй грузить не поячеечно, а блоками.
Ответить с цитированием
  #5  
Старый 11.04.2007, 18:36
Аватар для mav_c
mav_c mav_c вне форума
Активный
 
Регистрация: 26.03.2007
Адрес: Москва
Сообщения: 287
Репутация: 30
По умолчанию

Цитата:
Сообщение от Тимониссимо
Не получится, так как мне нужно предварительно массив обработать
(кроме семи показателей будут еще несколько производных)

Или как то можно обычный массив загнать в dataset ?
Создай dataset с соответствующими полями!
После этого пиши так
ds.Insert();
ds.FieldByName('name').AsString := 'xxx';
ds.ApplyUpdates();
__________________
---------------------------------------------
Программирование - не профессия, а стиль жизни
Ответить с цитированием
  #6  
Старый 12.04.2007, 11:06
Тимониссимо Тимониссимо вне форума
Прохожий
 
Регистрация: 10.04.2007
Сообщения: 15
Репутация: 10
По умолчанию

А не может быть проблемы в том, что у меня остаются активными несколько ADOQuery и ADOTable ?
Где здесь вообще ошибка, на какой стадии: delphi и БД, delphi и excel?
почему после компиляции программа запускается только с гигабайтным файлом подкачки, хотя в процессе совершенно не тормозит?
Ответить с цитированием
  #7  
Старый 12.04.2007, 12:36
Аватар для Aristarh Dark
Aristarh Dark Aristarh Dark вне форума
Модератор
 
Регистрация: 07.10.2005
Адрес: Москва
Сообщения: 2,906
Версия Delphi: Delphi XE
Репутация: выкл
По умолчанию

А еще оптимизируй запросы. Зачем выбирать в запросах все поля (*) если все ты их не используешь?
Например вот:
Код:
with unit2.DataModule2.ADOQuery1 do
begin
Active:=false;
sql.Clear;
sql.Add('select * ');
sql.Add('from alldata'); //+unit1.Form1.Edit1.Text+
sql.add('where region like ''117%''');
active:=true;
unit1.Form1.Edit2.Text:=inttostr(unit1.Form1.DBGri d1.DataSource.DataSet.RecordCount);
end;
для интереса прикинь сколько инфы у тебя передается этим запросом и сразу станет ясно куда отгребается виртуальная память системы.
Я не в курсе структуры, но вот этот запрос скорее всего аналогичен, точнее результат ты получишь тот же - т.е. количество:
Код:
SELECT COUNT(Region) FROM AllData
WHERE Region LIKE '117%'
итого имеем датасет с однай записью и одним полем.
Ответить с цитированием
  #8  
Старый 12.04.2007, 12:59
Тимониссимо Тимониссимо вне форума
Прохожий
 
Регистрация: 10.04.2007
Сообщения: 15
Репутация: 10
По умолчанию

Цитата:
Сообщение от Aristarh Dark
А еще оптимизируй запросы.
Вот это попробую...
Хотя не думал, что даже такие запросы могут быть так требовательны к ресурсам. Табличка то небольшая, всего 1000х200, не думал, что выборка даже всех записей так загружать память системы
Ответить с цитированием
  #9  
Старый 12.04.2007, 14:15
Аватар для Aristarh Dark
Aristarh Dark Aristarh Dark вне форума
Модератор
 
Регистрация: 07.10.2005
Адрес: Москва
Сообщения: 2,906
Версия Delphi: Delphi XE
Репутация: выкл
По умолчанию

Цитата:
Сообщение от Тимониссимо
Вот это попробую...
Хотя не думал, что даже такие запросы могут быть так требовательны к ресурсам. Табличка то небольшая, всего 1000х200, не думал, что выборка даже всех записей так загружать память системы
хм... 200 000 полей, даже если по 10 байт на поле - 2 мегабайта, а на поле явно не по 10 байт
Ответить с цитированием
  #10  
Старый 12.04.2007, 14:51
Тимониссимо Тимониссимо вне форума
Прохожий
 
Регистрация: 10.04.2007
Сообщения: 15
Репутация: 10
По умолчанию

Цитата:
Сообщение от Aristarh Dark
хм... 200 000 полей, даже если по 10 байт на поле - 2 мегабайта, а на поле явно не по 10 байт

да у меня даже .exe файл не открывается (пишет, что недостаточно памяти), хотя выборка данных и создание excel.application начинается только после нажатия одной кнопки на форме
Ответить с цитированием
  #11  
Старый 12.04.2007, 18:04
Тимониссимо Тимониссимо вне форума
Прохожий
 
Регистрация: 10.04.2007
Сообщения: 15
Репутация: 10
По умолчанию

Может быть такое, что прогу я компилил на мощном компе с большим файлом подкачки, а запускаю на менее мощном и из-за этого ошибка?
Ответить с цитированием
  #12  
Старый 12.04.2007, 18:58
Аватар для mav_c
mav_c mav_c вне форума
Активный
 
Регистрация: 26.03.2007
Адрес: Москва
Сообщения: 287
Репутация: 30
По умолчанию

Цитата:
Сообщение от Тимониссимо
Может быть такое, что прогу я компилил на мощном компе с большим файлом подкачки, а запускаю на менее мощном и из-за этого ошибка?
нет из-за этого не может
__________________
---------------------------------------------
Программирование - не профессия, а стиль жизни
Ответить с цитированием
Ответ


Delphi Sources

Опции темы Поиск в этой теме
Поиск в этой теме:

Расширенный поиск
Опции просмотра

Ваши права в разделе
Вы не можете создавать темы
Вы не можете отвечать на сообщения
Вы не можете прикреплять файлы
Вы не можете редактировать сообщения

BB-коды Вкл.
Смайлы Вкл.
[IMG] код Вкл.
HTML код Выкл.
Быстрый переход


Часовой пояс GMT +3, время: 15:16.


 

Сайт

Форум

FAQ

RSS лента

Прочее

 

Copyright © Форум "Delphi Sources" by BrokenByte Software, 2004-2023

ВКонтакте   Facebook   Twitter