[excel] быстро выдернуть данные из excel-а во внешнюю прогу?
ODBC/OleDb с какой скоростью данные выдергивают?
ODBC/OleDb с какой скоростью данные выдергивают?Из экселя - с очень медленной.
Самый быстрый из известных мне способов - DDE, но у него свои косяки есть.
один из самых заметных - "эффект 4/7", когда строка "4/7" определяется экселем как седьмое апреля и данные передаются уже как "дата"
эти абревиатуры конечно интересно звучат, только не могли бы вы написать кусок кода на бэйсике на скачать кусок таблицы из экселя?
![](/images/graemlins/smirk.gif)
// Взять данные из Excel'я
// =======================
function QueryData(
IBook // Книга с листом
: I_Workbook;
ISheet // Лист, с которго будут браться данные
: I_Worksheet;
var Data // Данные
: TValueTable;
SelRange // Выбираемая область
: I_Range)
// код возврата
: integer;
var
xlDDE // Соединение DDE
: TDDEClientConv;
i,j, // индексы
sx,sy, // размеры
lp,p // позиции в буфере
: integer;
Buf: string;
begin
Result:=0;
xlDDE := TDDEClientConv.Create(nil);
try
if xlDDE.SetLink('EXCEL', '['+IBook.Name+']'+ISheet.Name) then
Buf:=xlDDE.RequestData(OLEVariant(SelRange).Address[ReferenceStyle:=xlR1C1])
else result:=-1;
finally
xlDDE.Free;
end;
if (Result=-1) then
begin
writeln('failed to gain data');
exit;
end;
// writeln('gained data.');
// writeln(buf);
sy:=SelRange.rows.count;
sx:=SelRange.columns.count;
SetLength(Data,sy);
for i:=0 to sy-1 do
SetLength(Data[i],sx);
i:=0;j:=0;
lp:=1;p:=1;
while p<=length(buf) do
begin
case Buf[p] of
egin
Data[i,j]:=StrToFloatDef(copy(Buf,lp,p-lp0);
inc(j);
lp:=p+1;
end;
egin
Data[i,j]:=StrToFloatDef(copy(Buf,lp,p-lp-10);
lp:=p+1;
inc(i);
j:=0;
end;
; // игнорировать этот символ
end;
inc(p);
end;
// StrDispose(Buf);
end;
// Послать данные в Excel
// ======================
function SendData(
IBook // Книга, которой принадлежит лист
: I_Workbook;
ISheet // Лист, в который будут записываться данные
: I_Worksheet;
Data // Данные
: TValueTable;
SelRange // Регион, куда складывать данные
: I_Range)
// код возврата
: integer;
var
xlDDE // Соединение DDE
: TDDEClientConv;
i,j // индексы
: integer;
Buf : string;
begin
Buf:=''; Result:=0;
for j:=0 to length(Data[0])-1 do
begin
for i:=0 to length(Data)-1 do
begin
Buf:=Buf+Format('%6.4f',[Data[i,j]]);
if i<length(Data)-1 then Buf:=Buf+#09;
end;
if j<length(Data[0])-1 then Buf:=Buf+#10;
end;
xlDDE := TDDEClientConv.Create(nil);
try
if xlDDE.SetLink('EXCEL', ISheet.Name) then
xlDDE.PokeData(OLEVariant(SelRange).Address[ReferenceStyle:=xlR1C1], PChar(Buf
else result:=-1;
finally
xlDDE.Free;
end;
end;
разбирайся-портируй в свой бейсик
очень медленной - это сколько записей в секунду?
сохранить csv во временный файл и распарсить.
.FormulaArray для объекта Range. Замерил время, получилось только медленней.
удивительно, я тоже замерял время, получилось на 1-2 порядка быстрее. Надеюсь, ты Range не для каждой ячейки используешь, а для диапазона ячеек?
![](/images/graemlins/tongue.gif)
если не помогает, сохраняй в текстовый файл, потом открывай его из бейсика.
begin = Timer
Set myRange = Worksheets("лист1").Range("A1:AD300")
myRange.FormulaArray = ""
Debug.Print (Timer - begin)
может что не так?
сохранить csv во временный файл и распарсить.+1
help
If you transfer data by using an array instead of cell by cell, you can realize an enormous performance gain with a lot of data. Consider this line from the earlier code, which transfers data to 300 cells in the worksheet.
а как из экселя в массив?
DataArray = oSheet.Range("A2").Resize(100, 3).Value
плз. подскажите, кто знает (данные из ячеек в массив)
Самый быстрый из известных мне способов - DDE, но у него свои косяки есть.а мегаизвратный способ через буффер обмена?
Оставить комментарий
Christina
думаю как быстрее перекинуть данные из ячеек экселя в массив вижал бэйсика (и наоборот).в книжке написано, что лучше обращаться не к каждой ячейке, а использовать метод .FormulaArray для объекта Range. Замерил время, получилось только медленней.
Кто-нить знает, возможно ли это сделать быстрее, чем обращением к каждой ячейке?