[英]How to convert cv::Mat to torch::Tensor and feed it to libtorch model?
[英]Convert tensor outputs to cv::mat
為 TensorFlow .PB編寫推理代碼。
我正在嘗試轉換std::vector<Tensor> outputs;
到vector<Mat>& outputs;
而我的張量 output 形狀是Tensor<type: float shape: [16900,13] values: [4.09118605 1.63703501 6.61954...]...>
代碼
int main(int argc, char *argv[])
{
string image = "image/june_2021_wfh3735.jpg";
string graph = "model/6_nov10.pb";
string labels = "model/classes.txt";
int32 input_width = 416;
int32 input_height = 416;
float input_mean = 0;
float input_std = 255;
string input_layer = "input/input_data";
vector<string> output_layer ={ "predict/concat", "lane/concat/concat" };
bool self_test = false;
string root_dir = "";
// First we load and initialize the model.
std::unique_ptr<tensorflow::Session> session;
string graph_path = tensorflow::io::JoinPath(root_dir, graph);
LOG(ERROR) << "graph_path:" << graph_path;
Status load_graph_status = LoadGraph(graph_path, &session);
if (!load_graph_status.ok()) {
LOG(ERROR) << "LoadGraph ERROR!!!!"<< load_graph_status;
return -1;
}
// Get the image from disk as a float array of numbers, resized and normalized
// to the specifications the main graph expects.
std::vector<Tensor> resized_tensors;
string image_path = tensorflow::io::JoinPath(root_dir, image);
Status read_tensor_status =
ReadTensorFromImageFile(image_path, input_height, input_width, input_mean,
input_std, &resized_tensors);
if (!read_tensor_status.ok()) {
LOG(ERROR) << read_tensor_status;
return -1;
}
const Tensor& resized_tensor = resized_tensors[0];
LOG(ERROR) <<"image shape:" << resized_tensor.shape().DebugString()<< ",len:" << resized_tensors.size() << ",tensor type:"<< resized_tensor.dtype();
std::vector<Tensor> outputs;
Status run_status = session->Run({{input_layer, resized_tensor}},
output_layer, {}, &outputs);
auto height = resized_tensor.shape().dim_sizes()[1];
auto width = resized_tensor.shape().dim_sizes()[2];
if (!run_status.ok()) {
LOG(ERROR) << "Running model failed: " << run_status;
return -1;
}
std::cout << " " << outputs[0].shape().DebugString() << std::endl;
return 0;
}
要獲取tensorflow::Tensor
存儲的數據,您可以:
[1] 使用返回void*
的Tensor::data()
方法。 張量中的數據按行主要順序存儲,因此對於 2D 張量,您可以編寫:
float* data = static_cast<float*>(tensor.data());
int width = ...; // read here second dim of tensor
auto accessData = [&](int y, int x) {
return data[y * width + x];
};
cv::Mat m(height,width,CV_32FC1);
for (int y = 0; y < height; ++y)
for (int x = 0; x < width; ++x)
m.at<float>(y,x) = accessData(y,x);
[2] 使用tensorflow::Tensor
的tensor<T,NDIMS>()
模板方法獲取data()
指針的包裝器,它提供了operator()(Indices...)
運算符,簡化了數據訪問:
auto tensorMap = tensor.tensor<float,2>();
for (int y = 0; y < height; ++y)
for (int x = 0; x < width; ++x)
m.at<float>(y,x) = tensorMap(y,x);
( 'type: float shape: [16900,13]'
索引張量具有 2-dims,因此resized_tensor.shape().dim_sizes()[2];
超出范圍訪問)
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.