#!/usr/bin/env python
# coding:utf-8
# Author:  mozman -- <mozman@gmx.at>
# Purpose: TreeSlice
# Created: 11.04.2011
# Copyright (C) 2010, 2011 by Manfred Moitzi
# License: LGPLv3


class TreeSlice(object):
    __slots__ = ['_tree', '_start', '_stop']

    def __init__(self, tree, start, stop):
        self._tree = tree
        self._start = start
        self._stop = stop

    def __repr__(self):
        tpl = "%s({%s})" % (self._tree.__class__.__name__, '%s')
        return tpl % ", ".join(
            ("%r: %r" % item for item in self._tree.itemslice(
                self._start,
                self._stop)))

    def __contains__(self, key):
        if self._inrange(key):
            return key in self._tree
        else:
            return False

    def _inrange(self, key):
        if self._start is not None and key < self._start:
            return False
        if self._stop is not None and key >= self._stop:
            return False
        return True

    def __getitem__(self, key):
        if isinstance(key, slice):
            return self._subslice(key.start, key.stop)
        if self._inrange(key):
            return self._tree[key]
        else:
            raise KeyError(key)

    def _subslice(self, start, stop):
        def newstart():
            if start is None:
                return self._start
            elif self._start is None:
                return start
            else:
                return max(start, self._start)

        def newstop():
            if stop is None:
                return self._stop
            elif self._stop is None:
                return stop
            else:
                return min(stop, self._stop)

        return TreeSlice(self._tree, newstart(), newstop())

    def keys(self):
        return self._tree.keyslice(self._start, self._stop)
    __iter__ = keys

    def values(self):
        return self._tree.valueslice(self._start, self._stop)

    def items(self):
        return self._tree.itemslice(self._start, self._stop)
