如何使用 php 从 xls 中准确读取 09/09/2017?
how to read 09/09/2017 exactly from xls using php?
var_dump($objPHPExcel->getActiveSheet()->getCell('B2')->getValue());
我尝试了上面的代码,我得到了 "float(42987)"
作为输出。
我只想要那个单元格的确切值!
var_dump($objPHPExcel->getActiveSheet()->getCell('C2')->getValue());
当我执行这个时,我得到了正确的值"2017/09/12"
那么我如何从 xls 中获取这种 "09/09/2017"
格式的数据?
编辑 1:
the data cannot be predicted ! it can be a string or date with different formats !
example : B2 can be 'string','09/09/2017','09-09-2017','2017/09/09','10/20-25/14'
就像这个例子,任何数据都可以存在!所以我只想要用户提供的单元格中的准确数据!
编辑 2:我正在使用 rangeToArray
for ($row = 2; $row <= $highestRow; $row++){
$rowData = $sheet->rangeToArray('A'.$row.':' . $highestColumn.$row,NULL,TRUE,FALSE);
}
那么我将如何在 rangeToArray
中实施 ->getFormattedValue()
?
我认为有几种方法可以做到这一点,例如 ExcelToPHP()
和 toFormattedString()
。
使用后者,您可以将 Excel 值 $value
转换为您要查找的字符串,例如:
$string = \PHPExcel_Style_NumberFormat::toFormattedString($value, 'DD/MM/YYYY');
MS Excel 对日期使用序列化时间戳(有点像 unix 时间戳),也就是 PHPExcel [=34= 的 float(42987)
] 当您调用 getValue()
时...请注意,此 是 单元格的确切值...。该浮点数是通过数字格式掩码转换为 date/time 在 MS Excel 中显示。您在 MS Excel 中看到的是单元格的 格式 值,应用了数字格式掩码,因此您需要告诉 PHPExcel获取格式化值而不是确切的(原始)值。
只要您没有加载文件,readDataOnly 设置为 true(它告诉 PHPExcel not 加载样式和格式数据),然后使用
var_dump($objPHPExcel->getActiveSheet()->getCell('B2')->getFormattedValue());
这是一个 OADate(OLE 自动化日期)。您得到的 float(42987)
是下面的确切值。 Excel 只是以您选择的任何格式将其显示为日期。
使用此 class 进行转换。
class OLEAutomationDateConverter
{
/**
* Get the OLE Automation Date epoch
*
* @return DateTimeImmutable
*/
public static function BaseDate()
{
static $baseDate = null;
if ($baseDate == null) {
$baseDate = new DateTimeImmutable('1899-12-30 00:00:00');
}
return $baseDate;
}
/**
* Convert a DateTime object to a float representing an OLE Automation Date
*
* @param DateTimeInterface $dateTime
* @return float
*/
public static function DateTimeToOADate(DateTimeInterface $dateTime)
{
$interval = self::BaseDate()->diff($dateTime);
$mSecs = ($interval->h * 3600000)
+ ($interval->i * 60000)
+ ($interval->s * 1000)
+ floor($dateTime->format('u') / 1000);
return $interval->days + ($mSecs / 86400000);
}
/**
* Convert a float representing an OLE Automation Date to a DateTime object
*
* The returned value has a microsecond component, but resolution is millisecond and even
* this should not be relied upon as it is subject to floating point precision errors
*
* @param float $oaDate
* @return DateTime
*/
public static function OADateToDateTime($oaDate)
{
$days = floor($oaDate);
$msecsFloat = ($oaDate - $days) * 86400000;
$msecs = floor($msecsFloat);
$hours = floor($msecs / 3600000);
$msecs %= 3600000;
$mins = floor($msecs / 60000);
$msecs %= 60000;
$secs = floor($msecs / 1000);
$msecs %= 1000;
$dateTime = self::BaseDate()
->add(new DateInterval(sprintf('P%sDT%sH%sM%sS', $days, $hours, $mins, $secs)))
->format('Y-m-d H:i:s');
return new DateTime("$dateTime.$msecs");
}
}
或者,如果可以使用 javascript,请使用 moment 库。有一个将 OADates TO 和 FROM 转换的函数。
https://github.com/markitondemand/moment-msdate#about-ole-automation-dates
将 OA 日期转换为时刻(或 JavaScript 日期):
moment.fromOADate(41493)
returns Wed Aug 07 2013 00:00:00 GMT-0600 (MDT)
确切的日期和时间(时间是小数点右边的值):
moment.fromOADate(41493.706892280097000)
returns Wed Aug 07 2013 16:57:55 GMT-0600 (MDT)
默认情况下 moment.fromOADate()
使用服务器时间作为与 UTC 的偏移量,可以提供第二个参数来指示 OA 日期与 UTC 的偏移量(以分钟为单位)。
moment.fromOADate(42754.835023148145, 360)
returns Fri Jan 20 2017 02:02:25 GMT+0000 (UTC)
时刻格式:
//convert OA date into Moment (JavaScript date)
var momentDate = moment.fromOADate(41493.706892280097000);
//use Moment's awesomeness
var formattedDate = momentDate.format('MMM Do YY);
//formattedDate === "Aug 7th 13"
这可以很容易地链接在一起:
moment.fromOADate(41493.706892280097000).format('MMM Do YY); //Aug 7th 13
注意:OLE 自动化日期未指定,这意味着它们默认基于本地时区。
如果您使用 rangeToArray()
方法获取数据,请查看 rangeToArray()
的参数
/**
* Create array from a range of cells
*
* @param string $pRange Range of cells (i.e. "A1:B10"), or just one cell (i.e. "A1")
* @param mixed $nullValue Value returned in the array entry if a cell doesn't exist
* @param boolean $calculateFormulas Should formulas be calculated?
* @param boolean $formatData Should formatting be applied to cell values?
* @param boolean $returnCellRef False - Return a simple array of rows and columns indexed by number counting from zero
* True - Return rows and columns indexed by their actual row and column IDs
* @return array
*/
因此,要获取 rangeToArray()
返回的格式化值,您需要将 $formatData
参数设置为 true
来调用它
$rowData = $sheet->rangeToArray('A'.$row.':' . $highestColumn.$row,NULL,TRUE,TRUE);
var_dump($objPHPExcel->getActiveSheet()->getCell('B2')->getValue());
我尝试了上面的代码,我得到了 "float(42987)"
作为输出。
我只想要那个单元格的确切值!
var_dump($objPHPExcel->getActiveSheet()->getCell('C2')->getValue());
当我执行这个时,我得到了正确的值"2017/09/12"
那么我如何从 xls 中获取这种 "09/09/2017"
格式的数据?
编辑 1:
the data cannot be predicted ! it can be a string or date with different formats !
example : B2 can be 'string','09/09/2017','09-09-2017','2017/09/09','10/20-25/14'
就像这个例子,任何数据都可以存在!所以我只想要用户提供的单元格中的准确数据!
编辑 2:我正在使用 rangeToArray
for ($row = 2; $row <= $highestRow; $row++){
$rowData = $sheet->rangeToArray('A'.$row.':' . $highestColumn.$row,NULL,TRUE,FALSE);
}
那么我将如何在 rangeToArray
中实施 ->getFormattedValue()
?
我认为有几种方法可以做到这一点,例如 ExcelToPHP()
和 toFormattedString()
。
使用后者,您可以将 Excel 值 $value
转换为您要查找的字符串,例如:
$string = \PHPExcel_Style_NumberFormat::toFormattedString($value, 'DD/MM/YYYY');
MS Excel 对日期使用序列化时间戳(有点像 unix 时间戳),也就是 PHPExcel [=34= 的 float(42987)
] 当您调用 getValue()
时...请注意,此 是 单元格的确切值...。该浮点数是通过数字格式掩码转换为 date/time 在 MS Excel 中显示。您在 MS Excel 中看到的是单元格的 格式 值,应用了数字格式掩码,因此您需要告诉 PHPExcel获取格式化值而不是确切的(原始)值。
只要您没有加载文件,readDataOnly 设置为 true(它告诉 PHPExcel not 加载样式和格式数据),然后使用
var_dump($objPHPExcel->getActiveSheet()->getCell('B2')->getFormattedValue());
这是一个 OADate(OLE 自动化日期)。您得到的 float(42987)
是下面的确切值。 Excel 只是以您选择的任何格式将其显示为日期。
使用此 class 进行转换。
class OLEAutomationDateConverter
{
/**
* Get the OLE Automation Date epoch
*
* @return DateTimeImmutable
*/
public static function BaseDate()
{
static $baseDate = null;
if ($baseDate == null) {
$baseDate = new DateTimeImmutable('1899-12-30 00:00:00');
}
return $baseDate;
}
/**
* Convert a DateTime object to a float representing an OLE Automation Date
*
* @param DateTimeInterface $dateTime
* @return float
*/
public static function DateTimeToOADate(DateTimeInterface $dateTime)
{
$interval = self::BaseDate()->diff($dateTime);
$mSecs = ($interval->h * 3600000)
+ ($interval->i * 60000)
+ ($interval->s * 1000)
+ floor($dateTime->format('u') / 1000);
return $interval->days + ($mSecs / 86400000);
}
/**
* Convert a float representing an OLE Automation Date to a DateTime object
*
* The returned value has a microsecond component, but resolution is millisecond and even
* this should not be relied upon as it is subject to floating point precision errors
*
* @param float $oaDate
* @return DateTime
*/
public static function OADateToDateTime($oaDate)
{
$days = floor($oaDate);
$msecsFloat = ($oaDate - $days) * 86400000;
$msecs = floor($msecsFloat);
$hours = floor($msecs / 3600000);
$msecs %= 3600000;
$mins = floor($msecs / 60000);
$msecs %= 60000;
$secs = floor($msecs / 1000);
$msecs %= 1000;
$dateTime = self::BaseDate()
->add(new DateInterval(sprintf('P%sDT%sH%sM%sS', $days, $hours, $mins, $secs)))
->format('Y-m-d H:i:s');
return new DateTime("$dateTime.$msecs");
}
}
或者,如果可以使用 javascript,请使用 moment 库。有一个将 OADates TO 和 FROM 转换的函数。
https://github.com/markitondemand/moment-msdate#about-ole-automation-dates
将 OA 日期转换为时刻(或 JavaScript 日期):
moment.fromOADate(41493)
returns Wed Aug 07 2013 00:00:00 GMT-0600 (MDT)
确切的日期和时间(时间是小数点右边的值):
moment.fromOADate(41493.706892280097000)
returns Wed Aug 07 2013 16:57:55 GMT-0600 (MDT)
默认情况下 moment.fromOADate()
使用服务器时间作为与 UTC 的偏移量,可以提供第二个参数来指示 OA 日期与 UTC 的偏移量(以分钟为单位)。
moment.fromOADate(42754.835023148145, 360)
returns Fri Jan 20 2017 02:02:25 GMT+0000 (UTC)
时刻格式:
//convert OA date into Moment (JavaScript date)
var momentDate = moment.fromOADate(41493.706892280097000);
//use Moment's awesomeness
var formattedDate = momentDate.format('MMM Do YY);
//formattedDate === "Aug 7th 13"
这可以很容易地链接在一起:
moment.fromOADate(41493.706892280097000).format('MMM Do YY); //Aug 7th 13
注意:OLE 自动化日期未指定,这意味着它们默认基于本地时区。
如果您使用 rangeToArray()
方法获取数据,请查看 rangeToArray()
/**
* Create array from a range of cells
*
* @param string $pRange Range of cells (i.e. "A1:B10"), or just one cell (i.e. "A1")
* @param mixed $nullValue Value returned in the array entry if a cell doesn't exist
* @param boolean $calculateFormulas Should formulas be calculated?
* @param boolean $formatData Should formatting be applied to cell values?
* @param boolean $returnCellRef False - Return a simple array of rows and columns indexed by number counting from zero
* True - Return rows and columns indexed by their actual row and column IDs
* @return array
*/
因此,要获取 rangeToArray()
返回的格式化值,您需要将 $formatData
参数设置为 true
$rowData = $sheet->rangeToArray('A'.$row.':' . $highestColumn.$row,NULL,TRUE,TRUE);