Bug #71858 [Wfx]: A lot of performance loss for huge bit operation
| From: | jacky at xsteach dot com | Date: | Mon, 21 Mar 2016 11:09:56 +0000 |
| Subject: | Bug #71858 [Wfx]: A lot of performance loss for huge bit operation | ||
| References: | 1 | Groups: | php.bugs |
| Request: | Send a blank email to php-bugs+get-199991@lists.php.net to get a copy of this message | ||
Edit report at https://bugs.php.net/bug.php?id=71858&edit=1
ID: 71858
User updated by: jacky at xsteach dot com
Reported by: jacky at xsteach dot com
Summary: A lot of performance loss for huge bit operation
Status: Wont fix
Type: Bug
Package: Performance problem
Operating System: Mac OS X
PHP Version: 7.0.4
Block user comment: N
Private report: N
New Comment:
<?php
class ImageFilter
{ #R G B
private $colorA = 7944996; #79 3B 24
private $colorB = 16696767; #FE C5 BF
private $arA = array();
private $arB = array();
function __construct()
{
$this->arA['R'] = ($this->colorA >> 16) & 0xFF;
$this->arA['G'] = ($this->colorA >> 8) & 0xFF;
$this->arA['B'] = $this->colorA & 0xFF;
$this->arB['R'] = ($this->colorB >> 16) & 0xFF;
$this->arB['G'] = ($this->colorB >> 8) & 0xFF;
$this->arB['B'] = $this->colorB & 0xFF;
}
function getScore($image)
{
$x = 0; $y = 0;
$img = $this->_getImageResource($image, $x, $y);
if(!$img) return false;
$score = 0;
$xPoints = array($x/8, $x/4, ($x/8 + $x/4), $x-($x/8 + $x/4), $x-($x/4), $x-($x/8));
$yPoints = array($y/8, $y/4, ($y/8 + $y/4), $y-($y/8 + $y/4), $y-($y/8), $y-($y/8));
$zPoints = array($xPoints[2], $yPoints[1], $xPoints[3], $y);
for($i=1; $i<$x; $i++)
{
for($j=1; $j<$y; $j++)
{
$color = imagecolorat($img, $i, $j);
if($color >= $this->colorA && $color <= $this->colorB)
{
$color = array('R'=> ($color >> 16) & 0xFF,
'G'=> ($color >> 8) & 0xFF, 'B'=> $color & 0xFF);
if($color['G'] >= $this->arA['G'] &&
$color['G'] <= $this->arB['G'] && $color['B'] >=
$this->arA['B'] && $color['B'] <= $this->arB['B'])
{
if($i >= $zPoints[0] && $j >= $zPoints[1] && $i <=
$zPoints[2] && $j <= $zPoints[3])
{
$score += 3;
}
elseif($i <= $xPoints[0] || $i >=$xPoints[5] || $j <= $yPoints[0]
|| $j >= $yPoints[5])
{
$score += 0.10;
}
elseif($i <= $xPoints[0] || $i >=$xPoints[4] || $j <= $yPoints[0]
|| $j >= $yPoints[4])
{
$score += 0.40;
}
else
{
$score += 1.50;
}
}
}
}
}
imagedestroy($img);
$score = sprintf('%01.2f', ($score * 100) / ($x * $y));
if($score > 100) $score = 100;
return $score;
}
public function getScoreAndFill($image, $outputImage)
{
$x = 0; $y = 0;
$img = $this->_getImageResource($image, $x, $y);
if(!$img) return false;
$score = 0;
$xPoints = array($x/8, $x/4, ($x/8 + $x/4), $x-($x/8 + $x/4), $x-($x/4), $x-($x/8));
$yPoints = array($y/8, $y/4, ($y/8 + $y/4), $y-($y/8 + $y/4), $y-($y/8), $y-($y/8));
$zPoints = array($xPoints[2], $yPoints[1], $xPoints[3], $y);
for($i=1; $i<=$x; $i++)
{
for($j=1; $j<=$y; $j++)
{
$color = imagecolorat($img, $i, $j);
if($color >= $this->colorA && $color <= $this->colorB)
{
$color = array('R'=> ($color >> 16) & 0xFF,
'G'=> ($color >> 8) & 0xFF, 'B'=> $color & 0xFF);
if($color['G'] >= $this->arA['G'] &&
$color['G'] <= $this->arB['G'] && $color['B'] >=
$this->arA['B'] && $color['B'] <= $this->arB['B'])
{
if($i >= $zPoints[0] && $j >= $zPoints[1] && $i <=
$zPoints[2] && $j <= $zPoints[3])
{
$score += 3;
imagefill($img, $i, $j, 16711680);
}
elseif($i <= $xPoints[0] || $i >=$xPoints[5] || $j <= $yPoints[0]
|| $j >= $yPoints[5])
{
$score += 0.10;
imagefill($img, $i, $j, 14540253);
}
elseif($i <= $xPoints[0] || $i >=$xPoints[4] || $j <= $yPoints[0]
|| $j >= $yPoints[4])
{
$score += 0.40;
imagefill($img, $i, $j, 16514887);
}
else
{
$score += 1.50;
imagefill($img, $i, $j, 512);
}
}
}
}
}
imagejpeg($img, $outputImage);
imagedestroy($img);
$score = sprintf('%01.2f', ($score * 100) / ($x * $y));
if($score > 100) $score = 100;
return $score;
}
protected function _getImageResource($image, &$x, &$y)
{
$info = getimagesize($image);
$x = $info[0];
$y = $info[1];
switch( $info[2] )
{
case IMAGETYPE_GIF:
return @imagecreatefromgif($image);
case IMAGETYPE_JPEG:
return @imagecreatefromjpeg($image);
case IMAGETYPE_PNG:
return @imagecreatefrompng($image);
default:
return false;
}
}
}
function microtime_float()
{
list($usec, $sec) = explode(" ", microtime());
return ((float)$usec + (float)$sec);
}
$time_start = microtime_float();
$filter = new ImageFilter();
echo $filter->getScore('test.jpg').PHP_EOL;
$time_end = microtime_float();
$time = $time_end - $time_start;
echo "Done in $time seconds\n";
Previous Comments:
------------------------------------------------------------------------
[2016-03-19 14:19:57] nikic@php.net
Closing as Won't Fix due to licensing concerns. Please relicense the code, or provide a reduced
reproduce case not covered by this license.
------------------------------------------------------------------------
[2016-03-19 11:35:58] jacky at xsteach dot com
Description:
------------
I run an image filter script, which contain many bit operation, to test an image. Whatever the
image size, a lot of performance loss with php 5.6 or 7.0 than 5.5. With a small image, run it with
php5.5 is about 10x fast than php 5.6/7.0. Which part goes wrongï¼
Test script:
---------------
<?php
//
// +-----------------------------------+
// | Image Filter v 1.0 |
// | http://www.SysTurn.com |
// +-----------------------------------+
//
//
// This program is free software; you can redistribute it and/or modify
// it under the terms of the ISLAMIC RULES and GNU Lesser General Public
// License either version 2, or (at your option) any later version.
//
// ISLAMIC RULES should be followed and respected if they differ
// than terms of the GNU LESSER GENERAL PUBLIC LICENSE
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the license with this software;
// If not, please contact support @ S y s T u r n .com to receive a copy.
//
class ImageFilter
{ #R G B
private $colorA = 7944996; #79 3B 24
private $colorB = 16696767; #FE C5 BF
private $arA = array();
private $arB = array();
function __construct()
{
$this->arA['R'] = ($this->colorA >> 16) & 0xFF;
$this->arA['G'] = ($this->colorA >> 8) & 0xFF;
$this->arA['B'] = $this->colorA & 0xFF;
$this->arB['R'] = ($this->colorB >> 16) & 0xFF;
$this->arB['G'] = ($this->colorB >> 8) & 0xFF;
$this->arB['B'] = $this->colorB & 0xFF;
}
function getScore($image)
{
$x = 0; $y = 0;
$img = $this->_getImageResource($image, $x, $y);
if(!$img) return false;
$score = 0;
$xPoints = array($x/8, $x/4, ($x/8 + $x/4), $x-($x/8 + $x/4), $x-($x/4), $x-($x/8));
$yPoints = array($y/8, $y/4, ($y/8 + $y/4), $y-($y/8 + $y/4), $y-($y/8), $y-($y/8));
$zPoints = array($xPoints[2], $yPoints[1], $xPoints[3], $y);
for($i=1; $i<$x; $i++)
{
for($j=1; $j<$y; $j++)
{
$color = imagecolorat($img, $i, $j);
if($color >= $this->colorA && $color <= $this->colorB)
{
$color = array('R'=> ($color >> 16) & 0xFF,
'G'=> ($color >> 8) & 0xFF, 'B'=> $color & 0xFF);
if($color['G'] >= $this->arA['G'] &&
$color['G'] <= $this->arB['G'] && $color['B'] >=
$this->arA['B'] && $color['B'] <= $this->arB['B'])
{
if($i >= $zPoints[0] && $j >= $zPoints[1] && $i <=
$zPoints[2] && $j <= $zPoints[3])
{
$score += 3;
}
elseif($i <= $xPoints[0] || $i >=$xPoints[5] || $j <= $yPoints[0]
|| $j >= $yPoints[5])
{
$score += 0.10;
}
elseif($i <= $xPoints[0] || $i >=$xPoints[4] || $j <= $yPoints[0]
|| $j >= $yPoints[4])
{
$score += 0.40;
}
else
{
$score += 1.50;
}
}
}
}
}
imagedestroy($img);
$score = sprintf('%01.2f', ($score * 100) / ($x * $y));
if($score > 100) $score = 100;
return $score;
}
public function getScoreAndFill($image, $outputImage)
{
$x = 0; $y = 0;
$img = $this->_getImageResource($image, $x, $y);
if(!$img) return false;
$score = 0;
$xPoints = array($x/8, $x/4, ($x/8 + $x/4), $x-($x/8 + $x/4), $x-($x/4), $x-($x/8));
$yPoints = array($y/8, $y/4, ($y/8 + $y/4), $y-($y/8 + $y/4), $y-($y/8), $y-($y/8));
$zPoints = array($xPoints[2], $yPoints[1], $xPoints[3], $y);
for($i=1; $i<=$x; $i++)
{
for($j=1; $j<=$y; $j++)
{
$color = imagecolorat($img, $i, $j);
if($color >= $this->colorA && $color <= $this->colorB)
{
$color = array('R'=> ($color >> 16) & 0xFF,
'G'=> ($color >> 8) & 0xFF, 'B'=> $color & 0xFF);
if($color['G'] >= $this->arA['G'] &&
$color['G'] <= $this->arB['G'] && $color['B'] >=
$this->arA['B'] && $color['B'] <= $this->arB['B'])
{
if($i >= $zPoints[0] && $j >= $zPoints[1] && $i <=
$zPoints[2] && $j <= $zPoints[3])
{
$score += 3;
imagefill($img, $i, $j, 16711680);
}
elseif($i <= $xPoints[0] || $i >=$xPoints[5] || $j <= $yPoints[0]
|| $j >= $yPoints[5])
{
$score += 0.10;
imagefill($img, $i, $j, 14540253);
}
elseif($i <= $xPoints[0] || $i >=$xPoints[4] || $j <= $yPoints[0]
|| $j >= $yPoints[4])
{
$score += 0.40;
imagefill($img, $i, $j, 16514887);
}
else
{
$score += 1.50;
imagefill($img, $i, $j, 512);
}
}
}
}
}
imagejpeg($img, $outputImage);
imagedestroy($img);
$score = sprintf('%01.2f', ($score * 100) / ($x * $y));
if($score > 100) $score = 100;
return $score;
}
protected function _getImageResource($image, &$x, &$y)
{
$info = getimagesize($image);
$x = $info[0];
$y = $info[1];
switch( $info[2] )
{
case IMAGETYPE_GIF:
return @imagecreatefromgif($image);
case IMAGETYPE_JPEG:
return @imagecreatefromjpeg($image);
case IMAGETYPE_PNG:
return @imagecreatefrompng($image);
default:
return false;
}
}
}
function microtime_float()
{
list($usec, $sec) = explode(" ", microtime());
return ((float)$usec + (float)$sec);
}
$time_start = microtime_float();
$filter = new ImageFilter();
echo $filter->getScore('test.jpg').PHP_EOL;
$time_end = microtime_float();
$time = $time_end - $time_start;
echo "Done in $time seconds\n";
Expected result:
----------------
fast execution.
Actual result:
--------------
slower than php 5.5
------------------------------------------------------------------------
--
Edit this bug report at https://bugs.php.net/bug.php?id=71858&edit=1