Что нового

Экспорт таблицы в Excel

AlexVong

Новичок
Сообщения
112
Репутация
1
Как наиболее эфективно с веб страницы выгрузить таблицу в эксель? Таблица 10-20 тыс. строк выгружается порядка 20-30 минут.
Использую код
Код:
$oTable = _IETableGetCollection($oFrame, 2)
$aTable = _IETableWriteToArray($oTable, True)
$oExcel = _ExcelBookNew()
_ExcelWriteSheetFromArrayEx($oExcel, $aTable, 1, 1, 0, 0)

Может есть более эффективный способ?
 

WSWR

AutoIT Гуру
Сообщения
941
Репутация
363
AlexVong

Код:
InetRead()

+
Код:
StringRegExp()

+
обработка полученного массива?
 
Автор
A

AlexVong

Новичок
Сообщения
112
Репутация
1
WSWR
:rolleyes: С массивами пока еще не сильно дружу. Если возможно можно примерчик на моем файлике? Спасибо!
 

sngr

AutoIT Гуру
Сообщения
1,010
Репутация
408
Код:
$file=FileRead(@ScriptDir&'\table0.htm')
$str=StringRegExpReplace($file,'(?s)^.+?(<TD title=.+?)</TBODY></TABLE></DIV>.+','\1')
$str=StringRegExpReplace($str,'<TR style=[^>]+>\R+','')
$str=StringReplace($str,'</TR>', @LF )
$str=StringReplace($str,'&gt;', '>' )
$str=StringReplace($str,';', ',' )
$str=StringRegExpReplace($str,'<TD title=.+?=[^>]+>([^<]*)</TD>\R','\1;')
$str=StringRegExpReplace($str,'<TD onclick=[^>]+>([^<]*)</TD>\R','\1;')
$str=StringRegExpReplace($str,'<TD style.+?right>([^<]*)</TD>\R','\1;')
$str=StringRegExpReplace($str,'<TD style=[^<]+</TD>','')
$str=StringRegExpReplace($str,'<TD align=[^>]+>([^<]*)</TD>\R','\1;')
$str=StringRegExpReplace($str,'<TD noWrap[^>]+>([^<]*)</TD>\R','\1;')
FileWrite(@DesktopDir&'\123.csv',$str)
 

WSWR

AutoIT Гуру
Сообщения
941
Репутация
363
AlexVong

Как-то так:

Код:
#include <Array.au3>

$sText = FileRead('table0.htm'); BinaryToString(InetRead(''))

$aTemp = StringRegExp($sText, '<TD.*>(.*?)</TD', 3)
_ArrayDelete($aTemp, 0)
_ArrayDelete($aTemp, 0)
_ArrayDelete($aTemp, 0)

$Height = 21
$Width = 17
Dim $uArray[$Height][$Width]; массив - высота в строках на кол-во столбцов

$iK = $Width * $Height - 1
If $iK > UBound($aTemp) - 1 Then $iK = UBound($aTemp) - 1

For $i = 0 To $iK
	$y = Floor($i / ($Width))
	$x = ($i - $y * $Width)
	$uArray[$y][$x] = $aTemp[$i]
Next

_ArrayDisplay($uArray)
 

madmasles

Модератор
Глобальный модератор
Сообщения
7,790
Репутация
2,322
AlexVong,
Попробуйте так. Проверял на Excel 2003.
Код:
#include <Excel.au3>

Global $sUrl = @ScriptDir & '\table0.htm', $sSourse, $aTable, $iUb, $hFile, $iColumn = 17, $iRow, $oObjEr, $iObjEr, $oExcel, _
		$sExcelFile = @ScriptDir & '\table', $sTmpFile = $sExcelFile & '.txt'

$oObjEr = ObjEvent('AutoIt.Error', '_Obj_Error')

$sSourse = FileRead($sUrl)
$sSourse = StringRegExpReplace($sSourse, '(?is).*<div id=otable>(.+?)</tr></tbody>.*', '$1')
If @extended <> 1 Then Exit 13
$sSourse = StringReplace($sSourse, '&gt;', '>')
$aTable = StringRegExp($sSourse, '(?i)<td.+?(?:align|width|onclick)=.+?>(.*?)<', 3)
$sSourse = ''
$iUb = UBound($aTable)
If (Not $iUb) Or Mod($iUb, $iColumn) Then Exit 13
$iRow = $iUb / $iColumn
For $i = 0 To $iUb - 1 Step $iColumn
	For $j = 0 To $iColumn - 1
		$sSourse &= $aTable[$i + $j] & @TAB
	Next
	$sSourse &= @CRLF
