1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134
|
//
// Copyright © 2017 Arm Ltd. All rights reserved.
// SPDX-License-Identifier: MIT
//
#pragma once
#include "InferenceTestImage.hpp"
#include "ObjectDetectionCommon.hpp"
#include <armnnUtils/QuantizeHelper.hpp>
#include <armnn/TypesUtils.hpp>
#include <armnn/utility/NumericCast.hpp>
#include <array>
#include <memory>
#include <string>
#include <vector>
namespace
{
struct MobileNetSsdTestCaseData
{
MobileNetSsdTestCaseData(
const std::vector<uint8_t>& inputData,
const std::vector<DetectedObject>& expectedDetectedObject,
const std::vector<std::vector<float>>& expectedOutput)
: m_InputData(inputData)
, m_ExpectedDetectedObject(expectedDetectedObject)
, m_ExpectedOutput(expectedOutput)
{}
std::vector<uint8_t> m_InputData;
std::vector<DetectedObject> m_ExpectedDetectedObject;
std::vector<std::vector<float>> m_ExpectedOutput;
};
class MobileNetSsdDatabase
{
public:
explicit MobileNetSsdDatabase(const std::string& imageDir, float scale, int offset);
std::unique_ptr<MobileNetSsdTestCaseData> GetTestCaseData(unsigned int testCaseId);
private:
std::string m_ImageDir;
float m_Scale;
int m_Offset;
};
constexpr unsigned int k_MobileNetSsdImageWidth = 300u;
constexpr unsigned int k_MobileNetSsdImageHeight = k_MobileNetSsdImageWidth;
// Test cases
const std::array<ObjectDetectionInput, 1> g_PerTestCaseInput =
{
ObjectDetectionInput
{
"Cat.jpg",
{
DetectedObject(16.0f, BoundingBox(0.216785252f, 0.079726994f, 0.927124202f, 0.939067304f), 0.79296875f)
}
}
};
MobileNetSsdDatabase::MobileNetSsdDatabase(const std::string& imageDir, float scale, int offset)
: m_ImageDir(imageDir)
, m_Scale(scale)
, m_Offset(offset)
{}
std::unique_ptr<MobileNetSsdTestCaseData> MobileNetSsdDatabase::GetTestCaseData(unsigned int testCaseId)
{
const unsigned int safeTestCaseId =
testCaseId % armnn::numeric_cast<unsigned int>(g_PerTestCaseInput.size());
const ObjectDetectionInput& testCaseInput = g_PerTestCaseInput[safeTestCaseId];
// Load test case input
const std::string imagePath = m_ImageDir + testCaseInput.first;
std::vector<uint8_t> imageData;
try
{
InferenceTestImage image(imagePath.c_str());
// Resize image (if needed)
const unsigned int width = image.GetWidth();
const unsigned int height = image.GetHeight();
if (width != k_MobileNetSsdImageWidth || height != k_MobileNetSsdImageHeight)
{
image.Resize(k_MobileNetSsdImageWidth, k_MobileNetSsdImageHeight, CHECK_LOCATION());
}
// Get image data as a vector of floats
std::vector<float> floatImageData = GetImageDataAsNormalizedFloats(ImageChannelLayout::Rgb, image);
imageData = armnnUtils::QuantizedVector<uint8_t>(floatImageData, m_Scale, m_Offset);
}
catch (const InferenceTestImageException& e)
{
ARMNN_LOG(fatal) << "Failed to load image for test case " << testCaseId << ". Error: " << e.what();
return nullptr;
}
std::vector<float> numDetections = { static_cast<float>(testCaseInput.second.size()) };
std::vector<float> detectionBoxes;
std::vector<float> detectionClasses;
std::vector<float> detectionScores;
for (DetectedObject expectedObject : testCaseInput.second)
{
detectionBoxes.push_back(expectedObject.m_BoundingBox.m_YMin);
detectionBoxes.push_back(expectedObject.m_BoundingBox.m_XMin);
detectionBoxes.push_back(expectedObject.m_BoundingBox.m_YMax);
detectionBoxes.push_back(expectedObject.m_BoundingBox.m_XMax);
detectionClasses.push_back(expectedObject.m_Class);
detectionScores.push_back(expectedObject.m_Confidence);
}
// Prepare test case expected output
std::vector<std::vector<float>> expectedOutputs;
expectedOutputs.reserve(4);
expectedOutputs.push_back(detectionBoxes);
expectedOutputs.push_back(detectionClasses);
expectedOutputs.push_back(detectionScores);
expectedOutputs.push_back(numDetections);
return std::make_unique<MobileNetSsdTestCaseData>(imageData, testCaseInput.second, expectedOutputs);
}
} // anonymous namespace
|