基于PHPExcel库的EXCEL导入导出

PHPExcel类是php一个excel表格处理插件,最近由于工作需要用到了这个插件,完成了一个excel导入导入的功能。现在将主要逻辑整理一下和大家分享,有需要的可以参考一下。

下面的事例只是完成了一个excel的上传下载的基本功能,还有一些设置表格样式、合并单元格等操作没有体现在这里,大家可以参考PHPExcel的手册,事例后面是我摘出来的PHPExcel的常见的一些操作,供大家参考:

将PHPExcel提供的API根据需要封装成一个供上传和下载使用的类,其实就是两个函数,一个用于上传一个用于下载,这里我就直接将代码贴出来了。

<?php
/* PHPExcel库可以从https://phpexcel.codeplex.com/下载,例子中用的版本是1.8.0 */
require_once dirname(__FILE__) . ‘/PHPExcel/PHPExcel.class.php‘;

class parseExcel
{
    function __construct()
    {
	    /* do nothing */
    }

    /**
     * 将excel文件转化为一个二维数组(这里还没有考虑excel中的页签)
     * 将excel的内容全部读取回去
     * 第一行为标题行,不在返回的数据里面
     *
     * @param $file : excel文件名
     * @param $filed: 要读取的列
     *
     * @access  public
     *
     * @return  对象的array,每行数据为一个对象,array的大小为行数(不包含标题)
     *          每一行是一个对象
     */
    public function excel2array($file, $fields = array())
    {
        /* 如果文件名为空或者要读取的列为空,则返回一个空的数组 */
        if ($file == "" || count($fields) == 0)
        {
            return array();
        }

        /* 创建reader */
        $phpReader = new PHPExcel_Reader_Excel2007();
        if(!$phpReader->canRead($file))
        {
            /* 如果PHPExcel_Reader_Excel2007无法读取excel,则销毁刚才创建的对象,使用PHPExcel_Reader_Excel5来读 */
            unset($phpReader);
            $phpReader = new PHPExcel_Reader_Excel5();
        }

        if(!$phpReader->canRead($file))
        {
            /* 文件无法读取,返回空的数组 */
            return array();
        }

        $phpExcel     = $phpReader->load($file);

        /* 目前的实现只读取第一个工作表 */
        $currentSheet = $phpExcel->getSheet(0);

        /* 拿到工作表的行数和列数 */
        $allRows      = $currentSheet->getHighestRow();
        $allColumns   = $currentSheet->getHighestColumn();
        $allColumns++;
        $currentColumn = ‘A‘;

        /* 解析第一个行,记录$fields中要读取的行 */
        while($currentColumn != $allColumns)
        {
            $title = $currentSheet->getCell($currentColumn . ‘1‘)->getValue();
            $field = array_search($title, $fields);
            $columnKey[$currentColumn] = $field ? $field : ‘‘;
            $currentColumn++;
        }

        $dataList = array();

        /* 跳过标题行(第一行)开始读取数据 */
        for($currentRow = 2; $currentRow <= $allRows; $currentRow++)
        {
            $currentColumn = ‘A‘;
            $data          = new stdclass();
            $ignore        = true; /* 对于空行,需要忽略,这里通过记录一个标记处理 */

            while($currentColumn != $allColumns)
            {
                $cellValue = trim($currentSheet->getCell($currentColumn . $currentRow)->getValue());

                if(empty($columnKey[$currentColumn]))
                {
                    $currentColumn++;
                    continue;
                }

                $field = $columnKey[$currentColumn];
                $currentColumn++;
                if (empty($cellValue))
                {
                    $data->$field = ‘‘;
                }
                else
                {
                    $data->$field = $cellValue;
                    $ignore = false;
                }
            }

            if ($ignore == true)
            {
                continue;
            }

            /* 设置没有从excel中读到的数据 */
            foreach(array_keys($fields) as $key)
            {
                if(!isset($data->$key))
                {
                    $data->$key = ‘‘;
                }
            }

            $dataList[] = $data;
        }

        return $dataList;
    }

