From f746c103a79dfa33b2c81e2d7acd28552c9c67d8 Mon Sep 17 00:00:00 2001
From: Urvang Joshi <urvang@google.com>
Date: Wed, 10 Aug 2016 15:56:47 -0700
Subject: [PATCH] Handle centroid rounding inside palette.c itself.

Mostly refactoring, but a very tiny functional change:
Do all rounding in calc_centroids() itself, instead of rounding in two
places inside palette.c

This gives a slight performance improvement for screen content:
0.078% on average.

Change-Id: I7a0e007d30ebf4e59839483a167123f31a222dd4
---
 vp10/encoder/palette.c | 10 ++++++----
 vp10/encoder/palette.h |  7 +++++++
 vp10/encoder/rdopt.c   |  4 ++--
 3 files changed, 15 insertions(+), 6 deletions(-)

diff --git a/vp10/encoder/palette.c b/vp10/encoder/palette.c
index 97cf14c882..371d1b93be 100644
--- a/vp10/encoder/palette.c
+++ b/vp10/encoder/palette.c
@@ -16,7 +16,7 @@ static float calc_dist(const float *p1, const float *p2, int dim) {
   float dist = 0;
   int i;
   for (i = 0; i < dim; ++i) {
-    const float diff = p1[i] - roundf(p2[i]);
+    const float diff = p1[i] - p2[i];
     dist += diff * diff;
   }
   return dist;
@@ -74,6 +74,11 @@ static void calc_centroids(const float *data, float *centroids,
       for (j = 0; j < dim; ++j) centroids[i * dim + j] *= norm;
     }
   }
+
+  // Round to nearest integers.
+  for (i = 0; i < k * dim; ++i) {
+    centroids[i] = roundf(centroids[i]);
+  }
 }
 
 static float calc_total_dist(const float *data, const float *centroids,
@@ -127,9 +132,6 @@ int vp10_remove_duplicates(float *centroids, int num_centroids) {
   int num_unique;  // number of unique centroids
   int i;
   qsort(centroids, num_centroids, sizeof(*centroids), float_comparer);
-  for (i = 0; i < num_centroids; ++i) {
-    centroids[i] = roundf(centroids[i]);
-  }
   // Remove duplicates.
   num_unique = 1;
   for (i = 1; i < num_centroids; ++i) {
diff --git a/vp10/encoder/palette.h b/vp10/encoder/palette.h
index d417085fc4..eb1a571448 100644
--- a/vp10/encoder/palette.h
+++ b/vp10/encoder/palette.h
@@ -19,11 +19,18 @@ extern "C" {
 
 void vp10_calc_indices(const float *data, const float *centroids,
                        uint8_t *indices, int n, int k, int dim);
+
+// Given 'data' of size 'n' and initial guess of 'centroids' of size 'k x dim',
+// runs up to 'max_itr' iterations of k-means algorithm to get updated
+// 'centroids' and the centroid 'indices' for elements in 'data'.
+// Note: the output centroids are rounded off to nearest integers.
 void vp10_k_means(const float *data, float *centroids, uint8_t *indices, int n,
                   int k, int dim, int max_itr);
 
 // Given a list of centroids, returns the unique number of centroids 'k', and
 // puts these unique centroids in first 'k' indices of 'centroids' array.
+// Ideally, the centroids should be rounded to integers before calling this
+// method.
 int vp10_remove_duplicates(float *centroids, int num_centroids);
 
 int vp10_count_colors(const uint8_t *src, int stride, int rows, int cols);
diff --git a/vp10/encoder/rdopt.c b/vp10/encoder/rdopt.c
index 6fe544bfbb..96926cee41 100644
--- a/vp10/encoder/rdopt.c
+++ b/vp10/encoder/rdopt.c
@@ -3616,11 +3616,11 @@ static void rd_pick_palette_intra_sbuv(
 #if CONFIG_VP9_HIGHBITDEPTH
           if (cpi->common.use_highbitdepth)
             pmi->palette_colors[i * PALETTE_MAX_SIZE + j] = clip_pixel_highbd(
-                (int)lroundf(centroids[j * 2 + i - 1]), cpi->common.bit_depth);
+                (int)centroids[j * 2 + i - 1], cpi->common.bit_depth);
           else
 #endif  // CONFIG_VP9_HIGHBITDEPTH
             pmi->palette_colors[i * PALETTE_MAX_SIZE + j] =
-                clip_pixel((int)lroundf(centroids[j * 2 + i - 1]));
+                clip_pixel((int)centroids[j * 2 + i - 1]);
         }
       }
 
-- 
GitLab