<?php

/*
 * This file is part of the Predis package.
 *
 * (c) Daniele Alessandri <suppakilla@gmail.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Predis\Iterator\Scan;

use Predis\ClientInterface;

/**
 * Abstracts the iteration of members stored in a sorted set
 * by leveraging the ZSCAN command (Redis >= 2.8) wrapped in
 * a fully-rewindable PHP iterator.
 *
 * @author Daniele Alessandri <suppakilla@gmail.com>
 * @link http://redis.io/commands/scan
 */
class SortedSetIterator extends AbstractScanIterator
{
    protected $key;

    /**
     * {@inheritdoc}
     */
    public function __construct(ClientInterface $client, $key, $match = null, $count = null)
    {
        $this->requiredCommand($client, 'ZSCAN');

        parent::__construct($client, $match, $count);

        $this->key = $key;
    }

    /**
     * {@inheritdoc}
     */
    protected function executeScanCommand()
    {
        return $this->client->zscan($this->key, $this->cursor, $this->getScanOptions());
    }

    /**
     * {@inheritdoc}
     */
    protected function extractNext()
    {
        $element = array_shift($this->elements);

        $this->position = $element[0];
        $this->current = $element[1];
    }
}

Implement PHP iterator based on the ZSCAN command (Redis 2.8).
Implement PHP iterator based on the ZSCAN command (Redis 2.8).

This iterator allows to perform full iterations over the members of a sorted
set by wrapping the incremental nature of ZSCAN just like we did for SCAN:

  $client = new Predis\Client('tcp://127.0.0.1', ['profile' => '2.8']);
  $iterator = new Predis\Iterator\Scan\SortedSetIterator($client, "zset_key");

  foreach ($iterator as $member => $rank) {
      echo "$rank => $member" . PHP_EOL;
  }

Being ZSCAN closely related to SCAN, it is subject to the same behaviour,
see http://redis.io/commands/scan for reference.

This iterator implementation returns the member as key and the rank as value
since the rank is a float value which would be truncated when transforming
the iteration to an array (e.g. using iterator_to_array()). Luckily PHP
preserves the insertion order for named arrays members still result sorted.
