@@ -502,17 +502,110 @@ public PList extend(PList list, Object source,
502
502
@ GenerateNodeFactory
503
503
public abstract static class ListInsertNode extends PythonBuiltinNode {
504
504
505
+ public abstract PNone execute (PList list , Object index , Object value );
506
+
507
+ @ Specialization (guards = "isIntStorage(list)" )
508
+ public PNone insertIntInt (PList list , int index , int value ) {
509
+ IntSequenceStorage target = (IntSequenceStorage ) list .getSequenceStorage ();
510
+ target .insertIntItem (normalizeIndex (index , list .len ()), value );
511
+ return PNone .NONE ;
512
+ }
513
+
514
+ @ Specialization (guards = "isLongStorage(list)" )
515
+ public PNone insertLongLong (PList list , int index , int value ) {
516
+ LongSequenceStorage target = (LongSequenceStorage ) list .getSequenceStorage ();
517
+ target .insertLongItem (normalizeIndex (index , list .len ()), value );
518
+ return PNone .NONE ;
519
+ }
520
+
521
+ @ Specialization (guards = "isLongStorage(list)" )
522
+ public PNone insertLongLong (PList list , int index , long value ) {
523
+ LongSequenceStorage target = (LongSequenceStorage ) list .getSequenceStorage ();
524
+ target .insertLongItem (normalizeIndex (index , list .len ()), value );
525
+ return PNone .NONE ;
526
+ }
527
+
528
+ @ Specialization (guards = "isDoubleStorage(list)" )
529
+ public PNone insertDoubleDouble (PList list , int index , double value ) {
530
+ DoubleSequenceStorage target = (DoubleSequenceStorage ) list .getSequenceStorage ();
531
+ target .insertDoubleItem (normalizeIndex (index , list .len ()), value );
532
+ return PNone .NONE ;
533
+ }
534
+
535
+ @ Specialization (guards = "isNotSpecialCase(list, value)" )
536
+ public PNone insert (PList list , int index , Object value ) {
537
+ list .insert (normalizeIndex (index , list .len ()), value );
538
+ return PNone .NONE ;
539
+ }
540
+
505
541
@ Specialization
506
- public PList insert (PList list , int index , Object value ) {
507
- list .insert (index , value );
508
- return list ;
542
+ public PNone insertLongIndex (PList list , long index , Object value ,
543
+ @ Cached ("createListInsertNode()" ) ListInsertNode insertNode ) {
544
+ int where = index < Integer .MIN_VALUE ? 0 : index > Integer .MAX_VALUE ? Integer .MAX_VALUE : (int ) index ;
545
+ where = normalizeIndex (where , list .len ());
546
+ return insertNode .execute (list , where , value );
509
547
}
510
548
511
549
@ Specialization
512
- @ SuppressWarnings ("unused" )
513
- public PList insert (PList list , Object i , Object arg1 ) {
514
- throw new RuntimeException ("invalid arguments for insert()" );
550
+ public PNone insertPIntIndex (PList list , PInt index , Object value ,
551
+ @ Cached ("createListInsertNode()" ) ListInsertNode insertNode ) {
552
+ int where = normalizePIntForIndex (index );
553
+ where = normalizeIndex (where , list .len ());
554
+ return insertNode .execute (list , where , value );
555
+ }
556
+
557
+ @ Specialization (guards = {"!isIntegerOrPInt(i)" })
558
+ public PNone insert (PList list , Object i , Object value ,
559
+ @ Cached ("create(__INDEX__)" ) LookupAndCallUnaryNode indexNode ,
560
+ @ Cached ("createListInsertNode()" ) ListInsertNode insertNode ) {
561
+ Object indexValue = indexNode .executeObject (i );
562
+ if (PNone .NO_VALUE == indexValue ) {
563
+ throw raise (TypeError , "'%p' object cannot be interpreted as an integer" , i );
564
+ }
565
+ return insertNode .execute (list , indexValue , value );
566
+ }
567
+
568
+ @ TruffleBoundary
569
+ private static int normalizePIntForIndex (PInt index ) {
570
+ int where = 0 ;
571
+ BigInteger bigIndex = index .getValue ();
572
+ if (bigIndex .compareTo (BigInteger .valueOf (Integer .MIN_VALUE )) == -1 ) {
573
+ where = 0 ;
574
+ } else if (bigIndex .compareTo (BigInteger .valueOf (Integer .MAX_VALUE )) == 1 ) {
575
+ where = Integer .MAX_VALUE ;
576
+ } else {
577
+ where = bigIndex .intValue ();
578
+ }
579
+ return where ;
580
+ }
581
+
582
+ private static int normalizeIndex (int index , int len ) {
583
+ int idx = index ;
584
+ if (idx < 0 ) {
585
+ idx += len ;
586
+ if (idx < 0 ) {
587
+ idx = 0 ;
588
+ }
589
+ }
590
+ if (idx > len ) {
591
+ idx = len ;
592
+ }
593
+ return idx ;
594
+ }
595
+
596
+ protected boolean isNotSpecialCase (PList list , Object value ) {
597
+ return !((PGuards .isIntStorage (list ) && value instanceof Integer ) || (PGuards .isLongStorage (list ) && PGuards .isInteger (value )) ||
598
+ (PGuards .isDoubleStorage (list ) && value instanceof Double ));
515
599
}
600
+
601
+ protected boolean isIntegerOrPInt (Object index ) {
602
+ return index instanceof Integer || index instanceof PInt ;
603
+ }
604
+
605
+ protected ListInsertNode createListInsertNode () {
606
+ return ListBuiltinsFactory .ListInsertNodeFactory .create (new PNode [0 ]);
607
+ }
608
+
516
609
}
517
610
518
611
// list.remove(x)
0 commit comments