К сожалению, невозможно прочитать имена рабочих листов без загрузки всего файла.
Использование номера индекса вместо имени при вызове setLoadSheetsOnly () не даст предсказуемый результат:логика кода, которая выполняет эту проверку, использует in_array () для проверки, находится ли имя листа, которое он собирается прочитать, в массиве имен листов для чтения.например,
// check if sheet should be skipped
if (isset($this->_loadSheetsOnly) && !in_array($sheet['name'], $this->_loadSheetsOnly)) {
continue;
}
Я подозреваю, что сравнение строки с числовым значением даст истинный результат для 0 == "mySheetName" при выполнении этого теста (на основе свободных правил PHP для типизации и сравнения)).
Возможно, я мог бы предоставить метод Reader, который бы возвращал список имен рабочих листов без фактической загрузки всего файла, хотя это могло бы привести к снижению производительности.
EDIT
Если вы добавите следующий метод в классы / PHPExcel / Reader / Excel2007.php
/**
* Reads names of the worksheets from a file, without loading the whole file to a PHPExcel object
*
* @param string $pFilename
* @throws Exception
*/
public function listWorksheetNames($pFilename)
{
// Check if file exists
if (!file_exists($pFilename)) {
throw new Exception("Could not open " . $pFilename . " for reading! File does not exist.");
}
$worksheetNames = array();
$zip = new ZipArchive;
$zip->open($pFilename);
$rels = simplexml_load_string($this->_getFromZipArchive($zip, "_rels/.rels")); //~ http://schemas.openxmlformats.org/package/2006/relationships");
foreach ($rels->Relationship as $rel) {
switch ($rel["Type"]) {
case "http://schemas.openxmlformats.org/officeDocument/2006/relationships/officeDocument":
$xmlWorkbook = simplexml_load_string($this->_getFromZipArchive($zip, "{$rel['Target']}")); //~ http://schemas.openxmlformats.org/spreadsheetml/2006/main");
if ($xmlWorkbook->sheets) {
foreach ($xmlWorkbook->sheets->sheet as $eleSheet) {
// Check if sheet should be skipped
$worksheetNames[] = (string) $eleSheet["name"];
}
}
}
}
$zip->close();
return $worksheetNames;
}
Вы можете вызвать его с помощью:
$inputFileType = 'Excel2007';
$inputFileName = 'biostat-behfisk-2005.xlsx';
$objReader = PHPExcel_IOFactory::createReader($inputFileType);
$worksheetNames = $objReader->listWorksheetNames($inputFileName);
foreach ($worksheetNames as $sheetName) {
echo $sheetName, '<br />';
}
возвращаемый $ worksheetNames должен содержать массив всех имен рабочих листов в виде строк UTF-8.Поскольку это только чтение абсолютного минимума из .xlsx для извлечения этих имен, оно должно быть достаточно быстрым.Я сделаю еще несколько тестов, прежде чем проверять его в PHPExcel SVN, но (пока) он, кажется, делает то, что вам нужно.
EDIT2
Эквивалентный метод дляЧитатель Excel5
/**
* Reads names of the worksheets from a file, without loading the whole file to a PHPExcel object
*
* @param string $pFilename
* @throws Exception
*/
public function listWorksheetNames($pFilename)
{
// Check if file exists
if (!file_exists($pFilename)) {
throw new Exception("Could not open " . $pFilename . " for reading! File does not exist.");
}
$worksheetNames = array();
// Read the OLE file
$this->_loadOLE($pFilename);
// total byte size of Excel data (workbook global substream + sheet substreams)
$this->_dataSize = strlen($this->_data);
$this->_pos = 0;
$this->_sheets = array();
// Parse Workbook Global Substream
while ($this->_pos < $this->_dataSize) {
$code = self::_GetInt2d($this->_data, $this->_pos);
switch ($code) {
case self::XLS_Type_BOF: $this->_readBof(); break;
case self::XLS_Type_SHEET: $this->_readSheet(); break;
case self::XLS_Type_EOF: $this->_readDefault(); break 2;
default: $this->_readDefault(); break;
}
}
foreach ($this->_sheets as $sheet) {
if ($sheet['sheetType'] != 0x00) {
// 0x00: Worksheet, 0x02: Chart, 0x06: Visual Basic module
continue;
}
$worksheetNames[] = $sheet['name'];
}
return $worksheetNames;
}
Не так эффективен, как версия Читателя Excel2007, но все равно должен быть быстрее, чем синтаксический анализ всего файла .xls только для имен листов, потому что я анализирую только глобальный поток.