2016-07-11 6 views
0

Ich muss das erste Arbeitsblatt ein paar Mal entsprechend der Menge der Zeilen klonen, aber etwas kann falsch sein.PHPExcel Clone Arbeitsblatt - Effiziente Verwendung von Speicher

Der Code ist:

public function downloadFile() 
{ 
    date_default_timezone_set('America/Sao_Paulo'); 

    if(file_exists("xpto.xlsx")){ 

     $objPHPExcel = PHPExcel_IOFactory::load("xpto.xlsx"); 

     $sheets = 3;//3 is enough to throw the error 
     for($i = 0; $i<$sheets; $i++){ 

      $objClonedWorksheet = clone $objPHPExcel->getSheet(0); 
      $objClonedWorksheet->setTitle('Sheet ' . $i); 
      $objClonedWorksheet->setCellValue('A1', 'Test ' . $i); 
      $objPHPExcel->addSheet($objClonedWorksheet); 
     } 

     $objPHPExcel->setActiveSheetIndex(0); 

     $filename = 'file.xlsx'; 
     header('Content-Type: application/vnd.openxmlformats-officedocument.spreadsheetml.sheet'); 
     header('Content-Disposition: attachment;filename="'.$filename.'"'); 
     header('Cache-Control: max-age=0'); 

     $objWriter = PHPExcel_IOFactory::createWriter($objPHPExcel, 'Excel2007'); 
     ob_end_clean(); 
     $ret = $objWriter->save('php://output'); 

     exit; 
    } 
} 

Aber ich habe einen erschöpften Speicherfehler. Als ich die am meisten kommentierten Lösung versucht (das ist eigentlich eine Abhilfe) das ist

ini_set('memory_limit', '-1'); 

ich diese Zeile nach der Ladefunktion nur hinzugefügt, um hinzuzufügen und es hat funktioniert, aber ich glaube nicht, es ist eine gute Lösung zu Verwendung in einer SaaS-Anwendung. Ich denke nicht einmal, dass die meisten Hosts (zum Beispiel AWS) mir erlauben werden, das zu nutzen.

Ich habe auch versucht, das Blatt vor der for-Schleife zu klonen, aber bei Verwendung von addSheet erkannte ich, dass diese Funktion kein neues Objekt erstellt und wenn ich den Namen des Blattes ändern (durch die zweite Iteration der for Schleife), ändert es das zuletzt erstellte Blatt und wirft ein "bereits bestehendes Blatt mit dem gleichen Namen" -Fehler.

Der Versuch, einen der Links zu verwenden @rhazen aufgelistet, änderte ich die for-Schleife:

Aber es scheint nicht zu funktionieren. Gibt es ein Missverständnis über Iterator oder XfIndex?

Nun ... Ich habe nicht die Antworten für die oben genannten Probleme gefunden, aber ich entschied mich, Mark Baker Vorschlag zu versuchen und trotz der Zeit, die es dauert, um das Ergebnis zu verarbeiten, das war die Lösung, die funktionierte. Ich hoffe, dass mein Server-Host es mir erlaubt, es zu benutzen.

Die Lösung sieht wie folgt aus:

public function downloadFile() 
{ 
    date_default_timezone_set('America/Sao_Paulo'); 

    if(file_exists("xpto.xlsx")){ 

     $cacheMethod = PHPExcel_CachedObjectStorageFactory:: cache_to_phpTemp; 
     $cacheSettings = array(
       'memoryCacheSize' => '8MB' 
     ); 
     PHPExcel_Settings::setCacheStorageMethod($cacheMethod, $cacheSettings); 

     $objPHPExcel = PHPExcel_IOFactory::load("xpto.xlsx"); 

     $sheets = $this->calculateNumberOfSheets(); 
     for($i = 0; $i<$sheets; $i++){ 

      $objClonedWorksheet = clone $objPHPExcel->getSheet(0); 
      $objClonedWorksheet->setTitle('Sheet ' . $i); 
      $objClonedWorksheet->setCellValue('A1', 'Test ' . $i); 
      $objPHPExcel->addSheet($objClonedWorksheet); 
     } 

     $objPHPExcel->setActiveSheetIndex(0); 

     $filename = 'file.xlsx'; 
     header('Content-Type: application/vnd.openxmlformats-officedocument.spreadsheetml.sheet'); 
     header('Content-Disposition: attachment;filename="'.$filename.'"'); 
     header('Cache-Control: max-age=0'); 

     $objWriter = PHPExcel_IOFactory::createWriter($objPHPExcel, 'Excel2007'); 
     ob_end_clean(); 
     $ret = $objWriter->save('php://output'); 

     exit; 
    } 
} 
+0

Vorausgesetzt, dass das Arbeitsblatt mit seiner Sammlung von Zellen viel Arbeitsspeicher benötigt, ist es nicht verwunderlich, dass das Klonen des Arbeitsblatts die Speicherauslastung Ihres Skripts erhöht. Erwägen Sie die Verwendung von [Zellen-Caching] (https://github.com/PHPOffice/PHPExcel/blob/develop/Documentation/markdown/Overview/04-Configuration-Settings.md), um den Speicherbedarf zu reduzieren. –

+0

Dies könnte nützlich sein: http: //stackoverflow.com/questions/34774486/cloning-the-content-and-styling-of-one-sheet-to-another-php-excel und dieses: http://stackoverflow.com/questions/4817651/phpexcel -aus-256-512-und-auch-1024mb-of-ram – rhazen

Antwort

0

Die Lösung in der editierten Frage. Danke für die Hilfe.