    public function setExcelFiled($count)
    {
        $letter = ‘A‘;
        for($i = 1; $i <= $count; $i++) $letter++;
        return $letter;
    }

    /**
     * 将一个对象写入到文件
     *
     * @param $data     : 要写入到excel文件的数据
     *                    kind     :页签名称
     *                    fields   : 标题行,输入的文件要包含的字段
     *                    rows     :对象数组,每一个数据,这些数据会通过fields过滤,只保留fields的内容(和excel2array的返回值格式一致)
     *                    fileName : 要保存的文件名
     * @param $fileType : 输入文件类型,包括xls和xlsx两种类型
     * @param $savePath : 文件路径
     *
     * @access  public
     *
     * @return  对象的array,每行数据为一个对象,array的大小为行数(不包含标题)
     *          如果输入为空,则可能是由于参数不对或者excel文件无法读取
     */
    public function export2excel($data, $savePath = ‘‘)
    {
        $this->phpExcel     = new phpExcel();

        $this->rawExcelData = $data;
        $this->fields       = $this->rawExcelData->fields;
        $this->rows         = $this->rawExcelData->rows;
        $this->fieldsKey    = array_keys($this->fields);

        if(!$this->rawExcelData->fileName) $this->rawExcelData->fileName = $this->rawExcelData->kind;

        $this->excelKey = array();
        for($i = 0; $i < count($this->fieldsKey); $i++) $this->excelKey[$this->fieldsKey[$i]] = $this->setExcelFiled($i);

        /* Set file base property */
        $excelProps = $this->phpExcel->getProperties();
        $excelProps->setCreator(‘ricky‘);
        $excelProps->setLastModifiedBy(‘ricky‘);
        $excelProps->setTitle(‘Office XLS Document‘);
        $excelProps->setSubject(‘Office XLS Document‘);
        $excelProps->setDescription(‘Document generated by PHPExcel.‘);
        $excelProps->setKeywords(‘office excel PHPExcel‘);
        $excelProps->setCategory(‘Result file‘);

        /* 处理第一个页签 */
        $this->phpExcel->setActiveSheetIndex(0);
        $sheetTitle = $this->rawExcelData->kind;
        $excelSheet = $this->phpExcel->getActiveSheet();

        /* 设置页签名称 */
        if($sheetTitle) $excelSheet->setTitle($sheetTitle);
        foreach($this->fields as $key => $field) $excelSheet->setCellValueExplicit($this->excelKey[$key] . ‘1‘, $field, PHPExcel_Cell_DataType::TYPE_STRING);

        $i = 1;
        foreach($this->rows as $num => $row)
        {
            $i++;
            foreach($row as $key => $value)
            {
                if(isset($this->excelKey[$key]))
                {
                    $excelSheet->setCellValueExplicit($this->excelKey[$key] . $i, $value, PHPExcel_Cell_DataType::TYPE_STRING);
                }
            }
        }

        /* urlencode the filename for ie. */
        $fileName = $this->rawExcelData->fileName;
        if(strpos($_SERVER[‘HTTP_USER_AGENT‘], ‘MSIE‘) !== false || strpos($_SERVER[‘HTTP_USER_AGENT‘], ‘Trident‘) !== false) $fileName = urlencode($fileName);

        $excelWriter = PHPExcel_IOFactory::createWriter($this->phpExcel, ‘Excel5‘);
        $excelWriter->setPreCalculateFormulas(false);
        if($savePath == ‘‘)
        {
            header(‘Content-Type: application/vnd.ms-excel‘);
            header("Content-Disposition: attachment;filename=\"{$fileName}.xls\"");
            header(‘Cache-Control: max-age=0‘);

            $excelWriter->save(‘php://output‘);
        }
        else
        {
            $excelWriter->save($savePath);
        }
    }
}

测试代码:

测试代码中完成了excel文件的上传和下载:从本客户端择一个excel文件导入,然后完成解析后,再下载到客户端。

HTML代码很简单,没有css、js,只有一个file空间和一个提交按钮。如下所示:

<!doctype html>
<html>
    <body>
        <form action="excel.php" method="post" enctype="multipart/form-data">
            <label for="file">Filename:</label>
            <input type="file" name="file" id="file" />
            <br />
            <input type="submit" name="submit" value="Submit" />
        </form>
    </body>
</html>

对应的后台的代码如下:

<?php 

function output($var)
{
    echo "<xmp class=‘a-left‘>";
    print_r($var);
    echo "</xmp>";
}

include_once ‘parseexcel.class.php‘;

/* 处理上传的文件 */
if ($_FILES["file"]["error"] > 0)
{
  echo "Error: " . $_FILES["file"]["error"] . "<br />";
  exit;
}
move_uploaded_file($_FILES["file"]["tmp_name"], $_FILES["file"]["name"]);

/**
 * excel格式:
 *
 * 姓名         | 性别
 * -----------------
 * ricky | 男
 * xxxxx | xxx
 */

/* 定义要读取的列,数组的值需要和excel的每一行的标题一致或子集 */
$fileds = array(
        ‘name‘ => ‘姓名‘,
        ‘sex‘  => ‘性别‘,
);

$parse = new parseExcel();

/* 从上传的文件中解析出数据 */
$rows = $parse->excel2array($_FILES["file"]["name"], $fileds);

/* 注意: 测试导入的时候,打开这个注释行,测试下载的时候需要关闭该注释行 */
//output($rows);exit;

/* 将数据原封不动在写入一个新的文件,供用户下载 */
$data = new stdClass();

/* excel的文件名 */
$data->fileName = ‘ceshi‘;
/* 页签的名字 */
$data->kind     = ‘ceshi‘;
/* excel的标题 */
$data->fields   = $fileds;
/* 要写入的数据 */
$data->rows     = $rows;

$parse->export2excel($data);

上述事例只是完成了一个excel的上传下载的基本功能,还有一些设置表格样式、合并单元格等没有体现在这里,大家可以参考PHPExcel的手册,下面是我摘出来的PHPExcel的常见的一些操作,供大家参考:

创建excel
$objPHPExcel = new PHPExcel();

创建一个worksheet
$objPHPExcel->createSheet();
$objWriter = PHPExcel_IOFactory::createWriter($objExcel, ‘Excel5‘);
$objWriter-save(‘php://output‘);

保存excel(2007)
$objWriter = new PHPExcel_Writer_Excel2007($objPHPExcel);
非2007格式:$objWriter = new PHPExcel_Writer_Excel5($objPHPExcel);
$objWriter->save("xxx.xlsx");

直接输出到浏览器供下载
header(‘Content-Type: application/vnd.ms-excel‘);
header("Content-Disposition: attachment;filename=\"{$fileName}.xls\"");
header(‘Cache-Control: max-age=0‘);
$excelWriter->save(‘php://output‘);

设置excel的属性:
创建人
$objPHPExcel->getProperties()->setCreator("Maarten Balliauw");
最后修改人
$objPHPExcel->getProperties()->setLastModifiedBy("Maarten Balliauw");
标题
$objPHPExcel->getProperties()->setTitle("Office 2007 XLSX Test Document");
题目
$objPHPExcel->getProperties()->setSubject("Office 2007 XLSX Test Document");
描述
$objPHPExcel->getProperties()->setDescription("Test document for Office 2007 XLSX, generated using PHP classes.");
关键字
$objPHPExcel->getProperties()->setKeywords("office 2007 openxml php");
种类
$objPHPExcel->getProperties()->setCategory("Test result file");

设置当前的sheet
$objPHPExcel->setActiveSheetIndex(0);

设置sheet的name
$objPHPExcel->getActiveSheet()->setTitle(‘Simple‘);

设置单元格的值
$objPHPExcel->getActiveSheet()->setCellValue(‘A1‘, ‘String‘);
$objPHPExcel->getActiveSheet()->setCellValue(‘A1‘, 12);
$objPHPExcel->getActiveSheet()->setCellValue(‘A1‘, true);
$objPHPExcel->getActiveSheet()->setCellValue(‘A1‘, ‘=SUM(C2:C4)‘);
$objPHPExcel->getActiveSheet()->setCellValue(‘A1‘, ‘=MIN(B2:C5)‘);

合并单元格
$objPHPExcel->getActiveSheet()->mergeCells(‘A18:E22‘);

分离单元格
$objPHPExcel->getActiveSheet()->unmergeCells(‘A28:B28‘);

设置宽度
$objPHPExcel->getActiveSheet()->getColumnDimension(‘B‘)->setAutoSize(true);
$objPHPExcel->getActiveSheet()->getColumnDimension(‘D‘)->setWidth(12);

设置字体
$objPHPExcel->getActiveSheet()->getStyle(‘B1‘)->getFont()->setName(‘Candara‘);
$objPHPExcel->getActiveSheet()->getStyle(‘B1‘)->getFont()->setSize(20);
$objPHPExcel->getActiveSheet()->getStyle(‘B1‘)->getFont()->setBold(true);
$objPHPExcel->getActiveSheet()->getStyle(‘B1‘)->getFont()->setUnderline(PHPExcel_Style_Font::UNDERLINE_SINGLE);
$objPHPExcel->getActiveSheet()->getStyle(‘B1‘)->getFont()->getColor()->setARGB(PHPExcel_Style_Color::COLOR_WHITE);
$objPHPExcel->getActiveSheet()->getStyle(‘B1‘)->getFont()->setBold(true);

设置对齐方式
$objPHPExcel->getActiveSheet()->getStyle(‘C1‘)->getAlignment()->setHorizontal(PHPExcel_Style_Alignment::HORIZONTAL_RIGHT);
$objPHPExcel->getActiveSheet()->getStyle(‘C1‘)->getAlignment()->setHorizontal(PHPExcel_Style_Alignment::HORIZONTAL_JUSTIFY);
$objPHPExcel->getActiveSheet()->getStyle(‘C1‘)->getAlignment()->setVertical(PHPExcel_Style_Alignment::VERTICAL_CENTER);

设置单元格border
$objPHPExcel->getActiveSheet()->getStyle(‘D1‘)->getBorders()->getTop()->setBorderStyle(PHPExcel_Style_Border::BORDER_THIN);

设置border的color
$objPHPExcel->getActiveSheet()->getStyle(‘E1‘)->getBorders()->getLeft()->getColor()->setARGB(‘FF993300‘);;
$objPHPExcel->getActiveSheet()->getStyle(‘E1‘)->getBorders()->getRight()->getColor()->setARGB(‘FF993300‘);
$objPHPExcel->getActiveSheet()->getStyle(‘E1‘)->getBorders()->getTop()->getColor()->setARGB(‘FF993300‘);
$objPHPExcel->getActiveSheet()->getStyle(‘E1‘)->getBorders()->getBottom()->getColor()->setARGB(‘FF993300‘);

设置填充颜色
$objPHPExcel->getActiveSheet()->getStyle(‘F1‘)->getFill()->setFillType(PHPExcel_Style_Fill::FILL_SOLID);
$objPHPExcel->getActiveSheet()->getStyle(‘F1‘)->getFill()->getStartColor()->setARGB(‘FF808080‘);

加载图片
$objDrawing = new PHPExcel_Worksheet_Drawing();
$objDrawing->setName(‘Logo‘);
$objDrawing->setDescription(‘Logo‘);
$objDrawing->setPath(‘./images/officelogo.jpg‘);
$objDrawing->setHeight(36);
$objDrawing->setWorksheet($objPHPExcel->getActiveSheet());
$objDrawing = new PHPExcel_Worksheet_Drawing();
时间: 2024-12-13 07:52:15

基于PHPExcel库的EXCEL导入导出的相关文章

一个基于POI的通用excel导入导出工具类的简单实现及使用方法

前言: 最近PM来了一个需求,简单来说就是在录入数据时一条一条插入到系统显得非常麻烦,让我实现一个直接通过excel导入的方法一次性录入所有数据.网上关于excel导入导出的例子很多,但大多相互借鉴.经过思考,认为一百个客户在录入excel的时候,就会有一百个格式版本,所以在实现这个功能之前,所以要统一excel的格式.于是提供了一个通用excel模版的下载功能.当所有客户用模版录入好数据再上传到系统,后端对excel进行解析,然后再持久化到数据库. 概述: 此工具类的几大特点 1.基本导入导出

Mego(04) - NET简单实现EXCEL导入导出

前言 相信做过信息系统的朋友都会遇到EXCEL导入导出的相关开发,做过不少EXCEL导入导出后总结起来大致有如下几种方式实现: ADO.NET的OldDb或ODBC连接EXCEL使用DataTable来读取数据. Microsoft.Office.Interop.Excel用微软提供的组件操作WorkSheet对象. 使用一些第三方的库比如Fast Excel.ExcelDataReader等等. 今天要向大家介绍的更简单的方式来实现日常开发的各种EXCEL导入导出需求. 简单导入 我们还是使用

Java - Excel 导入 导出,报无效数据

用Java,做了套后台账号管理系统,内有Excel导入导出模块 后台管理员登录后,可以通过<input type="file">,读取指定格式的Excel工作薄 系统会解析读取到的Excel,获取工作薄中,各工作表的数据 当然,如果 上传文件,不是Excel文件,则会显示上传失败 或是 是Excel文件,但其内工作表的数据不符合要求,则会将不符合要求的数据行,自动过滤掉 问题来了: 记得以前测试的时候,是没问题的,但今天,把导出文件,再次导入时,就一直报无效数据 (别提当时

TP5.0 excel 导入导出

引第三方的phpexcel类库放到 ThinkPHP\Library\Vendor\demo下,自己建的文件夹demo 再将Excel.class放到ThinkPHP\Library\Org\class下,自己建的文件夹class 控制器: <?php namespace Admin\Controller; use Think\Controller; class ExcelController extends Controller { public function excelList(){ $

Excel导入导出的业务进化场景及组件化的设计方案(转)

1:前言 看过我文章的网友们都知道,通常前言都是我用来打酱油扯点闲情的. 自从写了上面一篇文章之后,领导就找我谈话了,怕我有什么想不开. 所以上一篇的(下)篇,目前先不出来了,哪天我异地二次回忆的时候,再分享分享. 话说最近外面IT行情飞涨还咋的,人都飞哪去了呢,听说各地的军情都进入紧急状态了. 回归下正题,今天就抽点时间,写写技术文,和大伙分享一下近年在框架设计上的取的一些技术成果. 2:项目背景 在针对运营商(移动.联通.电信.铁塔)的信息类的系统中,由于相关的从业人员习惯于Excel的办公

利用反射实现通用的excel导入导出

如果一个项目中存在多种信息的导入导出,为了简化代码,就需要用反射实现通用的excel导入导出 实例代码如下: 1.创建一个 Book类,并编写set和get方法 1 package com.bean; 2 3 public class Book { 4 private int id; 5 private String name; 6 private String type; 7 // public int a; 8 9 public String getType() { 10 System.ou

excel导入导出优化

对于上一篇excel中出现的问题,在excel导入导出中都做了优化.还是eclipse+jdk1.8,但是这个项目是一个web项目,需要配合Tomcat服务器,并且使用了SSH框架, I/O操作过多 首先,对于I/O操作过多,那么就不像之前一样,一条一条的添加或者更新;而且凑齐一堆,也就是一个list集合,然后统一的批量保存. 使用SessionFactory获取当前的session,然后调用session的persist方法,保存实体.只是设置了一个批量的量值.每到30条数据,就将缓存同步到数

POI实现excel导入导出

1.分析excel import org.apache.poi.hssf.usermodel.*; import org.apache.poi.ss.usermodel.Cell; import org.apache.poi.ss.usermodel.Row; import org.apache.poi.ss.usermodel.Sheet; import org.apache.poi.ss.usermodel.Workbook; import org.apache.poi.ss.util.Ce

[Utils]POI实现excel导入导出

1.分析excel 2.poi工具类 import org.apache.poi.hssf.usermodel.*; import org.apache.poi.ss.usermodel.Cell; import org.apache.poi.ss.usermodel.Row; import org.apache.poi.ss.usermodel.Sheet; import org.apache.poi.ss.usermodel.Workbook; import org.apache.poi.s