0

ArrayList data example: BJM 300 AC4507 TOM_JONES, BDM 290 DC4058 ALAN_FIELD, ADG 350 BA3240 JON_THORN

I need to sort the arraylist above into ascending sequence of the third column within the second column within the first column?

I tried nesting the loops as follows but it's not working! What am I doing wrong??

    public static ArrayList sortLoad1(ArrayList<TeachingLoad> loads){
    String s1, s2;
    TeachingLoad temp;                                   //Some local variables
    for(int i = 0 ; i < loads.size(); i++){              //Loop throuth 
        for(int j = loads.size()-1; j>i  ;j--){          //Loop through 
            s1 = loads.get(j-1).getSchoolCode();        //Extract 1st
            s2 = loads.get(j).getSchoolCode();          //Extract 2nd
                if(i+1<loads.size()&&s1.compareTo(s2)>-1){  //Compare them lexicographically
                    temp = loads.get(j-1);
                    //If s1 follows s2 then switch both
                    loads.set(j-1, loads.get(j));
                    loads.set(j, temp);
                }
                else{
                    for(int k = 0 ; k < loads.size(); k++){            
                        for(int l = loads.size()-1; l>i  ;l--){     
                            s1 = loads.get(l-1).getDepartmentNumber();
                            s2 = loads.get(l).getDepartmentNumber();
                            if(k+1<loads.size()&&s1.compareTo(s2)>-1){
                                temp = loads.get(l-1);
                                loads.set(l-1, loads.get(l));
                                loads.set(l, temp);
                            }
                            else{
                                for(int m = 0 ; m < loads.size(); m++){         
                                    for(int n = loads.size()-1; n>i  ;n--){         
                                        s1 = loads.get(n-1).getLecturerID();
                                        s2 = loads.get(n).getLecturerID();
                                        if(m+1<loads.size()&&s1.compareTo(s2)>-1){
                                            temp = loads.get(n-1);
                                            loads.set(n-1, loads.get(n));
                                            loads.set(n, temp);
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
        }//end loop
    }//end loop
    return loads;
} 

I know I can use a Comparator to do this, but I don't want to.

Any help welcome?

Many thanks TeachingLoad held in arraylist is:

    public TeachingLoad(String schoolCode, String departmentNumber, 
        String lecturerID, String lecturerName, 
        String moduleNo, String creditHours, String classSize) {
    this.schoolCode = schoolCode;
    this.departmentNumber = departmentNumber;
    this.lecturerID = lecturerID;
    this.lecturerName = lecturerName;
    this.moduleNo = moduleNo;
    this.creditHours = creditHours;
    this.classSize = classSize;
}

public String getSchoolCode() {
    return schoolCode;
}

public String getDepartmentNumber(){
    return departmentNumber;
}

public String getModuleNo() {
    return moduleNo;
}

public String getCreditHours() {
    return creditHours;
}

public String getClassSize() {
    return classSize;
}
public String getLecturerID() {
    return lecturerID;
}

public String getLecturerName() {
    return lecturerName;
}

public void setLecturerID(String lecturerID) {
    this.lecturerID = lecturerID;
}

public void setLecturerName(String lecturerName) {
    this.lecturerName = lecturerName;
}

public void setSchoolCode(String schoolCode) {
    this.schoolCode = schoolCode;
}

public void setDepartmentNumber(String departmentNumber){
    this.departmentNumber = departmentNumber;
}

public void setModuleNo(String moduleNo) {
    this.moduleNo = moduleNo;
}

public void setCreditHours(String creditHours) {
    this.creditHours = creditHours;
}

public void setClassSize(String classSize) {
    this.classSize = classSize;
}

ETC

Cheers

2
  • 2
    can you add some quotes around that arraylist data, so we can see what you really have in there? (we're just humans, we can't tell whether you're delimited on spaces, or commas, or both, or...) Commented Dec 9, 2013 at 23:47
  • 1
    Are you sure you mean "third column within the second column within the third column"? You've got third column appearing twice, but your code uses three different keys. You'd probably find it easier if you either used Comparator with one of Java's sort methods, or if you have to implement your own sort, use one that works with a comparator function, so you separate out the sort logic from the key logic. Commented Dec 10, 2013 at 0:00

3 Answers 3

3

A sort algorithm should not have 6 levels of nested loop. I don't think this particular attempt can be "rescued".

My advice would be to start again:

  • Implement a simple Bubblesort algorithm. Alternatively use the Collections.sort method provided by the Java SE libraries. (Read the javadocs ... even if you don't plan to use it not ... because it is a good thing to know about it!!)

  • Implement and use the Comparator or Comparable interfaces, or your own custom "compare two TeachingLoad objects" method.

Note that there should only be two levels of nesting in a Bubblesort, which looks to be the algorithm that you were trying to implement.


While I agree with @Ingo that Bubblesort is a poor algorithm, I think that this is entirely beside the point. If you have been asked to implement a sort as a programming exercise, and you have not been taught about advanced sorting algorithms, then trying to implement an advanced algorithm is "jumping the gun". By all means learn about it, but if you try something too far in advance of your current skills you are setting yourself up to fail.

Or to put it another way, don't "show off" :-)

On the other hand, if:

  • you should know (say) Quicksort, and
  • you are expected to implement the algorithm from scratch,

then my advice would be different.

Sign up to request clarification or add additional context in comments.

5 Comments

And, unless you're a genius, use the sort function provided by your language/library. Bubblesort is just telling: "An idiot was here."
@Ingo - Maybe. We don't know if the OP is required to implement the sorting himself. This certainly seems like a "learning exercise".
As I said I know I can use a comparator and yes I'm trying to do the sorting myself and was hoping for some pointers!
Yes, maybe, but he didn't mention it. I'd also say that a prof who lets his studenst do bubblesort is .... well, at most semi-good.
@TripVoltage - I acknowledge your striving for that. Two pointers: a) the base for a sorting algorithm is the comparision function and b) look for mergesort or quicksort, they are easy and good sorting algorithms. But first write a method that takes two data items and compares them.
2

I don't understand what you hope to achieve with your approach; just use a Comparator like this

public static class TeachingLoadComparator implements Comparator<TeachingLoad> {

  /**
   * @see java.util.Comparator#compare(java.lang.Object, java.lang.Object)
   */
  @Override
  public int compare(TeachingLoad o1, TeachingLoad o2) {
    if (o1 == null) {
      if (o2 == null) {
        return 0;
      }
      return -1;
    } else if (o2 == null) {
      return 1;
    }
    if (o1 == o2) {
      return 0;
    }
    switch (o1.getSchoolCode().compareTo(o2.getSchoolCode())) {
    case -1:
      return -1;
    case 1:
      return 1;
    }
    switch (o1.getDepartmentNumber().compareTo(o2.getDepartmentNumber())) {
    case -1:
      return -1;
    case 1:
      return 1;
    }
    return o1.getLecturerID().compareTo(o2.getLecturerID());
  }

and then use it with

Collections.sort(loads, new TeachingLoadComparator());

Comments

1

Taking your input data, this is what I would do:

public class StringArraySort {

public static void main(String[] args) {

    List<String> arrayToSort = new ArrayList<String>();
    arrayToSort.add("BJM 300 AC4507 TOM_JONES"); 
    arrayToSort.add("BDM 290 DC4058 ALAN_FIELD"); 
    arrayToSort.add("ADG 350 BA3240 JON_THORN");
    arrayToSort.add("ADG 340 BA3240 JON_THORN");
    arrayToSort.add("ADF 340 BA3240 JON_THORN");

    Collections.sort(arrayToSort, customStringComparator);

    System.out.println(arrayToSort);

}

static final Comparator<String> customStringComparator = new Comparator<String>() {

    @Override
    public int compare(String o1, String o2) {
        String[] o1Columns = o1.split(" ");
        String[] o2Columns = o2.split(" ");

        if(o1Columns[2].compareTo(o2Columns[2]) == 0) {
            if(o1Columns[1].compareTo(o2Columns[1]) == 0) {
                // should it be first column?
                return o1Columns[0].compareTo(o2Columns[0]);
            } else {
                return o1Columns[1].compareTo(o2Columns[1]);
            }
        } else {
            return o1Columns[2].compareTo(o2Columns[2]);
        }
    }
}; }

I'm not sure I understood this statement:

third column within the second column within the third column?

So the columns may not be right.

As a rule of thumb always use a language construct, when there is one, in this case the Comparator.

EDIT: Seeing @Elliott Frisch's answer I think the best thing for you is to implement Comparable in your object.

2nd EDIT:

Here it is a method to do a simple bubble sort, but it is NOT advised for production code, as it performs very bad with large collections. Collections.sort(List list) is way faster, and if you look at the source you would see why.

public static <T extends Comparable<T>> void bubleSort(List<T> list) {
    boolean resort = false;
    for (int i = 0; i < list.size(); i++) {
        T t = list.get(i);
        int nextElementIndex = i + 1;
        if(nextElementIndex < list.size()) {
            T temp = list.get(nextElementIndex);
            if(t.compareTo(temp) > 0) {
                resort = true;
                list.set(nextElementIndex, t);
                list.set(i, temp);
            } else {
                continue;
            }
        } 
    }
    if(resort) {
        bubleSort(list);
    }
}

And here is the compareTo method from TeachingLoad:

public int compareTo(TeachingLoad o) {
        if(schoolCode.compareTo(o.schoolCode) == 0) {
            if(departmentNumber.compareTo(o.departmentNumber) == 0) {
                return lecturerID.compareTo(o.lecturerID);          
            }else {
                return departmentNumber.compareTo(o.departmentNumber);          
            }
        } else {
            return schoolCode.compareTo(o.schoolCode);
        }
    }

It's worth to mention that after a short Google search I found better algorithms than mine, like this, so I'm still not sure if this is what you are looking for.

6 Comments

@ Alberto, it should have read sort the third within the second within the first - Thanks
@TripVoltage You are welcome. Now I re read your question and some comments you made, and see that this wasn't what you were looking for. Are you allowed to see the java source code?
@ Alberto - yes. I wanted to be able to do the sorting without using a comparator...
@TripVoltage I'll try that in a few moments, it's interesting.
@ Alberto - yeah it is.. suppose we count the number of ranges within a each field first then use these for the loop counter etc...
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.