Skip to content

Commit

Permalink
ENH: Add HashableIndexes to core/index.py
Browse files Browse the repository at this point in the history
  • Loading branch information
jtratner committed Jun 15, 2013
1 parent 3349ea7 commit 880a8ea
Show file tree
Hide file tree
Showing 2 changed files with 73 additions and 1 deletion.
25 changes: 25 additions & 0 deletions pandas/core/common.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@

import itertools
from datetime import datetime
import types

from numpy.lib.format import read_array, write_array
import numpy as np
Expand Down Expand Up @@ -42,6 +43,30 @@ class AmbiguousIndexError(PandasError, KeyError):
pass


def bind_method(cls, name, func):
"""Bind a method to class, python 2 and python 3 compatible.
Parameters
----------
cls : type
class to receive bound method
name : basestring
name of method on class instance
func : function
function to be bound as method
Returns
-------
None
"""
# only python 2 has bound/unbound method issue
if not py3compat.PY3:
setattr(cls, name, types.MethodType(func, None, cls))
else:
setattr(cls, name, func)

_POSSIBLY_CAST_DTYPES = set([ np.dtype(t) for t in ['M8[ns]','m8[ns]','O','int8','uint8','int16','uint16','int32','uint32','int64','uint64'] ])
_NS_DTYPE = np.dtype('M8[ns]')
_TD_DTYPE = np.dtype('m8[ns]')
Expand Down
49 changes: 48 additions & 1 deletion pandas/core/index.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
from pandas.lib import Timestamp

from pandas.util.decorators import cache_readonly
from pandas.core.common import isnull
from pandas.core.common import isnull, bind_method
import pandas.core.common as com
from pandas.util import py3compat
from pandas.core.config import get_option
Expand Down Expand Up @@ -2688,6 +2688,53 @@ def _wrap_joined_index(self, joined, other):
return MultiIndex.from_tuples(joined, names=names)


def hashable_class_factory(klass, hash_func=None):
"""Creates Hashable Class for given Index type
and adds `ashashable` method to the Index"""

class HashableIndexMixin(object):
"""
Implements hashing methods...note that this is
very crude, and *only* works if it's mixed into a parent
class that is a subclass of (or just is) an index
"""

def __init__(self, index):
self._index = index

def __eq__(self, other):
if issubclass(other, klass):
return (self.values == other.values).all()
else:
return False

if hash_func:
__hash__ = hash_func
else:
def __hash__(self):
return hash(str(self))

# should this be a property??
def asindex(self):
return self._index

HashableClass = type("Hashable{klass}".format(klass=klass.__name__), (HashableIndexMixin, klass))

def ashashable(self):
"""convert {klass} to a hashable type that
can be used for key/value lookup
"""
return HashableClass(self)

ashashable.__doc__ = ashashable.__doc__.format(klass=klass.__name__)
bind_method(klass, "ashashable", ashashable)

return HashableClass

HashableIndex = hashable_class_factory(Index)
HashableInt64Index = hashable_class_factory(Int64Index)
HashableMultiIndex = hashable_class_factory(MultiIndex)

# For utility purposes

def _sparsify(label_list, start=0,sentinal=''):
Expand Down

0 comments on commit 880a8ea

Please sign in to comment.