sorting two different arrays

My program has to store the words in a text and count the most used ones; this part of the program works perfectly and I have a String[] tracking the unuque words and a int[] that tracks how many times the word was used. They work togheder as if String[] usedWords={"hi" ; "acrasial" }; int[] timesUsed={12 ; 1};

to express that hi was used 12 times ecc...

now to sort from the most used to the least used I convert the two arrays into a table, and then use table.sortReverse() . It doesn't work because the int is treated as a String, so the order would be 990-90-890-84-8-7700 ecc.

So I need to order an array of Strings and one of ints in the same way, but how?

Answers

  • nice it was perfect! Is there a way to sort them by 2 different criterias? So that the ones that are used an equal number of times are also sorted Alphabetically?

  • _vk_vk
    edited October 2015 Answer ✓

    Sure implement the algorithm in the class it self. just do something if ints are equals like this:

    import java.util.Collections;
    
    ArrayList <Data> d = new ArrayList<Data>();
    
    void setup() {
      size(600, 600);
    
      d.add(new Data("A", 12));
      d.add(new Data("B", 2));
      d.add(new Data("Asdrubal", 4));
      d.add(new Data("C", 4));
      d.add(new Data("Asdrabal", 4));
      d.add(new Data("D", 6));
      d.add(new Data("E", 23));
    
    
    
      println("before sorting:\n" + d);
    
      Collections.sort(d);
    
      println("after sorting:\n" + d);
    }
    
    
    /////// i wanted to sort it as E:23,    A:12,    D:6,     C:4,     B:2
    
    
    class Data implements Comparable {
      String name;
      int mark;
    
      Data(String _n, int _m) {
        name = _n;
        mark = _m;
      }
    
      // this sets the 'natural order of Data
      //@Override
        int compareTo(Object o) {
        Data other = (Data) o;
        if (other.mark > mark) {
          return -1;
        } else if (other.mark < mark) {
          return 1;
        }
        // String method compare to already returns
        // -1/1/0 depending on alphabetical order
        return name.compareTo(other.name);
      }
    
    
      // this to get a nice looking output in console...
      //@Override
        String toString() {
        return name + ":" + nf(mark, 2);
      }
    }
    

    For a more complex stuff you can use comparator here an old example:

    import java.util.*;
    int[] xSizes = new int[5];
    int[] ySizes = new int[5];
    int xPos;
    PFont f;
    Test[] tests = new Test[5];
    
    void setup()
    {
      size(800, 408);
      xSizes[0] = 140; 
      xSizes[1] = 80; 
      xSizes[2] = 200;
      xSizes[3] = 100;
      xSizes[4] = 85;
      ySizes[0] = 70;
      ySizes[1] = 100;
      ySizes[2] = 40;
      ySizes[3] = 40;
      ySizes[4] = 85;
    
      for (int i=0 ; i<tests.length ; i++)
      {
        tests[i] = new Test(xSizes[i], ySizes[i]);
      }
      f = createFont("arial", 18);
      stroke(50);
    
      background(70);
    }
    
    
    void draw()
    {
      // Draw first without sorting
      xPos = 0;
      fill(255);
      for (int i=0 ; i<tests.length ; i++)
      {
        tests[i].display(xPos, 0);
        xPos = xPos + tests[i].xSz;
      } 
      fill(0);
      text("no sorting", 10, 10);
    
      // sort by x size
      Arrays.sort(tests, new xSzComparator());
    
      xPos = 0;
      fill(255);
      for (int i=0 ; i<tests.length ; i++)
      {
        tests[i].display(xPos, 102);
        xPos = xPos + tests[i].xSz;
      } 
    
       fill(0);
      text("sorted by width (szX)", 10, 115);
    
    
      // sort by y size
      Arrays.sort(tests, new ySzComparator());
    
      xPos = 0;
      fill(255);
      for (int i=0 ; i<tests.length ; i++)
      {
        tests[i].display(xPos, 204);
        xPos = xPos + tests[i].xSz;
      }
    
       fill(0);
      text("sorted by height (szY)", 10, 220);
    
      //sort by "natural order" implemented with compareTo()
      // here if y size is equal bigger x sizes come first...
      Arrays.sort(tests);
    
      xPos = 0;
      fill(255);
      for (int i=0 ; i<tests.length ; i++)
      {
        tests[i].display(xPos, 308);
        xPos = xPos + tests[i].xSz;
      }
      fill(0);
      text("sorted by \"natural order\" \n if height equals, bigger width come first", 10, 320); 
      noLoop();
    }
    
    
    
    
    //// class Test
    
    
    class Test implements Comparable
    { 
      int xSz;
      int ySz;
    
      Test (int _xSz, int _ySz)
      {
        xSz =_xSz;
        ySz =_ySz;
      }
    
    
    
      void display(int x, int y)
      {
        rect(x, y, xSz, ySz);
      }
    
      /// setting the natural order
      /// not need to use x thought 
      // i did to test comparing by this and then by that
      int compareTo(Object o)
      {
        Test other=(Test)o;
    
        if (other.ySz > ySz) 
        { 
          return -1;
        }
        else if (other.ySz == ySz && other.xSz < xSz) // then.. 
        {
          return -1;
        }
        else if (other.ySz == ySz && other.xSz == xSz)
        {
          return 0;
        }
        else 
        {
          return 1;
        }
      }
    }
    
    
    //// end of Test class
    
    
    
    class xSzComparator implements Comparator {
    
      public int compare(Object test1, Object test2) {    
    
        //parameter are of type Object, so we have to downcast it to Test objects
    
        int test1xSz = ((Test)test1).xSz; 
        int test2xSz = ((Test)test2).xSz;
    
        if (test1xSz > test2xSz)
          return 1;
        else if (test1xSz < test2xSz)
          return -1;
        else
          return 0;
      }
    }
    
    
    class ySzComparator implements Comparator {
    
      public int compare(Object test1, Object test2) {    
    
        //parameter are of type Object, so we have to downcast it to Employee objects
    
        int test1ySz = ((Test)test1).ySz;        
        int test2ySz = ((Test)test2).ySz;
    
        if (test1ySz > test2ySz)
          return 1;
        else if (test1ySz < test2ySz)
          return -1;
        else
          return 0;
      }
    }
    
  • edited October 2015 Answer ✓

    Apparently IntDict's sortValues() & sortValuesReverse() already apply alphabetic order for equal values:

    // forum.Processing.org/two/discussion/13248/sorting-two-different-arrays
    // GoToLoop (2015-Oct-25)
    
    // forum.Processing.org/two/discussion/13044/creating-a-rank-list-by-sorting-an-array
    // GoToLoop (2015-Oct-16)
    
    static final int[] RANKS = {
      12, 2, 4, 6, 23, 12, 6, 6, 12, 12
    };
    
    static final String[] NAMES = new String[RANKS.length];
    
    static {
      for (int i = 0; i != NAMES.length; NAMES[i] = str((char) (i++ + 'A')));
      println(shuffle(NAMES));
      println(RANKS);
    }
    
    final IntDict sortedRanks = new IntDict(NAMES, RANKS);
    
    void setup() {
      println(sortedRanks);
    
      sortedRanks.sortValues();
      println(sortedRanks);
    
      sortedRanks.sortValuesReverse();
      println(sortedRanks);
      exit();
    }
    
    static final <T> T[] shuffle(T... arr) {
      for (int rnd, idx = arr.length; idx > 1; ) {
        rnd = (int) (Math.random()*idx);
        T tmp = arr[--idx];
        arr[idx] = arr[rnd];
        arr[rnd] = tmp;
      }
    
      return arr;
    }
    
  • yes I just noticed that. Thank everybody

Sign In or Register to comment.