MJDude
MJDude

Reputation: 73

How to sort a String Array first by letters in the beginning and then by numbers afterwards

I am attempting to sort a large String array. I want it to be ordered primarily by the words in the beginning, based on an order that I have. But I have more than 1 item with the same beginning word, so I want to be able to order the words with numbers that are after the initial word.

For example:

String[] unordered = {"Pencil 2", "Cat 3", "Pencil 1", "Cat 1", "Cat 2"}

I would want the result of sort to be:

String[] ordered = {"Cat 1", "Cat 2", "Cat 3", "Pencil 1", "Pencil 2"}

As it stands right now, I am sorting my list while ignoring the numbers afterwards. So I end up with something like this:

String somewhat ordered = {"Cat 3", "Cat 1", "Cat 2", "Pencil 2", "Pencil 1"}

My code right now looks like this:

String[] sortlist = {"Pencil 2", "Cat 3", "Pencil 1", "Cat 1", "Cat 2"}

String[] Bookorder = {"Cat", "Pencil", etc...}

List<String>[] results = new List[bookorder.length];
            LinkedList<String> remainders = new LinkedList<String>();

            for (String word : sortlist) {
                boolean found = false;
                for (int i = 0; i < bookorder.length; i++) {
                    if (word.startsWith(bookorder[i])) {
                        if (results[i] == null) results[i] = new LinkedList<String>();
                        results[i].add(word);
                        found = true;
                        break;
                    }
                }

                if (!found) {
                    remainders.add(word);
                }
            }

            finalsortedlist = new ArrayList<String>(sortlist.length);
            for (List<String> result : results) {
                if (result != null) {
                    finalsortedlist.addAll(result);
                }
            }

            finalsortedlist.addAll(remainders);

            String[] finalsortedarray = new String[finalsortedlist.size()];
            finalsortedarray = finalsortedlist.toArray(finalsortedarray);

            dblinesequivalent = Arrays.toString(finalsortedarray);

This works great, except for the fact that it doesn't sort the numbers. I can't figure out a way to do this without messing up the previous sorting of the words.

I would appreciate any help you would be willing to offer. Thanks in advance.

Edit:

I do not wish to sort the items alphabetically, they are sorted based on another list the specifies the desired order.

Upvotes: 0

Views: 204

Answers (1)

Alex Loper
Alex Loper

Reputation: 135

private void reorder() {
    String[] unordered = {"Pencil 2", "Cat 3", "Pencil 1", "Cat 1", "Cat 2"};
    Arrays.sort(unordered);
}

EDIT: Here's a version that works for all numbers

private static void reorder() {
    String[] unordered = { "Pencil 2", "Cat 11", "Pencil 1", "Cat 1", "Cat 2" };
    Arrays.sort(unordered);
    System.out.println("After Arrays.sort()");
    for (String s : unordered)
        System.out.println(s);
    for (int i = 0; i < unordered.length; i++) {
        for (int j = i + 1; j < unordered.length - 1; j++) {
            if (unordered[i].substring(0, unordered[i].indexOf(' '))
                    .equals(unordered[j].substring(0, unordered[j].indexOf(' ')))) {
                String numI = unordered[i].substring(unordered[i].indexOf(' ') + 1);
                String numJ = unordered[j].substring(unordered[j].indexOf(' ') + 1);
                if (Integer.parseInt(numI) > Integer.parseInt(numJ)) {
                    String tmp = unordered[i];
                    unordered[i] = unordered[j];
                    unordered[j] = tmp;
                }
            }
        }
    }
    System.out.println("After sorting");
    for (String s : unordered)
        System.out.println(s);
}

Upvotes: 1

Related Questions