Add TensorsToSegmentationCalculator test utilities.
PiperOrigin-RevId: 586817713
This commit is contained in:
parent
7013b23785
commit
a0eda45baf
|
@ -1555,12 +1555,37 @@ cc_library(
|
||||||
],
|
],
|
||||||
)
|
)
|
||||||
|
|
||||||
|
cc_library(
|
||||||
|
name = "tensors_to_segmentation_calculator_test_utils",
|
||||||
|
testonly = 1,
|
||||||
|
srcs = ["tensors_to_segmentation_calculator_test_utils.cc"],
|
||||||
|
hdrs = ["tensors_to_segmentation_calculator_test_utils.h"],
|
||||||
|
deps = [
|
||||||
|
":tensors_to_segmentation_calculator_cc_proto",
|
||||||
|
"//mediapipe/framework:calculator_cc_proto",
|
||||||
|
"//mediapipe/framework/port:parse_text_proto",
|
||||||
|
"@com_google_absl//absl/log:absl_log",
|
||||||
|
"@com_google_absl//absl/strings",
|
||||||
|
],
|
||||||
|
)
|
||||||
|
|
||||||
|
cc_test(
|
||||||
|
name = "tensors_to_segmentation_calculator_test_utils_test",
|
||||||
|
srcs = ["tensors_to_segmentation_calculator_test_utils_test.cc"],
|
||||||
|
deps = [
|
||||||
|
":tensors_to_segmentation_calculator_cc_proto",
|
||||||
|
":tensors_to_segmentation_calculator_test_utils",
|
||||||
|
"//mediapipe/framework/port:gtest_main",
|
||||||
|
],
|
||||||
|
)
|
||||||
|
|
||||||
cc_test(
|
cc_test(
|
||||||
name = "tensors_to_segmentation_calculator_test",
|
name = "tensors_to_segmentation_calculator_test",
|
||||||
srcs = ["tensors_to_segmentation_calculator_test.cc"],
|
srcs = ["tensors_to_segmentation_calculator_test.cc"],
|
||||||
deps = [
|
deps = [
|
||||||
":tensors_to_segmentation_calculator",
|
":tensors_to_segmentation_calculator",
|
||||||
":tensors_to_segmentation_calculator_cc_proto",
|
":tensors_to_segmentation_calculator_cc_proto",
|
||||||
|
":tensors_to_segmentation_calculator_test_utils",
|
||||||
"//mediapipe/framework:calculator_framework",
|
"//mediapipe/framework:calculator_framework",
|
||||||
"//mediapipe/framework:calculator_runner",
|
"//mediapipe/framework:calculator_runner",
|
||||||
"//mediapipe/framework:packet",
|
"//mediapipe/framework:packet",
|
||||||
|
@ -1571,10 +1596,6 @@ cc_test(
|
||||||
"//mediapipe/framework/formats:rect_cc_proto",
|
"//mediapipe/framework/formats:rect_cc_proto",
|
||||||
"//mediapipe/framework/formats:tensor",
|
"//mediapipe/framework/formats:tensor",
|
||||||
"//mediapipe/framework/port:gtest_main",
|
"//mediapipe/framework/port:gtest_main",
|
||||||
"//mediapipe/framework/port:parse_text_proto",
|
|
||||||
"@com_google_absl//absl/log",
|
|
||||||
"@com_google_absl//absl/log:absl_log",
|
|
||||||
"@com_google_absl//absl/strings",
|
|
||||||
],
|
],
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
|
@ -17,10 +17,8 @@
|
||||||
#include <utility>
|
#include <utility>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
#include "absl/log/absl_log.h"
|
|
||||||
#include "absl/log/log.h"
|
|
||||||
#include "absl/strings/substitute.h"
|
|
||||||
#include "mediapipe/calculators/tensor/tensors_to_segmentation_calculator.pb.h"
|
#include "mediapipe/calculators/tensor/tensors_to_segmentation_calculator.pb.h"
|
||||||
|
#include "mediapipe/calculators/tensor/tensors_to_segmentation_calculator_test_utils.h"
|
||||||
#include "mediapipe/framework/calculator_framework.h"
|
#include "mediapipe/framework/calculator_framework.h"
|
||||||
#include "mediapipe/framework/calculator_runner.h"
|
#include "mediapipe/framework/calculator_runner.h"
|
||||||
#include "mediapipe/framework/formats/image.h"
|
#include "mediapipe/framework/formats/image.h"
|
||||||
|
@ -30,7 +28,6 @@
|
||||||
#include "mediapipe/framework/formats/tensor.h"
|
#include "mediapipe/framework/formats/tensor.h"
|
||||||
#include "mediapipe/framework/packet.h"
|
#include "mediapipe/framework/packet.h"
|
||||||
#include "mediapipe/framework/port/gtest.h"
|
#include "mediapipe/framework/port/gtest.h"
|
||||||
#include "mediapipe/framework/port/parse_text_proto.h"
|
|
||||||
#include "mediapipe/framework/port/status_matchers.h"
|
#include "mediapipe/framework/port/status_matchers.h"
|
||||||
#include "mediapipe/framework/timestamp.h"
|
#include "mediapipe/framework/timestamp.h"
|
||||||
|
|
||||||
|
@ -40,58 +37,17 @@ namespace {
|
||||||
using ::testing::SizeIs;
|
using ::testing::SizeIs;
|
||||||
using ::testing::TestWithParam;
|
using ::testing::TestWithParam;
|
||||||
using Options = mediapipe::TensorsToSegmentationCalculatorOptions;
|
using Options = mediapipe::TensorsToSegmentationCalculatorOptions;
|
||||||
|
namespace test_utils = ::mediapipe::tensors_to_segmentation_utils;
|
||||||
|
|
||||||
std::string ActivationTypeToString(Options::Activation activation) {
|
using TensorsToSegmentationCalculatorTest =
|
||||||
switch (activation) {
|
TestWithParam<test_utils::FormattingTestCase>;
|
||||||
case Options::NONE:
|
|
||||||
return "NONE";
|
|
||||||
case Options::SIGMOID:
|
|
||||||
return "SIGMOID";
|
|
||||||
case Options::SOFTMAX:
|
|
||||||
return "SOFTMAX";
|
|
||||||
default:
|
|
||||||
ABSL_LOG(FATAL) << "Unknown activation type: " << activation;
|
|
||||||
return "UNKNOWN";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
struct FormattingTestCase {
|
|
||||||
std::string test_name;
|
|
||||||
std::vector<float> inputs;
|
|
||||||
std::vector<float> expected_outputs;
|
|
||||||
Options::Activation activation;
|
|
||||||
int rows = 1;
|
|
||||||
int cols = 1;
|
|
||||||
int rows_new = 1;
|
|
||||||
int cols_new = 1;
|
|
||||||
int channels = 1;
|
|
||||||
double max_abs_diff = 1e-7;
|
|
||||||
};
|
|
||||||
|
|
||||||
using TensorsToSegmentationCalculatorTest = TestWithParam<FormattingTestCase>;
|
|
||||||
|
|
||||||
TEST_P(TensorsToSegmentationCalculatorTest, ParameterizedTests) {
|
TEST_P(TensorsToSegmentationCalculatorTest, ParameterizedTests) {
|
||||||
const auto& [test_name, inputs, expected_outputs, activation, rows, cols,
|
const auto& [test_name, inputs, expected_outputs, activation, rows, cols,
|
||||||
rows_new, cols_new, channels, max_abs_diff] = GetParam();
|
rows_new, cols_new, channels, max_abs_diff] = GetParam();
|
||||||
|
|
||||||
auto graph_config =
|
auto graph_config =
|
||||||
mediapipe::ParseTextProtoOrDie<CalculatorGraphConfig>(absl::Substitute(
|
test_utils::CreateGraphConfigForTest(/*test_gpu=*/false, activation);
|
||||||
R"pb(
|
|
||||||
input_stream: "tensors"
|
|
||||||
input_stream: "size"
|
|
||||||
node {
|
|
||||||
calculator: "TensorsToSegmentationCalculator"
|
|
||||||
input_stream: "TENSORS:tensors"
|
|
||||||
input_stream: "OUTPUT_SIZE:size"
|
|
||||||
output_stream: "MASK:image_as_mask"
|
|
||||||
options: {
|
|
||||||
[mediapipe.TensorsToSegmentationCalculatorOptions.ext] {
|
|
||||||
activation: $0
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
)pb",
|
|
||||||
ActivationTypeToString(activation)));
|
|
||||||
|
|
||||||
std::vector<Packet> output_packets;
|
std::vector<Packet> output_packets;
|
||||||
tool::AddVectorSink("image_as_mask", &graph_config, &output_packets);
|
tool::AddVectorSink("image_as_mask", &graph_config, &output_packets);
|
||||||
|
@ -151,7 +107,7 @@ TEST_P(TensorsToSegmentationCalculatorTest, ParameterizedTests) {
|
||||||
|
|
||||||
INSTANTIATE_TEST_SUITE_P(
|
INSTANTIATE_TEST_SUITE_P(
|
||||||
TensorsToSegmentationCalculatorTests, TensorsToSegmentationCalculatorTest,
|
TensorsToSegmentationCalculatorTests, TensorsToSegmentationCalculatorTest,
|
||||||
testing::ValuesIn<FormattingTestCase>({
|
testing::ValuesIn<test_utils::FormattingTestCase>({
|
||||||
{.test_name = "NoActivationAndNoOutputResize",
|
{.test_name = "NoActivationAndNoOutputResize",
|
||||||
.inputs = {1.0, 2.0, 3.0, 4.0, 5.0, 6.0, 7.0, 8.0, 9.0, 10.0, 11.0,
|
.inputs = {1.0, 2.0, 3.0, 4.0, 5.0, 6.0, 7.0, 8.0, 9.0, 10.0, 11.0,
|
||||||
12.0, 13.0, 14.0, 15.0, 16.0},
|
12.0, 13.0, 14.0, 15.0, 16.0},
|
||||||
|
|
|
@ -0,0 +1,111 @@
|
||||||
|
// Copyright 2023 The MediaPipe Authors.
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
|
||||||
|
#include "mediapipe/calculators/tensor/tensors_to_segmentation_calculator_test_utils.h"
|
||||||
|
|
||||||
|
#include <string>
|
||||||
|
#include <vector>
|
||||||
|
|
||||||
|
#include "absl/log/absl_log.h"
|
||||||
|
#include "absl/strings/substitute.h"
|
||||||
|
#include "mediapipe/calculators/tensor/tensors_to_segmentation_calculator.pb.h"
|
||||||
|
#include "mediapipe/framework/calculator.pb.h"
|
||||||
|
#include "mediapipe/framework/port/parse_text_proto.h"
|
||||||
|
|
||||||
|
namespace mediapipe {
|
||||||
|
namespace tensors_to_segmentation_utils {
|
||||||
|
|
||||||
|
std::string ActivationTypeToString(
|
||||||
|
const TensorsToSegmentationCalculatorOptions::Activation& activation) {
|
||||||
|
switch (activation) {
|
||||||
|
case TensorsToSegmentationCalculatorOptions::NONE:
|
||||||
|
return "NONE";
|
||||||
|
case TensorsToSegmentationCalculatorOptions::SIGMOID:
|
||||||
|
return "SIGMOID";
|
||||||
|
case TensorsToSegmentationCalculatorOptions::SOFTMAX:
|
||||||
|
return "SOFTMAX";
|
||||||
|
}
|
||||||
|
ABSL_LOG(FATAL) << "Unknown activation type: " << activation;
|
||||||
|
return "UNKNOWN";
|
||||||
|
}
|
||||||
|
|
||||||
|
std::vector<unsigned char> ArrayFloatToUnsignedChar(
|
||||||
|
const std::vector<float>& array) {
|
||||||
|
std::vector<unsigned char> result;
|
||||||
|
result.reserve(array.size());
|
||||||
|
for (int i = 0; i < array.size(); ++i) {
|
||||||
|
result.push_back(static_cast<unsigned char>(array[i]));
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::vector<float> MakeRedAlphaMatrix(const std::vector<float>& values) {
|
||||||
|
std::vector<float> result;
|
||||||
|
result.reserve(values.size() * 4);
|
||||||
|
for (const float& value : values) {
|
||||||
|
result.push_back(value);
|
||||||
|
result.push_back(0);
|
||||||
|
result.push_back(0);
|
||||||
|
result.push_back(value);
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
// For GPU tests, the input tensor needs to be moved to GPU, using
|
||||||
|
// TensorViewRequestor. After calculation, the output needs to be moved back
|
||||||
|
// to CPU, using ToImageCalculator. The output is an ImageFrame.
|
||||||
|
mediapipe::CalculatorGraphConfig CreateGraphConfigForTest(
|
||||||
|
bool test_gpu,
|
||||||
|
const TensorsToSegmentationCalculatorOptions::Activation& activation) {
|
||||||
|
std::string pre_process = R"pb(
|
||||||
|
node {
|
||||||
|
calculator: "mediapipe.aimatter.TensorViewRequestor"
|
||||||
|
input_stream: "TENSORS:tensors"
|
||||||
|
output_stream: "TENSORS:tensors_gpu"
|
||||||
|
options {
|
||||||
|
[mediapipe.aimatter.TensorViewRequestorOptions.ext] { gpu {} }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
)pb";
|
||||||
|
std::string post_process = R"pb(
|
||||||
|
node {
|
||||||
|
calculator: "FromImageCalculator"
|
||||||
|
input_stream: "IMAGE:image_as_mask_gpu"
|
||||||
|
output_stream: "IMAGE_CPU:image_as_mask"
|
||||||
|
}
|
||||||
|
)pb";
|
||||||
|
return mediapipe::ParseTextProtoOrDie<mediapipe::CalculatorGraphConfig>(
|
||||||
|
absl::Substitute(
|
||||||
|
R"pb(
|
||||||
|
input_stream: "tensors"
|
||||||
|
input_stream: "size" $0
|
||||||
|
node {
|
||||||
|
calculator: "TensorsToSegmentationCalculator"
|
||||||
|
input_stream: "TENSORS:tensors$1"
|
||||||
|
input_stream: "OUTPUT_SIZE:size"
|
||||||
|
output_stream: "MASK:image_as_mask$2"
|
||||||
|
options: {
|
||||||
|
[mediapipe.TensorsToSegmentationCalculatorOptions.ext] {
|
||||||
|
activation: $3
|
||||||
|
gpu_origin: TOP_LEFT
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} $4
|
||||||
|
)pb",
|
||||||
|
test_gpu ? pre_process : "", test_gpu ? "_gpu" : "",
|
||||||
|
test_gpu ? "_gpu" : "", ActivationTypeToString(activation),
|
||||||
|
test_gpu ? post_process : ""));
|
||||||
|
}
|
||||||
|
} // namespace tensors_to_segmentation_utils
|
||||||
|
} // namespace mediapipe
|
|
@ -0,0 +1,57 @@
|
||||||
|
// Copyright 2023 The MediaPipe Authors.
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
|
||||||
|
#ifndef MEDIAPIPE_CALCULATORS_TENSOR_TENSORS_TO_SEGMENTATION_CALCULATOR_TEST_UTILS_H_
|
||||||
|
#define MEDIAPIPE_CALCULATORS_TENSOR_TENSORS_TO_SEGMENTATION_CALCULATOR_TEST_UTILS_H_
|
||||||
|
|
||||||
|
#include <memory>
|
||||||
|
#include <string>
|
||||||
|
#include <utility>
|
||||||
|
#include <vector>
|
||||||
|
|
||||||
|
#include "mediapipe/calculators/tensor/tensors_to_segmentation_calculator.pb.h"
|
||||||
|
#include "mediapipe/framework/calculator.pb.h"
|
||||||
|
|
||||||
|
namespace mediapipe {
|
||||||
|
namespace tensors_to_segmentation_utils {
|
||||||
|
std::string ActivationTypeToString(
|
||||||
|
const mediapipe::TensorsToSegmentationCalculatorOptions::Activation&
|
||||||
|
activation);
|
||||||
|
|
||||||
|
std::vector<unsigned char> ArrayFloatToUnsignedChar(
|
||||||
|
const std::vector<float>& array);
|
||||||
|
|
||||||
|
std::vector<float> MakeRedAlphaMatrix(const std::vector<float>& values);
|
||||||
|
|
||||||
|
mediapipe::CalculatorGraphConfig CreateGraphConfigForTest(
|
||||||
|
bool test_gpu,
|
||||||
|
const mediapipe::TensorsToSegmentationCalculatorOptions::Activation&
|
||||||
|
activation);
|
||||||
|
|
||||||
|
struct FormattingTestCase {
|
||||||
|
std::string test_name;
|
||||||
|
std::vector<float> inputs;
|
||||||
|
std::vector<float> expected_outputs;
|
||||||
|
mediapipe::TensorsToSegmentationCalculatorOptions::Activation activation;
|
||||||
|
int rows = 1;
|
||||||
|
int cols = 1;
|
||||||
|
int rows_new = 1;
|
||||||
|
int cols_new = 1;
|
||||||
|
int channels = 1;
|
||||||
|
double max_abs_diff = 1e-7;
|
||||||
|
};
|
||||||
|
} // namespace tensors_to_segmentation_utils
|
||||||
|
} // namespace mediapipe
|
||||||
|
|
||||||
|
#endif // MEDIAPIPE_CALCULATORS_TENSOR_TENSORS_TO_SEGMENTATION_CALCULATOR_TEST_UTILS_H_
|
|
@ -0,0 +1,50 @@
|
||||||
|
// Copyright 2023 The MediaPipe Authors.
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
|
||||||
|
#include "mediapipe/calculators/tensor/tensors_to_segmentation_calculator_test_utils.h"
|
||||||
|
|
||||||
|
#include <vector>
|
||||||
|
|
||||||
|
#include "mediapipe/calculators/tensor/tensors_to_segmentation_calculator.pb.h"
|
||||||
|
#include "mediapipe/framework/port/gtest.h"
|
||||||
|
|
||||||
|
namespace mediapipe::tensors_to_segmentation_utils {
|
||||||
|
namespace {
|
||||||
|
|
||||||
|
using Options = ::mediapipe::TensorsToSegmentationCalculatorOptions;
|
||||||
|
|
||||||
|
TEST(TensorsToSegmentationCalculatorTestUtilsTest,
|
||||||
|
ActivationTypeToStringWorksCorrectly) {
|
||||||
|
EXPECT_EQ(ActivationTypeToString(Options::NONE), "NONE");
|
||||||
|
EXPECT_EQ(ActivationTypeToString(Options::SIGMOID), "SIGMOID");
|
||||||
|
EXPECT_EQ(ActivationTypeToString(Options::SOFTMAX), "SOFTMAX");
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST(TensorsToSegmentationCalculatorTestUtilsTest,
|
||||||
|
ArrayFloatToUnsignedCharWorksCorrectly) {
|
||||||
|
std::vector<float> input = {1.0, 2.0, 3.0};
|
||||||
|
std::vector<unsigned char> expected = {1, 2, 3};
|
||||||
|
EXPECT_EQ(ArrayFloatToUnsignedChar(input), expected);
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST(TensorsToSegmentationCalculatorTestUtilsTest,
|
||||||
|
MakeRedAlphaMatrixWorksCorrectly) {
|
||||||
|
std::vector<float> input = {1.0, 2.0, 3.0};
|
||||||
|
std::vector<float> expected = {1.0, 0.0, 0.0, 1.0, 2.0, 0.0,
|
||||||
|
0.0, 2.0, 3.0, 0.0, 0.0, 3.0};
|
||||||
|
EXPECT_EQ(MakeRedAlphaMatrix(input), expected);
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace
|
||||||
|
} // namespace mediapipe::tensors_to_segmentation_utils
|
Loading…
Reference in New Issue
Block a user