benfry / processing4

Processing 4.x releases for Java 17
https://processing.org
Other
1.35k stars 237 forks source link

increase the speed of reverse() function by 3 minimum #709

Closed knupel closed 1 year ago

knupel commented 1 year ago

Change the algorithm to compute the half of the array and swap the rest. Plus add reverse for long and double, just in case !!!

Here a test the difference of speed.

/**
* reverse function faster than Processing
* may be when I've the possibility I push this one on Processing
*/
import rope.utils.R_Utils.Ru;
import rope.core.Rope;

int num = 30_000_000;

void setup() {
  // Machin [] arr = new Machin[num];
  // long [] arr = new long[num];
  // float [] arr = new float[num];
  // Integer [] arr = new Integer[num];
  // boolean [] arr = new boolean[num];
  // char [] arr = new char[num];
  // int [] arr = new int[num];
  // double [] arr = new double[num];
  PVector [] arr = new PVector[num];
  // String [] arr = new String[num];

  // long Rope faster x100
  // double Rope faster x100
  // boolean Rope faster x1.5
  // char Rope faster x2.5
  // int Rope faster x3.5
  // float Rope faster x3.5
  // Integer Rope faster x9
  // PVector Rope faster x3.5
  // Machin Rope faster x9

  // ONLY CASE where processing is faster
  // String Processing faster x1.1

  for(int i = 0 ; i < arr.length ; i++) {
    // arr[i] = true;
    // arr[i] = i;
    // arr[i] = (char)i;
    // arr[i] = ""+i;
    arr[i] = new PVector(i,i);
    // arr[i] = new Machin();
  }

  float start = millis();
  reverse(arr);
  println("P5",millis() - start);

  start = millis();
  Ru.reverse(arr); 
  println("Rope",millis() - start);
}

class Machin {
  Machin(){}
}

to compare easily the performance, may me you need to install the rope Library or copy and paste the new function reverse() https://github.com/knupel/Rope/blob/master/build_rope/Rope.zip

<T> T [] reverse(T [] arr) {
  for(int i = 0 ; i < arr.length / 2; i++) {
    T buf = arr[i];
    arr[i] = arr[arr.length - i - 1];
    arr[arr.length - i - 1] = buf;
  }
  return arr;
}
benfry commented 1 year ago

This isn't a replacement, unfortunately. The performance increase is largely coming from changing the function of the reverse method. It reverses in place rather than returning a new array that's been reversed.

knupel commented 1 year ago

@benfry are interessting if I made the changement with a new array instead ?

benfry commented 1 year ago

Does it actually improve performance in that case? I assume perhaps a little but I'd be surprised if the difference is significant.

knupel commented 1 year ago

Hi it's August holyday time now, and I find a little time to improve the reverse() and reverse_copy() algo to see if when I add a copy array function in it, that's ok... For the major cases that's better of the original, but like you write @benfry the performance decrease, but stay a good think... Now there only two cases where it's slower: for String and for boolean If I understand well the performance decrease for the small data... because for long it's amazing and step by step when we go closer to a very small data (boolean) the performance decrease. I just don't undestand why the performance is bad for the String. Because for me String is a Class...and I think the performance must be equal to Class Machin or PVector but NOOOOOOOOO.

Below the result, If the performance is ok for you and you are interesting. I can write a pullrequest for that.

  // GOOD CASE

  // double
  // reverse Rope faster x120
  // reverse_copy Rope faster x43

  // long
  // reverse() Rope faster x120
  // reverse_copy() Rope faster x45

  // class Float
  // reverse Rope faster x8.5
  // reverse_copy Rope faster x6.5

  // class Integer
  // reverse Rope faster x8.5
  // reverse_copy Rope faster x4.7

  // PVector
  // reverse() Rope faster x8
  // reverse_copy() Rope faster x7

  // class Machin
  // reverse Rope faster x8
  // reverse_copy Rope faster x4.5

  // int
  // reverse() Rope faster x4
  // reverse_copy() Rope faster x2

  // float
  // reverse() Rope faster x4
  // reverse_copy() Rope faster x2

  // char
  // reverse Rope faster x2.2
  // reverse_copy Rope faster x1.8

  // BAD CASE
  // boolean
  //reverse() Rope faster x1.2
  //reverse_copy() Rope slower x0.8 // BAD

  // String
  //reverse() Rope faster x1.8
  //reverse_copy() Rope slower x0.8 // BAD
benfry commented 1 year ago

If it's still faster I'm happy to take on a PR. If possible, please do your best to stick with the Style Guidelines so I don't need to rewrite it. Thanks!