@@ -353,9 +353,9 @@ def test_constructor_from_index_series_period(self):
353
353
result = Categorical (Series (idx ))
354
354
tm .assert_index_equal (result .categories , idx )
355
355
356
- def test_constructor_invariant ( self ):
357
- # GH 14190
358
- vals = [
356
+ @ pytest . mark . parametrize (
357
+ "values" ,
358
+ [
359
359
np .array ([1.0 , 1.2 , 1.8 , np .nan ]),
360
360
np .array ([1 , 2 , 3 ], dtype = "int64" ),
361
361
["a" , "b" , "c" , np .nan ],
@@ -366,11 +366,13 @@ def test_constructor_invariant(self):
366
366
Timestamp ("2014-01-02" , tz = "US/Eastern" ),
367
367
NaT ,
368
368
],
369
- ]
370
- for val in vals :
371
- c = Categorical (val )
372
- c2 = Categorical (c )
373
- tm .assert_categorical_equal (c , c2 )
369
+ ],
370
+ )
371
+ def test_constructor_invariant (self , values ):
372
+ # GH 14190
373
+ c = Categorical (values )
374
+ c2 = Categorical (c )
375
+ tm .assert_categorical_equal (c , c2 )
374
376
375
377
@pytest .mark .parametrize ("ordered" , [True , False ])
376
378
def test_constructor_with_dtype (self , ordered ):
@@ -470,61 +472,66 @@ def test_construction_with_null(self, klass, nulls_fixture):
470
472
471
473
tm .assert_categorical_equal (result , expected )
472
474
473
- def test_from_codes (self ):
475
+ def test_from_codes_empty (self ):
476
+ cat = ["a" , "b" , "c" ]
477
+ result = Categorical .from_codes ([], categories = cat )
478
+ expected = Categorical ([], categories = cat )
474
479
475
- # too few categories
480
+ tm .assert_categorical_equal (result , expected )
481
+
482
+ def test_from_codes_too_few_categories (self ):
476
483
dtype = CategoricalDtype (categories = [1 , 2 ])
477
484
msg = "codes need to be between "
478
485
with pytest .raises (ValueError , match = msg ):
479
486
Categorical .from_codes ([1 , 2 ], categories = dtype .categories )
480
487
with pytest .raises (ValueError , match = msg ):
481
488
Categorical .from_codes ([1 , 2 ], dtype = dtype )
482
489
483
- # no int codes
490
+ def test_from_codes_non_int_codes (self ):
491
+ dtype = CategoricalDtype (categories = [1 , 2 ])
484
492
msg = "codes need to be array-like integers"
485
493
with pytest .raises (ValueError , match = msg ):
486
494
Categorical .from_codes (["a" ], categories = dtype .categories )
487
495
with pytest .raises (ValueError , match = msg ):
488
496
Categorical .from_codes (["a" ], dtype = dtype )
489
497
490
- # no unique categories
498
+ def test_from_codes_non_unique_categories ( self ):
491
499
with pytest .raises (ValueError , match = "Categorical categories must be unique" ):
492
500
Categorical .from_codes ([0 , 1 , 2 ], categories = ["a" , "a" , "b" ])
493
501
494
- # NaN categories included
502
+ def test_from_codes_nan_cat_included ( self ):
495
503
with pytest .raises (ValueError , match = "Categorial categories cannot be null" ):
496
504
Categorical .from_codes ([0 , 1 , 2 ], categories = ["a" , "b" , np .nan ])
497
505
498
- # too negative
506
+ def test_from_codes_too_negative ( self ):
499
507
dtype = CategoricalDtype (categories = ["a" , "b" , "c" ])
500
508
msg = r"codes need to be between -1 and len\(categories\)-1"
501
509
with pytest .raises (ValueError , match = msg ):
502
510
Categorical .from_codes ([- 2 , 1 , 2 ], categories = dtype .categories )
503
511
with pytest .raises (ValueError , match = msg ):
504
512
Categorical .from_codes ([- 2 , 1 , 2 ], dtype = dtype )
505
513
514
+ def test_from_codes (self ):
515
+ dtype = CategoricalDtype (categories = ["a" , "b" , "c" ])
506
516
exp = Categorical (["a" , "b" , "c" ], ordered = False )
507
517
res = Categorical .from_codes ([0 , 1 , 2 ], categories = dtype .categories )
508
518
tm .assert_categorical_equal (exp , res )
509
519
510
520
res = Categorical .from_codes ([0 , 1 , 2 ], dtype = dtype )
511
521
tm .assert_categorical_equal (exp , res )
512
522
513
- def test_from_codes_with_categorical_categories (self ):
523
+ @pytest .mark .parametrize ("klass" , [Categorical , CategoricalIndex ])
524
+ def test_from_codes_with_categorical_categories (self , klass ):
514
525
# GH17884
515
526
expected = Categorical (["a" , "b" ], categories = ["a" , "b" , "c" ])
516
527
517
- result = Categorical .from_codes ([0 , 1 ], categories = Categorical (["a" , "b" , "c" ]))
528
+ result = Categorical .from_codes ([0 , 1 ], categories = klass (["a" , "b" , "c" ]))
518
529
tm .assert_categorical_equal (result , expected )
519
530
520
- result = Categorical .from_codes (
521
- [0 , 1 ], categories = CategoricalIndex (["a" , "b" , "c" ])
522
- )
523
- tm .assert_categorical_equal (result , expected )
524
-
525
- # non-unique Categorical still raises
531
+ @pytest .mark .parametrize ("klass" , [Categorical , CategoricalIndex ])
532
+ def test_from_codes_with_non_unique_categorical_categories (self , klass ):
526
533
with pytest .raises (ValueError , match = "Categorical categories must be unique" ):
527
- Categorical .from_codes ([0 , 1 ], Categorical (["a" , "b" , "a" ]))
534
+ Categorical .from_codes ([0 , 1 ], klass (["a" , "b" , "a" ]))
528
535
529
536
def test_from_codes_with_nan_code (self ):
530
537
# GH21767
@@ -535,24 +542,16 @@ def test_from_codes_with_nan_code(self):
535
542
with pytest .raises (ValueError , match = "codes need to be array-like integers" ):
536
543
Categorical .from_codes (codes , dtype = dtype )
537
544
538
- def test_from_codes_with_float (self ):
545
+ @pytest .mark .parametrize ("codes" , [[1.0 , 2.0 , 0 ], [1.1 , 2.0 , 0 ]])
546
+ def test_from_codes_with_float (self , codes ):
539
547
# GH21767
540
- codes = [ 1.0 , 2.0 , 0 ] # integer, but in float dtype
548
+ # float codes should raise even if values are equal to integers
541
549
dtype = CategoricalDtype (categories = ["a" , "b" , "c" ])
542
550
543
- # empty codes should not raise for floats
544
- Categorical .from_codes ([], dtype .categories )
545
-
546
- with pytest .raises (ValueError , match = "codes need to be array-like integers" ):
547
- Categorical .from_codes (codes , dtype .categories )
548
-
549
- with pytest .raises (ValueError , match = "codes need to be array-like integers" ):
550
- Categorical .from_codes (codes , dtype = dtype )
551
-
552
- codes = [1.1 , 2.0 , 0 ] # non-integer
553
- with pytest .raises (ValueError , match = "codes need to be array-like integers" ):
551
+ msg = "codes need to be array-like integers"
552
+ with pytest .raises (ValueError , match = msg ):
554
553
Categorical .from_codes (codes , dtype .categories )
555
- with pytest .raises (ValueError , match = "codes need to be array-like integers" ):
554
+ with pytest .raises (ValueError , match = msg ):
556
555
Categorical .from_codes (codes , dtype = dtype )
557
556
558
557
def test_from_codes_with_dtype_raises (self ):
0 commit comments