IVGCVSW-3247: Refactor reference Gather workload

 * Refactored Gather reference workload to not use templates for different types
 * Added quantization values in Gather unit tests for Quantized types

Signed-off-by: Ellen Norris-Thompson <ellen.norris-thompson@arm.com>
Change-Id: Ibe5d655aa1c287824e45b83818c5862bda7f92b0
diff --git a/src/backends/reference/workloads/Gather.cpp b/src/backends/reference/workloads/Gather.cpp
index 45491c7..c848a7c 100644
--- a/src/backends/reference/workloads/Gather.cpp
+++ b/src/backends/reference/workloads/Gather.cpp
@@ -14,13 +14,12 @@
 namespace armnn
 {
 
-template <typename T>
 void Gather(const TensorInfo& paramsInfo,
             const TensorInfo& indicesInfo,
             const TensorInfo& outputInfo,
-            const T* params,
+            Decoder<float>& params,
             const int32_t* indices,
-            T* output)
+            Encoder<float>& output)
 {
     const TensorShape& paramsShape = paramsInfo.GetShape();
 
@@ -39,9 +38,13 @@
 
         unsigned int startOffset = indx * paramsProduct;
         unsigned int endOffset = startOffset + paramsProduct;
+
         for (unsigned int j = startOffset; j < endOffset; ++j)
         {
-            output[outIndex] = params[j];
+            params[j];
+            float outputValue = params.Get();
+            output[outIndex];
+            output.Set(outputValue);
             ++outIndex;
         }
     }
@@ -49,18 +52,4 @@
     BOOST_ASSERT(outIndex == outputInfo.GetNumElements());
 }
 
-template void Gather<float>(const TensorInfo& paramsInfo,
-                            const TensorInfo& indicesInfo,
-                            const TensorInfo& outputInfo,
-                            const float* params,
-                            const int32_t* indices,
-                            float* output);
-
-template void Gather<uint8_t>(const TensorInfo& paramsInfo,
-                              const TensorInfo& indicesInfo,
-                              const TensorInfo& outputInfo,
-                              const uint8_t* params,
-                              const int32_t* indices,
-                              uint8_t* output);
-
 } //namespace armnn
diff --git a/src/backends/reference/workloads/Gather.hpp b/src/backends/reference/workloads/Gather.hpp
index 0ad4f8c..16c983e 100644
--- a/src/backends/reference/workloads/Gather.hpp
+++ b/src/backends/reference/workloads/Gather.hpp
@@ -7,15 +7,18 @@
 
 #include "armnn/Tensor.hpp"
 
+#include "BaseIterator.hpp"
+#include "Decoders.hpp"
+#include "Encoders.hpp"
+
 namespace armnn
 {
 
-template <typename T>
 void Gather(const TensorInfo& paramsInfo,
             const TensorInfo& indicesInfo,
             const TensorInfo& outputInfo,
-            const T* params,
+            Decoder<float>& params,
             const int32_t* indices,
-            T* output);
+            Encoder<float>& output);
 
 } //namespace armnn
diff --git a/src/backends/reference/workloads/RefGatherWorkload.cpp b/src/backends/reference/workloads/RefGatherWorkload.cpp
index bca3f18..8edf14c 100644
--- a/src/backends/reference/workloads/RefGatherWorkload.cpp
+++ b/src/backends/reference/workloads/RefGatherWorkload.cpp
@@ -13,25 +13,23 @@
 namespace armnn
 {
 
-template <armnn::DataType DataType>
-void RefGatherWorkload<DataType>::Execute() const
+void RefGatherWorkload::Execute() const
 {
-    using T = ResolveType<DataType>;
-
     ARMNN_SCOPED_PROFILING_EVENT(Compute::CpuRef, "RefGatherWorkload_Execute");
 
     const TensorInfo& inputInfo0 = GetTensorInfo(m_Data.m_Inputs[0]);
     const TensorInfo& inputInfo1 = GetTensorInfo(m_Data.m_Inputs[1]);
     const TensorInfo& outputInfo = GetTensorInfo(m_Data.m_Outputs[0]);
 
-    const T* paramsData = GetInputTensorData<T>(0, m_Data);
+    std::unique_ptr<Decoder<float>> decoderPtr = MakeDecoder<float>(inputInfo0, m_Data.m_Inputs[0]->Map());
+    Decoder<float>& decoder = *decoderPtr;
+
     const int32_t* indicesData = GetInputTensorData<int32_t>(1, m_Data);
-    T* outputData = GetOutputTensorData<T>(0, m_Data);
 
-    Gather(inputInfo0, inputInfo1, outputInfo, paramsData, indicesData, outputData);
+    std::unique_ptr<Encoder<float>> encoderPtr = MakeEncoder<float>(outputInfo, m_Data.m_Outputs[0]->Map());
+    Encoder<float>& encoder = *encoderPtr;
+
+    Gather(inputInfo0, inputInfo1, outputInfo, decoder, indicesData, encoder);
 }
 
-template class RefGatherWorkload<DataType::Float32>;
-template class RefGatherWorkload<DataType::QuantisedAsymm8>;
-
 } //namespace armnn
diff --git a/src/backends/reference/workloads/RefGatherWorkload.hpp b/src/backends/reference/workloads/RefGatherWorkload.hpp
index 2782749..30019a8 100644
--- a/src/backends/reference/workloads/RefGatherWorkload.hpp
+++ b/src/backends/reference/workloads/RefGatherWorkload.hpp
@@ -9,28 +9,18 @@
 #include <backendsCommon/WorkloadData.hpp>
 
 #include <armnn/TypesUtils.hpp>
+#include "BaseIterator.hpp"
+#include "Decoders.hpp"
+#include "Encoders.hpp"
 
 namespace armnn
 {
 
-template <armnn::DataType DataType>
-class RefGatherWorkload : public FirstInputTypedWorkload<GatherQueueDescriptor, DataType>
+class RefGatherWorkload : public BaseWorkload<GatherQueueDescriptor>
 {
 public:
-
-    static const std::string& GetName()
-    {
-        static const std::string name = std::string("RefGather") + GetDataTypeName(DataType) + "Workload";
-        return name;
-    }
-
-    using FirstInputTypedWorkload<GatherQueueDescriptor, DataType>::m_Data;
-    using FirstInputTypedWorkload<GatherQueueDescriptor, DataType>::FirstInputTypedWorkload;
-
+    using BaseWorkload<GatherQueueDescriptor>::BaseWorkload;
     void Execute() const override;
 };
 
-using RefGatherFloat32Workload = RefGatherWorkload<DataType::Float32>;
-using RefGatherUint8Workload = RefGatherWorkload<DataType::QuantisedAsymm8>;
-
 } // namespace armnn