简体   繁体   中英

Generic array - Unchecked cast from Object[] to T[]

I am very new to Java and I have have read some general information about typecasting, which is probably the solution to my problem. And I think I do grasp the concept in general - like if there was just one method one would like to use which has been made for a different class. But I am unable to apply it to my own code with generic arrays because I don't know at which point to cast and which method or do I have to make a loop to send the entire array through?

Here is my mergesort algorithm which should probably be working fine if it wasn't for the generic type ...

package src;

import java.util.Arrays;

public class MergeSort {

// sort array of type T using the Mergesort algorithm
public static <T extends Comparable<T>> T[] sort(T[] arr) {

            @SuppressWarnings("unchecked")
    T[] leftArray = (T[]) new Comparable[12]; // ERROR: Type safety: Unchecked cast from 
 // Object[] to T[]
    @SuppressWarnings("unchecked")
            T[] rightArray =(T[]) new Comparable[12]; // ERROR: Type safety: Unchecked cast from 
 // Object[] to T[]

    if (arr.length > 1) {


        int half = arr.length / 2;

        leftArray = Arrays.copyOfRange(arr, 0, half);
        rightArray = Arrays.copyOfRange(arr, half + 1, arr.length);

    }
    return merge( sort(leftArray), sort(rightArray));
}

private static <T extends Comparable<T>> T[] merge(T[] leftArray, T[] rightArray) {
            @SuppressWarnings("unchecked")
    T[] tempArray = (T[]) new Comparable[12];   // ERROR: Type safety: Unchecked cast from 
 // Object[] to T[]
     int i = 0;
     int leftIndex = 0;
     int rightIndex = 0; 

    while ( leftIndex < leftArray.length ||  rightIndex < rightArray.length ) {
        if ( leftIndex < leftArray.length && rightIndex < rightArray.length ) {
            if (leftArray[leftIndex].compareTo(rightArray[rightIndex]) < 0 )  {
                 tempArray[i] = leftArray[leftIndex] ;
                 leftIndex++; 
            }
            else {
                 tempArray[i] = rightArray[rightIndex] ;
                 rightIndex++; 
            }
        }
        else if ( leftIndex < leftArray.length ) {
                tempArray[i] = leftArray[leftIndex] ;
                leftIndex++; 
        }       
        else if ( rightIndex < rightArray.length ) {
            tempArray[i] = rightArray[rightIndex] ;
            rightIndex++;   

        }           
    } // end while  

    return tempArray;
}


public static void main(String[] args) {

    // Edit this line to check with different values for the array
    // or add more unit tests to test/MergeSortTest.java

    // // sort list of Characters
    Character[] charArr = { 'H', 'e', 'l', 'l', 'o', ' ', 'w', 'o', 'r',
            'l', 'd', '!' };

    charArr = MergeSort.<Character> sort(charArr);
    System.out.println(Arrays.toString(charArr));

    // sort list of Integers
    Integer[] intArr = { 23, 4, 15, 8, 42, 16 };

    intArr = MergeSort.<Integer> sort(intArr);
    System.out.println(Arrays.toString(intArr));
}
}

Any suggestions would be very much appreciated!

Unfortunately, there isn't anything you can do about it. Because of type erasure, the type information that could be used to see if the cast would work is lost, and so the check has to be deferred to runtime, where a ClassCastException could be thrown, terminating your program. As the compiler cannot prove that this will not happen, it emits a warning instead.


One more thing -- your code is going to fail anyways. Types are erased to their bounding type, which in this case is Comparable . Thus, code like this:

T[] leftArray = (T[]) new Object[12];

Gets erased to this:

Comparable[] leftArray = (Comparable[]) new Object[12];

And because Object does not implement Comparable , the cast will fail.

The solution is to create Comparable arrays instead:

T[] leftArray = (T[]) new Comparable[12];

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM