@@ -726,6 +726,8 @@ public boolean containsValue(double pattern) {
726726
727727 @ Override
728728 public boolean containsValueWithReference (double pattern , double [] reference ) {
729+ if (Double .isNaN (pattern ))
730+ return super .containsValueWithReference (pattern , reference );
729731 final int nCol = reference .length ;
730732 for (int i = 0 ; i < _values .length ; i ++)
731733 if (_values [i ] + reference [i % nCol ] == pattern )
@@ -913,46 +915,7 @@ public IDictionary replaceWithReference(double pattern, double replace, double[]
913915 final int nCol = reference .length ;
914916 final int nRow = _values .length / nCol ;
915917 if (Util .eq (pattern , Double .NaN )) {
916- Set <Integer > colsWithNan = null ;
917- for (int i = 0 ; i < reference .length ; i ++) {
918- if (Util .eq (reference [i ], Double .NaN )) {
919- if (colsWithNan == null )
920- colsWithNan = new HashSet <>();
921- colsWithNan .add (i );
922- reference [i ] = replace ;
923- }
924- }
925-
926- if (colsWithNan != null ) {
927- final double [] retV = new double [_values .length ];
928- for (int i = 0 ; i < nRow ; i ++) {
929- final int off = i * reference .length ;
930- for (int j = 0 ; j < nCol ; j ++) {
931- final int cell = off + j ;
932- if (colsWithNan .contains (j ))
933- retV [cell ] = 0 ;
934- else if (Util .eq (_values [cell ], Double .NaN ))
935- retV [cell ] = replace - reference [j ];
936- else
937- retV [cell ] = _values [cell ];
938- }
939- }
940- return create (retV );
941- }
942- else {
943- final double [] retV = new double [_values .length ];
944- for (int i = 0 ; i < nRow ; i ++) {
945- final int off = i * reference .length ;
946- for (int j = 0 ; j < nCol ; j ++) {
947- final int cell = off + j ;
948- if (Util .eq (_values [cell ], Double .NaN ))
949- retV [cell ] = replace - reference [j ];
950- else
951- retV [cell ] = _values [cell ] ;
952- }
953- }
954- return create (retV );
955- }
918+ return replaceWithReferenceNaN (replace , reference , nCol , nRow );
956919 }
957920 else {
958921 final double [] retV = new double [_values .length ];
@@ -969,6 +932,62 @@ else if(Util.eq(_values[cell], Double.NaN))
969932 }
970933 }
971934
935+ private IDictionary replaceWithReferenceNaN (double replace , double [] reference , final int nCol , final int nRow ) {
936+ final Set <Integer > colsWithNan = getColsWithNan (replace , reference );
937+ final double [] retV ;
938+ if (colsWithNan != null ) {
939+ if (colsWithNan .size () == nCol && replace == 0 )
940+ return null ;
941+ retV = new double [_values .length ];
942+ replaceWithReferenceNanDenseWithNanCols (replace , reference , nRow , nCol , colsWithNan , _values , retV );
943+ }
944+ else {
945+ retV = new double [_values .length ];
946+ replaceWithReferenceNanDenseWithoutNanCols (replace , reference , nRow , nCol , retV , _values );
947+ }
948+ return create (retV );
949+ }
950+
951+ protected static Set <Integer > getColsWithNan (double replace , double [] reference ) {
952+ Set <Integer > colsWithNan = null ;
953+ for (int i = 0 ; i < reference .length ; i ++) {
954+ if (Util .eq (reference [i ], Double .NaN )) {
955+ if (colsWithNan == null )
956+ colsWithNan = new HashSet <>();
957+ colsWithNan .add (i );
958+ reference [i ] = replace ;
959+ }
960+ }
961+ return colsWithNan ;
962+ }
963+
964+ protected static void replaceWithReferenceNanDenseWithoutNanCols (final double replace , final double [] reference ,
965+ final int nRow , final int nCol , final double [] retV , final double [] values ) {
966+ int off = 0 ;
967+ for (int i = 0 ; i < nRow ; i ++) {
968+ for (int j = 0 ; j < nCol ; j ++) {
969+ final double v = values [off ];
970+ retV [off ++] = Util .eq (Double .NaN , v ) ? replace - reference [j ] : v ;
971+ }
972+ }
973+ }
974+
975+ protected static void replaceWithReferenceNanDenseWithNanCols (final double replace , final double [] reference ,
976+ final int nRow , final int nCol , Set <Integer > colsWithNan , final double [] values , final double [] retV ) {
977+ int off = 0 ;
978+ for (int i = 0 ; i < nRow ; i ++) {
979+ for (int j = 0 ; j < nCol ; j ++) {
980+ final double v = values [off ];
981+ if (colsWithNan .contains (j ))
982+ retV [off ++] = 0 ;
983+ else if (Util .eq (v , Double .NaN ))
984+ retV [off ++] = replace - reference [j ];
985+ else
986+ retV [off ++] = v ;
987+ }
988+ }
989+ }
990+
972991 @ Override
973992 public void product (double [] ret , int [] counts , int nCol ) {
974993 if (ret [0 ] == 0 )
@@ -1024,17 +1043,22 @@ public void productWithReference(double[] ret, int[] counts, double[] reference,
10241043 if (ret [0 ] == 0 )
10251044 return ;
10261045 final MathContext cont = MathContext .DECIMAL128 ;
1027- final int len = counts .length ;
1046+ final int nRow = counts .length ;
10281047 final int nCol = reference .length ;
1048+
10291049 BigDecimal tmp = BigDecimal .ONE ;
10301050 int off = 0 ;
1031- for (int i = 0 ; i < len ; i ++) {
1051+ for (int i = 0 ; i < nRow ; i ++) {
10321052 for (int j = 0 ; j < nCol ; j ++) {
10331053 final double v = _values [off ++] + reference [j ];
10341054 if (v == 0 ) {
10351055 ret [0 ] = 0 ;
10361056 return ;
10371057 }
1058+ else if (!Double .isFinite (v )) {
1059+ ret [0 ] = v ;
1060+ return ;
1061+ }
10381062 tmp = tmp .multiply (new BigDecimal (v ).pow (counts [i ], cont ), cont );
10391063 }
10401064 }
@@ -1044,6 +1068,7 @@ public void productWithReference(double[] ret, int[] counts, double[] reference,
10441068 ret [0 ] = 0 ;
10451069 else if (!Double .isInfinite (ret [0 ]))
10461070 ret [0 ] = new BigDecimal (ret [0 ]).multiply (tmp , MathContext .DECIMAL128 ).doubleValue ();
1071+
10471072 }
10481073
10491074 @ Override
@@ -1192,7 +1217,7 @@ public void TSMMToUpperTriangleSparseScaling(SparseBlock left, IColIndex rowsLef
11921217 public boolean equals (IDictionary o ) {
11931218 if (o instanceof Dictionary )
11941219 return Arrays .equals (_values , ((Dictionary ) o )._values );
1195- else if (o != null )
1220+ else if (o != null )
11961221 return o .equals (this );
11971222 return false ;
11981223 }
@@ -1219,7 +1244,7 @@ public IDictionary reorder(int[] reorder) {
12191244 return ret ;
12201245 }
12211246
1222- @ Override
1247+ @ Override
12231248 protected IDictionary rightMMPreAggSparseSelectedCols (int numVals , SparseBlock b , IColIndex thisCols ,
12241249 IColIndex aggregateColumns ) {
12251250
@@ -1264,7 +1289,7 @@ private void sparseAddSelected(int sPos, int sEnd, int aggColSize, IColIndex agg
12641289 retIdx = 0 ;
12651290 }
12661291
1267- @ Override
1292+ @ Override
12681293 protected IDictionary rightMMPreAggSparseAllColsRight (int numVals , SparseBlock b , IColIndex thisCols ,
12691294 int nColRight ) {
12701295 final int thisColsSize = thisCols .size ();
@@ -1291,15 +1316,14 @@ protected IDictionary rightMMPreAggSparseAllColsRight(int numVals, SparseBlock b
12911316 return Dictionary .create (ret );
12921317 }
12931318
1294- private void SparseAdd (int sPos , int sEnd , double [] ret , int offOut , int [] sIdx , double [] sVals , double v ) {
1319+ private void SparseAdd (int sPos , int sEnd , double [] ret , int offOut , int [] sIdx , double [] sVals , double v ) {
12951320 if (v != 0 ) {
12961321 for (int k = sPos ; k < sEnd ; k ++) { // cols right with value
12971322 ret [offOut + sIdx [k ]] += v * sVals [k ];
12981323 }
12991324 }
13001325 }
13011326
1302-
13031327 @ Override
13041328 public IDictionary append (double [] row ) {
13051329 double [] retV = new double [_values .length + row .length ];
@@ -1308,5 +1332,4 @@ public IDictionary append(double[] row) {
13081332 return new Dictionary (retV );
13091333 }
13101334
1311-
13121335}
0 commit comments