Laravel Excel 2.1.0版本表头日期被转换为数字的问题求助
解决Laravel Excel 2.1.0表头日期被转为数字的问题
这个问题其实是Excel日期的底层逻辑导致的:Excel里的日期本质是从1900年1月1日开始计数的序列化数字(你看到的43243就是2018-05-23对应的天数)。Laravel Excel默认会自动识别数据行的日期并转换,但表头行默认是按原始单元格值读取,没有触发日期转换逻辑。
下面给你两种可行的解决方法:
方法一:读取后手动转换表头
先读取数据,再把表头中的数字日期转换为正常日期格式:
$data = Excel::load($request['file'], function($reader) {})->get(); // 获取原始表头 $originalHeaders = $data->first()->keys()->toArray(); // 转换表头中的日期数字 $processedHeaders = array_map(function($header) { // 筛选出可能是Excel日期的数字(这里以1970年为界,对应数字25569) if (is_numeric($header) && $header > 25569) { // 修正Excel的1900闰年bug后转换为日期字符串 return \Carbon\Carbon::parse('1900-01-01')->addDays($header - 2)->toDateString(); } return $header; }, $originalHeaders); // 替换数据集合的表头键名 $finalData = $data->map(function($item) use ($originalHeaders, $processedHeaders) { $newItem = []; foreach ($originalHeaders as $index => $oldKey) { $newItem[$processedHeaders[$index]] = $item[$oldKey]; } return (object)$newItem; });
方法二:读取时直接处理表头
利用Laravel Excel的回调,在读取过程中直接修改表头单元格的值:
$finalData = Excel::load($request['file'], function($reader) { $activeSheet = $reader->getActiveSheet(); // 获取第一行(表头行) $headerRow = $activeSheet->getRowIterator(1)->current(); $cellIterator = $headerRow->getCellIterator(); $cellIterator->setIterateOnlyExistingCells(false); // 确保遍历所有单元格 foreach ($cellIterator as $cell) { $cellValue = $cell->getValue(); // 判断是否为Excel日期数字 if (is_numeric($cellValue) && $cellValue > 25569) { $date = \Carbon\Carbon::parse('1900-01-01')->addDays($cellValue - 2)->toDateString(); $cell->setValue($date); } } })->get();
注意事项
Excel有个历史遗留的1900闰年bug:它错误地将1900年识别为闰年,导致日期数字比实际多了2天(对于1900年3月1日之后的日期)。所以转换时我们要减去2天来修正这个偏差,如果你的表头日期是1900年3月之前的,可以根据情况调整减的天数。
内容的提问来源于stack exchange,提问作者Martin
相关产品推荐
相关产品推荐