Next
$hFile = FileOpen($sTmpFile, 2)
FileWrite($hFile, $sSourse)
FileClose($hFile)

$iUb = 0
$oExcel = _ExcelBookOpen($sTmpFile);, 0)
If @error Then Exit 13
$oExcel.Columns('D').NumberFormat = '0'
$oExcel.Columns('K').NumberFormat = '0'
With $oExcel.Range('A1:' & Chr(64 + $iColumn) & 1)
	.Font.Bold = True
	.HorizontalAlignment = $xlCenter
EndWith
$oExcel.Columns('A:' & Chr(64 + $iColumn)).EntireColumn.AutoFit
$oRange = $oExcel.Range('A1:' & Chr(64 + $iColumn) & $iRow)
For $i = $xlEdgeLeft To $xlInsideHorizontal
	With $oRange.Borders($i)
		.LineStyle = $xlContinuous
	EndWith
Next
_ExcelBookSaveAs($oExcel, $sExcelFile)
$iUb = @error
_ExcelBookClose($oExcel)
If Not $iUb Then FileDelete($sTmpFile)
Exit $iUb

Func _Obj_Error()
	$iObjEr = $oObjEr.number
	ConsoleWrite('Object error: ' & $iObjEr & @LF)
	ConsoleWrite('Scriptline :' & $oObjEr.scriptline & @LF)
EndFunc   ;==>_Obj_Error
 
Автор
A

AlexVong

Новичок
Сообщения
112
Репутация
1
Всем спасибо!
Все примеры работают отлично.


Добавлено:
Сообщение автоматически объединено:

madmasles
А в Вашем коде есть ограничение на объем таблицы? Таблица > 5000 строк не отрабатывает.
 

madmasles

Модератор
Глобальный модератор
Сообщения
7,790
Репутация
2,322
AlexVong [?]
А в Вашем коде есть ограничение на объем таблицы? Таблица > 5000 строк не отрабатывает.
Дайте файл с большой таблицей (чем больше, тем лучше).


Добавлено:
Сообщение автоматически объединено:

При достаточно большом кол-ве строк не срабатывает эта строка:
Код:
$sSourse = StringRegExpReplace($sSourse, '(?is).*<div id=otable>(.+?)</tr></tbody>.*', '$1')


Сделал в файле 65536 строк (прикреплен). Так у меня работает, но долго.
Код:
#include <Excel.au3>

Global $sUrl = @ScriptDir & '\65536_table.htm', $sSourse, $aTable, $iUb, $hFile, $iColumn = 17, $iRow, $oObjEr, $iObjEr, $oExcel, _
		$sTmpFile, $iTmp, $iTimer, $iAllTimer

$sExcelFile = StringLeft($sUrl, StringInStr($sUrl, '.', 0, -1) - 1)
$sTmpFile = $sExcelFile & '.txt'
$oObjEr = ObjEvent('AutoIt.Error', '_Obj_Error')
$iTimer = TimerInit()
$iAllTimer = $iTimer
$sSourse = FileRead($sUrl)
_ConsoleWrite('FileRead', $iTimer)
$iTimer = TimerInit()
$iTmp = StringInStr($sSourse, 'id=otable')
_ConsoleWrite('StringInStr (id=otable)', $iTimer)
If Not $iTmp Then Exit 13
$iTimer = TimerInit()
$sSourse = StringTrimLeft($sSourse, $iTmp)
_ConsoleWrite('StringTrimLeft', $iTimer)
$iTimer = TimerInit()
$iTmp = StringInStr($sSourse, 'id=oControls', 0, -1)
_ConsoleWrite('StringInStr (id=oControls)', $iTimer)
If Not $iTmp Then Exit 13
$iTimer = TimerInit()
$sSourse = StringLeft($sSourse, $iTmp)
_ConsoleWrite('StringLeft', $iTimer)
$iTmp = 0
$iTimer = TimerInit()
;~ $aTable = StringRegExp($sSourse, '(?i)<td.+?(?:align|width|onclick)=.+?>(.*?)<', 3);?
$aTable = StringRegExp($sSourse, '(?i)<td.+?(?<!-)>(.*?)<', 3);?
_ConsoleWrite('StringRegExp', $iTimer)
$sSourse = ''
$iTimer = TimerInit()
$iUb = UBound($aTable)
_ConsoleWrite('UBound', $iTimer)
If (Not $iUb) Or Mod($iUb, $iColumn) Then Exit 13
$iRow = $iUb / $iColumn
$iTimer = TimerInit()
For $i = 0 To $iUb - 1 Step $iColumn
	For $j = 0 To $iColumn - 1
		Switch $j
			Case 14
				$sSourse &= StringReplace($aTable[$i + $j], '&gt;', '>') & @TAB
			Case Else
				$sSourse &= $aTable[$i + $j] & @TAB
		EndSwitch
	Next
	$sSourse &= @CRLF
