public static void scaleFrequencies(int[] freq,int total){
  int len=freq.length, sum=0;
  for (  int x : freq) {
    sum+=x;
  }
  int[] errors=new int[len];
  int totalError=-total;
  for (int i=0; i < len; i++) {
    int old=freq[i];
    if (old == 0) {
      continue;
    }
    int ideal=(int)(old * total * 256L / sum);
    int x=1 + ideal / 256;
    freq[i]=x;
    totalError+=x;
    errors[i]=((x * 256 - ideal) << 8) + i;
  }
  Arrays.sort(errors);
  if (totalError < 0) {
    throw new IllegalArgumentException();
  }
  while (totalError > 0) {
    for (int i=0; totalError > 0 && i < len; i++) {
      int index=errors[i] & 0xff;
      if (freq[index] > 1) {
        freq[index]--;
        totalError--;
      }
    }
  }
}

public static void scaleFrequencies ( int [ ] freq , int total ) { int len = freq . length , sum = 0 ; for ( int x : freq ) { sum += x ; } int [ ] errors = new int [ len ] ; int totalError = - total ; for ( int i = 0 ; i < len ; i ++ ) { int old = freq [ i ] ; if ( old == 0 ) { continue ; } int ideal = ( int ) ( old * total * 256L / sum ) ; int x = 1 + ideal / 256 ; freq [ i ] = x ; totalError += x ; errors [ i ] = ( ( x * 256 - ideal ) << 8 ) + i ; } Arrays . sort ( errors ) ; if ( totalError < 0 ) { throw new IllegalArgumentException ( ) ; } while ( totalError > 0 ) { for ( int i = 0 ; totalError > 0 && i < len ; i ++ ) { int index = errors [ i ] & 0xff ; if ( freq [ index ] > 1 ) { freq [ index ] -- ; totalError -- ; } } } }
scale the frequencies to a new total . frequencies of 0 are kept as 0 ; larger frequencies result in at least 1 .
