2
2
import unittest
3
3
import nose
4
4
import itertools
5
+ from StringIO import StringIO
5
6
6
7
from numpy import random , nan
7
8
from numpy .random import randn
@@ -45,7 +46,7 @@ def _get_value(f, i, values=False):
45
46
# check agains values
46
47
if values :
47
48
return f .values [i ]
48
-
49
+
49
50
# this is equiv of f[col][row].....
50
51
#v = f
51
52
#for a in reversed(i):
@@ -70,7 +71,7 @@ def _get_result(obj, method, key, axis):
70
71
xp = getattr (obj , method ).__getitem__ (_axify (obj ,key ,axis ))
71
72
except :
72
73
xp = getattr (obj , method ).__getitem__ (key )
73
-
74
+
74
75
return xp
75
76
76
77
def _axify (obj , key , axis ):
@@ -127,11 +128,11 @@ def setUp(self):
127
128
setattr (self ,o ,d )
128
129
129
130
def check_values (self , f , func , values = False ):
130
-
131
+
131
132
if f is None : return
132
133
axes = f .axes
133
134
indicies = itertools .product (* axes )
134
-
135
+
135
136
for i in indicies :
136
137
result = getattr (f ,func )[i ]
137
138
@@ -194,7 +195,7 @@ def _print(result, error = None):
194
195
if fails is True :
195
196
if result == 'fail' :
196
197
result = 'ok (fail)'
197
-
198
+
198
199
if not result .startswith ('ok' ):
199
200
raise AssertionError (_print (result ))
200
201
@@ -212,7 +213,7 @@ def _print(result, error = None):
212
213
result = 'ok (%s)' % type (detail ).__name__
213
214
_print (result )
214
215
return
215
-
216
+
216
217
result = type (detail ).__name__
217
218
raise AssertionError (_print (result , error = detail ))
218
219
@@ -244,14 +245,14 @@ def _print(result, error = None):
244
245
obj = d [t ]
245
246
if obj is not None :
246
247
obj = obj .copy ()
247
-
248
+
248
249
k2 = key2
249
250
_eq (t , o , a , obj , key1 , k2 )
250
251
251
252
def test_at_and_iat_get (self ):
252
253
253
254
def _check (f , func , values = False ):
254
-
255
+
255
256
if f is not None :
256
257
indicies = _generate_indices (f , values )
257
258
for i in indicies :
@@ -260,7 +261,7 @@ def _check(f, func, values = False):
260
261
assert_almost_equal (result , expected )
261
262
262
263
for o in self ._objs :
263
-
264
+
264
265
d = getattr (self ,o )
265
266
266
267
# iat
@@ -274,11 +275,11 @@ def _check(f, func, values = False):
274
275
_check (d ['labels' ],'at' )
275
276
_check (d ['ts' ], 'at' )
276
277
_check (d ['floats' ],'at' )
277
-
278
+
278
279
def test_at_and_iat_set (self ):
279
280
280
281
def _check (f , func , values = False ):
281
-
282
+
282
283
if f is not None :
283
284
indicies = _generate_indices (f , values )
284
285
for i in indicies :
@@ -287,7 +288,7 @@ def _check(f, func, values = False):
287
288
assert_almost_equal (expected , 1 )
288
289
289
290
for t in self ._objs :
290
-
291
+
291
292
d = getattr (self ,t )
292
293
293
294
_check (d ['ints' ],'iat' ,values = True )
@@ -302,12 +303,12 @@ def _check(f, func, values = False):
302
303
_check (d ['floats' ],'at' )
303
304
304
305
def test_at_timestamp (self ):
305
-
306
+
306
307
# as timestamp is not a tuple!
307
308
dates = date_range ('1/1/2000' , periods = 8 )
308
309
df = DataFrame (randn (8 , 4 ), index = dates , columns = ['A' , 'B' , 'C' , 'D' ])
309
310
s = df ['A' ]
310
-
311
+
311
312
result = s .at [dates [5 ]]
312
313
xp = s .values [5 ]
313
314
self .assert_ (result == xp )
@@ -320,7 +321,7 @@ def test_iloc_getitem_int(self):
320
321
# integer
321
322
self .check_result ('integer' , 'iloc' , 2 , 'ix' , { 0 : 4 , 1 : 6 , 2 : 8 }, typs = ['ints' ])
322
323
self .check_result ('integer' , 'iloc' , 2 , 'indexer' , 2 , typs = ['labels' ,'mixed' ,'ts' ,'floats' ,'empty' ], fails = IndexError )
323
-
324
+
324
325
def test_iloc_getitem_neg_int (self ):
325
326
326
327
# neg integer
@@ -332,7 +333,7 @@ def test_iloc_getitem_list_int(self):
332
333
# list of ints
333
334
self .check_result ('list int' , 'iloc' , [0 ,1 ,2 ], 'ix' , { 0 : [0 ,2 ,4 ], 1 : [0 ,3 ,6 ], 2 : [0 ,4 ,8 ] }, typs = ['ints' ])
334
335
self .check_result ('list int' , 'iloc' , [0 ,1 ,2 ], 'indexer' , [0 ,1 ,2 ], typs = ['labels' ,'mixed' ,'ts' ,'floats' ,'empty' ], fails = IndexError )
335
-
336
+
336
337
def test_iloc_getitem_dups (self ):
337
338
338
339
# no dups in panel (bug?)
@@ -378,7 +379,7 @@ def test_iloc_setitem(self):
378
379
assert_frame_equal (result , expected )
379
380
380
381
def test_iloc_multiindex (self ):
381
- df = DataFrame (np .random .randn (3 , 3 ),
382
+ df = DataFrame (np .random .randn (3 , 3 ),
382
383
columns = [[2 ,2 ,4 ],[6 ,8 ,10 ]],
383
384
index = [[4 ,4 ,8 ],[8 ,10 ,12 ]])
384
385
@@ -415,7 +416,7 @@ def test_loc_getitem_label_out_of_range(self):
415
416
416
417
# out of range label
417
418
self .check_result ('label range' , 'loc' , 'f' , 'ix' , 'f' , typs = ['ints' ,'labels' ,'mixed' ,'ts' ,'floats' ], fails = KeyError )
418
-
419
+
419
420
def test_loc_getitem_label_list (self ):
420
421
421
422
# list of labels
@@ -426,15 +427,15 @@ def test_loc_getitem_label_list(self):
426
427
self .check_result ('list lbl' , 'loc' , ['A' ,'B' ,'C' ], 'ix' , ['A' ,'B' ,'C' ], typs = ['labels' ], axes = 1 )
427
428
self .check_result ('list lbl' , 'loc' , ['Z' ,'Y' ,'W' ], 'ix' , ['Z' ,'Y' ,'W' ], typs = ['labels' ], axes = 2 )
428
429
self .check_result ('list lbl' , 'loc' , [2 ,8 ,'null' ], 'ix' , [2 ,8 ,'null' ], typs = ['mixed' ], axes = 0 )
429
- self .check_result ('list lbl' , 'loc' , [Timestamp ('20130102' ),Timestamp ('20130103' )], 'ix' ,
430
+ self .check_result ('list lbl' , 'loc' , [Timestamp ('20130102' ),Timestamp ('20130103' )], 'ix' ,
430
431
[Timestamp ('20130102' ),Timestamp ('20130103' )], typs = ['ts' ], axes = 0 )
431
432
432
433
# fails
433
434
self .check_result ('list lbl' , 'loc' , [0 ,1 ,2 ], 'indexer' , [0 ,1 ,2 ], typs = ['empty' ], fails = KeyError )
434
435
self .check_result ('list lbl' , 'loc' , [0 ,2 ,3 ], 'ix' , [0 ,2 ,3 ], typs = ['ints' ], axes = 0 , fails = KeyError )
435
436
self .check_result ('list lbl' , 'loc' , [3 ,6 ,7 ], 'ix' , [3 ,6 ,9 ], typs = ['ints' ], axes = 1 , fails = KeyError )
436
437
self .check_result ('list lbl' , 'loc' , [4 ,8 ,10 ], 'ix' , [4 ,8 ,12 ], typs = ['ints' ], axes = 2 , fails = KeyError )
437
-
438
+
438
439
# array like
439
440
self .check_result ('array like' , 'loc' , Series (index = [0 ,2 ,4 ]).index , 'ix' , [0 ,2 ,4 ], typs = ['ints' ], axes = 0 )
440
441
self .check_result ('array like' , 'loc' , Series (index = [3 ,6 ,9 ]).index , 'ix' , [3 ,6 ,9 ], typs = ['ints' ], axes = 1 )
@@ -449,10 +450,10 @@ def test_loc_getitem_bool(self):
449
450
450
451
def test_loc_getitem_int_slice (self ):
451
452
452
- # int slices in int
453
+ # int slices in int
453
454
self .check_result ('int slice1' , 'loc' , slice (2 ,4 ), 'ix' , { 0 : [2 ,4 ], 1 : [3 ,6 ], 2 : [4 ,8 ] }, typs = ['ints' ], fails = KeyError )
454
455
455
- # ok
456
+ # ok
456
457
self .check_result ('int slice2' , 'loc' , slice (2 ,4 ), 'ix' , [2 ,4 ], typs = ['ints' ], axes = 0 )
457
458
self .check_result ('int slice2' , 'loc' , slice (3 ,6 ), 'ix' , [3 ,6 ], typs = ['ints' ], axes = 1 )
458
459
self .check_result ('int slice2' , 'loc' , slice (4 ,8 ), 'ix' , [4 ,8 ], typs = ['ints' ], axes = 2 )
@@ -589,7 +590,7 @@ def test_iloc_getitem_frame(self):
589
590
result = df .iloc [s .index ]
590
591
expected = df .ix [[2 ,4 ,6 ,8 ]]
591
592
assert_frame_equal (result , expected )
592
-
593
+
593
594
# out-of-bounds slice
594
595
self .assertRaises (IndexError , df .iloc .__getitem__ , tuple ([slice (None ),slice (1 ,5 ,None )]))
595
596
self .assertRaises (IndexError , df .iloc .__getitem__ , tuple ([slice (None ),slice (- 5 ,3 ,None )]))
@@ -648,7 +649,7 @@ def test_iloc_multiindex(self):
648
649
['A' , 'A' , 'B' ]],
649
650
index = [['i' , 'i' , 'j' , 'k' ], ['X' , 'X' , 'Y' ,'Y' ]])
650
651
651
- mi_int = DataFrame (np .random .randn (3 , 3 ),
652
+ mi_int = DataFrame (np .random .randn (3 , 3 ),
652
653
columns = [[2 ,2 ,4 ],[6 ,8 ,10 ]],
653
654
index = [[4 ,4 ,8 ],[8 ,10 ,12 ]])
654
655
@@ -679,7 +680,7 @@ def test_loc_multiindex(self):
679
680
['A' , 'A' , 'B' ]],
680
681
index = [['i' , 'i' , 'j' ], ['X' , 'X' , 'Y' ]])
681
682
682
- mi_int = DataFrame (np .random .randn (3 , 3 ),
683
+ mi_int = DataFrame (np .random .randn (3 , 3 ),
683
684
columns = [[2 ,2 ,4 ],[6 ,8 ,10 ]],
684
685
index = [[4 ,4 ,8 ],[8 ,10 ,12 ]])
685
686
@@ -749,7 +750,7 @@ def test_xs_multiindex(self):
749
750
assert_frame_equal (result , expected )
750
751
751
752
def test_setitem_dtype_upcast (self ):
752
-
753
+
753
754
# GH3216
754
755
df = DataFrame ([{"a" : 1 }, {"a" : 3 , "b" : 2 }])
755
756
df ['c' ] = np .nan
@@ -761,7 +762,7 @@ def test_setitem_dtype_upcast(self):
761
762
762
763
def test_setitem_iloc (self ):
763
764
764
-
765
+
765
766
# setitem with an iloc list
766
767
df = DataFrame (np .arange (9 ).reshape ((3 , 3 )), index = ["A" , "B" , "C" ], columns = ["A" , "B" , "C" ])
767
768
df .iloc [[0 ,1 ],[1 ,2 ]]
@@ -830,20 +831,20 @@ def test_indexing_mixed_frame_bug(self):
830
831
self .assert_ (df .iloc [0 ,2 ] == '-----' )
831
832
832
833
#if I look at df, then element [0,2] equals '_'. If instead I type df.ix[idx,'test'], I get '-----', finally by typing df.iloc[0,2] I get '_'.
833
-
834
+
834
835
835
836
def test_set_index_nan (self ):
836
837
837
838
# GH 3586
838
- df = DataFrame ({'PRuid' : {17 : 'nonQC' , 18 : 'nonQC' , 19 : 'nonQC' , 20 : '10' , 21 : '11' , 22 : '12' , 23 : '13' ,
839
- 24 : '24' , 25 : '35' , 26 : '46' , 27 : '47' , 28 : '48' , 29 : '59' , 30 : '10' },
840
- 'QC' : {17 : 0.0 , 18 : 0.0 , 19 : 0.0 , 20 : nan , 21 : nan , 22 : nan , 23 : nan , 24 : 1.0 , 25 : nan ,
841
- 26 : nan , 27 : nan , 28 : nan , 29 : nan , 30 : nan },
842
- 'data' : {17 : 7.9544899999999998 , 18 : 8.0142609999999994 , 19 : 7.8591520000000008 , 20 : 0.86140349999999999 ,
839
+ df = DataFrame ({'PRuid' : {17 : 'nonQC' , 18 : 'nonQC' , 19 : 'nonQC' , 20 : '10' , 21 : '11' , 22 : '12' , 23 : '13' ,
840
+ 24 : '24' , 25 : '35' , 26 : '46' , 27 : '47' , 28 : '48' , 29 : '59' , 30 : '10' },
841
+ 'QC' : {17 : 0.0 , 18 : 0.0 , 19 : 0.0 , 20 : nan , 21 : nan , 22 : nan , 23 : nan , 24 : 1.0 , 25 : nan ,
842
+ 26 : nan , 27 : nan , 28 : nan , 29 : nan , 30 : nan },
843
+ 'data' : {17 : 7.9544899999999998 , 18 : 8.0142609999999994 , 19 : 7.8591520000000008 , 20 : 0.86140349999999999 ,
843
844
21 : 0.87853110000000001 , 22 : 0.8427041999999999 , 23 : 0.78587700000000005 , 24 : 0.73062459999999996 ,
844
- 25 : 0.81668560000000001 , 26 : 0.81927080000000008 , 27 : 0.80705009999999999 , 28 : 0.81440240000000008 ,
845
- 29 : 0.80140849999999997 , 30 : 0.81307740000000006 },
846
- 'year' : {17 : 2006 , 18 : 2007 , 19 : 2008 , 20 : 1985 , 21 : 1985 , 22 : 1985 , 23 : 1985 ,
845
+ 25 : 0.81668560000000001 , 26 : 0.81927080000000008 , 27 : 0.80705009999999999 , 28 : 0.81440240000000008 ,
846
+ 29 : 0.80140849999999997 , 30 : 0.81307740000000006 },
847
+ 'year' : {17 : 2006 , 18 : 2007 , 19 : 2008 , 20 : 1985 , 21 : 1985 , 22 : 1985 , 23 : 1985 ,
847
848
24 : 1985 , 25 : 1985 , 26 : 1985 , 27 : 1985 , 28 : 1985 , 29 : 1985 , 30 : 1986 }}).reset_index ()
848
849
849
850
result = df .set_index (['year' ,'PRuid' ,'QC' ]).reset_index ().reindex (columns = df .columns )
@@ -871,7 +872,7 @@ def test_iloc_panel_issue(self):
871
872
self .assert_ (p .iloc [1 , 1 , :3 ].shape == (3 ,))
872
873
self .assert_ (p .iloc [1 , :3 , 1 ].shape == (3 ,))
873
874
self .assert_ (p .iloc [:3 , 1 , 1 ].shape == (3 ,))
874
-
875
+
875
876
def test_multi_assign (self ):
876
877
877
878
# GH 3626, an assignement of a sub-df to a df
@@ -892,7 +893,7 @@ def test_multi_assign(self):
892
893
'PF' :[0 ,0 ,0 ,0 ,1 ,1 ],
893
894
'col1' :Series ([0 ,1 ,4 ,6 ,8 ,10 ]),
894
895
'col2' :[12 ,7 ,16 ,np .nan ,20 ,22 ]})
895
-
896
+
896
897
897
898
# frame on rhs
898
899
df2 .ix [mask , cols ]= dft .ix [mask , cols ]
@@ -1006,7 +1007,7 @@ def test_non_unique_loc(self):
1006
1007
## https://groups.google.com/forum/?fromgroups#!topic/pydata/zTm2No0crYs
1007
1008
1008
1009
# these are going to raise becuase the we are non monotonic
1009
- df = DataFrame ({'A' : [1 ,2 ,3 ,4 ,5 ,6 ], 'B' : [3 ,4 ,5 ,6 ,7 ,8 ]}, index = [0 ,1 ,0 ,1 ,2 ,3 ])
1010
+ df = DataFrame ({'A' : [1 ,2 ,3 ,4 ,5 ,6 ], 'B' : [3 ,4 ,5 ,6 ,7 ,8 ]}, index = [0 ,1 ,0 ,1 ,2 ,3 ])
1010
1011
self .assertRaises (KeyError , df .loc .__getitem__ , tuple ([slice (1 ,None )]))
1011
1012
self .assertRaises (KeyError , df .loc .__getitem__ , tuple ([slice (0 ,None )]))
1012
1013
self .assertRaises (KeyError , df .loc .__getitem__ , tuple ([slice (1 ,2 )]))
@@ -1066,6 +1067,36 @@ def test_iloc_non_unique_indexing(self):
1066
1067
result = df2 .loc [idx ]
1067
1068
assert_frame_equal (result , expected )
1068
1069
1070
+ def test_mi_access (self ):
1071
+
1072
+ # GH 4145
1073
+ data = """h1 main h3 sub h5
1074
+ 0 a A 1 A1 1
1075
+ 1 b B 2 B1 2
1076
+ 2 c B 3 A1 3
1077
+ 3 d A 4 B2 4
1078
+ 4 e A 5 B2 5
1079
+ 5 f B 6 A2 6
1080
+ """
1081
+
1082
+ df = pd .read_csv (StringIO (data ),sep = '\s+' ,index_col = 0 )
1083
+ df2 = df .set_index (['main' , 'sub' ]).T .sort_index (1 )
1084
+ index = Index (['h1' ,'h3' ,'h5' ])
1085
+ columns = MultiIndex .from_tuples ([('A' ,'A1' )],names = ['main' ,'sub' ])
1086
+ expected = DataFrame ([['a' ,1 ,1 ]],index = columns ,columns = index ).T
1087
+
1088
+ result = df2 .loc [:,('A' ,'A1' )]
1089
+ assert_frame_equal (result ,expected )
1090
+
1091
+ result = df2 [('A' ,'A1' )]
1092
+ assert_frame_equal (result ,expected )
1093
+
1094
+ # GH 4146, not returning a block manager when selecting a unique index
1095
+ # from a duplicate index
1096
+ expected = DataFrame ([['a' ,1 ,1 ]],index = ['A1' ],columns = ['h1' ,'h3' ,'h5' ],).T
1097
+ df3 = df2 ['A' ]
1098
+ result = df3 ['A1' ]
1099
+ assert_frame_equal (result ,expected )
1069
1100
1070
1101
if __name__ == '__main__' :
1071
1102
import nose
0 commit comments