Next
_ConsoleWrite('(For...Next) * 2', $iTimer)
$iTimer = TimerInit()
$hFile = FileOpen($sTmpFile, 2)
FileWrite($hFile, $sSourse)
_ConsoleWrite('FileWrite', $iTimer)
FileClose($hFile)
ConsoleWrite('----' & @LF)
ConsoleWrite('All Time native: ' & StringFormat('%.2f sec', TimerDiff($iAllTimer) / 1000) & @LF)
ConsoleWrite('----' & @LF)
$iUb = 0
$iTimer = TimerInit()
$oExcel = _ExcelBookOpen($sTmpFile, 0)
If @error Then Exit 13
_ConsoleWrite('_ExcelBookOpen', $iTimer)
$iTimer = TimerInit()
$oExcel.Columns('D').NumberFormat = '0'
$oExcel.Columns('K').NumberFormat = '0'
With $oExcel.Range('A1:' & Chr(64 + $iColumn) & 1)
	.Font.Bold = True
	.HorizontalAlignment = $xlCenter
EndWith
$oExcel.Columns('A:' & Chr(64 + $iColumn)).EntireColumn.AutoFit
$oRange = $oExcel.Range('A1:' & Chr(64 + $iColumn) & $iRow)
For $i = $xlEdgeLeft To $xlInsideHorizontal
	With $oRange.Borders($i)
		.LineStyle = $xlContinuous
	EndWith
Next
_ConsoleWrite('Formating Excel', $iTimer)
$iTimer = TimerInit()
_ExcelBookSaveAs($oExcel, $sExcelFile)
$iUb = @error
_ConsoleWrite('_ExcelBookSaveAs', $iTimer)
_ExcelBookClose($oExcel)
If Not $iUb Then FileDelete($sTmpFile)
ConsoleWrite('----' & @LF)
ConsoleWrite('All Time: ' & StringFormat('%.2f sec', TimerDiff($iAllTimer) / 1000) & @LF)
Exit $iUb

Func _ConsoleWrite($s_Text, $i_Timer)
	ConsoleWrite(StringFormat($s_Text & ': %.2f msec', TimerDiff($iTimer)) & @LF)
EndFunc   ;==>_ConsoleWrite

Func _Obj_Error()
	$iObjEr = $oObjEr.number
	ConsoleWrite('Object error: ' & $iObjEr & @LF)
	ConsoleWrite('Scriptline :' & $oObjEr.scriptline & @LF)
EndFunc   ;==>_Obj_Error
В консоле пишет:
Код:
FileRead: 1500.15 msec
StringInStr (id=otable): 0.28 msec
StringTrimLeft: 71.96 msec
StringInStr (id=oControls): 0.46 msec
StringLeft: 73.36 msec
StringRegExp: 3583.63 msec
UBound: 0.04 msec
(For...Next) * 2: 4636.98 msec
FileWrite: 28.19 msec
----
All Time native: 9.91 sec
----
_ExcelBookOpen: 2888.30 msec
Formating Excel: 2340.10 msec
_ExcelBookSaveAs: 542.17 msec
----
All Time: 16.06 sec
Opera у меня этот файл полчаса открывала. :smile:
 
Автор
A

AlexVong

Новичок
Сообщения
112
Репутация
1
madmasles
Спасибо!
По скорости мой код работал в десятки раз медленее, а на таких объемах ваш код отрабатывает мгновенно :beer:
 
Верх