Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to create Price Range dynamically with PHP

Tags:

php

range

How can I create Price Ranges from price array? Let's say I have this array which holds prices:

  Array ( [0] => 500 [1] => 500 [2] => 520 [3] => 540 [4] => 551 [5] => 599 [6] => 601 [7] => 601 [8] => 650 [9] => 681 [10] => 750 [11] => 750 [12] => 851 [13] => 871 [14] => 871 [15] => 900 [16] => 990 [17] => 999 [18] => 1101 [19] => 1130 [20] => 1149 [21] => 1151 [22] => 1278 [23] => 1300 [24] => 1460 ) 

Minimum value is = 500 and maximum value is 1460. I need to show users like this :

[x] 500-750 (11)
[x] 750-1000 (8)
[x] 1000+ (7)

the tricky part is if values are reached 1500 or there are more than 1500 above needs look like this :

[x] 500-750 (11)
[x] 750-1000 (8)
[x] 1000-1500 (n)
[x] 1500+ (if more than 1500 but not reached 2000).

we can say 1500 is the limit but if there are prices between 1500$ and 2000$ and more than 2000$ like 2300$ , 2400$ , 2499$, 2000$+ must be the limit. which will look like this:

[x] 500-750 (11)
[x] 750-1000 (8)
[x] 1000-1500 (n)
[x] 1500-2000 (n)
[x] 2000$+ (n)

This will create 5 range. As you can see lowest price is 500, but min. prices may 20$ or 120$ so function must not break 5 range rule. first range can be 20$-750$ (n).

And of course max prices may not 1000$+ so may need to show something like this :

[x] 25-50 (11)
[x] 50-100(8)
[x] 100-200(n)
[x] 200-400(n)
[x] 400+ (n)

I hope I make this proper. There are many conditions and I don't know the usages of pow or range like functions in php. Hope you can help :/

like image 598
T. Cem Yılmaz Avatar asked Feb 25 '14 11:02

T. Cem Yılmaz


3 Answers

I Created this function based on my $array element of my question.

If this is a good aproach of my question please make some comments for like pointing my mistakes.

http://laravel.io/bin/VLJn this is the output.

private function createRange($array){
    sort($array);

    //Setting range limits.
    //Check if array has 5 digit number.
    $countDigitedNumbers = preg_grep('/\d{5}/',$array);
    if(count($countDigitedNumbers) > 3){
        $rangeLimits = array(0,1000,2500,5000,10000,15000,20000,25000);
    }else{
        $rangeLimits = array(0,50,250,500,1000,1500,2000,2500);
    }
    $ranges = array();

    for($i = 0; $i < count($rangeLimits); $i++){
        if($i == count($rangeLimits)-1){
            break;
        }
        $lowLimit = $rangeLimits[$i];
        $highLimit = $rangeLimits[$i+1];

        $ranges[$i]['ranges']['min'] = $lowLimit;
        $ranges[$i]['ranges']['max'] = $highLimit;

        foreach($array as $perPrice){
            if($perPrice >= $lowLimit && $perPrice < $highLimit){
                $ranges[$i]['values'][] = $perPrice;
            }
        }
    }
    return $ranges;
}
like image 76
T. Cem Yılmaz Avatar answered Nov 09 '22 23:11

T. Cem Yılmaz


I made it automated; i didnt use classes but it is easily able to be converted.

<?php
$prices=Array ( 500 , 500 , 520 , 540 , 551 , 599 ,601 ,601 , 650 ,681 ,750 ,750 ,851 , 871 , 871 , 900 , 990 , 999 , 1101 , 1130 , 1149 , 1151 , 1278 , 1300 , 1460 );

// round the highest price 
$lastElement=end($prices);
$highestPrice=round($lastElement, -2);
$minimumPrice=$prices[0];

$maxPRoductInRange=5;

$rangeChart=array();
$chart=array();

function calculateRange(){
global $highestPrice,$maxPRoductInRange ,$rangeChart, $prices,$minimumPrice, $chart;
// range list initialize
makeRangeChart($minimumPrice,$highestPrice,$rangeChart);


$count=count($rangeChart);

for($a=0;$a<$count;$a++){
    if(isset($rangeChart[$a+1])){
        $min=$rangeChart[$a];
        $max=$rangeChart[$a+1];
        $result=checkProductCount($min,$max,$prices);
        // if count bigger than $maxPRoductInRange create bigger rangeChart and call this function recursively
        if($result[0]>$maxPRoductInRange){
            //create bigger range chart
            makeRangeChart($min,$max,$rangeChart);
            calculateRange();
        } 

    }
}
}


function checkProductCount($min,$max,$priceList){
    global $chart;
    $count=0;
    $rest=0;

    foreach( $priceList as $price){
        if($price>=$min && $price<$max) { 
            $count++; 
        } else { $rest++; }

    }
    $chart[$min]=$count;

    return array($count,$rest);
}


function makeRangeChart($min=0,$max,&$rangeChart){
    $middleOfRange=($max+$min)/2;
    $rangeChart[]=$min;
    $rangeChart[]=$middleOfRange;
    $rangeChart[]=$max;
    $rangeChart=array_unique ($rangeChart);
    sort($rangeChart, SORT_NUMERIC );
}

function printChart(){
global $chart,$highestPrice;

$minPrices=array_keys($chart);
$count=count($minPrices);
$line='';
    for($a=0;$a<$count;$a++){
        $line.=$minPrices[$a];
        $line.=(isset($minPrices[$a+1]))?' - '.$minPrices[$a+1]:'+';
        $line.='('.$chart[$minPrices[$a]].')<br>';
    }
return $line;
}

calculateRange();
echo printChart();
?>
like image 30
Emrah Toy Avatar answered Nov 09 '22 22:11

Emrah Toy


Personally, I would go and define an array (in a config or directly) with the needed ranges, since you may be selling metal screws, worth 0.01$, and at the same time a machine making metal screws, worth 1000$ (for example). This way you have control of all possible price ranges. Going with dynamic price factor could work, but could also go wrong if you suddenly receive an item worth 20000$, and I doubt you will have so many ranges that you would not be able to define them manually. (Feel free pull out the forks and torches here)

Here's an example. Let's say you have an array of prices. You define your ranges like this:

$prices = array(1, 5, 10, 25, 500, 100);
$price_ranges = array(250 => array(), 100 => array(), 10 => array(), 1 => array());
// edit to your liking

Then you can cycle over all available prices, compare them to the available ranges, starting from the top and go to the bottom. If it fits, it sits.

foreach ($prices as $price) {
    foreach ($price_ranges as $price_range_key => &$price_range_array) {
        if ($price >= $price_range_key) {
            $price_range_array[] = $price;
            break;
        }
    }
}

This will produce a nice array with each range (as a key) containing your prices.

var_dump($price_ranges);
array(4) {
  [250] =>
  array(1) {
    [0] =>
    int(500)
  }
  [100] =>
  array(1) {
    [0] =>
    int(100)
  }
  [10] =>
  array(2) {
    [0] =>
    int(10)
    [1] =>
    int(25)
  }
  [1] =>
  array(2) {
    [0] =>
    int(1)
    [1] =>
    int(5)
  }
}

I'm sure you can figure how to get the number of items in each one and display them accordingly. Usually you'll mark the last item as 250+ or something similar.

Cheers.

like image 1
NorthBridge Avatar answered Nov 10 '22 00:11

NorthBridge