@@ -42,10 +42,10 @@ class IncompatibilityWarning(Warning): pass
42
42
where criteria is being ignored as this version [%s] is too old (or not-defined),
43
43
read the file in and write it out to a new file to upgrade (with the copy_to method)
44
44
"""
45
- class FrequencyWarning (Warning ): pass
46
- frequency_doc = """
47
- the frequency of the existing index is [%s] which conflicts with the new freq [%s],
48
- resetting the frequency to None
45
+ class AttributeConflictWarning (Warning ): pass
46
+ attribute_conflict_doc = """
47
+ the [%s] attribute of the existing index is [%s] which conflicts with the new [%s],
48
+ resetting the attribute to None
49
49
"""
50
50
class PerformanceWarning (Warning ): pass
51
51
performance_doc = """
@@ -873,9 +873,9 @@ def _write_to_group(self, key, value, index=True, table=False, append=False, com
873
873
if not s .is_table or (s .is_table and table is None and s .is_exists ):
874
874
raise ValueError ('Can only append to Tables' )
875
875
if not s .is_exists :
876
- s .set_info ()
876
+ s .set_object_info ()
877
877
else :
878
- s .set_info ()
878
+ s .set_object_info ()
879
879
880
880
if not s .is_table and complib :
881
881
raise ValueError ('Compression not supported on non-table' )
@@ -949,7 +949,7 @@ class IndexCol(object):
949
949
is_an_indexable = True
950
950
is_data_indexable = True
951
951
is_searchable = False
952
- _info_fields = ['freq' ,'tz' ,'name ' ]
952
+ _info_fields = ['freq' ,'tz' ,'index_name ' ]
953
953
954
954
def __init__ (self , values = None , kind = None , typ = None , cname = None , itemsize = None ,
955
955
name = None , axis = None , kind_attr = None , pos = None , freq = None , tz = None ,
@@ -965,7 +965,7 @@ def __init__(self, values=None, kind=None, typ=None, cname=None, itemsize=None,
965
965
self .pos = pos
966
966
self .freq = freq
967
967
self .tz = tz
968
- self .index_name = None
968
+ self .index_name = index_name
969
969
self .table = None
970
970
971
971
if name is not None :
@@ -1042,7 +1042,7 @@ def convert(self, values, nan_rep):
1042
1042
kwargs ['freq' ] = self .freq
1043
1043
if self .tz is not None :
1044
1044
kwargs ['tz' ] = self .tz
1045
- if self .name is not None :
1045
+ if self .index_name is not None :
1046
1046
kwargs ['name' ] = self .index_name
1047
1047
try :
1048
1048
self .values = Index (_maybe_convert (values , self .kind ), ** kwargs )
@@ -1128,7 +1128,7 @@ def validate_attr(self, append):
1128
1128
1129
1129
def update_info (self , info ):
1130
1130
""" set/update the info for this indexable with the key/value
1131
- if validate is True, then raise if an existing value does not match the value """
1131
+ if there is a conflict raise/warn as needed """
1132
1132
1133
1133
for key in self ._info_fields :
1134
1134
@@ -1140,15 +1140,16 @@ def update_info(self, info):
1140
1140
idx = info [self .name ] = dict ()
1141
1141
1142
1142
existing_value = idx .get (key )
1143
- if key in idx and existing_value != value :
1143
+ if key in idx and value is not None and existing_value != value :
1144
1144
1145
- # frequency just warn
1146
- if key == 'freq' :
1147
- ws = frequency_doc % (existing_value ,value )
1148
- warnings .warn (ws , FrequencyWarning )
1145
+ # frequency/name just warn
1146
+ if key in [ 'freq' , 'index_name' ] :
1147
+ ws = attribute_conflict_doc % (key , existing_value ,value )
1148
+ warnings .warn (ws , AttributeConflictWarning )
1149
1149
1150
1150
# reset
1151
1151
idx [key ] = None
1152
+ setattr (self ,key ,None )
1152
1153
1153
1154
else :
1154
1155
raise ValueError ("invalid info for [%s] for [%s]" ""
@@ -1554,7 +1555,7 @@ def __repr__(self):
1554
1555
def __str__ (self ):
1555
1556
return self .__repr__ ()
1556
1557
1557
- def set_info (self ):
1558
+ def set_object_info (self ):
1558
1559
""" set my pandas type & version """
1559
1560
self .attrs .pandas_type = self .pandas_kind
1560
1561
self .attrs .pandas_version = _version
@@ -2275,16 +2276,20 @@ def values_cols(self):
2275
2276
""" return a list of my values cols """
2276
2277
return [i .cname for i in self .values_axes ]
2277
2278
2279
+ def set_info (self ):
2280
+ """ update our table index info """
2281
+ self .attrs .info = self .info
2282
+
2278
2283
def set_attrs (self ):
2279
2284
""" set our table type & indexables """
2280
2285
self .attrs .table_type = self .table_type
2281
2286
self .attrs .index_cols = self .index_cols ()
2282
2287
self .attrs .values_cols = self .values_cols ()
2283
2288
self .attrs .non_index_axes = self .non_index_axes
2284
2289
self .attrs .data_columns = self .data_columns
2285
- self .attrs .info = self .info
2286
2290
self .attrs .nan_rep = self .nan_rep
2287
2291
self .attrs .levels = self .levels
2292
+ self .set_info ()
2288
2293
2289
2294
def get_attrs (self ):
2290
2295
""" retrieve our attributes """
@@ -2487,7 +2492,7 @@ def create_axes(self, axes, obj, validate=True, nan_rep=None, data_columns=None,
2487
2492
axes = [ a .axis for a in existing_table .index_axes ]
2488
2493
data_columns = existing_table .data_columns
2489
2494
nan_rep = existing_table .nan_rep
2490
- self .info = existing_table .info
2495
+ self .info = copy . copy ( existing_table .info )
2491
2496
else :
2492
2497
existing_table = None
2493
2498
@@ -2879,6 +2884,9 @@ def write(self, obj, axes=None, append=False, complib=None,
2879
2884
else :
2880
2885
table = self .table
2881
2886
2887
+ # update my info
2888
+ self .set_info ()
2889
+
2882
2890
# validate the axes and set the kinds
2883
2891
for a in self .axes :
2884
2892
a .validate_and_set (table , append )
@@ -3036,10 +3044,10 @@ def read(self, where=None, columns=None, **kwargs):
3036
3044
if self .is_transposed :
3037
3045
values = a .cvalues
3038
3046
index_ = cols
3039
- cols_ = Index (index )
3047
+ cols_ = Index (index , name = getattr ( index , 'name' , None ) )
3040
3048
else :
3041
3049
values = a .cvalues .T
3042
- index_ = Index (index )
3050
+ index_ = Index (index , name = getattr ( index , 'name' , None ) )
3043
3051
cols_ = cols
3044
3052
3045
3053
# if we have a DataIndexableCol, its shape will only be 1 dim
@@ -3157,12 +3165,17 @@ class AppendableNDimTable(AppendablePanelTable):
3157
3165
obj_type = Panel4D
3158
3166
3159
3167
def _convert_index (index ):
3168
+ index_name = getattr (index ,'name' ,None )
3169
+
3160
3170
if isinstance (index , DatetimeIndex ):
3161
3171
converted = index .asi8
3162
- return IndexCol (converted , 'datetime64' , _tables ().Int64Col (), freq = getattr (index ,'freq' ,None ), tz = getattr (index ,'tz' ,None ))
3172
+ return IndexCol (converted , 'datetime64' , _tables ().Int64Col (),
3173
+ freq = getattr (index ,'freq' ,None ), tz = getattr (index ,'tz' ,None ),
3174
+ index_name = index_name )
3163
3175
elif isinstance (index , (Int64Index , PeriodIndex )):
3164
3176
atom = _tables ().Int64Col ()
3165
- return IndexCol (index .values , 'integer' , atom , freq = getattr (index ,'freq' ,None ))
3177
+ return IndexCol (index .values , 'integer' , atom , freq = getattr (index ,'freq' ,None ),
3178
+ index_name = index_name )
3166
3179
3167
3180
if isinstance (index , MultiIndex ):
3168
3181
raise Exception ('MultiIndex not supported here!' )
@@ -3173,36 +3186,45 @@ def _convert_index(index):
3173
3186
3174
3187
if inferred_type == 'datetime64' :
3175
3188
converted = values .view ('i8' )
3176
- return IndexCol (converted , 'datetime64' , _tables ().Int64Col ())
3189
+ return IndexCol (converted , 'datetime64' , _tables ().Int64Col (),
3190
+ freq = getattr (index ,'freq' ,None ), tz = getattr (index ,'tz' ,None ),
3191
+ index_name = index_name )
3177
3192
elif inferred_type == 'datetime' :
3178
3193
converted = np .array ([(time .mktime (v .timetuple ()) +
3179
3194
v .microsecond / 1E6 ) for v in values ],
3180
3195
dtype = np .float64 )
3181
- return IndexCol (converted , 'datetime' , _tables ().Time64Col ())
3196
+ return IndexCol (converted , 'datetime' , _tables ().Time64Col (),
3197
+ index_name = index_name )
3182
3198
elif inferred_type == 'date' :
3183
3199
converted = np .array ([time .mktime (v .timetuple ()) for v in values ],
3184
3200
dtype = np .int32 )
3185
- return IndexCol (converted , 'date' , _tables ().Time32Col ())
3201
+ return IndexCol (converted , 'date' , _tables ().Time32Col (),
3202
+ index_name = index_name )
3186
3203
elif inferred_type == 'string' :
3187
3204
# atom = _tables().ObjectAtom()
3188
3205
# return np.asarray(values, dtype='O'), 'object', atom
3189
3206
3190
3207
converted = np .array (list (values ), dtype = np .str_ )
3191
3208
itemsize = converted .dtype .itemsize
3192
- return IndexCol (converted , 'string' , _tables ().StringCol (itemsize ), itemsize = itemsize )
3209
+ return IndexCol (converted , 'string' , _tables ().StringCol (itemsize ), itemsize = itemsize ,
3210
+ index_name = index_name )
3193
3211
elif inferred_type == 'unicode' :
3194
3212
atom = _tables ().ObjectAtom ()
3195
- return IndexCol (np .asarray (values , dtype = 'O' ), 'object' , atom )
3213
+ return IndexCol (np .asarray (values , dtype = 'O' ), 'object' , atom ,
3214
+ index_name = index_name )
3196
3215
elif inferred_type == 'integer' :
3197
3216
# take a guess for now, hope the values fit
3198
3217
atom = _tables ().Int64Col ()
3199
- return IndexCol (np .asarray (values , dtype = np .int64 ), 'integer' , atom )
3218
+ return IndexCol (np .asarray (values , dtype = np .int64 ), 'integer' , atom ,
3219
+ index_name = index_name )
3200
3220
elif inferred_type == 'floating' :
3201
3221
atom = _tables ().Float64Col ()
3202
- return IndexCol (np .asarray (values , dtype = np .float64 ), 'float' , atom )
3222
+ return IndexCol (np .asarray (values , dtype = np .float64 ), 'float' , atom ,
3223
+ index_name = index_name )
3203
3224
else : # pragma: no cover
3204
3225
atom = _tables ().ObjectAtom ()
3205
- return IndexCol (np .asarray (values , dtype = 'O' ), 'object' , atom )
3226
+ return IndexCol (np .asarray (values , dtype = 'O' ), 'object' , atom ,
3227
+ index_name = index_name )
3206
3228
3207
3229
def _unconvert_index (data , kind ):
3208
3230
if kind == 'datetime64' :
0 commit comments