jablonka.czprosek.czf

freenet-router

Subversion Repositories:
[/] [trunk/] [freenet-router/] [var/] [www/] [freenet-router/] [Framework/] [Core/] [Collection.php] - Rev 2

Compare with Previous - Blame - Download


<?php

namespace Phem\Core;

use Countable;
use Iterator;
use JsonSerializable;
use Phem\ToolSuite;

/**
 * @author Jakub PetrŞílka <petrzilka@czweb.net>
 * 
 */
class Collection implements Iterator, Countable, JsonSerializable
{

    protected $items = array();

    public function __construct($items = null)
    {
        if (is_array($items))
        {
            $this->items = $items;
        }
    }

    public function current()
    {
        return current($this->items);
    }

    public function key()
    {
        return key($this->items);
    }

    public function next()
    {
        return next($this->items);
    }

    public function rewind()
    {
        reset($this->items);
    }

    public function valid()
    {
        $key = key($this->items);
        return ($key !== null && $key !== false);
    }

    public function getFirst()
    {
        $this->rewind();
        return $this->current();
    }
    
    public function getFirstKey()
    {
        $this->rewind();
        return $this->key();
    }
    
    public function getLastKey()
    {
        end($this->items);
        return $this->key();
    }
                                    

    public function contains($value)
    {
        return ($this->getKey($value) != null);
    }

    public function containsKey($key)
    {
        return array_key_exists($key, $this->items);
    }

    public function containsAnyKeyOf(array $keys)
    {
        foreach ($keys as $key)
        {
            if (array_key_exists($key, $this->items))
                return true;
        }
        return false;
    }

    public function put($key, $value)
    {
        if (!($this->containsKey($key)))
        {
            $this->items[$key] = $value;
        }
    }

    public function add($value)
    {
        $this->items[] = $value;
    }

    public function set($key, $value)
    {
        $this->items[$key] = $value;
    }

    public function get($key)
    {
        if (array_key_exists($key, $this->items))
            return $this->items[$key];
        else
            return null;
    }

    public function getKey($value)
    {
        foreach ($this->items as $key => $currentValue)
        {
            if ($currentValue == $value)
                return $key;
        }
        return null;
    }

    public function count()
    {
        return count($this->items);
    }
    
    public function uniqueValues()
    {
        return array_unique($this->items);
    }

    public function getKeys()
    {
        return array_keys($this->items);
    }

    public function toArray()
    {
        return $this->items;
    }

    public function isEmpty()
    {
        return (count($this->items) == 0);
    }

    public function removeKey($key)
    {
        if (array_key_exists($key, $this->items))
        {
            $this->items[$key] = null;
            unset($this->items[$key]);
        }
    }
    
    public function getSubCollection($path)
    {
        return ToolSuite::getSubCollection($this->items, $path);
    }
    
    public function join(Collection $collection)
    {
        $this->items = array_merge($this->items,$collection->toArray());
    }
    
    public function findNearestGreaterThanOrEqual($needleKey)
    {
        $min = null;
        $result = null;
        
        foreach ($this->items as $key => $value)
        {
            if ($key >= $needleKey)
            {
                if (($min === null)||($key <= $min))
                {
                    $min = $key;
                    $result = $value;
                }                
            }
            
        }
        
        return $result;
    }

    /**
     * Sorts the collection according to strategy given in $sortBy argument.
     * Available strategies can be found in CollectionSortType.
     * 
     * Sort on nested object attributes can be done using $sortOnAttribute,
     * Provide an optional path string to identifiy the field to sort on.
     * Eg. 'prop1/attr2' will be translated to $collectionEntry->getProp1()->getAttr2();
     * 
     * @param int $sortBy CollectionSortType strategy
     * @param string $sortOnAttribute Path to field to sort on
     */
    public function sort($sortType, $sortOnAttribute = null)
    {
        if (($sortType & CollectionSortType::VALUE) == 0)
        {


            if ($sortOnAttribute != null)
            {

                $cmpFunction = function($a, $b) use ($sortOnAttribute, $sortType)
                        {
                            $comparedA = $a;
                            $comparedB = $a;
                            if ($sortOnAttribute != null)
                            {
                                $comparedA = ToolSuite::getObjectValueFromPath($a, $sortOnAttribute);
                                $comparedB = ToolSuite::getObjectValueFromPath($b, $sortOnAttribute);
                            }

                            if ($sortType & CollectionSortType::CASE_STRING)
                            {
                                if (($sortType & CollectionSortType::DESC) == 0)
                                {
                                    strcasecmp($comparedA, $comparedB);
                                }
                                else
                                {
                                    -strcasecmp($comparedA, $comparedB);
                                }
                            }                            
                            else if (($sortType & CollectionSortType::STRING) == 0)
                            {
                                if (($sortType & CollectionSortType::DESC) == 0)
                                {
                                    
                                    return (int) $comparedA - (int) $comparedB;
                                }
                                else
                                {
                                    return -($comparedA - $comparedB);
                                }
                            }
                            else if ($sortType & CollectionSortType::STRING)
                            {
                                if (($sortType & CollectionSortType::DESC) == 0)
                                {
                                    return strcmp($comparedA, $comparedB);
                                }
                                else
                                {
                                    return -strcmp($comparedA, $comparedB);
                                }
                            }
                        };
                uasort($this->items, $cmpFunction);
            }
            else
            {
                if ($sortType & CollectionSortType::NUMERIC)
                {
                    if ($sortType & CollectionSortType::ASC)
                    {
                        asort($this->items, SORT_NUMERIC);
                    }
                    else
                    {
                        arsort($this->items, SORT_NUMERIC);
                    }
                }
                else if ($sortType & CollectionSortType::STRING)
                {
                    if ($sortType & CollectionSortType::ASC)
                    {
                        asort($this->items, SORT_STRING);
                    }
                    else
                    {
                        arsort($this->items, SORT_STRING);
                    }
                }
                else if ($sortType & CollectionSortType::CASE_STRING)
                {
                    if ($sortType & CollectionSortType::ASC)
                    {
                        asort($this->items, SORT_STRING | SORT_FLAG_CASE);
                    }
                    else
                    {
                        arsort($this->items, SORT_STRING | SORT_FLAG_CASE);
                    }
                }
            }
        }
        else
        {
            if ($sortType & CollectionSortType::NUMERIC)
            {
                if ($sortType & CollectionSortType::ASC)
                {
                    ksort($this->items, SORT_NUMERIC);
                }
                else
                {
                    krsort($this->items, SORT_NUMERIC);
                }
            }
            else if ($sortType & CollectionSortType::STRING)
            {
                if ($sortType & CollectionSortType::ASC)
                {
                    ksort($this->items, SORT_STRING);
                }
                else
                {
                    krsort($this->items, SORT_STRING);
                }
            }
            else if ($sortType & CollectionSortType::CASE_STRING)
            {
                if ($sortType & CollectionSortType::ASC)
                {
                    ksort($this->items, SORT_STRING | SORT_FLAG_CASE);
                }
                else
                {
                    krsort($this->items, SORT_STRING | SORT_FLAG_CASE);
                }
            }
        }
    }
    
    public function reverse($preserveKeys = false)
    {
        $this->items = array_reverse($this->items, $preserveKeys);
    }

    public function jsonSerialize()
    {
        return json_encode($this->toArray());
    }

}

Powered by WebSVN 2.2.1