Using comparator in custom quicksort in java

强颜欢笑 提交于 2020-01-15 03:18:07

问题


I have a quicksort method that i implemented myself. i give an array of objects to that method. how do i use a comparator to tell the method which attribute the objects will be sorted by? I have googled around and found out how to implement a comparator, but not how to use it in the search method as every example ive found just used arrays.sort().

i need different getter-methods to get to the different attributes, i dont see how a comparator helps with that?

i just need a little help to kickstart the whole thing, or maybe someone can manage to find a good example online?

    public WifiData[] qsortSSID(WifiData[] array, int left, int right){
    int ll=left;
    int rr=right;

        if (rr>ll){
            String pivot=array[(ll+rr)/2].getSSID();
            //System.out.println(pivot);
            while (ll <=rr){
                //finde erstes element >= pivot
                while(ll<right && array[ll].getSSID().compareTo(pivot) < 0){
                    ll +=1;
                }
                //finde letztes elemtn kleiner gleich pivot
                while(rr>left && array[rr].getSSID().compareTo(pivot) > 0){
                    rr -=1;
                }
                if (ll <=rr){
                    swap(array, ll ,rr);
                    ll +=1;
                    rr -=1;

                }
            }
            if (left < rr){
                qsortSSID(array,left,rr);

            }
            if (ll<right){
                qsortSSID(array,ll,right);
            }
        }



    return array;
}

回答1:


WifiData should implement Comparable<WifiData> interface by comparing the SSID of this and other.

The signature of your method would then become:

public Comparable[] qsort(Comparable[] array, int left, int right)

and the implementation will be more abstract, so:

String pivot=array[(ll+rr)/2].getSSID();

will become:

Comparable pivot=array[(ll+rr)/2];

and

while(ll<right && array[ll].getSSID().compareTo(pivot) < 0){

will become:

while(ll<right && array[ll].compareTo(pivot) < 0){

etc.

Example:

class WifiData implements Comparable<WifiData> {
    String SSID;

    public String getSSID() {
        return SSID;
    }

    @Override
    public int compareTo(WifiData o) {
        return this.SSID.compareTo(o.getSSID());
    }

    public Comparable[] qsort(Comparable[] array, int left, int right){
        int ll=left;
        int rr=right;

        if (rr>ll){
            Comparable pivot = array[(ll+rr)/2];
            while (ll <=rr){
                while(ll<right && array[ll].compareTo(pivot) < 0){
                    ll +=1;
                }
                while(rr>left && array[rr].compareTo(pivot) > 0){
                    rr -=1;
                }
                if (ll <=rr){
                    swap(array, ll ,rr);
                    ll +=1;
                    rr -=1;
                }
            }
            if (left < rr){
                qsort(array,left,rr);

            }
            if (ll<right){
                qsort(array,ll,right);
            }
        }
        return array;
    }

    void swap(Comparable[] arr, int l, int r) {
        Comparable t = arr[l];
        arr[l] = arr[r];
        arr[r] = t;
    }
}

UPDATE
After reading your comment below your question is clearer. What you should do is use a Comparator: you can implement different Comparators, each of which sorts by a different property.

See the following example:

class WifiData {
    String SSID;

    public String getSSID() {
        return SSID;
    }

    // example how to use it
    public static void main(String[] args) {
        Comparator<WifiData> comp = new SSIDComparator();
        WifiData[] arr = new WifiData[10];
        // ... fill the array
        arr = qsort(arr, 0, arr.length-1, comp);        
    }

    public static WifiData[] qsort(WifiData[] array, 
                                    int left, 
                                    int right,                        
                                    Comparator<WifiData> comp){
        int ll=left;
        int rr=right;

        if (rr>ll){
            WifiData pivot = array[(ll+rr)/2];
            while (ll <=rr){
                // that's how we'll use the comparator:
                while(ll<right && comp.compare(array[ll], pivot) < 0){
                    ll +=1;
                }
                while(rr>left &&  comp.compare(array[rr], pivot) > 0){
                    rr -=1;
                }
                if (ll <=rr){
                    swap(array, ll ,rr);
                    ll +=1;
                    rr -=1;
                }
            }
            if (left < rr){
                qsort(array,left,rr, comp);

            }
            if (ll<right){
                qsort(array, ll, right, comp);
            }
        }
        return array;
    }    

    // an example of Comparator that sorts by SSID
    static class SSIDComparator implements Comparator<WifiData>{
        @Override
        public int compare(WifiData o1, WifiData o2) {
            return o1.getSSID().compareTo(o2.getSSID());
        }
    }
}



回答2:


Here's a sample Comparator I wrote to sort multi-dimensional arrays by their first element:

    private static class FirstItemComparator implements Comparator<int[]> {
        public int compare(int[] first, int[] second) {
            if (first[0] < second[0]) {
                return -1;
            } else if (first[0] == second[0]) {
                return 0;
            } else {
                return 1;
            }
        }
    }

    int[][] test = {{0,1},{4,8},{3,5}, {10,12}, {9,10}};
    Arrays.sort(input, new FirstItemComparator());
    // test is now {{0,1},{3,5},{4,8},{9,10},{10,12}}

Usually you will only write a comparator if you are going to pass it into a static method that compares two instances (passing a Comparator is essentially like passing a function in other languages). You can write different comparators to sort the same type of object in several different ways.

If you want to compare one instance to another instance, then you would implement the interface Comparable on the class itself (rather than create a new class, as I did). However, this imposes an ordering on the object, so you can't write three or four compareTo methods to sort objects in different ways.



来源:https://stackoverflow.com/questions/29592021/using-comparator-in-custom-quicksort-in-java

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!