Java with?Pits that occur when expressions are combined

  • 2021-06-28 12:41:53
  • OfStack

Preface

First of all, the background, just after returning home from vacation to be relatively idle, I took out a project that had written some algorithm questions before to continue writing, and wanted to modify the insertion sort to support ascending and descending order, then this pit appeared, specifically as follows:

Let's put out the code to insert the sort first.


/**
 *  Insert Sort 
 * @param arr  Input Array 
 * @param order  order  1 For ascending order  0 For descending order 
 */
static void insertionSort(int arr[],int order){
 
 for (int i = 1; i < arr.length; i++)
 {
  int get = arr[i];
  int j = i - 1;
  while (j >= 0 && (order == 1) ? (arr[j] > get):(arr[j] < get))
  {
   arr[j + 1] = arr[j];
   j--;
  }
  arr[j + 1] = get;
 }
}

The main function is called as follows:


public static void main(String[] args){
 
 int[] arr = {8,96,23,5,6,43};
 for(int a :arr){
  System.out.print(a + ",");
 }
 System.out.println();
 insertionSort(arr,1);
 
 for(int a :arr){
  System.out.print(a + ",");
 }
 System.out.println();
 
 insertionSort(arr,0);
 
 for(int a :arr){
  System.out.print(a + ",");
 }
 
}

The post-run log looks like this:

8,96,23,5,6,43,
Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: -1

Exception means the array is out of bounds and the problem is in this line


while (j >= 0 && (order == 1) ? (arr[j] > get):(arr[j] < get))

Each j loop in the code decreases by 1 until both conditions are not met. debug found an exception when j=-1, but the problem is that when j=-1, arrays are not used, because it is known that & & It is a short-circuit operation, that is, if the first operand can determine the result, then the second operand will no longer be evaluated, that is, the expression after j=-1 is not calculated, but it is calculated here, it is taken from the array, so this exception occurs.

I also freely wrote some code to test this situation:


/**
 *  Comparing the size of two input parameters 
 * @param a  input parameter 1
 * @param b  input parameter 2
 * @return boolean  If a > b  Return true, Reverse Return false
 */
static boolean compare(int a,int b){
  System.out.println(a + ">" + b + "?");
  System.out.println(a > b);
  return a > b;
 
}
public static void main(String[] args){
 int a = 1;
 int b = 2;
 int c = 3;
 boolean result = compare(a ,a) && (a == 1) ? (compare(b,b)):(compare(c,c));
 
 System.out.println();
 
 result = compare(b ,b) && compare(c ,c);
 
}

Here's a function for comparing sizes, which will be logged to make it clear to us & & The expression before and after did not run, there are two in the main function & & Expression,

First & & B is one ? in the expression;Expression, the second & & The B of the expression is an compare function, and the log result is:

1 > 1?
false
3 > 3?
false

2 > 2?
false

From the log results we can clearly see that when B is ?When expression, B still runs when A is not established, but B is not ?When expression is used, B will not execute if A is false.

summary


Related articles: